GitHub and Railway: Repo Variables, Secrets, and Services Without the UI

Version: 1.0
Date: March 10, 2026
Purpose: Enable Cursor AI agents (and humans) to configure GitHub repo variables/secrets and create Railway services using only the CLI—no dashboard or browser required.


1. Prerequisites

  • GitHub CLI (gh) installed and authenticated: gh auth status shows a logged-in user with repo and workflow scopes.
  • Railway CLI (railway) installed and authenticated: railway whoami shows a user. Run railway login once if needed.

See GitHub CLI Setup and Railway CLI Setup for installation and auth.


2. GitHub: Repository Variables and Secrets (CLI Only)

All operations use gh with --repo owner/repo. No need to open GitHub Settings in the browser.

2.1 List Variables and Secrets

# Repository variables (names and updated timestamps; values are not shown)
gh variable list --repo brainforge-ai/brainforge-platform
 
# Repository secrets (names and updated timestamps only; values are never shown)
gh secret list --repo brainforge-ai/brainforge-platform

2.2 Set a Repository Variable

gh variable set VARIABLE_NAME --body "value" --repo brainforge-ai/brainforge-platform

Example:

gh variable set RAILWAY_MARKETING_PROJECT_ID --body "88d90404-beb5-4e31-8a24-5b4a13403f56" --repo brainforge-ai/brainforge-platform
gh variable set RAILWAY_MARKETING_SERVICE --body "marketing-site" --repo brainforge-ai/brainforge-platform

2.3 Set a Repository Secret

Option A — value from stdin (recommended; avoids exposing secret in shell history):

echo -n "secret-value" | gh secret set SECRET_NAME --repo brainforge-ai/brainforge-platform

Option B — value from a file or another command:

jq -r '.user.token' ~/.railway/config.json | gh secret set RAILWAY_TOKEN --repo brainforge-ai/brainforge-platform

Option C — inline (use only when necessary):

gh secret set SECRET_NAME --body "secret-value" --repo brainforge-ai/brainforge-platform

2.4 Delete a Variable or Secret

gh variable delete VARIABLE_NAME --repo brainforge-ai/brainforge-platform
gh secret delete SECRET_NAME --repo brainforge-ai/brainforge-platform

2.5 Permissions

  • Listing and setting repo variables/secrets requires admin (or maintain) access to the repository.
  • If gh variable list or gh secret set fails with a permission error, the authenticated user needs higher repo access or an org owner must grant it.

3. Railway: Create a Service and Get IDs (CLI Only)

You can create a new service in an existing project and link the repo without using the Railway dashboard.

When multiple workspaces or environments exist, the CLI requires explicit flags in non-interactive use:

# Link by project ID (from Railway dashboard URL or bot comment in a PR)
railway link \
  --workspace "Brainforge" \
  --project "88d90404-beb5-4e31-8a24-5b4a13403f56" \
  --environment "6e0d9cdf-b92e-48d9-8dcc-278be80f4279"
  • Workspace name: From railway list (e.g. “Brainforge”).
  • Project ID: UUID from the project URL or from a Railway bot PR comment (railway-project-id="...").
  • Environment ID: UUID of the environment to use (e.g. a PR preview env or staging). Omit to be prompted.

3.2 Create a New Service

From the repo root (or the app directory you want to associate with the service):

# Creates an empty service named "marketing-site" in the linked project
railway add --service marketing-site

You may be prompted for “What do you need?” (e.g. Empty Service) and a service name; the name can be passed as above. After this, railway status should show the new service.

railway service marketing-site

3.4 Get Project ID and Service Name for GitHub

  • Project ID: Use the same UUID you used in railway link --project (or from a Railway deployment bot comment on a PR: railway-project-id="88d90404-...").
  • Service name: The name you passed to railway add --service (e.g. marketing-site). GitHub Actions and the Railway CLI use this name with --service marketing-site.

