# How Lepton's Configuration System Resolves Settings Using nconf and Default Configs

> Discover how Lepton's configuration system resolves settings using nconf and default configs. Lepton merges command-line args, env vars, and files for seamless configuration.

- Repository: [CosmoX/Lepton](https://github.com/hackjutsu/lepton)
- Tags: internals
- Published: 2026-02-23

---

**Lepton's configuration system uses the nconf library to merge command-line arguments, environment variables, user configuration files, and built-in defaults in a strict precedence order, exposing the final resolved settings as a global singleton.**

Lepton is an open-source snippet manager built on Electron, and its flexible configuration system allows users to customize everything from themes to keyboard shortcuts without modifying source code. Understanding how Lepton's configuration system resolves settings is essential for developers who want to override defaults or debug configuration issues. The system is built on the **nconf** library, which implements a hierarchical configuration pattern with four distinct layers of precedence.

## The Four Layers of Configuration Precedence in Lepton

Lepton's configuration resolution follows a deterministic hierarchy where later sources have lower priority. This means values defined in higher-priority sources always override those from lower-priority sources.

### Command-Line Arguments and Environment Variables

The resolution process begins with **command-line arguments** parsed via `nconf.argv()`, followed immediately by **environment variables** added through `nconf.env()`. These two sources occupy the highest priority levels, allowing users to quickly override settings without touching configuration files.

### User Configuration Files

Next, Lepton checks for a user-specific configuration file located at `~/.leptonrc`. If this file exists, it is loaded via `nconf.file({ file: configFilePath })`. This layer provides persistent user preferences that survive application restarts while still allowing temporary overrides via environment variables or CLI flags.

### Built-in Default Configuration

Finally, Lepton merges **built-in defaults** defined in [`configs/defaultConfig.js`](https://github.com/hackjutsu/Lepton/blob/main/configs/defaultConfig.js) using `nconf.defaults(defaultConfig)`. These defaults ensure the application functions immediately after installation with sensible values for themes, logging levels, and keyboard shortcuts.

## How Lepton Initializes nconf in main.js

The configuration initialization logic resides in **[`main.js`](https://github.com/hackjutsu/Lepton/blob/main/main.js)** at lines 356-363. This sequence explicitly defines the precedence order by chaining nconf methods:

```javascript
nconf.argv().env()                     // 1 + 2: CLI args and environment variables

if (fs.existsSync(configFilePath)) {
  nconf.file({ file: configFilePath }) // 3: User config file (~/.leptonrc)
}

nconf.defaults(defaultConfig)          // 4: Built-in defaults
global.conf = nconf                    // Expose as global singleton

```

After initialization, the resolved configuration is exposed as [`global.conf`](https://github.com/hackjutsu/Lepton/blob/main/global.conf), making it accessible throughout the application without requiring repeated imports.

## Accessing Resolved Configuration Values Throughout the Application

Lepton reads specific settings using `nconf.get(key)` (or `conf.get(key)` when accessing the global). The following examples demonstrate how different subsystems consume configuration values:

**Theme Selection** in [`app/containers/appContainer/index.js`](https://github.com/hackjutsu/Lepton/blob/main/app/containers/appContainer/index.js) (line 23):

```javascript
const theme = conf.get('theme');
themeManager.setTheme(theme);

```

**Keyboard Shortcuts** in [`main.js`](https://github.com/hackjutsu/Lepton/blob/main/main.js) (line 43):

```javascript
const shortcuts = nconf.get('shortcuts');
// Used when building application menu accelerators
accelerator: shortcuts.keyNewGist,

```

**Auto-Update Behavior** in [`main.js`](https://github.com/hackjutsu/Lepton/blob/main/main.js) (line 26):

```javascript
autoUpdater.autoDownload = nconf.get('autoUpdate');

```

## Configuration Resolution Flow Summary

| Source | nconf Method | Priority (High → Low) |
|--------|--------------|----------------------|
| Command-line arguments (`--key=val`) | `nconf.argv()` | 1 |
| Environment variables | `nconf.env()` | 2 |
| User file (`~/.leptonrc`) | `nconf.file({ file })` | 3 |
| Built-in defaults | `nconf.defaults(defaultConfig)` | 4 |

When a key exists in multiple sources, the value from the highest-priority source takes precedence. This deterministic merging allows developers to override any setting temporarily via CLI flags or permanently via config files without modifying the source code in [`configs/defaultConfig.js`](https://github.com/hackjutsu/Lepton/blob/main/configs/defaultConfig.js).

## Summary

- Lepton's configuration system relies on the **nconf** library to merge multiple configuration sources.
- Resolution follows strict precedence: **command-line arguments** > **environment variables** > **user config file** (~/.leptonrc) > **built-in defaults**.
- Initialization occurs in **[`main.js`](https://github.com/hackjutsu/Lepton/blob/main/main.js)** (lines 356-363), where sources are chained and exposed as [`global.conf`](https://github.com/hackjutsu/Lepton/blob/main/global.conf).
- Default values are defined in **[`configs/defaultConfig.js`](https://github.com/hackjutsu/Lepton/blob/main/configs/defaultConfig.js)**, covering themes, logging, and keyboard shortcuts.
- Application code accesses settings via `conf.get(key)`, enabling consistent configuration consumption across main and renderer processes.

## Frequently Asked Questions

### What configuration file format does Lepton use for user settings?

Lepton expects the user configuration file at `~/.leptonrc` to be in **JSON format**. When `nconf.file()` loads this path, it parses the JSON to merge with other configuration layers. If the file does not exist, Lepton simply skips this layer and relies on built-in defaults.

### How do I override a specific setting without changing the default config file?

You can override any setting using **command-line arguments** or **environment variables**, which take precedence over the user config file and defaults. For example, starting Lepton with `--theme=dark` overrides the default light theme, or setting an environment variable `THEME=dark` achieves the same effect with slightly lower priority.

### Where are the default configuration values defined in the source code?

All built-in defaults are centralized in **[`configs/defaultConfig.js`](https://github.com/hackjutsu/Lepton/blob/main/configs/defaultConfig.js)**. This file exports an object containing default values for themes, logger levels, keyboard shortcuts, and other application settings. These values serve as the final fallback when no overrides are provided via CLI arguments, environment variables, or the user config file.

### Can I access Lepton's configuration settings from renderer processes?

Yes. After initialization in [`main.js`](https://github.com/hackjutsu/Lepton/blob/main/main.js), the configuration is exposed as **[`global.conf`](https://github.com/hackjutsu/Lepton/blob/main/global.conf)**, making the nconf instance available throughout the application. Renderer processes can access this global to read settings using `conf.get(key)`, ensuring consistent configuration values across both main and renderer contexts without requiring separate initialization logic.