87 lines
3.1 KiB
TypeScript
87 lines
3.1 KiB
TypeScript
// Ported from apps/server/test (CR-014 Step 14.5): now runs on the engine.
|
|
import { content } from "@deadhead/content";
|
|
import { errorResponseSchema } from "@deadhead/schema";
|
|
import { describe, expect, it } from "vitest";
|
|
import {
|
|
useTestApp,
|
|
signUp,
|
|
call,
|
|
getState,
|
|
setCredits,
|
|
tutorialBoard,
|
|
flyTutorialRun,
|
|
} from "../support";
|
|
|
|
const testApp = useTestApp();
|
|
|
|
describe("tutorial flow v2", () => {
|
|
it("starts a guest with the starting cushion, the Company Courier loaner at Earth and no runs", async () => {
|
|
const { app } = testApp();
|
|
const guest = await signUp(app);
|
|
const state = await getState(app, guest);
|
|
expect(state.company).toMatchObject({
|
|
credits: content.config.startingCredits,
|
|
loanBalance: 0,
|
|
});
|
|
expect(state.tutorial).toEqual({
|
|
loanerLocationId: "earth",
|
|
runInFlight: false,
|
|
runsCompleted: 0,
|
|
dealAvailable: false,
|
|
});
|
|
expect(state.pilots[0]).toMatchObject({ isAvatar: true, locationId: "earth" });
|
|
expect(state.goals).toEqual([]);
|
|
});
|
|
|
|
it("counts each resolved run and gives every run a fresh three-contract board", async () => {
|
|
const guest = await signUp(testApp().app);
|
|
const first = await tutorialBoard(testApp().app, guest);
|
|
expect(first).toHaveLength(3);
|
|
|
|
const state = await flyTutorialRun(testApp(), guest);
|
|
expect(state.tutorial).toMatchObject({ runsCompleted: 1, loanerLocationId: "moon" });
|
|
|
|
const second = await tutorialBoard(testApp().app, guest);
|
|
expect(second).toHaveLength(3);
|
|
for (const c of second) expect([c.originId, c.destinationId]).toEqual(["moon", "earth"]);
|
|
expect(second.map((c) => c.id)).not.toEqual(first.map((c) => c.id));
|
|
});
|
|
|
|
it("offers Unmarked crates on the third run's board", async () => {
|
|
const guest = await signUp(testApp().app);
|
|
await flyTutorialRun(testApp(), guest);
|
|
await flyTutorialRun(testApp(), guest);
|
|
const third = await tutorialBoard(testApp().app, guest);
|
|
expect(third.find((c) => c.scriptedId === "unmarked-crates")).toBeDefined();
|
|
});
|
|
|
|
it("makes the deal available after five runs ending at the Moon, not after four (CR-017)", async () => {
|
|
const guest = await signUp(testApp().app);
|
|
for (let run = 1; run <= 4; run++) await flyTutorialRun(testApp(), guest);
|
|
const afterFour = await getState(testApp().app, guest);
|
|
expect(afterFour.tutorial).toMatchObject({
|
|
runsCompleted: 4,
|
|
loanerLocationId: "earth",
|
|
dealAvailable: false,
|
|
});
|
|
|
|
const afterFive = await flyTutorialRun(testApp(), guest);
|
|
expect(afterFive.tutorial).toMatchObject({
|
|
runsCompleted: 5,
|
|
loanerLocationId: "moon",
|
|
runInFlight: false,
|
|
dealAvailable: true,
|
|
});
|
|
});
|
|
|
|
it("blocks hiring pilots during the tutorial", async () => {
|
|
const { app } = testApp();
|
|
const guest = await signUp(app);
|
|
await setCredits(testApp().app, 1_000_000);
|
|
const response = await call(app, guest, "POST", "/api/pilots", { locationId: "earth" });
|
|
expect(response.statusCode).toBe(409);
|
|
expect(errorResponseSchema.parse(response.json()).error.code).toBe("tutorial-active");
|
|
expect((await getState(app, guest)).pilots).toHaveLength(1);
|
|
});
|
|
});
|