FactuGES_ERP/tests/e2e/support/e2e-contract.ts
David da362fef64 feat(e2e): implement end-to-end testing framework with database preparation and lifecycle management
- Add E2ESchemaDatabaseConfig interface for database configuration validation.
- Implement assertE2ESchemaDatabaseConfig function to enforce schema requirements.
- Create prepareE2ESchema function to handle schema preparation and initialization.
- Develop E2E lifecycle management functions to provision, prepare, and run tests.
- Introduce Docker Compose setup for E2E database environment.
- Add Playwright configuration for E2E testing.
- Implement various test cases to validate E2E schema preparation and lifecycle.
- Create utility functions for environment variable management and database assertions.
- Establish smoke tests to verify initial data setup and integrity.
2026-09-22 16:49:08 +02:00

68 lines
2.2 KiB
TypeScript

export const E2E_DATABASE_PREFIX = "factuges_erp_e2e_";
export const E2E_BACKEND_PORT = "3002";
export const E2E_API_BASE_PATH = "/api/v1";
export const E2E_FRONTEND_URL = "http://127.0.0.1:5173";
export const E2E_API_URL = "http://127.0.0.1:3002/api/v1";
type Environment = Record<string, string | undefined>;
export type E2EExecutionMode = "official" | "external";
/** Impide que el comando oficial herede un destino o modo externo. */
export function assertOfficialE2EExecution(environment: Environment): void {
if (environment.E2E_EXECUTION_MODE !== undefined) {
throw new Error("Official E2E does not accept E2E_EXECUTION_MODE.");
}
if (environment.E2E_BASE_URL) {
throw new Error(
"Official E2E does not accept E2E_BASE_URL. Use the explicit test:e2e:external command."
);
}
}
/** Valida las invariantes del backend que arranca el modo E2E oficial. */
export function assertOfficialE2EEnvironment(environment: Environment): void {
const expectedValues: Readonly<Record<string, string>> = {
NODE_ENV: "test",
DB_SYNC_MODE: "none",
PORT: E2E_BACKEND_PORT,
API_BASE_PATH: E2E_API_BASE_PATH,
FRONTEND_URL: E2E_FRONTEND_URL,
};
for (const [name, expectedValue] of Object.entries(expectedValues)) {
if (environment[name] !== expectedValue) {
throw new Error(
`Official E2E requires ${name}=${expectedValue}; received ${environment[name] ?? "<missing>"}.`
);
}
}
if (!new RegExp(`^${E2E_DATABASE_PREFIX}[a-z0-9_]+$`).test(environment.DB_NAME ?? "")) {
throw new Error(`Official E2E requires DB_NAME with prefix ${E2E_DATABASE_PREFIX}.`);
}
}
/** Determina el modo de ejecución sin permitir destinos externos implícitos. */
export function resolveE2EExecutionMode(environment: Environment): E2EExecutionMode {
const mode = environment.E2E_EXECUTION_MODE;
const externalBaseUrl = environment.E2E_BASE_URL;
if (mode === "external") {
if (!externalBaseUrl) {
throw new Error("External E2E requires E2E_BASE_URL.");
}
try {
new URL(externalBaseUrl);
} catch {
throw new Error("External E2E requires E2E_BASE_URL to be an absolute URL.");
}
return "external";
}
throw new Error(`Unsupported E2E_EXECUTION_MODE=${mode ?? "<missing>"}.`);
}