No need to look up a service UUID in the UI; the service name is sufficient for the CLI and for repo variables.


4. Using the Railway Token in GitHub Actions

GitHub Actions needs a Railway token (e.g. RAILWAY_TOKEN) to run railway up or the Railway CLI in CI.

4.1 Source the Token Without the UI

If the human (or agent) has already run railway login, the CLI stores a token in:

  • Path: ~/.railway/config.json
  • Key: user.token

To set the repo secret from that token (without displaying it):

jq -r '.user.token' ~/.railway/config.json | gh secret set RAILWAY_TOKEN --repo brainforge-ai/brainforge-platform

Security note: That token is an account token (full access for the logged-in user). For production or shared repos, prefer a project or workspace token from Railway → Account → Tokens, then set it the same way via stdin.

4.2 Marketing Site CI: use a project token

The workflow .github/workflows/marketing-site-cicd.yml runs railway up --project ... --service ... in CI. Railway CLI in that context requires a project token, not the account token from ~/.railway/config.json. Using an account token can yield Unauthorized in CI.

  1. In Railway: open the brainforge-platform project (ID 88d90404-beb5-4e31-8a24-5b4a13403f56) → SettingsTokens (or Project → Settings → Tokens).
  2. Create a new token (e.g. “GitHub Actions marketing-site deploy”). Copy the value.
  3. Store the token in 1Password (Brainforge AI Team vault), e.g. as “Railway Github Marketing Production Token” or similar.
  4. Set the GitHub secret (from 1Password or stdin):
    op read "op://Brainforge AI Team/Railway Github Marketing Production Token/notesPlain" | gh secret set RAILWAY_MARKETING_SITE_TOKEN -R brainforge-ai/brainforge-platform

5. End-to-End Example: Marketing-Site CI/CD

This is the flow used to enable the marketing-site workflow (.github/workflows/marketing-site-cicd.yml) without opening GitHub or Railway in the browser.

  1. Ensure auth

    • gh auth status and railway whoami both show a logged-in user.
  2. Link Railway and create the service

    railway link --workspace "Brainforge" --project "88d90404-beb5-4e31-8a24-5b4a13403f56" --environment "<ENVIRONMENT_ID>"
    railway add --service marketing-site
    railway service marketing-site
  3. Set GitHub repo variables

    gh variable set RAILWAY_MARKETING_PROJECT_ID --body "88d90404-beb5-4e31-8a24-5b4a13403f56" --repo brainforge-ai/brainforge-platform
    gh variable set RAILWAY_MARKETING_SERVICE --body "marketing-site" --repo brainforge-ai/brainforge-platform
  4. Set GitHub repo secret
    For marketing-site CI/CD, use a project token (see §4.2), not the account token:

    op read "op://Brainforge AI Team/<Railway Marketing Token Item>/notesPlain" | gh secret set RAILWAY_MARKETING_SITE_TOKEN -R brainforge-ai/brainforge-platform
  5. Verify

    gh variable list --repo brainforge-ai/brainforge-platform
    gh secret list --repo brainforge-ai/brainforge-platform

After this, the marketing-site workflow can deploy to the marketing-site service without any UI steps.


6. Reference: Useful Commands

GoalCommand
List repo variablesgh variable list -R owner/repo
Set repo variablegh variable set NAME -b "value" -R owner/repo
List repo secretsgh secret list -R owner/repo
Set repo secret from stdinecho -n "val" | gh secret set NAME -R owner/repo
Railway: list projectsrailway list
Railway: link (non-interactive)railway link -w "Workspace" -p "project-uuid" -e "env-uuid"
Railway: add servicerailway add --service service-name
Railway: link to servicerailway service service-name
Railway: token path~/.railway/config.jsonjq -r '.user.token'

7. Version History

  • v1.0 (March 10, 2026) — Initial doc: GitHub variables/secrets via gh, Railway service creation and token usage without UI.