let app: INestApplication;
beforeAll(async () => {
const moduleRef = await Test.createTestingModule({ imports: [AppModule] })
.overrideProvider(MailService).useValue({ send: jest.fn() })
.compile();
app = moduleRef.createNestApplication();
app.useGlobalPipes(new ValidationPipe({ whitelist: true }));
await app.init();
});
afterAll(() => app.close());
it("GET /cats", () => request(app.getHttpServer()).get("/cats").expect(200));
Start the real app inside a testing module, then send HTTP requests to it with Supertest.
The steps:
- Compile a testing module that imports the real
AppModule. - Optionally, replace external services like mail or payment providers with
overrideProvider().useValue(). - Call
createNestApplication()andawait app.init(). You get a full app with all middleware, guards, pipes and filters connected. - Use Supertest to send real HTTP requests to
app.getHttpServer(). Check the status and the body. - Close the app in
afterAll. Otherwise open connections keep Jest running.
A common problem: global setup in main.ts is not applied here, because the test doesn't run main.ts. Examples are useGlobalPipes and setGlobalPrefix. Fix it in one of these ways:
- Repeat the setup in the test.
- Move it into a shared function that both use.
- Register it as
APP_*providers, such asAPP_PIPE.
- Import the real
AppModuleinto a testing module. - Call
createNestApplication()and thenapp.init(). - Send requests with Supertest to
app.getHttpServer(). - Override external services, and close the app after the tests.
- Global setup in
main.tsis not applied automatically.
Read more
- Testing (https://docs.nestjs.com/fundamentals/testing)docs.nestjs.com