Files
healer-man/server/arena-simulation.test.mjs
T
2026-09-05 21:27:30 -04:00

51 lines
3.3 KiB
JavaScript

import assert from "node:assert/strict";
import test from "node:test";
import { ARENA_STAGES } from "./arena-stages.mjs";
import { ArenaSimulation, ARENA_TICK_RATE, arenaDynamicObjectState } from "./arena-simulation.mjs";
function participants() {
return [
{ actorId: "left-healer", name: "Left Healer", team: 0, role: "healer", isBot: false, rating: 1200 },
{ actorId: "left-damage", name: "Left Damage", team: 0, role: "damage", isBot: true, rating: 1200 },
{ actorId: "right-healer", name: "Right Healer", team: 1, role: "healer", isBot: true, rating: 1200 },
{ actorId: "right-damage", name: "Right Damage", team: 1, role: "damage", isBot: true, rating: 1200 },
];
}
test("authoritative simulation seals ten seconds, runs 20 Hz, and rejects duplicate packets", () => {
const stage = ARENA_STAGES.find((entry) => entry.id === "warnorken-arena");
const simulation = new ArenaSimulation({ id: "sim", stage, bracket: "2v2", mode: "rated-ai", ruleset: "wow", participants: participants(), random: () => 0 });
for (let index = 0; index < ARENA_TICK_RATE * 10 - 1; index += 1) simulation.step();
assert.equal(simulation.snapshot().phase, "preparation");
simulation.step();
assert.equal(simulation.snapshot().phase, "active");
assert.equal(simulation.receiveIntent("left-healer", { sequence: 1, type: "movement", movement: { x: 1, z: 0 } }).accepted, true);
assert.equal(simulation.receiveIntent("left-healer", { sequence: 1, type: "movement", movement: { x: 1, z: 0 } }).reason, "stale-sequence");
const before = simulation.actor("left-healer").position[0];
simulation.step();
assert.ok(simulation.actor("left-healer").position[0] > before);
});
test("a deferred practice start receives a fresh preparation clock", () => {
const stage = ARENA_STAGES.find((entry) => entry.id === "warnorken-arena");
const simulation = new ArenaSimulation({ id: "deferred", stage, bracket: "2v2", mode: "practice", ruleset: "wow", participants: participants(), startedAt: 1_000 });
assert.equal(simulation.resetPreparationClock(20_000), true);
assert.equal(simulation.snapshot().serverTime, 20_000);
assert.equal(simulation.snapshot().phaseEndsAt, 30_000);
});
test("Dalaran and Ring of Valor mechanics synchronize collision state", () => {
const dalaran = ARENA_STAGES.find((entry) => entry.id === "dalaran-sewers");
const warning = arenaDynamicObjectState(dalaran, 27_000).find((entry) => entry.id === "waterfall");
const active = arenaDynamicObjectState(dalaran, 31_000).find((entry) => entry.id === "waterfall");
assert.equal(warning.state, "warning");
assert.equal(active.state, "active");
assert.equal(active.collisionEnabled, true);
const ring = ARENA_STAGES.find((entry) => entry.id === "ring-of-valor");
assert.equal(arenaDynamicObjectState(ring, 20_000).find((entry) => entry.id === "elevators").state, "raised");
assert.equal(arenaDynamicObjectState(ring, 21_000).find((entry) => entry.id === "elevators").state, "moving");
assert.equal(arenaDynamicObjectState(ring, 22_500).find((entry) => entry.id === "elevators").state, "open");
assert.equal(arenaDynamicObjectState(ring, 24_000).find((entry) => entry.id === "pillars-north").state, "lowered");
assert.equal(arenaDynamicObjectState(ring, 26_000).find((entry) => entry.id === "pillars-north").state, "raised");
});