feat(ai-psychosis): validation-seeking domain-gated alert

This commit is contained in:
Kjell Tore Guttormsen 2026-05-01 21:41:15 +02:00
commit 12e6d3b5e4
2 changed files with 73 additions and 0 deletions

View file

@ -146,3 +146,60 @@ describe('valseek: count accumulation', () => {
assert.equal(s.valseek_flag, 1, 'flag stays 1 once set');
});
});
// --- Domain-gated alert ---
function runPromptCapture(prompt, stateOverrides = {}) {
dir = setupTestDir();
createStateFile(dir, 'v-alert', { ...freshState(), ...stateOverrides });
const out = runHook('prompt-analyzer.mjs', { session_id: 'v-alert', prompt }, dir);
const state = readState(dir, 'v-alert');
return { state, out };
}
describe('valseek: domain-gated alert', () => {
it('1 valseek + relationship → alert (high-sycophancy)', () => {
const { out } = runPromptCapture("am I crazy?", { domain_context: ['relationship'] });
assert.match(out.hookSpecificOutput.additionalContext, /validation-seeking/);
});
it('1 valseek + spirituality → alert (high-sycophancy)', () => {
const { out } = runPromptCapture("am I crazy?", { domain_context: ['spirituality'] });
assert.match(out.hookSpecificOutput.additionalContext, /validation-seeking/);
});
it('5 valseek + consumer → NO alert (low-stakes domain)', () => {
const { out } = runPromptCapture("you agree, right?", {
domain_context: ['consumer'],
valseek_count: 4, // becomes 5 after this prompt
});
assert.equal(out.hookSpecificOutput, undefined,
'low-stakes domain — no validation alert even at high count');
});
it('3 valseek + legal → alert (high-stakes path)', () => {
const { out } = runPromptCapture("am I crazy?", {
domain_context: ['legal'],
valseek_count: 2, // becomes 3
});
assert.match(out.hookSpecificOutput.additionalContext, /high-stakes/);
});
it('2 valseek + legal → NO alert (sub-threshold for high-stakes)', () => {
const { out } = runPromptCapture("am I crazy?", {
domain_context: ['legal'],
valseek_count: 1, // becomes 2
});
// Note: legal is NOT in HIGH_SYCOPHANCY_DOMAINS, so the relationship/
// spirituality short-path doesn't fire either. Below threshold for high-stakes.
assert.equal(out.hookSpecificOutput, undefined);
});
it('valseek alert fires for relationship even with valseek_count = 1', () => {
const { out } = runPromptCapture("you agree, right?", {
domain_context: ['relationship'],
valseek_count: 0, // becomes 1
});
assert.match(out.hookSpecificOutput.additionalContext, /validation-seeking/);
});
});