96 lines
2.5 KiB
TypeScript
96 lines
2.5 KiB
TypeScript
import { execSync } from 'node:child_process';
|
|
import { createDB } from 'mysql-memory-server';
|
|
|
|
process.env.NODE_ENV ??= 'test';
|
|
process.env.LOG_LEVEL ??= 'silent';
|
|
process.env.CORS_ORIGIN ??= 'http://localhost:5173';
|
|
process.env.RATE_LIMIT_MAX ??= '10000';
|
|
process.env.AUTH_RATE_LIMIT_MAX ??= '10000';
|
|
process.env.AUTH_SESSION_TTL_HOURS ??= '168';
|
|
|
|
const DOCKER_TEST_URL = 'mysql://novya:novya@127.0.0.1:3306/novya_test';
|
|
|
|
type MemoryDb = Awaited<ReturnType<typeof createDB>>;
|
|
|
|
const globalForTestDb = globalThis as unknown as {
|
|
__novyaMemoryDb?: MemoryDb;
|
|
};
|
|
|
|
function migrateDeploy(): void {
|
|
try {
|
|
execSync('npx prisma generate --schema=./prisma/schema.prisma', {
|
|
stdio: 'inherit',
|
|
env: process.env,
|
|
});
|
|
} catch {
|
|
// Ignore file-lock error if another process (e.g. dev server) holds query engine
|
|
}
|
|
execSync('npx prisma migrate deploy --schema=./prisma/schema.prisma', {
|
|
stdio: 'inherit',
|
|
env: process.env,
|
|
});
|
|
}
|
|
|
|
async function startTestDatabase(): Promise<void> {
|
|
const preferMemory = process.env.USE_MEMORY_MYSQL === 'true';
|
|
const dockerUrl = process.env.TEST_DATABASE_URL ?? DOCKER_TEST_URL;
|
|
|
|
if (!preferMemory) {
|
|
process.env.DATABASE_URL = dockerUrl;
|
|
try {
|
|
migrateDeploy();
|
|
return;
|
|
} catch (err) {
|
|
console.warn('Docker MySQL (novya_test) is not ready. Falling back if possible.');
|
|
console.warn(err instanceof Error ? err.message : err);
|
|
}
|
|
}
|
|
|
|
if (process.env.SKIP_MEMORY_MYSQL === 'true') {
|
|
process.env.DATABASE_URL = dockerUrl;
|
|
return;
|
|
}
|
|
|
|
try {
|
|
const db = await createDB({
|
|
version: '8.4.x',
|
|
dbName: 'novya_test',
|
|
username: 'root',
|
|
xEnabled: 'OFF',
|
|
logLevel: 'ERROR',
|
|
downloadBinaryOnce: true,
|
|
downloadRetries: 1,
|
|
});
|
|
|
|
globalForTestDb.__novyaMemoryDb = db;
|
|
process.env.DATABASE_URL = `mysql://root@127.0.0.1:${db.port}/novya_test`;
|
|
migrateDeploy();
|
|
|
|
const stop = async () => {
|
|
try {
|
|
await db.stop();
|
|
} catch {
|
|
// ignore shutdown races
|
|
}
|
|
};
|
|
|
|
process.once('exit', () => {
|
|
void stop();
|
|
});
|
|
process.once('SIGINT', () => {
|
|
void stop();
|
|
});
|
|
process.once('SIGTERM', () => {
|
|
void stop();
|
|
});
|
|
} catch (err) {
|
|
console.warn(
|
|
'MySQL is not running. Database tests will be skipped. Start Docker: docker compose -f docker-compose.dev.yml up -d',
|
|
);
|
|
console.warn(err instanceof Error ? err.message : err);
|
|
process.env.DATABASE_URL ??= dockerUrl;
|
|
}
|
|
}
|
|
|
|
await startTestDatabase();
|