---
title: "Building a NestJS App on Railway"
description: "Learn how to build and scale a NestJS application on Railway"
date: 2024-12-13T00:00:00.000Z
updated: 2026-10-29T11:13:05.478Z
topics: ["Guides"]
tags: []
url: https://railway.com/guides/building-nestjs-on-railway
---

# Building a NestJS App on Railway

[Nestjs](https://nestjs.com/) is a javascript framework with a typescript flavour. Often described as the swiss-army of javascript backend applications, it allows you to write following an object-oriented programming paradigm or functional programming and is easily a good switch for anyone coming from a non-js background to make the switch.

This article covers the nitty gritty of getting out Nestjs running on Railway.  [Here is the link to the project we will build in GitHub](https://github.com/D-Lite/rail-nest).

Let's get started.

## Create a new Nestjs Project

You can use your preferred `cli` tool on your machine to get started.

To create a new project, just type the commands below sequentially

- Install nestjs:

```bash
npm i -g @nestjs/cli
```

- Create a new nestjs project:

```bash
nest new rail-nest
```

The project name is `rail-nest` which can be replaced with any name you like.

- Run the command below to enter the new project directory and start the nestjs project locally on your machine:

```bash
cd rail-nest
npm run start
```

If you navigate to `http://localhost:3000` on your browser, you should get a positive response showing your nestjs application is running.

### Add a Dockerfile

To have an application that can easily scale, where we can continually add more components as our application grows, containerization is a great approach to ensuring we can have an all-in-one application.

To get started, we need to create a [Dockerfile](https://docs.docker.com/build/concepts/dockerfile/), where we can add detailed instructions for our Docker applications.

- In your `cli`, run the command below to create a `Dockerfile` and a `.dockerignore` in your project root directory.

```bash
touch Dockerfile .dockerignore
```

- Then let's add the instruction below to the Dockerfile

```docker
# Base image
FROM node:20

# Create app directory
WORKDIR /usr/src/app

# A wildcard is used to ensure both package.json AND package-lock.json are copied
COPY package*.json ./

# Install app dependencies
RUN npm ci

# Bundle app source
COPY . .

# Creates a "dist" folder with the production build
RUN npm run build

# Expose the port on which the app will run
EXPOSE 3000

# Start the server using the production build
CMD ["npm", "run", "start:prod"]
```

- Add the following to your `.dockerignore`.

```docker
Dockerfile
 .dockerignore
node_modules
npm-debug.log
Dist
```

### Deploy to Railway

Now let’s deploy the project to Railway.  See [Railway docs](https://docs.railway.com/quick-start#deploying-your-project---from-github) for reference if needed.

- Push the NestJS code to a github repo.
- On your project canvas in Railway
    - Create a new project
    - Add a new Github service
    - Select your Github repo
    - Connect your github repo to the source repo in the source section.
    - Apply changes to deploy the app

## Setup the app database, cache, and task scheduler

The setup ensures that the database, migrations, queues and scheduled tasks are all operational and can run seamlessly.

### Setup the cache manager

We will start by using the Nestjs cache manager, the native cache manager stores the cache in memory, we will then configure the cache to be stored in Redis.

- Install this cache manager package via your cli:

```bash
npm install @nestjs/cache-manager cache-manager@5.1.1 @nestjs/config
```

- Then import the `CacheModule` into your`app.module.ts`:

```tsx
import { Module } from '@nestjs/common';
import { ConfigModule } from '@nestjs/config';
import { CacheModule } from '@nestjs/cache-manager';
import { AppController } from './app.controller';
import { AppService } from './app.service';

@Module({
  imports: [
	ConfigModule.forRoot(),
	CacheModule.register()
  ],
  controllers: [AppController],
  providers: [AppService],
})
export class AppModule {}
```

**Implement the cache module globally (Optional)**

If you want to leverage the cache module across different modules, you can pass the `isGlobal` flag property:

```tsx
CacheModule.register({ isGlobal: true })
```

For example, here's a CacheModule implementation applied globally to a NestJS app in the `app.module.ts` file:

```tsx
import { CacheModule, Module } from '@nestjs/common';
import * as redisStore from 'cache-manager-redis-store';
import { ConfigModule } from '@nestjs/config';

@Module({
  imports: [
    ConfigModule.forRoot(),
    CacheModule.register({
      isGlobal: true,
    }),
  ],
})
export class AppModule {}
```

**Implement Redis for caching**

Up to this point, our cache will be stored in memory, to migrate easily to Redis, we will need to update the cache module configuration and also create a Redis server in Railway.

- Let's install the relevant packages:

```bash
npm install cache-manager-redis-store@3.0.1
npm install --save-dev @types/cache-manager-redis-store
```

- Now, proceed to change the cache module to use Redis.

```tsx
import { Module } from '@nestjs/common';
import { AppController } from './app.controller';
import { AppService } from './app.service';
import { CacheModule } from '@nestjs/cache-manager';
import * as redisStore from 'cache-manager-redis-store';
import { ConfigModule } from '@nestjs/config';

@Module({
  imports: [
    ConfigModule.forRoot(),
    CacheModule.register({
    isGlobal: true,
    store: redisStore,
    host: process.env.REDISHOST,
    port: process.env.REDISPORT
  })],
  controllers: [AppController],
  providers: [AppService],
})
export class AppModule {}
```

- After, we will tweak our cache module to the instruction below:

```bash
import { Module } from '@nestjs/common';
import { AppController } from './app.controller';
import { AppService } from './app.service';
import { ConfigModule } from '@nestjs/config';
import { CacheModule, CacheStore } from '@nestjs/cache-manager';
import { redisStore } from 'cache-manager-redis-store';

@Module({
  imports: [
    ConfigModule.forRoot(),
    CacheModule.registerAsync({
      isGlobal: true,
      useFactory: async () => {
        const store = await redisStore({
          socket: {
            host: process.env.REDISHOST,
            port: +process.env.REDISPORT,
          },
          url: process.env.REDISURL,
          password: process.env.REDISPASSWORD
        });
        return {
          store: store as unknown as CacheStore,
          ttl: 60 * 60 * 24 * 7,
        }
      }
    })
  ],
  controllers: [AppController],
  providers: [AppService],
})
export class AppModule {}
```

All set locally, simply push to your github repo the latest changes.

**Add Redis to the Railway project**

Now let’s add a Redis service in Railway and connect it to NestJS.

- On your railway project canvas, create a new **redis** service.
- Head back to your App service and click on Variables.
- Add all necessary environment variables

```markdown
REDISHOST="${{Redis.REDISHOST}}"
REDISPASSWORD="${{Redis.REDIS_PASSWORD}}"
REDISPORT="${{Redis.REDISPORT}}"
REDISURL="${{Redis.REDIS_URL}}"
```

- Click Deploy

![View of NestJS project in Railway with Redis](https://cms.railway.com/media/d479c8ac93d10c42304667c1ea83acedba023cbb69591cfccd6ad0f2a87ff5b9.png)

### Adding Postgres

Currently, we have Redis infused into our Nestjs app. Let's add the postgres database.

- Locally, we are going to add `typeorm` and the `postgres` adapter package.

```
npm install @nestjs/typeorm typeorm
npm install pg
```

- Then add the following in our `app.module.ts`

```tsx
	TypeOrmModule.forRootAsync({
      useFactory: () => ({
        type: 'postgres',
        host: process.env.POSTGRESHOST,
        port: +process.env.POSTGRESPORT,
        username: process.env.POSTGRESUSER,
        password: process.env.POSTGRESPASSWORD,
        database: process.env.POSTGRESDB,
        synchronize: true,
        entities: []
      })
    })
```

Note the values in the `env` are random variables and should be replaced with their original representation based on your setup.

- Simply push to your github repo the latest changes.

**Add Postgres to the Railway project**

Now let’s add the Postgres service to our Railway project and connect it to NestJS.

- On your railway project canvas, create a new **Postgres** service.
- Head back to your App service and click on Variables.
- Add all necessary environment variables

```markdown
POSTGRESDB="${{Postgres.PGDATABASE}}"
POSTGRESHOST="${{Postgres.PGHOST}}"
POSTGRESPASSWORD="${{Postgres.PGPASSWORD}}"
POSTGRESPORT="${{Postgres.PGPORT}}"
POSTGRESUSER="${{Postgres.PGUSER}}"
```

- Click Deploy

![View of NestJS project in Railway with Postgres](https://cms.railway.com/media/2e23a7f1c0e4d981dcc0d8b885f662ba1ef4fba673c89290f20d90b0fa692cc2.png)

### Adding a task scheduler

Let us add a task scheduler in Nestjs.

- Installing the packages below:

```bash
npm install --save @nestjs/schedule
npm install --save-dev @types/cron
```

- Add the instruction below to your `app.module.ts` import section:

```tsx
ScheduleModule.forRoot()
```

Nestjs schedule runs alongside your main application, by integrating the cron functionality directly into the application lifecycle.

- A final push to the github repo and our setup is complete.

### Set up a Public URL

Let’s make the NestJS app available on the public internet.

- Navigate to the Networking section under the [Settings](https://docs.railway.com/overview/the-basics#service-settings) tab of your new service.
- Click [Generate Domain](https://docs.railway.com/networking/public-networking) to create a public URL for your app.

We now have a fully functional Nestjs application running in Railway!  

Let’s explore one more option for starting a NestJS project in Railway.

## One-Click Deploy from a Template

Railway provides [templates](https://railway.com/deploy) as a way to get started almost immediately with your NestJS project, enabling you to provision a service or set of services by simple clicks.

If you’re looking for the fastest way to get started, the one-click deploy option is ideal. It sets up your Nestjs app along with a Redis database, a Postgres database and the Nestjs scheduler. Just click the button below to get started.

[https://railway.com/new/template/nvnuEH?referralCode=BAh47U](https://railway.com/new/template/nvnuEH?referralCode=BAh47U)

After deploying, we recommend that you eject from the template to create a copy of the repository under your own GitHub account. This will give you full control over the source code and project.

## Conclusion

With that, we've successfully set up a Nestjs application coupled with everything needed to get started immediately, database, caching and cron schedule inclusive. You should also be able to use this as a reference to deploy your Nestjs application from scratch or via Github. There is no limit to what you can do, and can decide to extend to other Railway compatible service.