fix: align scenario 2400 long-run parity
This commit is contained in:
@@ -0,0 +1,79 @@
|
||||
#!/usr/bin/env node
|
||||
|
||||
import { DatabaseTurnDaemonTransport } from '../../app/game-api/dist/index.js';
|
||||
import {
|
||||
createTurnDaemonRuntime,
|
||||
resolveDatabaseUrl,
|
||||
} from '../../app/game-engine/dist/index.js';
|
||||
import { createGamePostgresConnector } from '../../packages/infra/dist/index.js';
|
||||
|
||||
const userCount = Number.parseInt(process.env.SEED_PARITY_USER_COUNT ?? '2', 10);
|
||||
if (!Number.isInteger(userCount) || userCount < 1 || userCount > 10) {
|
||||
throw new Error('SEED_PARITY_USER_COUNT must be an integer between 1 and 10');
|
||||
}
|
||||
|
||||
const databaseUrl = await resolveDatabaseUrl();
|
||||
const profile = process.env.PROFILE ?? 'hwe';
|
||||
const connector = createGamePostgresConnector({ url: databaseUrl });
|
||||
await connector.connect();
|
||||
|
||||
const runtime = await createTurnDaemonRuntime({
|
||||
profile,
|
||||
databaseUrl,
|
||||
enableDatabaseFlush: true,
|
||||
enableLeaseHeartbeat: false,
|
||||
leaseOwnerId: `${profile}-seed-parity-user-setup`,
|
||||
gameClockMode: 'manual',
|
||||
});
|
||||
const daemon = new DatabaseTurnDaemonTransport(connector.prisma, 30_000);
|
||||
// Manual mode intentionally advances scheduled turns without wall-clock waits.
|
||||
// Pause before the loop starts so this setup command cannot consume month 1.
|
||||
runtime.lifecycle.pause('seed parity user setup');
|
||||
const daemonLoop = runtime.lifecycle.start();
|
||||
|
||||
try {
|
||||
await daemon.requestStatus(30_000);
|
||||
for (let number = 1; number <= userCount; number += 1) {
|
||||
const userId = `gc2400-user-${String(number).padStart(2, '0')}`;
|
||||
const ownerDisplayName = `올스타${String(number).padStart(2, '0')}`;
|
||||
const generalName = `비교유저${String(number).padStart(2, '0')}`;
|
||||
const result = await daemon.requestCommand(
|
||||
{
|
||||
type: 'joinCreateGeneral',
|
||||
userId,
|
||||
ownerDisplayName,
|
||||
seedOwnerIdentity: number + 1,
|
||||
name: generalName,
|
||||
leadership: 100,
|
||||
strength: 105,
|
||||
intel: 105,
|
||||
pic: false,
|
||||
character: 'che_안전',
|
||||
profileId: profile,
|
||||
},
|
||||
30_000
|
||||
);
|
||||
if (result?.type !== 'joinCreateGeneral' || !result.ok) {
|
||||
throw new Error(`Failed to create ${userId}: ${JSON.stringify(result)}`);
|
||||
}
|
||||
|
||||
// Match the one explicit legacy appointment reservation. The remaining
|
||||
// slots stay as Rest so the scenario's autorun-user policy owns them.
|
||||
await connector.prisma.$transaction([
|
||||
connector.prisma.generalTurn.update({
|
||||
where: { generalId_turnIdx: { generalId: result.generalId, turnIdx: 0 } },
|
||||
data: { actionCode: 'che_랜덤임관', arg: {} },
|
||||
}),
|
||||
connector.prisma.generalTurnRevision.update({
|
||||
where: { generalId: result.generalId },
|
||||
data: { revision: { increment: 1 } },
|
||||
}),
|
||||
]);
|
||||
console.log(`${userId} created ${generalName} as general ${result.generalId}`);
|
||||
}
|
||||
} finally {
|
||||
await runtime.lifecycle.stop('seed parity user setup complete');
|
||||
await daemonLoop;
|
||||
await runtime.close();
|
||||
await connector.disconnect();
|
||||
}
|
||||
Reference in New Issue
Block a user