Testing with Supertest
Supertest Express app ko DIRECTLY leta hai (app.listen() ki zaroorat nahi) aur uske against real HTTP requests simulate karta hai. Isliye app.js mein "app" export karo aur listen() alag server.js mein rakho — warna test chalate waqt port bind ho jaayega.
Test mein status code, response body aur headers sab assert kiye ja sakte hain. External dependencies (DB, third-party API) ko mock karke tests fast aur deterministic rakho.
// app.js -> module.exports = app; (listen alag file mein)
const request = require("supertest");
const app = require("../app");
test("POST /users creates a user", async () => {
const res = await request(app)
.post("/users").send({ name: "Aarav", email: "a@b.com" });
expect(res.status).toBe(201);
expect(res.body).toHaveProperty("id");
});- Supertest bina port bind kiye app ke against real HTTP requests bhejta hai
- app aur server ko alag files mein rakho — testing aasaan ho jaati hai
- Status, body aur headers sab assert kar sakte ho
Sabse important testing setup decision — app.js sirf app banaye aur export kare, server.js use listen kare. Isse Supertest bina port bind kiye app ko test kar sakta hai, aur parallel test files bhi conflict nahi karti.
// app.js
const app = express(); /* ...routes... */ module.exports = app;
// server.js
require("./app").listen(process.env.PORT || 3000);Protected routes ke liye test mein token generate karke Authorization header bhejo, ya agent() se cookie session maintain karo. External services (payment, email) mock kar do taaki tests fast aur deterministic rahein.
test("GET /me requires auth", async () => {
await request(app).get("/me").expect(401);
const token = jwt.sign({ sub: 1 }, process.env.JWT_SECRET);
const res = await request(app).get("/me")
.set("Authorization", `Bearer ${token}`).expect(200);
expect(res.body.id).toBe(1);
});