feat: another balance and bug fix pass (#238)
Security Scan and Upload / Security & DefectDojo Upload (push) Successful in 1m10s
CI / Lint, Build & Test (push) Successful in 1m13s

Working through open issues — fixes, balance changes, and features.

## Closed

- Closes #161
- Closes #181
- Closes #191
- Closes #199
- Closes #201
- Closes #202
- Closes #203
- Closes #204
- Closes #205
- Closes #206
- Closes #208
- Closes #211
- Closes #212
- Closes #213
- Closes #214
- Closes #216
- Closes #219
- Closes #220
- Closes #221
- Closes #222
- Closes #224
- Closes #225
- Closes #226
- Closes #228
- Closes #229
- Closes #230
- Closes #231
- Closes #232
- Closes #233
- Closes #234
- Closes #235
- Closes #236

 This PR was created with help from Hikari~ 🌸

Reviewed-on: #238
Co-authored-by: Hikari <hikari@nhcarrigan.com>
Co-committed-by: Hikari <hikari@nhcarrigan.com>
This commit was merged in pull request #238.
This commit is contained in:
2026-04-06 18:17:00 -07:00
committed by Naomi Carrigan
parent b0227c1709
commit 1195b657a0
34 changed files with 980 additions and 203 deletions
+22
View File
@@ -477,6 +477,28 @@ describe("game route", () => {
expect(body.savedAt).toBeGreaterThan(0);
});
it("restores previous upgrades when incoming prestige count is lower (stale post-prestige save)", async () => {
const prevUpgrades = [
{ id: "click_1", purchased: false, unlocked: true, target: "click", multiplier: 2 },
] as GameState["upgrades"];
const prevState = makeState({
prestige: { count: 1, runestones: 10, productionMultiplier: 1.3, purchasedUpgradeIds: [] },
upgrades: prevUpgrades,
});
const incomingState = makeState({
prestige: { count: 0, runestones: 0, productionMultiplier: 1, purchasedUpgradeIds: [] },
upgrades: [
{ id: "click_1", purchased: true, unlocked: true, target: "click", multiplier: 2 },
] as GameState["upgrades"],
});
vi.mocked(prisma.gameState.findUnique).mockResolvedValueOnce({ state: prevState } as never);
vi.mocked(prisma.player.findUnique).mockResolvedValueOnce(makePlayer({ createdAt: Date.now() }) as never);
vi.mocked(prisma.player.update).mockResolvedValueOnce({} as never);
vi.mocked(prisma.gameState.upsert).mockResolvedValueOnce({} as never);
const res = await save({ state: incomingState });
expect(res.status).toBe(200);
});
it("validates companion when active companion is legitimately unlocked", async () => {
const prevState = makeState();
const stateWithCompanion = makeState({