fix(hwpod): 使用 YAML 数据库和健康超时
This commit is contained in:
@@ -28,8 +28,9 @@ export function hwpodSpecRegistryFromEnv(env: Record<string, string | undefined>
|
||||
const databaseUrl = requiredEnv(env, "HWPOD_SPEC_DATABASE_URL");
|
||||
const schema = postgresIdentifier(requiredEnv(env, "HWPOD_SPEC_DATABASE_SCHEMA"), "HWPOD_SPEC_DATABASE_SCHEMA");
|
||||
const table = postgresIdentifier(requiredEnv(env, "HWPOD_SPEC_DATABASE_TABLE"), "HWPOD_SPEC_DATABASE_TABLE");
|
||||
const connectionTimeoutMs = positiveIntegerEnv(env, "HWPOD_SPEC_DATABASE_CONNECTION_TIMEOUT_MS");
|
||||
const builtIns = parseBuiltIns(env.HWPOD_BUILTIN_SPEC_DOCUMENTS_JSON);
|
||||
return createHwpodSpecRegistry({ store: createPostgresHwpodRuntimeSpecStore({ databaseUrl, schema, table }), builtIns });
|
||||
return createHwpodSpecRegistry({ store: createPostgresHwpodRuntimeSpecStore({ databaseUrl, schema, table, connectionTimeoutMs }), builtIns });
|
||||
}
|
||||
|
||||
export function createHwpodSpecRegistry(options: { store: HwpodRuntimeSpecStore; builtIns?: BuiltInInput[]; now?: () => string }) {
|
||||
@@ -85,13 +86,14 @@ export function createHwpodSpecRegistry(options: { store: HwpodRuntimeSpecStore;
|
||||
return { list, get, create, update, delete: remove, close: async () => store.close?.() };
|
||||
}
|
||||
|
||||
export function createPostgresHwpodRuntimeSpecStore(options: { databaseUrl: string; schema: string; table: string }): HwpodRuntimeSpecStore {
|
||||
export function createPostgresHwpodRuntimeSpecStore(options: { databaseUrl: string; schema: string; table: string; connectionTimeoutMs: number }): HwpodRuntimeSpecStore {
|
||||
const schema = postgresIdentifier(options.schema, "schema");
|
||||
const table = postgresIdentifier(options.table, "table");
|
||||
const qualifiedTable = `${quoteIdentifier(schema)}.${quoteIdentifier(table)}`;
|
||||
const pool = new Pool(buildPostgresPoolConfig({
|
||||
dbUrl: options.databaseUrl,
|
||||
sslMode: postgresSslModeFromConnectionString(options.databaseUrl) ?? "disable",
|
||||
timeoutMs: options.connectionTimeoutMs,
|
||||
}));
|
||||
let ready: Promise<void> | undefined;
|
||||
|
||||
@@ -187,6 +189,7 @@ function normalizeBuiltIns(inputs: BuiltInInput[]) {
|
||||
}
|
||||
|
||||
function requiredEnv(env: Record<string, string | undefined>, key: string) { const value = String(env[key] ?? "").trim(); if (!value) throw codedError("hwpod_spec_database_config_required", `${key} is required`); return value; }
|
||||
function positiveIntegerEnv(env: Record<string, string | undefined>, key: string) { const value = Number(requiredEnv(env, key)); if (!Number.isSafeInteger(value) || value <= 0) throw codedError("invalid_hwpod_spec_database_config", `${key} must be a positive integer`); return value; }
|
||||
function postgresIdentifier(value: string, name: string) { if (!/^[a-z_][a-z0-9_]*$/u.test(value)) throw codedError("invalid_hwpod_spec_database_identifier", `${name} must be a lowercase PostgreSQL identifier`); return value; }
|
||||
function quoteIdentifier(value: string) { return `"${postgresIdentifier(value, "identifier")}"`; }
|
||||
function isoTimestamp(value: unknown) { const date = value instanceof Date ? value : new Date(String(value ?? "")); if (!Number.isFinite(date.getTime())) throw codedError("invalid_hwpod_runtime_spec", "runtime HWPOD spec timestamp is invalid"); return date.toISOString(); }
|
||||
|
||||
Reference in New Issue
Block a user