Skip to content
GitHub

Configuration

The ConfigBuilder constructor requires a validate function. This function receives two arguments: the final merged configuration and a Zod instance (v4). It must return the validated configuration.

import { ConfigBuilder, FileSource } from "@layerfig/config";

// config will be type `z.output<typeof schema>` (the actual object type)
export const config = new ConfigBuilder({
  validate: (finalConfig, z) => {
    const schema = z.object({
      appURL: z.url(),
      port: z.number(),
    });

    return schema.parse(finalConfig);
  },
})
  .addSource(new FileSource("base.json"))
  .build();

You can also use other validation libraries. Return the result of the schema validation from the validate function, and the config object will be typed accordingly:

import { ConfigBuilder, FileSource } from "@layerfig/config";
import * as v from "valibot";

export const configSchema = v.object({
  appURL: v.pipe(v.string(), v.url()),
});

export const config = new ConfigBuilder({
  validate: (finalConfig) => v.parse(configSchema, finalConfig),
})
  .addSource(new FileSource("base.json"))
  .build();

Default: '<process.cwd()>/config'

By default, file-based sources added via addSource are loaded from a config folder in the project’s root. You can customize this path using the absoluteConfigFolderPath option:

import path from "node:path";

const config = new ConfigBuilder({
  validate: (finalConfig) => schema.parse(finalConfig),
  absoluteConfigFolderPath: path.resolve(
    process.cwd(),
    "./path/to/config-folder"
  ),
})
  .addSource(new FileSource("base.json"))
  .build();

In this example, the library will look for <root>/path/to/config-folder/base.json.

Default: simple json parser

This option allows you to define a custom parser for non-JSON file types, such as .yaml, .jsonc, or .toml.

import yamlParser from "@layerfig/parser-yaml";

const config = new ConfigBuilder({
  validate: (finalConfig) => schema.parse(finalConfig),
  parser: yamlParser,
})
  .addSource(new FileSource("base.yaml"))
  .build();

In this case, the library will look for <root>/config/base.yaml and load it.

Default: "$"

A string that identifies placeholders to be replaced with environment variables.

By default, Layerfig looks for placeholders prefixed with $. You can customize this prefix to avoid conflicts or to match a team’s convention.

For example, to use a double underscore (__) as the prefix:

const config = new ConfigBuilder({
  validate: (finalConfig) => schema.parse(finalConfig),
  slotPrefix: "__",
})
  .addSource(new FileSource("base.json"))
  .build();

Layerfig will now look for placeholders like __PORT in your configuration files.

// config/base.json
{
  "appURL": "http://localhost:__PORT",
  "port": "__PORT"
}

Assuming the PORT environment variable is set, the resolved configuration will be:

config.appURL; // http://localhost:3000
config.port; // 3000