import { ErrorCode, type SignupInput } from "@batch-cooking/shared"; import { faker } from "@faker-js/faker"; import { expect } from "chai"; import request from "supertest"; import { createApp } from "../src/app.js"; import { prisma } from "../src/db/prisma.js"; import { resetDatabase } from "../test-support/reset-db.js"; /** See `auth.test.ts` — same rationale for generating rather than hardcoding. */ function buildSignupPayload(): SignupInput { const firstName = faker.person.firstName(); const lastName = faker.person.lastName(); return { firstName, lastName, email: faker.internet.email({ firstName, lastName }).toLowerCase(), password: faker.internet.password({ length: 16 }), }; } describe("Planning", () => { const app = createApp(); beforeEach(async () => { await resetDatabase(); }); after(async () => { await prisma.$disconnect(); }); describe("GET /planning/current", () => { it("rejects requests without a session cookie with 401 NOT_AUTHENTICATED", async () => { const res = await request(app).get("/planning/current"); expect(res.status).to.equal(401); expect(res.body.code).to.equal(ErrorCode.NOT_AUTHENTICATED); }); it("returns null when the household has no planning covering today", async () => { const agent = request.agent(app); await agent.post("/auth/signup").send(buildSignupPayload()); const res = await agent.get("/planning/current"); expect(res.status).to.equal(200); expect(res.body).to.equal(null); }); it("returns the household's planning covering today, with recipes resolved", async () => { const agent = request.agent(app); const signupRes = await agent.post("/auth/signup").send(buildSignupPayload()); const houseId: number = signupRes.body.houseId; const recipe = await prisma.recipe.create({ data: { name: "Ratatouille" } }); const today = new Date(); const planning = await prisma.planning.create({ data: { houseId, startDate: new Date( Date.UTC(today.getUTCFullYear(), today.getUTCMonth(), today.getUTCDate() - 2), ), finishDate: new Date( Date.UTC(today.getUTCFullYear(), today.getUTCMonth(), today.getUTCDate() + 2), ), }, }); await prisma.planningItem.create({ data: { planningId: planning.id, weekDay: "monday", meal: "dinner", recipeId: recipe.id }, }); const res = await agent.get("/planning/current"); expect(res.status).to.equal(200); expect(res.body.id).to.equal(planning.id); expect(res.body.items).to.have.length(1); expect(res.body.items[0]).to.include({ weekDay: "monday", meal: "dinner" }); expect(res.body.items[0].recipe).to.include({ id: recipe.id, name: "Ratatouille" }); }); it("returns null when the household's planning does not cover today", async () => { const agent = request.agent(app); const signupRes = await agent.post("/auth/signup").send(buildSignupPayload()); const houseId: number = signupRes.body.houseId; // A planning entirely in the past — shouldn't be picked up as "current". await prisma.planning.create({ data: { houseId, startDate: new Date(Date.UTC(2000, 0, 1)), finishDate: new Date(Date.UTC(2000, 0, 7)), }, }); const res = await agent.get("/planning/current"); expect(res.status).to.equal(200); expect(res.body).to.equal(null); }); }); });