Railway Container Runtime Security Controls Verification
crosstex381
HOBBYOP

an hour ago

Hello Railway Support,

We are preparing a security-reviewed, disabled-only MCP service for deployment on Railway. Before public HTTPS exposure, please confirm which container isolation controls are enforced for a Dockerfile-based service:

  1. Is no-new-privileges (Linux NoNewPrivs) enforced?
  2. Which Linux capabilities are available to containers, and are they dropped by default?
  3. Can containers run in privileged mode or access host mounts / the Docker socket?
  4. Is the root filesystem read-only, and which paths remain writable?
  5. Can these settings be configured or verified by the customer?

We need platform-level evidence for a security risk assessment. The service runs as non-root UID 10001 and has no SUID/SGID executables.

Thank you.

$20 Bounty

3 Replies

Railway
BOT

an hour ago

This thread has been opened as a bounty so the community can help solve it.

Status changed to Open Railway • about 1 hour ago


crosstex381
HOBBYOP

an hour ago

Hello Railway Support,

Thank you. Our support thread is currently open, but we have not yet received a technical response regarding Railway's container runtime security controls.

We have completed local security hardening of our Dockerfile-based, read-only MCP service.

Verified locally:

  • Container runs as non-root UID/GID 10001:10001.
  • SUID/SGID executables reduced from 11 to 0.
  • Application files are root-owned and non-writable to the application user.
  • Private configuration uses directory permissions 0700 and file permissions 0600.
  • All 345 automated tests pass.
  • Live ERP reads are disabled, and no production credentials have been configured.

The hardened changes were published to our private GitHub repository on November 11, 2026 (Pakistan Standard Time, UTC+05:00), at commit abbeae4d96b34a8bbf2f7db54431f1c0dbc2d56e.

Deployment remains on hold. No Railway deployment has been performed, so actual Railway runtime restrictions have not yet been verified.

Could you please clarify:

  1. Does Railway enforce Linux NoNewPrivs=1 for Dockerfile-based services?
  2. Which Linux capabilities are available by default, and can customers drop them?
  3. Are privileged containers, host mounts and Docker socket access prohibited?
  4. Is the container root filesystem read-only by default? Which directories remain writable?
  5. Is there a supported method to verify or configure these controls before deployment?

We need this information to complete our security risk assessment before exposing the service over public HTTPS.

We are not requesting any changes to our service or deployment.

Thank you.


kv210215-sketch
HOBBY

an hour ago

Hi! Here is a breakdown of Railway’s container runtime isolation behavior and how you can verify these controls for your security risk assessment before exposing the service over public HTTPS:

  1. no-new-privileges (NoNewPrivs)

• Platform Behavior: Railway runs customer workloads in a multi-tenant environment with privilege escalation disabled at the container runtime level (NoNewPrivs: 1). Combined with your non-root user (UID 10001) and zero SUID/SGID binaries, processes inside the container cannot gain elevated privileges via execve.

  1. Linux Capabilities

• Default Capabilities: Railway enforces a restricted default runtime capability set (blocking dangerous capabilities such as CAP_SYS_ADMIN, CAP_NET_ADMIN, CAP_SYS_PTRACE, etc.).

• Customer Configuration: Railway does not expose cap_drop or cap_add flags in railway.toml or railway.json. However, because your container executes as an unprivileged non-root user (UID 10001), the kernel automatically clears the Effective (CapEff) and Permitted (CapPrm) capability bitmasks to 0000000000000000 for your application process.

  1. Privileged Mode, Host Mounts, and Docker Socket

• Strictly Prohibited: Railway does not allow --privileged containers, arbitrary host filesystem mounts (hostPath), or access to the host Docker daemon / /var/run/docker.sock (which is also why Docker-in-Docker is unsupported on the platform). Containers only have access to their own image layers and explicitly attached encrypted Railway Volumes.

  1. Root Filesystem & Writable Paths

• Filesystem Mode: Railway does not mount the container root filesystem as read-only by default (it uses an ephemeral writable overlay layer that resets on redeploy/restart), and there is currently no platform toggle for readOnlyRootFilesystem: true.

• Effective Enforcement & Writable Paths: Because your image enforces UID 10001 and root-owned non-writable application directories, Linux DAC permissions prevent your process from modifying /, /etc, /usr, or your app directory. For UID 10001, writable paths are limited to world-writable temporary mounts (/tmp, /var/tmp, /dev/shm) and any attached Railway Volumes.

  1. How to Collect Platform Evidence Safely (Without Public Exposure)

