deadhead-space-freight-tycoon/packages/sim/test/priority.test.ts

83 lines
2.4 KiB
TypeScript

import { content } from "@deadhead/content";
import { describe, expect, it } from "vitest";
import { buildContract } from "../src/board";
import {
boardPeriodMs,
contractTripGameHours,
priorityWindow,
validateDispatch,
type Contract,
} from "../src/index";
const earth = content.location("earth")!;
const moon = content.location("moon")!;
const periodIndex = 4_000;
const offeredAt = periodIndex * boardPeriodMs(content.config);
function mailContract(priority: boolean): Contract {
const massTonnes = 6;
return buildContract(
{
id: "earth:4000:0",
origin: earth,
destination: moon,
good: content.good("mail")!,
tier: 0,
massTonnes,
firstContact: false,
periodIndex,
shipper: earth.shippers[0]!,
priority,
deliveryWindowGameHours: priority ? priorityWindow(earth, moon, massTonnes, content) : null,
},
content,
);
}
function check(modelId: string, contract: Contract) {
return validateDispatch(
{
ship: { id: "s", modelId, locationId: "earth", inFlight: false },
pilot: {
id: "p",
isAvatar: true,
assignedShipId: "s",
inFlight: false,
skills: {},
restEndsAt: null,
},
contract,
tutorial: false,
credits: 1_000_000,
now: offeredAt,
},
content,
);
}
describe("Priority validation (CR-007)", () => {
it("lets a Courier take a Priority Earth→Moon job but not a Bulk Hauler (Freighter reference)", () => {
const contract = mailContract(true);
expect(content.config.priorityReferenceShipModelId).toBe("freighter");
expect(check("courier", contract)).toEqual({ ok: true });
expect(check("freighter", contract)).toEqual({ ok: true });
expect(check("bulk-hauler", contract)).toEqual({ ok: false, reason: "too-slow" });
});
it("measures the trip the same way the window was set", () => {
const contract = mailContract(true);
const freighter = content.shipModel("freighter")!;
expect(contractTripGameHours(freighter, contract, content)).toBeCloseTo(
contract.deliveryWindowGameHours!,
);
});
it("never fails a normal contract as too slow", () => {
const contract = mailContract(false);
expect(contract.deliveryWindowGameHours).toBeNull();
for (const model of ["courier", "freighter", "bulk-hauler"]) {
expect(check(model, contract)).toEqual({ ok: true });
}
});
});