forked from Lilly-Protocol/lily-backend
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathenv.ts
More file actions
73 lines (66 loc) · 2.17 KB
/
Copy pathenv.ts
File metadata and controls
73 lines (66 loc) · 2.17 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
import dotenv from "dotenv";
import { z } from "zod";
dotenv.config();
export const trustProxySchema = z.preprocess(
(val) => (val === undefined || val === "" ? "false" : val),
z.union([
z.literal("false").transform(() => false as const),
z.literal("true").refine(() => false, {
message:
"TRUST_PROXY=true is unsafe in production; use a specific hop count or 'loopback'",
}),
z
.string()
.regex(/^\d+$/, {
message:
"TRUST_PROXY must be 'false', a positive integer hop count, or 'loopback'",
})
.transform((v) => parseInt(v, 10)),
z.literal("loopback"),
]),
);
const envSchema = z.object({
NODE_ENV: z
.enum(["development", "test", "production"])
.default("development"),
PORT: z.coerce.number().int().min(1).max(65535).default(4000),
APP_NAME: z.string().min(1).default("Lily Backend"),
BUILD_COMMIT: z
.string()
.trim()
.optional()
.transform((value) => value || undefined),
API_PREFIX: z.string().min(1).default("/api/v1"),
LOG_LEVEL: z
.enum(["fatal", "error", "warn", "info", "debug", "trace", "silent"])
.default("info"),
CORS_ORIGINS: z.string().min(1).default("http://localhost:3000"),
BODY_SIZE_LIMIT: z.string().min(1).default("1mb"),
RATE_LIMIT_WINDOW_MS: z.coerce
.number()
.int()
.positive()
.default(15 * 60 * 1000),
RATE_LIMIT_MAX_REQUESTS: z.coerce.number().int().positive().default(100),
AUTH_API_KEY: z.string().optional(),
AUTH_API_KEY_HEADER: z.string().min(1).default("x-api-key"),
TRUST_PROXY: trustProxySchema,
});
const parsedEnv = envSchema.safeParse(process.env);
if (!parsedEnv.success) {
throw new Error(
`Invalid environment configuration: ${parsedEnv.error.flatten().formErrors.join(", ")}`,
);
}
export const env = parsedEnv.data;
export const securityConfig = {
allowedOrigins: env.CORS_ORIGINS.split(",")
.map((origin) => origin.trim())
.filter(Boolean),
bodySizeLimit: env.BODY_SIZE_LIMIT,
rateLimitWindowMs: env.RATE_LIMIT_WINDOW_MS,
rateLimitMaxRequests: env.RATE_LIMIT_MAX_REQUESTS,
trustProxy: env.TRUST_PROXY,
authApiKey: env.AUTH_API_KEY,
authApiKeyHeader: env.AUTH_API_KEY_HEADER,
};