AI Workshop: learn to build apps with AI →
Railway: Using Railway private networking

Join the AI Workshop and learn to build real-world apps with AI. A hands-on, practical program to level up your skills.


Railway (mandatory referral link) has 2 different networking systems:

  1. a public network
  2. a private network

The public network gives you a public URL that can be referenced from anywhere.

The private network is a URL that’s private, internal to Railway.

The big benefit of the private network is that a service is inherently more secure when it’s not accessible from the public Internet and doesn’t need to be.

But on top of that, you get this huge advantage: using the private network has no cost, while the public network incurs egress fees ($0.10 / GB).

So by using the private network things are more secure, and cheaper to host.

For a while I had trouble using Railway’s (and Fly.io’s) private networking to connect my app with PocketBase but eventually I discovered the problem and since this might be something you can stumble upon too, let me explain.

When using the public network, you get a URL like:

<custom_subdomain>.up.railway.app

In your app, you connect to this using:

https://<the URL>

With private networking, you get a URL like this:

<custom_subdomain>.railway.internal

In your app, you must use the PORT as well. This is the internal port exposed by your Docker container.

In my case I used 8080, so I had to use this URL in my app:

<custom_subdomain>.railway.internal:8080

Super important: use http:// and NOT https:// or the internal network will not work.

You typically use variable references on Railway to avoid hardcoding the variables, so you can write your variables as something like:

POCKETBASE_URL=http://${{pocketbase.RAILWAY_PRIVATE_DOMAIN}}:${{pocketbase.PORT}}

assuming PORT was defined as a PocketBase service variable on Railway.

Lessons in this unit:

0: Introduction
1: Railway: Effortless Web App Deployments
2: ▶︎ Using Railway private networking