70 lines
2.4 KiB
TypeScript
70 lines
2.4 KiB
TypeScript
import { describe, it, expect } from 'vitest';
|
|
import { isOpen, tick } from '../../src/sim/clock';
|
|
import { CLOSE_MINUTES, createNewGame, OPEN_MINUTES } from '../../src/sim/state';
|
|
import { testCatalog } from './helpers';
|
|
|
|
const catalog = testCatalog();
|
|
|
|
describe('clock', () => {
|
|
it('opens the shop at 9:00 with no customers before', () => {
|
|
const s = createNewGame(1);
|
|
const events = tick(s, catalog, 60);
|
|
expect(s.minutes).toBe(OPEN_MINUTES);
|
|
expect(events).toEqual([{ type: 'shop_opened' }]);
|
|
expect(isOpen(s)).toBe(true);
|
|
});
|
|
|
|
it('brings customers during opening hours and closes at 19:00', () => {
|
|
const s = createNewGame(1);
|
|
s.reputation = 100;
|
|
const events = tick(s, catalog, 24 * 60);
|
|
expect(s.minutes).toBe(CLOSE_MINUTES);
|
|
expect(events.filter((e) => e.type === 'customer_arrived').length).toBeGreaterThan(10);
|
|
expect(events[events.length - 1]).toEqual({ type: 'shop_closed' });
|
|
expect(isOpen(s)).toBe(false);
|
|
});
|
|
|
|
it('never brings customers on the closing tick', () => {
|
|
for (let seed = 1; seed <= 20; seed++) {
|
|
const s = createNewGame(seed);
|
|
s.reputation = 100;
|
|
const arrivalMinutes: number[] = [];
|
|
let opened = 0;
|
|
let closed = 0;
|
|
while (s.minutes < CLOSE_MINUTES) {
|
|
const events = tick(s, catalog, 1);
|
|
if (events.some((e) => e.type === 'customer_arrived')) arrivalMinutes.push(s.minutes);
|
|
opened += events.filter((e) => e.type === 'shop_opened').length;
|
|
closed += events.filter((e) => e.type === 'shop_closed').length;
|
|
}
|
|
expect(arrivalMinutes.length).toBeGreaterThan(0);
|
|
expect(arrivalMinutes).not.toContain(CLOSE_MINUTES);
|
|
expect(opened).toBe(1);
|
|
expect(closed).toBe(1);
|
|
}
|
|
});
|
|
|
|
it('accumulates fractional ticks', () => {
|
|
const s = createNewGame(1);
|
|
const start = s.minutes;
|
|
for (let i = 0; i < 60; i++) tick(s, catalog, 1 / 60);
|
|
expect(s.minutes).toBe(start + 1);
|
|
});
|
|
|
|
it('advances one minute after two half-minute ticks', () => {
|
|
const s = createNewGame(1);
|
|
const start = s.minutes;
|
|
tick(s, catalog, 0.5);
|
|
expect(s.minutes).toBe(start);
|
|
tick(s, catalog, 0.5);
|
|
expect(s.minutes).toBe(start + 1);
|
|
});
|
|
|
|
it('does nothing once closed', () => {
|
|
const s = createNewGame(1);
|
|
tick(s, catalog, 24 * 60);
|
|
expect(tick(s, catalog, 60)).toEqual([]);
|
|
expect(s.minutes).toBe(CLOSE_MINUTES);
|
|
});
|
|
});
|