Github Branches

Documentation for Deployment

Railway GitHub Deployment Guide

Last Updated: January 22, 2026 (Session 59.2)


Overview

This guide documents the GitHub-based deployment workflow for Railway services. Each API service has a dedicated deploy branch that triggers automatic deployments.


Architecture

┌─────────────────┐     ┌──────────────────┐     ┌─────────────────┐
│  main branch    │ ──► │  deploy/api      │ ──► │  backend-api    │
│  (development)  │     │  deploy/ai-api   │ ──► │  backend-ai-api │
│                 │     │  deploy/docs-api │ ──► │  backend-docs-api│
└─────────────────┘     └──────────────────┘     └─────────────────┘
       Git                    GitHub                  Railway

Service Configuration

Service Deploy Branch Domain Health Check
backend-api deploy/api api.gograb.space /api/health
backend-ai-api deploy/ai-api ai-api.gograb.space /ai-api/health
backend-docs-api deploy/docs-api docs-api.gograb.space /docs-api/health

Deployment Commands

Deploy Single Service

# Deploy backend-api
git checkout deploy/api
git merge main
git push origin deploy/api
git checkout main

# Deploy backend-ai-api
git checkout deploy/ai-api
git merge main
git push origin deploy/ai-api
git checkout main

# Deploy backend-docs-api
git checkout deploy/docs-api
git merge main
git push origin deploy/docs-api
git checkout main

Deploy All Services

#!/bin/bash
# deploy-all.sh

for branch in deploy/api deploy/ai-api deploy/docs-api; do
  echo "Deploying $branch..."
  git checkout $branch
  git merge main --no-edit
  git push origin $branch
done
git checkout main
echo "All deployments triggered!"

Branch Structure

Each deploy branch contains a railway.toml at the repo root:

deploy/api → railway.toml

[build]
builder = "DOCKERFILE"
dockerfilePath = "deployment/Dockerfile.railway.backend"
dockerContext = "."

[deploy]
startCommand = "node dist/apis/backend-api/main.js"
healthcheckPath = "/api/health"
healthcheckTimeout = 300
restartPolicyType = "ON_FAILURE"
restartPolicyMaxRetries = 10

deploy/ai-api → railway.toml

[build]
builder = "DOCKERFILE"
dockerfilePath = "deployment/Dockerfile.railway.backend-ai"
dockerContext = "."

[deploy]
startCommand = "node dist/apis/backend-ai-api/main.js"
healthcheckPath = "/ai-api/health"
healthcheckTimeout = 300
restartPolicyType = "ON_FAILURE"
restartPolicyMaxRetries = 10

deploy/docs-api → railway.toml

[build]
builder = "DOCKERFILE"
dockerfilePath = "deployment/Dockerfile.railway.docs-api"
dockerContext = "."

[deploy]
startCommand = "node dist/apis/backend-docs-api/main.js"
healthcheckPath = "/docs-api/health"
healthcheckTimeout = 300
restartPolicyType = "ON_FAILURE"
restartPolicyMaxRetries = 10

Railway Settings

Source Configuration (per service)

Setting Value
Source Repo GoGrabSpace/editor
Branch deploy/api / deploy/ai-api / deploy/docs-api
Root Directory / (default)

Build Configuration

Setting Value
Builder Dockerfile (set via railway.toml)
Dockerfile Path From railway.toml
Use Metal Build Enabled (faster)

Watch Paths (Optional - Reduces Unnecessary Builds)

Service Watch Paths
backend-api apis/backend-api/**, libs/libs-api/**, package.json, yarn.lock
backend-ai-api apis/backend-ai-api/**, libs/libs-api/**, package.json, yarn.lock
backend-docs-api apis/backend-docs-api/**, libs/libs-api/**, package.json, yarn.lock

Environment Variables

All Services

Variable Required Description
NODE_ENV Yes production
JWT_SECRET Yes Shared JWT signing secret
MONGODB_CONNECTION_STRING Yes MongoDB Atlas URI
ALLOWED_ORIGINS Yes CORS allowed origins

ALLOWED_ORIGINS Value

https://gograb.space,https://app.gograb.space,https://api.gograb.space,https://ai-api.gograb.space,https://docs-api.gograb.space,http://localhost:5200,http://localhost:5701

Service-Specific

Service Variable Description
backend-ai-api ANTHROPIC_API_KEY Anthropic Claude API key
backend-ai-api OPENAI_API_KEY OpenAI API key
backend-docs-api MONGODB_CONNECTION_STRING_TEST_MODULES Test modules cluster
backend-docs-api SYSTEM_TOKEN Internal system token

Verification

Health Checks

curl -s https://api.gograb.space/api/health | jq
curl -s https://ai-api.gograb.space/ai-api/health | jq
curl -s https://docs-api.gograb.space/docs-api/health | jq

Expected Response

{
  "status": "ok",
  "timestamp": "2026-01-22T22:30:00.000Z"
}

Troubleshooting

Build Uses Railpack Instead of Dockerfile

Symptom: Error "No start command was found"

Cause: Railway not reading railway.toml

Fix:

  1. Ensure railway.toml exists at repo root in the deploy branch
  2. Verify branch is correctly set in Railway Settings → Source
  3. Check that railway.toml has builder = "DOCKERFILE"

Dockerfile Path Locked in UI

Symptom: Cannot edit Dockerfile path in Railway Settings

Cause: Value is controlled by railway.toml

Fix: This is expected. Edit the railway.toml file in the deploy branch instead.

CORS Errors in Browser

Symptom: Access-Control-Allow-Origin errors

Fix: Add missing origin to ALLOWED_ORIGINS in Railway Variables

Deploy Branch Out of Sync

Symptom: Deployment doesn't include latest changes

Fix:

git checkout deploy/api
git merge main
git push origin deploy/api

Legacy Deployment (Deprecated)

The CLI-based deployment scripts in deployment/ are deprecated but kept for reference:

Use GitHub branch-based deployment instead.


Related Files

File Purpose
deployment/Dockerfile.railway.backend Backend API Dockerfile
deployment/Dockerfile.railway.backend-ai Backend AI API Dockerfile
deployment/Dockerfile.railway.docs-api Backend Docs API Dockerfile
deployment/railway.backend.toml Reference config (not used directly)
deployment/railway.backend-ai.toml Reference config (not used directly)
deployment/railway.docs-api.toml Reference config (not used directly)

Last updated: Session 59.2