test: Phase 5 verification scripts and opt-in e2e integration spec

Adds scripts to seed scenario data, create Proclamations, snapshot schedules,
drive the Kiosk-facing HTTP endpoints, and an opt-in (P5_INTEGRATION=1)
Vitest spec exercising create/type/copy against a scratch database. The
integration spec is skipped by default so the normal suite needs no DB.
This commit is contained in:
NeilClack
2026-09-29 12:46:04 -05:00
parent be303dcd9c
commit e6021a6345
5 changed files with 466 additions and 0 deletions
+49
View File
@@ -0,0 +1,49 @@
import 'dotenv/config';
import pg from 'pg';
import { PrismaPg } from '@prisma/adapter-pg';
import { PrismaClient } from '../src/lib/generated/prisma/client';
const pool = new pg.Pool({ connectionString: process.env.DATABASE_URL });
const adapter = new PrismaPg(pool);
const prisma = new PrismaClient({ adapter });
// Two accounts, each with two License Keys, for scenario coverage:
// - acct A: keys KA1, KA2 (same account -> name uniqueness + copy)
// - acct B: key KB1 (cross-account isolation)
// Names are left NULL; the Kiosk sets them via the API.
const accounts = [
{ email: 'p5-alice@example.com', key: 'ALCE-AAAA-AAAA-0001' },
{ email: 'p5-alice@example.com', key: 'ALCE-AAAA-AAAA-0002' },
{ email: 'p5-bob@example.com', key: 'BOBB-BBBB-BBBB-0001' }
];
async function ensureUser(email) {
let user = await prisma.user.findUnique({ where: { email } });
if (!user) {
user = await prisma.user.create({
data: { id: crypto.randomUUID(), name: email.split('@')[0], email, emailVerified: true }
});
}
return user;
}
async function main() {
for (const { email, key } of accounts) {
const user = await ensureUser(email);
const existing = await prisma.licenseKey.findUnique({ where: { key } });
if (!existing) {
await prisma.licenseKey.create({ data: { key, active: true, userId: user.id } });
}
}
console.log('P5 test data ready:');
for (const { email, key } of accounts) console.log(` ${email} -> ${key}`);
await prisma.$disconnect();
await pool.end();
}
main().catch(async (e) => {
console.error(e);
await prisma.$disconnect();
await pool.end();
process.exit(1);
});