Files
dcrouter/ts/config/classes.db-seeder.ts

96 lines
2.6 KiB
TypeScript
Raw Permalink Normal View History

import { logger } from '../logger.js';
import type { ReferenceResolver } from './classes.reference-resolver.js';
import type { IRouteSecurity } from '../../ts_interfaces/data/route-management.js';
export interface ISeedData {
profiles?: Array<{
name: string;
description?: string;
security: IRouteSecurity;
extendsProfiles?: string[];
}>;
targets?: Array<{
name: string;
description?: string;
host: string | string[];
port: number;
}>;
}
export class DbSeeder {
constructor(private referenceResolver: ReferenceResolver) {}
/**
* Check if DB is empty and seed if configured.
* Called once during ConfigManagers service startup, after initialize().
*/
public async seedIfEmpty(
seedOnEmpty?: boolean,
seedData?: ISeedData,
): Promise<void> {
if (!seedOnEmpty) return;
const existingProfiles = this.referenceResolver.listProfiles();
const existingTargets = this.referenceResolver.listTargets();
if (existingProfiles.length > 0 || existingTargets.length > 0) {
logger.log('info', 'DB already contains profiles/targets, skipping seed');
return;
}
logger.log('info', 'Seeding database with initial profiles and targets...');
const profilesToSeed: NonNullable<ISeedData['profiles']> = seedData?.profiles ?? DEFAULT_PROFILES;
const targetsToSeed: NonNullable<ISeedData['targets']> = seedData?.targets ?? DEFAULT_TARGETS;
for (const p of profilesToSeed) {
await this.referenceResolver.createProfile({
name: p.name,
description: p.description,
security: p.security,
extendsProfiles: p.extendsProfiles,
createdBy: 'system-seed',
});
}
for (const t of targetsToSeed) {
await this.referenceResolver.createTarget({
name: t.name,
description: t.description,
host: t.host,
port: t.port,
createdBy: 'system-seed',
});
}
logger.log('info', `Seeded ${profilesToSeed.length} profile(s) and ${targetsToSeed.length} target(s)`);
}
}
const DEFAULT_PROFILES: Array<NonNullable<ISeedData['profiles']>[number]> = [
{
name: 'PUBLIC',
description: 'Allow all traffic — no IP restrictions',
security: {
ipAllowList: ['*'],
},
},
{
name: 'STANDARD',
description: 'Standard internal access with common private subnets',
security: {
ipAllowList: ['192.168.0.0/16', '10.0.0.0/8', '127.0.0.1', '::1'],
maxConnections: 1000,
},
},
];
const DEFAULT_TARGETS: Array<NonNullable<ISeedData['targets']>[number]> = [
{
name: 'LOCALHOST',
description: 'Local machine on port 443',
host: '127.0.0.1',
port: 443,
},
];