When to Use
- When unit testing Express 5 controllers in isolation without starting the server.
- When you want to completely decouple from a real database.
- When testing specific logic, role filters, or validation branches inside a controller.
- Do NOT use this for End-to-End (E2E) integration tests that genuinely require testing the full middleware chain (CORS, body-parser, global error handlers). For E2E, use Supertest.
Critical Patterns
- NEVER instantiate the full Server: Do not import or instantiate
new Server() or app from server.ts. It causes slow tests and port conflicts.
- Global Prisma Mock: Always use
jest.mock("@prisma/client", () => { ... }) to intercept Prisma Client instantiations before the controller executes.
- Isolate Request/Response: Use
createRequest and createResponse from node-mocks-http to simulate Express objects.
- Call Controller Directly: Invoke the controller method directly (e.g.,
await controller.sendMessage(req, res)).
- Clear Mocks: Always run
jest.clearAllMocks() in the beforeEach hook.
- Assertions: Use
res._getJSONData() to verify JSON responses and res.statusCode to check HTTP statuses.
Code Examples
Basic Controller Test Setup
import { createRequest, createResponse } from "node-mocks-http";
import { MyController } from "../my.controller";
import { PrismaClient } from "@prisma/client";
// 1. MOCK PRISMA GLOBALLY
jest.mock("@prisma/client", () => {
const mPrismaClient = {
user: {
findUnique: jest.fn(),
create: jest.fn(),
},
};
return { PrismaClient: jest.fn(() => mPrismaClient) };
});
const prismaMock = new PrismaClient() as jest.Mocked<any>;
describe("MyController", () => {
let controller: MyController;
beforeAll(() => {
controller = new MyController();
});
beforeEach(() => {
jest.clearAllMocks();
});
describe("getUser", () => {
it("should return 200 and the user data", async () => {
// Arrange
const req = createRequest({
method: "GET",
url: "/api/users/1",
params: { id: "1" },
user: { id_persona: "admin-123" } // If testing protected routes
});
const res = createResponse();
prismaMock.user.findUnique.mockResolvedValue({ id: "1", name: "John" });
// Act
await controller.getUser(req, res);
// Assert
expect(res.statusCode).toBe(200);
expect(res._getJSONData().name).toBe("John");
expect(prismaMock.user.findUnique).toHaveBeenCalledWith({
where: { id: "1" }
});
});
});
});
Commands
# Run backend tests
pnpm test
# Run specific test file
pnpm jest path/to/your/controller.test.ts
Source: davidleonmayor/proyecto-grado-unimayor — distributed by TomeVault.
1---2name: davidleonmayor-proyecto-grado-unimayor-express-mocks-testing3description: When to Use4---56## When to Use78- When unit testing Express 5 controllers in isolation without starting the server.9- When you want to completely decouple from a real database.10- When testing specific logic, role filters, or validation branches inside a controller.11- **Do NOT use this for** End-to-End (E2E) integration tests that genuinely require testing the full middleware chain (CORS, body-parser, global error handlers). For E2E, use Supertest.1213## Critical Patterns1415- **NEVER instantiate the full Server:** Do not import or instantiate `new Server()` or `app` from `server.ts`. It causes slow tests and port conflicts.16- **Global Prisma Mock:** Always use `jest.mock("@prisma/client", () => { ... })` to intercept Prisma Client instantiations before the controller executes.17- **Isolate Request/Response:** Use `createRequest` and `createResponse` from `node-mocks-http` to simulate Express objects.18- **Call Controller Directly:** Invoke the controller method directly (e.g., `await controller.sendMessage(req, res)`).19- **Clear Mocks:** Always run `jest.clearAllMocks()` in the `beforeEach` hook.20- **Assertions:** Use `res._getJSONData()` to verify JSON responses and `res.statusCode` to check HTTP statuses.2122## Code Examples2324### Basic Controller Test Setup2526```typescript27import { createRequest, createResponse } from "node-mocks-http";28import { MyController } from "../my.controller";29import { PrismaClient } from "@prisma/client";3031// 1. MOCK PRISMA GLOBALLY32jest.mock("@prisma/client", () => {33 const mPrismaClient = {34 user: {35 findUnique: jest.fn(),36 create: jest.fn(),37 },38 };39 return { PrismaClient: jest.fn(() => mPrismaClient) };40});4142const prismaMock = new PrismaClient() as jest.Mocked<any>;4344describe("MyController", () => {45 let controller: MyController;4647 beforeAll(() => {48 controller = new MyController();49 });5051 beforeEach(() => {52 jest.clearAllMocks();53 });5455 describe("getUser", () => {56 it("should return 200 and the user data", async () => {57 // Arrange58 const req = createRequest({59 method: "GET",60 url: "/api/users/1",61 params: { id: "1" },62 user: { id_persona: "admin-123" } // If testing protected routes63 });64 const res = createResponse();6566 prismaMock.user.findUnique.mockResolvedValue({ id: "1", name: "John" });6768 // Act69 await controller.getUser(req, res);7071 // Assert72 expect(res.statusCode).toBe(200);73 expect(res._getJSONData().name).toBe("John");74 expect(prismaMock.user.findUnique).toHaveBeenCalledWith({75 where: { id: "1" }76 });77 });78 });79});80```8182## Commands8384```bash85# Run backend tests86pnpm test8788# Run specific test file89pnpm jest path/to/your/controller.test.ts90```9192---93> Source: [davidleonmayor/proyecto-grado-unimayor](https://github.com/davidleonmayor/proyecto-grado-unimayor) — distributed by [TomeVault](https://tomevault.io).94<!-- tomevault:4.0:skill_md:2026-06-15 -->