397777089e
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
41 lines
2.0 KiB
JavaScript
41 lines
2.0 KiB
JavaScript
import { describe, it, expect } from 'vitest';
|
||
import { decide } from './enforce-supreme-gate.mjs';
|
||
import { classifyDestructive } from './classify-destructive.mjs';
|
||
|
||
// Δ7 (Машина 5 Пакет 2.5): defense-in-depth М2. Даже если разрушительное действие
|
||
// СОВПАДАЕТ с шагом замороженного плана, стена НЕ продвигает указатель — пол
|
||
// (classify-destructive.mjs) требует двери владельца. При незарегистрированном
|
||
// floor-хуке стена всё равно не благословляет снос.
|
||
|
||
const key = 'k';
|
||
const args = (object) => ({
|
||
toolUse: { name: 'Bash', input: { command: object } },
|
||
frozenPlan: { plan_id: 'p1', steps: [{ n: 1, op: 'Bash', object }] },
|
||
frozenArtifact: null,
|
||
stepPtr: 0,
|
||
key,
|
||
verifyImpl: () => true,
|
||
verifyArtifactImpl: () => true,
|
||
normalize: (s) => s,
|
||
});
|
||
|
||
describe('decide — Δ7: разрушительное in-plan не благословляется', () => {
|
||
const DESTRUCTIVE = ['rm -rf build', 'php artisan migrate:fresh', 'git push --force', 'git reset --hard HEAD~1'];
|
||
for (const cmd of DESTRUCTIVE) {
|
||
it(`разрушительный in-plan шаг → block, указатель не двигается: ${cmd}`, () => {
|
||
expect(classifyDestructive(cmd).floor).toBe(true); // пол считает это необратимым
|
||
const r = decide(args(cmd));
|
||
expect(r.decision).toBe('block');
|
||
expect(r.advanceTo).toBeUndefined();
|
||
});
|
||
}
|
||
|
||
it('обычный (не-floor, не-observe) in-plan шаг → allow + advanceTo', () => {
|
||
// php artisan migrate: не observe-only (не readonly) и не floor (N1) → доходит до allow-пути
|
||
expect(classifyDestructive('php artisan migrate').floor).toBe(false);
|
||
const r = decide(args('php artisan migrate'));
|
||
expect(r.decision).toBe('allow');
|
||
expect(r.advanceTo).toBe(1);
|
||
});
|
||
});
|