AI Implementation feature(820): Project Scaffold and Platform Foundations (#1)

This commit was merged in pull request #1.
This commit is contained in:
2026-07-21 14:23:53 +00:00
parent e55c9cda56
commit 03bcb6b156
131 changed files with 23657 additions and 0 deletions
+65
View File
@@ -0,0 +1,65 @@
import { Test } from '@nestjs/testing';
import { INestApplication } from '@nestjs/common';
import { ConfigModule } from '@nestjs/config';
import { validateEnv } from '../../backend/src/config/env.schema';
import { DatabaseModule } from '../../backend/src/database/database.module';
import { DatabaseInitService } from '../../backend/src/database/database-init.service';
import { CategoryEntity } from '../../backend/src/database/entities/category.entity';
import { SettingEntity } from '../../backend/src/database/entities/setting.entity';
describe('DatabaseInitService', () => {
let app: INestApplication;
let init: DatabaseInitService;
beforeAll(async () => {
process.env.DATABASE_PATH = ':memory:';
process.env.THEMES_DIR = './themes';
process.env.FRONTEND_DIST = './frontend/dist';
const moduleRef = await Test.createTestingModule({
imports: [
ConfigModule.forRoot({ isGlobal: true, validate: validateEnv }),
DatabaseModule,
],
}).compile();
app = moduleRef.createNestApplication();
init = app.get(DatabaseInitService);
});
afterAll(async () => {
if (app) await app.close();
});
it('creates the schema and seed data on first init()', async () => {
await init.init();
const ds = (init as any).dataSource;
expect(ds.isInitialized).toBe(true);
const tables: any[] = await ds.query("SELECT name FROM sqlite_master WHERE type='table'");
const names = tables.map((t) => t.name);
expect(names).toEqual(expect.arrayContaining([
'user', 'setting', 'category', 'challenge', 'challenge_file',
'solve', 'refresh_token', 'blog_post',
]));
const categories = await ds.getRepository(CategoryEntity).find();
const systemCats = categories.filter((c: any) => c.systemKey);
expect(systemCats.length).toBeGreaterThanOrEqual(6);
const settings = await ds.getRepository(SettingEntity).find();
const keys = settings.map((s: any) => s.key);
expect(keys).toEqual(expect.arrayContaining([
'pageTitle', 'logo', 'welcomeMarkdown', 'themeKey',
'defaultChallengeIp', 'registrationsEnabled',
'eventStartUtc', 'eventEndUtc',
]));
});
it('is idempotent — calling init() twice does not duplicate migrations or seeds', async () => {
await init.init();
await init.init();
const ds = (init as any).dataSource;
const categories = await ds.getRepository(CategoryEntity).find();
const systemCats = categories.filter((c: any) => c.systemKey);
expect(systemCats.length).toBe(6);
});
});