Today, we will discuss how to integrate a Serverless framework with the Nx generated NestJS application. The goal of the setup is,
- I should be able to run the application as a typical NestJS express application. No dependency on the serverless.
- Configure the serverless for higher environments.
- I should be able to run the application using the Serverless offline plugin locally as well.
There are multiple ways, but I came up with this approach for the project. The project has multiple applications so we want developers not to worry much about serverless, and effectively keeping the process simple.
Step 1: Create the NestJS application using the NX CLI,
workspace name: users-ws
app name: users-api
npx create-nx-workspace my-workspace --preset=nest
Step 2: Set up the application to run the app as an express application for local development.
- Rename the main.ts file to the local-main.ts file.
- Navigate to the project.json file, and add a new configuration called local, the sample configuration structure is:
{
"main": "apps/users-api/src/local-main.ts",
"optimization": false,
"extractLicenses": true,
"inspect": false,
}
With this, we can run the application as a typical express application. The command is as below,
npm run start -- --configuration=local
Step 3: Install the Serverless framework libraries
- Install the serverless global, for ease of running the application.
npm i -g serverless
- Install the libraries that help to run the NestJS app on the AWS serverless environment
npm i --save-dev serverless-offline serverless-plugin-optimize aws-lambda
npm i --save @vendia/serverless-express
Step 4: Setup serverless app
- Create a main.ts file and a sample example is below,
import { NestFactory } from '@nestjs/core';
import { configure as serverlessExpress } from '@vendia/serverless-express';
import { Callback, Context, Handler } from 'aws-lambda';
import { AppModule } from './app/app.module';
let server: Handler;
async function bootstrap(): Promise<Handler> {
const app = await NestFactory.create(AppModule);
const globalPrefix = 'users-api';
app.setGlobalPrefix(globalPrefix);
await app.init();
const expressApp = app.getHttpAdapter().getInstance();
return serverlessExpress({ app: expressApp });
}
export const handler: Handler = async (event: any, context: Context, callback: Callback) => {
server = server ?? (await bootstrap());
return server(event, context, callback);
};
- Create a serverless.yaml in the root folder and add the configuration to run the application in offline mode. The sample example is as below,
frameworkVersion: '>=3'
service: users-apis
configValidationMode: error
plugins:
- serverless-plugin-optimize
- serverless-offline
provider:
name: aws
stage: ${opt:stage, 'dev'}
runtime: nodejs16.x
deploymentMethod: direct
disableRollback: false
tracing:
# Can only be true if API Gateway is inside a stack.
apiGateway: true
# Optional, can be true (true equals 'Active'), 'Active' or 'PassThrough'
lambda: true
environment:
NODE_ENV: ${opt:stage, 'dev'}
versionFunctions: false
custom:
serverless-offline:
useChildProcesses: true
httpPort: 3000
websocketPort: 3001
lambdaPort: 3002
optimize:
external: ['swagger-ui-dist']
package:
patterns:
- '!./**'
- ./dist/apps/users-api/**
- node_modules/**
functions:
users-app:
handler: dist/apps/users-api/main.handler
package:
individually: false
events: # HTTP API endpoint (API Gateway v2)
- httpApi:
method: any
path: /users-api/{proxy+}
Now, we will be able to run the app in serverless mode.
npm run build && serverless offline --stage=local
Basically, the application is built and serverless CLI is used to run the application as a serverless app.
The nodemon library can be used during the development time to look for the changes in the src folder on the user-api app and run the above command. This will avoid rerunning the above command for each file change.
Summary
We learned how we can set up the NX NestJS application along with a serverless framework. Overall, we are building the application using the Nx build and serverless CLI used for running the application.
I will create a new story that talks about integrating serverless with Nx project.json in the coming days. Feel free to provide your thoughts on the approach, Thank you.