28 lines
1.6 KiB
TypeScript
28 lines
1.6 KiB
TypeScript
import { readFile } from 'node:fs/promises';
|
|
import { resolve } from 'node:path';
|
|
import { describe, expect, it } from 'vitest';
|
|
import { databaseMigrations } from '../../server/postgres/migration-catalog';
|
|
|
|
const migrationPath = resolve(import.meta.dirname, '..', '..', 'server', 'postgres', 'migrations', '014_environment_profiles_and_policy_snapshots.sql');
|
|
|
|
describe('PostgreSQL environment profile and policy snapshot migration', () => {
|
|
it('stores immutable profile revisions, source runs and aggregated technical states separately', async () => {
|
|
const sql = await readFile(migrationPath, 'utf8');
|
|
expect(databaseMigrations.find(migration => migration.version === '014'))
|
|
.toMatchObject({ version: '014', name: 'environment-profiles-and-policy-snapshots' });
|
|
expect(sql).toContain('CREATE TABLE assessor_environment_profiles');
|
|
expect(sql).toContain('supersedes_profile_id');
|
|
expect(sql).toContain('CREATE TABLE assessor_policy_snapshot_aggregation_runs');
|
|
expect(sql).toContain('CREATE TABLE assessor_policy_snapshot_aggregation_sources');
|
|
expect(sql).toContain('CREATE TABLE assessor_policy_snapshot_states');
|
|
expect(sql).toContain("run_status IN ('complete', 'partial', 'blocked')");
|
|
expect(sql).toContain("state_status IN ('configured', 'deleted', 'conflicted', 'indeterminate')");
|
|
});
|
|
|
|
it('does not create findings or effective-state columns at the aggregation boundary', async () => {
|
|
const sql = await readFile(migrationPath, 'utf8');
|
|
expect(sql).not.toMatch(/finding|effective_state/i);
|
|
expect(sql).toContain('identity_id text NOT NULL REFERENCES assessor_policy_identities(id)');
|
|
});
|
|
});
|