fix(memory): initialize candidates and enforce lifecycle rollout
Memind CI / Test, build, and release guards (push) Successful in 3m29s

This commit is contained in:
john
2026-07-21 22:55:19 +08:00
parent 0dd9331e5b
commit bfb1f6fea9
8 changed files with 207 additions and 14 deletions
+51
View File
@@ -76,6 +76,57 @@ test('createMemoryV2Runtime does not open pg pool when embedding module is missi
assert.equal(pgvector.reason, 'embedding_module_not_configured');
});
test('createMemoryV2Runtime ensures candidate schema before enabling MySQL persistence', async () => {
const calls = [];
const mysqlPool = {
async query(sql, params = []) {
calls.push({ sql, params });
if (sql.startsWith('CREATE TABLE')) return [[], []];
if (sql.startsWith('INSERT')) return [{ affectedRows: 1 }, []];
throw new Error(`Unexpected SQL: ${sql}`);
},
};
const memory = await createMemoryV2Runtime({
logger: silentLogger(),
legacyMemoryService: legacyService(),
mysqlPool,
env: {
MEMORY_CANDIDATE_ENABLED: '1',
MEMORY_CANDIDATE_MODE: 'shadow',
MEMORY_CANDIDATE_PERSISTENCE_ENABLED: '1',
},
});
assert.equal(memory.getStatus().personalMemory.persistence, 'mysql');
assert.match(calls[0].sql, /CREATE TABLE IF NOT EXISTS `h5_memory_v2_candidates`/);
const observed = await memory.observePersonalMemory({
userId: 'u-1',
sessionId: 's-1',
messages: [{ role: 'user', content: '请记住我偏好使用简洁的中文回答' }],
});
assert.equal(observed.accepted, 1);
assert.equal(calls[1].sql.startsWith('INSERT'), true);
await memory.close();
});
test('createMemoryV2Runtime fails open when candidate schema initialization fails', async () => {
const logger = silentLogger();
const memory = await createMemoryV2Runtime({
logger,
legacyMemoryService: legacyService(),
mysqlPool: { async query() { throw new Error('ddl denied'); } },
env: {
MEMORY_CANDIDATE_ENABLED: '1',
MEMORY_CANDIDATE_MODE: 'shadow',
MEMORY_CANDIDATE_PERSISTENCE_ENABLED: '1',
},
});
assert.equal(memory.getStatus().personalMemory.persistence, 'bounded-memory');
assert.match(logger.warnings[0], /candidate persistence unavailable: ddl denied/);
await memory.close();
});
test('createMemoryV2Runtime selects pgvector only when pool and embedding are configured', async () => {
const queries = [];
let poolEnded = false;