deadhead-space-freight-tycoon/packages/engine/test/fuel.test.ts

97 lines
3.5 KiB
TypeScript

import { content } from "@deadhead/content";
import { fuelPriceAt } from "@deadhead/sim";
import { describe, expect, it } from "vitest";
import {
edit,
getState,
putBoard,
readSave,
setCredits,
signUp,
signUpOwner,
testContract,
useTestApp,
} from "./support";
const testApp = useTestApp();
const tank = (id: string) => content.shipModel(id)!.tankCapacityFu;
const price = (id: string) => fuelPriceAt(content.location(id)!, content.config);
describe("fuel tanks in the engine (Step 15.4)", () => {
it("delivers a Market ship with a full tank, bought at the bay's price", async () => {
const { app } = testApp();
const owner = await signUpOwner(app);
await setCredits(app, content.shipModel("freighter")!.price);
const { ship } = await app.call("buyShip", { modelId: "freighter", bayId: owner.earthBayId });
expect(ship).toMatchObject({
fuelFu: tank("freighter"),
fuelAvgPrice: price("earth"),
refuelPolicy: "auto",
});
// The tank was included in the price.
expect((await getState(app)).company.credits).toBe(0);
});
it("hands over the deal's ships with a quarter tank (CR-015, user decision)", async () => {
const { app } = testApp();
await signUp(app);
await edit(app, (save) => {
save.player.tutorialRunsCompleted = content.config.tutorialRunsBeforeDeal;
save.player.loanerLocationId = "earth";
});
const state = await app.call("acceptDeal", {});
for (const ship of state.ships) {
expect(ship.fuelFu, ship.modelId).toBeCloseTo(tank(ship.modelId) * 0.25);
expect(ship.fuelAvgPrice).toBe(price("earth"));
}
});
it("burns the leg from the tank and, with Auto, tops up on landing at the local price", async () => {
const { app, clock } = testApp();
const owner = await signUpOwner(app);
await setCredits(app, 10_000);
const contract = testContract();
await putBoard(app, [contract]);
const { dispatch } = await app.call("createDispatch", {
kind: "contract",
contractId: contract.id,
shipId: owner.shipId,
pilotId: owner.avatarId,
});
expect((await getState(app)).company.credits).toBe(10_000);
clock.now = dispatch.arrivalAt;
const state = await getState(app);
const [summary] = state.summaries;
const bought = summary!.topUp!;
expect(bought.locationId).toBe("moon");
expect(bought.boughtFu).toBeCloseTo(dispatch.fuelBurnedFu);
expect(bought.cost).toBe(Math.round(dispatch.fuelBurnedFu * price("moon")));
expect(state.company.credits).toBe(10_000 + summary!.credits - bought.cost);
expect(state.ships[0]!.fuelFu).toBeCloseTo(tank("courier"));
});
it("leaves the tank as it landed with Manual", async () => {
const { app, clock } = testApp();
const owner = await signUpOwner(app);
await setCredits(app, 10_000);
await edit(app, (save) => {
save.ships.find((s) => s.id === owner.shipId)!.refuelPolicy = "manual";
});
const contract = testContract();
await putBoard(app, [contract]);
const { dispatch } = await app.call("createDispatch", {
kind: "contract",
contractId: contract.id,
shipId: owner.shipId,
pilotId: owner.avatarId,
});
clock.now = dispatch.arrivalAt;
const state = await getState(app);
expect(state.summaries[0]!.topUp).toBeNull();
expect(state.company.credits).toBe(10_000 + state.summaries[0]!.credits);
const saved = (await readSave(app)).ships.find((s) => s.id === owner.shipId)!;
expect(saved.fuelFu).toBeCloseTo(tank("courier") - dispatch.fuelBurnedFu);
});
});