Errors
@zap-studio/env throws three structured errors, each covering a different failure: a bad setup, a failed validation, and an out-of-bounds read. All three extend Error.
EnvironmentError
Thrown by createEnvironment and generateEnvironmentExample when the schema itself is misconfigured — not a runtime validation failure:
- a
clientkey declared without aclientPrefix - a
clientkey that doesn't start with the configuredclientPrefix - a key declared by more than one composed
extendssource with two different schemas
import { EnvironmentError } from "@zap-studio/env/errors";
try {
createEnvironment({ extends: [base, override], runtimeEnv: process.env });
} catch (error) {
if (error instanceof EnvironmentError) {
console.error(error.message);
}
}EnvironmentValidationError
Thrown by createEnvironment when one or more declared vars fail Standard Schema validation, and no onValidationError callback is provided.
| Property | Type | Description |
|---|---|---|
invalidKeys | readonly string[] | The keys that failed validation. Never their values. |
issues | Record<string, readonly StandardSchemaV1.Issue[]> | The full Standard Schema issues, per invalid key. |
import { createEnvironment, EnvironmentValidationError } from "@zap-studio/env";
import { z } from "zod";
try {
const env = createEnvironment({
server: { PORT: z.coerce.number() },
runtimeEnv: process.env,
});
} catch (error) {
if (error instanceof EnvironmentValidationError) {
console.error("Invalid env vars:", error.invalidKeys);
}
}Every key's issues are collected — the error is not thrown on the first invalid key, so invalidKeys and issues always report the full picture in one pass.
Custom Validation Handling
Pass onValidationError to run your own logic instead of throwing EnvironmentValidationError — for example, to format a startup error message. It receives the same per-key issues and must throw or otherwise never return:
createEnvironment({
server: { PORT: z.coerce.number() },
runtimeEnv: process.env,
onValidationError: (issues) => {
console.error("Invalid environment variables:", Object.keys(issues).join(", "));
process.exit(1);
},
});EnvironmentAccessError
Thrown by the object createEnvironment returns when client-side code reads a server-only key, and no onInvalidAccess callback is provided. See server/client/shared for when this fires and how to override it with onInvalidAccess.
| Property | Type | Description |
|---|---|---|
key | string | The server-only key that was accessed. |
import { EnvironmentAccessError } from "@zap-studio/env";
try {
env.DATABASE_URL; // server-only key, accessed from the browser
} catch (error) {
if (error instanceof EnvironmentAccessError) {
console.error(error.message);
}
}Subpath Import
All three errors are also available from the dedicated @zap-studio/env/errors subpath, for consumers who prefer granular imports:
import {
EnvironmentAccessError,
EnvironmentError,
EnvironmentValidationError,
} from "@zap-studio/env/errors";See Also
server/client/shared— whereEnvironmentErrorandEnvironmentAccessErrorcome fromextends— the conflict case that throwsEnvironmentError- Advanced Options —
skipValidationto bypassEnvironmentValidationErrorentirely