Files
clean-architecture-frontend…/src/bootstrap/runtime-config-schema.js
T

67 lines
2.0 KiB
JavaScript

import { z } from "zod";
const version = z.string().regex(/^\d+(?:\.\d+){0,2}$/);
export const runtimeConfigSchema = z
.object({
APP_ENV: z.enum(["local", "development", "staging", "production"]),
API_BASE_URL: z.url(),
REQUEST_TIMEOUT_MS: z.int().min(100).max(60_000).default(10_000),
MAX_RETRY_ATTEMPTS: z.int().min(0).max(2).default(2),
TELEMETRY_ENABLED: z.boolean(),
TELEMETRY_ENDPOINT: z.url().optional(),
AUTH_MODE: z.literal("external"),
CONFIG_SCHEMA_VERSION: version,
API_CONTRACT_VERSION: version,
RELEASE_MANIFEST_URL: z.string().min(1).default("/release-manifest.json"),
RELEASE_ID: z.string().min(1).optional(),
BUILD_ID: z.string().min(1).optional(),
})
.strict()
.superRefine((config, context) => {
if (config.TELEMETRY_ENABLED && !config.TELEMETRY_ENDPOINT) {
context.addIssue({
code: "custom",
path: ["TELEMETRY_ENDPOINT"],
message: "required when telemetry is enabled",
});
}
const local = config.APP_ENV === "local" || config.APP_ENV === "development";
const endpointEntries =
/** @type {Array<[string, string | undefined]>} */ ([
["API_BASE_URL", config.API_BASE_URL],
["TELEMETRY_ENDPOINT", config.TELEMETRY_ENDPOINT],
]);
for (const [key, value] of endpointEntries) {
if (value && !local && new URL(value).protocol !== "https:") {
context.addIssue({
code: "custom",
path: [key],
message: "HTTPS is required outside local environments",
});
}
}
});
/** @param {unknown} value */
export function validateRuntimeConfig(value) {
const result = runtimeConfigSchema.safeParse(value);
if (!result.success) {
return {
success: /** @type {false} */ (false),
issues: result.error.issues.map((issue) => ({
path: issue.path.join("."),
code: issue.code,
})),
};
}
return {
success: /** @type {true} */ (true),
data: structuredClone(result.data),
};
}