Skip to main content

Schema Types

Schemas are useful but not required, envitron loads all envs from a file and those envs can still be used, only they won't be type safe Envitron supports the following schema types for environment variables:

String

schema.string();
schema.string({ optional: true });

Number

schema.number();
schema.number({ optional: true });

Boolean

schema.boolean();
schema.boolean({ optional: true });

Enum

schema.enum(['development', 'production', 'test'] as const);

Array

Untyped Arrays

Arrays parsed from CSV strings or JSON arrays:

schema.array();
schema.array({ optional: true });

Typed Arrays

Define arrays with element validation for full type safety:

schema.array(schema.string());      // string[]
schema.array(schema.number()); // number[]
schema.array(schema.boolean()); // boolean[]

Arrays of Objects

Combine arrays with nested objects for complex structures:

const env = createEnvSchema((schema) => ({
users: schema.array(
schema.object({
name: schema.string(),
age: schema.number(),
})
),
}));

// Type: Array<{ name: string; age: number }>
const users = env.get('users');
console.log(users[0].name); // string
console.log(users[0].age); // number

Object

Define nested object schemas for complex configuration structures:

schema.object({
host: schema.string(),
port: schema.number(),
});

schema.object({
// nested schema
}, { optional: true });

Basic Nested Objects

const env = createEnvSchema((schema) => ({
database: schema.object({
host: schema.string(),
port: schema.number(),
}),
}));

// Access nested properties with full type safety
const dbHost = env.get('database').host; // string
const dbPort = env.get('database').port; // number

Deeply Nested Objects

Objects can be nested to any depth:

const env = createEnvSchema((schema) => ({
application: schema.object({
name: schema.string(),
services: schema.object({
api: schema.object({
url: schema.string(),
timeout: schema.number(),
}),
cache: schema.object({
enabled: schema.boolean(),
ttl: schema.number(),
}),
}),
}),
}));

// All properties are fully typed
const apiUrl = env.get('application').services.api.url; // string
const cacheTTL = env.get('application').services.cache.ttl; // number

Objects with Arrays

Combine objects and arrays for complex configurations:

const env = createEnvSchema((schema) => ({
services: schema.object({
api: schema.object({
endpoints: schema.array(schema.string()),
retries: schema.array(schema.number()),
}),
}),
}));

const endpoints = env.get('services').api.endpoints; // string[]
const retries = env.get('services').api.retries; // number[]

Custom

schema.custom((value) => {
// Your custom validation logic here
return transformedValue;
});

schema.custom(
(value) => {
// Your custom validation logic here
return transformedValue;
},
{ optional: true }
);

The custom validator allows you to define your own validation and transformation logic for environment variables. The validator function receives the raw environment value and should return the transformed value. The type of the env will be inferred from the return type of the function.

Example

const env = createEnvSchema((schema) => ({
// Divide the environment value by 2
CUSTOM_NUMBER: schema.custom((value) => Number(value) / 2),

// Transform a string to uppercase
CUSTOM_STRING: schema.custom((value) => String(value).toUpperCase()),

// Optional custom validator
OPTIONAL_CUSTOM: schema.custom((value) => Number(value) * 2, { optional: true }),
}));

Options

  • optional: true — makes the variable optional (value may be undefined)

Complete Example

const env = createEnvSchema((schema) => ({
// Primitives
HOST: schema.string(),
PORT: schema.number(),
DEBUG: schema.boolean({ optional: true }),
NODE_ENV: schema.enum(['development', 'production', 'test'] as const),

// Arrays
ALLOWED_HOSTS: schema.array({ optional: true }),
PORTS: schema.array(schema.number()),

// Nested objects
database: schema.object({
host: schema.string(),
port: schema.number(),
credentials: schema.object({
username: schema.string(),
password: schema.string(),
}),
}),

// Arrays of objects
services: schema.array(
schema.object({
name: schema.string(),
enabled: schema.boolean(),
})
),

// Custom
CUSTOM_VALUE: schema.custom((value) => Number(value) / 2),
}));

Usage with JSON Environment Files

Nested objects and typed arrays work seamlessly with JSON environment files:

{
"database": {
"host": "localhost",
"port": 5432,
"credentials": {
"username": "admin",
"password": "secret"
}
},
"PORTS": [3000, 4000, 5000],
"services": [
{ "name": "api", "enabled": true },
{ "name": "worker", "enabled": false }
]
}

See JSON Environment Files for more details.

See Also