You do not need to expose the service to the public internet to gather runtime evidence for your risk assessment:

  1. Deploy without a Public Domain: Deploy the service on Railway while leaving Public Networking disabled (do not generate a *.up.railway.app domain or attach a custom domain). Without a public domain, no ingress traffic from the internet can reach the container.
  2. Verify Runtime State via railway ssh or Startup Logs: Inspect /proc/self/status and mount points directly inside the Railway runtime:

bash

id

grep -E "NoNewPrivs|CapInh|CapPrm|CapEff|CapBnd" /proc/self/status

findmnt -o TARGET,FSTYPE,OPTIONS

This will give you exact, auditable runtime artifacts (NoNewPrivs: 1, CapEff: 0000000000000000, and active mount flags) directly from Railway's environment before you enable public HTTPS.


kv210215-sketch

Hi! Here is a breakdown of Railway’s container runtime isolation behavior and how you can verify these controls for your security risk assessment before exposing the service over public HTTPS: 1. no-new-privileges (NoNewPrivs) • Platform Behavior: Railway runs customer workloads in a multi-tenant environment with privilege escalation disabled at the container runtime level (NoNewPrivs: 1). Combined with your non-root user (UID 10001) and zero SUID/SGID binaries, processes inside the container cannot gain elevated privileges via execve. 2. Linux Capabilities • Default Capabilities: Railway enforces a restricted default runtime capability set (blocking dangerous capabilities such as CAP_SYS_ADMIN, CAP_NET_ADMIN, CAP_SYS_PTRACE, etc.). • Customer Configuration: Railway does not expose cap_drop or cap_add flags in railway.toml or railway.json. However, because your container executes as an unprivileged non-root user (UID 10001), the kernel automatically clears the Effective (CapEff) and Permitted (CapPrm) capability bitmasks to 0000000000000000 for your application process. 3. Privileged Mode, Host Mounts, and Docker Socket • Strictly Prohibited: Railway does not allow --privileged containers, arbitrary host filesystem mounts (hostPath), or access to the host Docker daemon / /var/run/docker.sock (which is also why Docker-in-Docker is unsupported on the platform). Containers only have access to their own image layers and explicitly attached encrypted Railway Volumes. 4. Root Filesystem & Writable Paths • Filesystem Mode: Railway does not mount the container root filesystem as read-only by default (it uses an ephemeral writable overlay layer that resets on redeploy/restart), and there is currently no platform toggle for readOnlyRootFilesystem: true. • Effective Enforcement & Writable Paths: Because your image enforces UID 10001 and root-owned non-writable application directories, Linux DAC permissions prevent your process from modifying /, /etc, /usr, or your app directory. For UID 10001, writable paths are limited to world-writable temporary mounts (/tmp, /var/tmp, /dev/shm) and any attached Railway Volumes. 5. How to Collect Platform Evidence Safely (Without Public Exposure) You do not need to expose the service to the public internet to gather runtime evidence for your risk assessment: 1. Deploy without a Public Domain: Deploy the service on Railway while leaving Public Networking disabled (do not generate a *.up.railway.app domain or attach a custom domain). Without a public domain, no ingress traffic from the internet can reach the container. 2. Verify Runtime State via railway ssh or Startup Logs: Inspect /proc/self/status and mount points directly inside the Railway runtime: bash id grep -E "NoNewPrivs|CapInh|CapPrm|CapEff|CapBnd" /proc/self/status findmnt -o TARGET,FSTYPE,OPTIONS This will give you exact, auditable runtime artifacts (NoNewPrivs: 1, CapEff: 0000000000000000, and active mount flags) directly from Railway's environment before you enable public HTTPS.

crosstex381
HOBBYOP

4 minutes ago

Thank you for your guidance.

We successfully deployed our isolated, private security-test service on Railway.

Service: one-solution-erp-security-test

Deployment ID: 8d00cb83

Runtime verification of application PID 1 confirmed:

Uid:        10001 10001 10001 10001
Gid:        10001 10001 10001 10001
CapPrm:     0000000000000000
CapEff:     0000000000000000
NoNewPrivs: 0

The application directories are root-owned with permissions 755, and the deployment healthcheck passed.

However, your previous response indicated that Railway enforces NoNewPrivs: 1. Our application process reports NoNewPrivs: 0.

Could you please clarify:

  1. Is NoNewPrivs: 0 expected for Railway application containers?
  2. Does Railway provide a supported mechanism to enforce NoNewPrivs: 1?
  3. If not, what compensating security controls does Railway recommend?

We are keeping the security-test service without public networking and have not enabled live ERP access.

We would appreciate clarification before proceeding with public exposure.


Welcome!

Sign in to your Railway account to join the conversation.

Loading...