database

Deploy PostgreSQL, Redis, MySQL, or MongoDB with pre-configured volumes, networking, and connection variables. Supports four official database templates: PostgreSQL, Redis, MySQL, and MongoDB, each with persistent volumes and automatic connection variable setup Always checks for existing databases before creating to avoid duplicates; queries environment config via GraphQL to detect running instances Provides reference variables for connecting other services (e.g., ${{Postgres.DATABASE_URL}} for backends; public URLs available for frontend-to-database patterns) Integrates with the environment skill to wire connection strings into dependent services after deployment

INSTALLATION
npx skills add https://github.com/railwayapp/railway-skills --skill database
Run in your project or agent environment. Adjust flags if your CLI version differs.

SKILL.md

Database

Add official Railway database services. These are maintained templates with pre-configured volumes, networking, and connection variables.

For non-database templates, see the templates skill.

When to Use

  • User asks to "add a database", "add Postgres", "add Redis", etc.
  • User needs a database for their application
  • User asks about connecting to a database
  • User says "add postgres and connect to my server"
  • User says "wire up the database"

Decision Flow

ALWAYS check for existing databases FIRST before creating.

User mentions database

        │

  Check existing DBs first

  (query env config for source.image)

        │

   ┌────┴────┐

 Exists    Doesn't exist

    │           │

    │      Create database

    │      (CLI or API)

    │           │

    │      Wait for deployment

    │           │

    └─────┬─────┘

          │

    User wants to

    connect service?

          │

    ┌─────┴─────┐

   Yes         No

    │           │

Wire vars    Done +

via env     suggest wiring

skill

Check for Existing Databases

Before creating a database, check if one already exists.

For full environment config structure, see environment-config.md.

railway status --json

Then query environment config and check source.image for each service:

query environmentConfig($environmentId: String!) {

  environment(id: $environmentId) {

    config(decryptVariables: false)

  }

}

The config.services object contains each service's configuration. Check source.image for:

  • ghcr.io/railway/postgres* or postgres:* → Postgres
  • ghcr.io/railway/redis* or redis:* → Redis
  • ghcr.io/railway/mysql* or mysql:* → MySQL
  • ghcr.io/railway/mongo* or mongo:* → MongoDB

Available Databases

Database

Template Code

PostgreSQL

postgres

Redis

redis

MySQL

mysql

MongoDB

mongodb

Prerequisites

Get project context:

railway status --json

Extract:

  • id - project ID
  • environments.edges[0].node.id - environment ID

Get workspace ID (not in status output):

bash <<'SCRIPT'

scripts/railway-api.sh \

  'query getWorkspace($projectId: String!) {

    project(id: $projectId) { workspaceId }

  }' \

  '{"projectId": "PROJECT_ID"}'

SCRIPT

Adding a Database

Step 1: Fetch Template

bash <<'SCRIPT'

scripts/railway-api.sh \

  'query template($code: String!) {

    template(code: $code) {

      id

      name

      serializedConfig

    }

  }' \

  '{"code": "postgres"}'

SCRIPT

This returns the template's id and serializedConfig needed for deployment.

Step 2: Deploy Template

bash <<'SCRIPT'

scripts/railway-api.sh \

  'mutation deployTemplate($input: TemplateDeployV2Input!) {

    templateDeployV2(input: $input) {

      projectId

      workflowId

    }

  }' \

  '{

    "input": {

      "templateId": "TEMPLATE_ID",

      "serializedConfig": SERIALIZED_CONFIG,

      "projectId": "PROJECT_ID",

      "environmentId": "ENVIRONMENT_ID",

      "workspaceId": "WORKSPACE_ID"

    }

  }'

SCRIPT

Important: serializedConfig is the exact object from the template query, not a string.

Connecting to the Database

After deployment, other services connect using reference variables.

For complete variable reference syntax and wiring patterns, see variables.md.

Backend Services (Server-side)

Use the private/internal URL for server-to-server communication:

Database

Variable Reference

PostgreSQL

${{Postgres.DATABASE_URL}}

Redis

${{Redis.REDIS_URL}}

MySQL

${{MySQL.MYSQL_URL}}

MongoDB

${{MongoDB.MONGO_URL}}

Frontend Applications

Important: Frontends run in the user's browser and cannot access Railway's private network. They must use public URLs or go through a backend API.

For direct database access from frontend (not recommended):

  • Use the public URL variables (e.g., ${{MongoDB.MONGO_PUBLIC_URL}})
  • Requires TCP proxy to be enabled

Better pattern: Frontend → Backend API → Database

Example: Add PostgreSQL

bash <<'SCRIPT'

# 1. Get context

railway status --json

# Extract project.id and environment.id

# 2. Get workspace ID

scripts/railway-api.sh \

  'query { project(id: "proj-id") { workspaceId } }' '{}'

# 3. Fetch Postgres template

scripts/railway-api.sh \

  'query { template(code: "postgres") { id serializedConfig } }' '{}'

# 4. Deploy template

scripts/railway-api.sh \

  'mutation deploy($input: TemplateDeployV2Input!) {

    templateDeployV2(input: $input) { projectId workflowId }

  }' \

  '{"input": {"templateId": "...", "serializedConfig": {...}, "projectId": "...", "environmentId": "...", "workspaceId": "..."}}'

SCRIPT

Then Connect From Another Service

Use environment skill to add the variable reference:

{

  "services": {

    "<backend-service-id>": {

      "variables": {

        "DATABASE_URL": { "value": "${{Postgres.DATABASE_URL}}" }

      }

    }

  }

}

Response

Successful deployment returns:

{

  "data": {

    "templateDeployV2": {

      "projectId": "e63baedb-e308-49e9-8c06-c25336f861c7",

      "workflowId": "deployTemplate/project/e63baedb-e308-49e9-8c06-c25336f861c7/xxx"

    }

  }

}

What Gets Created

Each database template creates:

  • A service with the database image
  • A volume for data persistence
  • Environment variables for connection strings
  • TCP proxy for external access (where applicable)

Error Handling

Error

Cause

Solution

Template not found

Invalid template code

Use: postgres, redis, mysql, mongodb

Permission denied

User lacks access

Need DEVELOPER role or higher

Project not found

Invalid project ID

Run railway status --json for correct ID

Example Workflows

"add postgres and connect to the server"

  • Check existing DBs via env config query
  • If postgres exists: Skip to step 5
  • If not exists: Deploy postgres template (fetch template → deploy)
  • Wait for deployment to complete
  • Identify target service (ask if multiple, or use linked service)
  • Use environment skill to stage: DATABASE_URL: { "value": "${{Postgres.DATABASE_URL}}" }
  • Apply changes

"add postgres"

  • Check existing DBs via env config query
  • If exists: "Postgres already exists in this project"
  • If not exists: Deploy postgres template
  • Inform user: "Postgres created. Connect a service with: DATABASE_URL=${{Postgres.DATABASE_URL}}"

"connect the server to redis"

  • Check existing DBs via env config query
  • If redis exists: Wire up REDIS_URL via environment skill → apply
  • If no redis: Ask "No Redis found. Create one?"
  • Deploy redis template
  • Wire REDIS_URL → apply

Composability

  • Connect services: Use environment skill to add variable references
  • View database service: Use service skill
  • Check logs: Use deployment skill
BrowserAct

Let your agent run on any real-world website

Bypass CAPTCHA & anti-bot for free. Start local, scale to cloud.

Explore BrowserAct Skills →

Stop writing automation&scrapers

Install the CLI. Run your first Skill in 30 seconds. Scale when you're ready.

Start free
free · no credit card