kt-template-online-api/test/modules/qqbot/napcat/napcat-persistent-login-state.spec.ts

70 lines
2.4 KiB
TypeScript

import { existsSync, readFileSync } from 'fs';
import { join } from 'path';
const repoRoot = join(__dirname, '../../../..');
const readSource = (relativePath: string) =>
readFileSync(join(repoRoot, relativePath), 'utf8');
describe('NapCat persistent login state contract', () => {
it('owns the approved third-phase persistence tables', () => {
const persistenceRoot = join(
repoRoot,
'src/modules/qqbot/napcat/infrastructure/persistence',
);
const sqlSchema = readSource('sql/refactor-v3/00-full-schema.sql');
const persistenceFiles = existsSync(persistenceRoot)
? readSource(
'src/modules/qqbot/napcat/infrastructure/persistence/qqbot-account-napcat.entity.ts',
) +
'\n' +
readSource(
'src/modules/qqbot/napcat/infrastructure/persistence/qqbot-napcat-container.entity.ts',
)
: '';
const source = `${sqlSchema}\n${persistenceFiles}`;
const missing = [
'napcat_container',
'napcat_device_identity',
'napcat_account_binding',
'napcat_login_session',
'napcat_login_challenge',
'napcat_runtime_cleanup',
].filter((tableName) => !source.includes(tableName));
expect(missing).toEqual([]);
});
it('keeps login truth in persistence rather than in-memory scan sessions', () => {
const loginSource = readSource(
'src/modules/qqbot/napcat/login/qqbot-napcat-login.service.ts',
);
const bannedMemorySignals = ['new Map', 'scanSessions'].filter((signal) =>
loginSource.includes(signal),
);
const missingPersistenceSignals = [
'loginSession',
'loginChallenge',
'runtimeCleanup',
].filter((signal) => !loginSource.includes(signal));
expect(bannedMemorySignals).toEqual([]);
expect(missingPersistenceSignals).toEqual([]);
});
it('keeps captcha and new-device challenges recoverable and separate', () => {
const stateMachine = readSource(
'src/modules/qqbot/napcat/login/napcat-login-state-machine.ts',
);
expect(stateMachine).toEqual(expect.stringContaining("type: 'captcha'"));
expect(stateMachine).toEqual(expect.stringContaining("type: 'new-device'"));
expect(stateMachine).toEqual(expect.stringContaining('qr-pending'));
expect(stateMachine).toEqual(expect.stringContaining('scanned'));
expect(stateMachine).toEqual(expect.stringContaining('confirming'));
expect(stateMachine).toEqual(expect.stringContaining('cleanup-failed'));
});
});