Search code examples
javascriptpythondjangonestjs

Are integration tests in the JS backend ecosystem frowned upon?


I worked with Python APIs before (Mostly Django and FastAPI). Our test setup, using standard practice in Django, involved creating a test database and check for db state in our integration and e2e tests. It made sense to me as there were no doubts that an endpoint did what it's supposed to do when the tests passed.

Now I'm working at a place that uses NestJS in TS and TypeORM. As I have found out, there are no testing features in jest that create a test database and resets it between tests. When I ask my colleagues and search around it seems like the general advice in NestJS and JS ecosystem in general is that you are supposed to write mostly unit tests and mock all the DB calls. Our current test setup doesn't fill me with confidence. There were several incidences where the mocked calls were too simple to catch mistakes in calling the DB.

So my question is, why is there such a difference between these two frameworks/languages? How do people write reliable integration tests without the DB layer in JS backends?


Solution

  • seems like the general advice in NestJS and JS ecosystem in general is that you are supposed to write mostly unit tests and mock all the DB calls

    This is wrong. Nest doesn't encourage only writing backend integration tests or unit tests. The docs show how to write both, and there are several test example repositories that show e2e and unit tests. What you might be noticing is that Nest has a way to go about writing unit tests where you should be mocking dependencies, and that may feel like it's the main focus, but in the end, integration tests would be very similar regardless of the HTTP framework, express, fastify, Nest, Koa, you just spin up a test server, hit the endpoints, assert the results, and verify in the database if necessary.

    You'd need to look at what specific database tool you're using (sounds like TypeORM) and see the tools around that to have integrations for creating and tearing down databases in test environments.

    My personal preference is to use a docker-compose.test.yml and start up a fully new database, migrate to it, seed it, and then run my tests. If the suite requires any specific test data, then I'd add that in a beforeAll block and clean it up in an afterAll