---
title: "WezTerm Configuration Guide"
aliases: [wezterm-lua-config, wezterm-setup, wezterm-config-files]
tags: [wezterm, terminal, lua, dotfiles, config]
sources:
  - "raw/Configuration - Wez's Terminal Emulator.md"
  - "daily/2026-04-16.md"
created: 2026-04-17
updated: 2026-04-16
---

## Overview

WezTerm is configured via a Lua script (`wezterm.lua`). The config system is live-reloading, highly flexible, and supports modular file splits.

## Config File Locations

WezTerm searches for config in this priority order:

1. `$HOME/.wezterm.lua` — recommended starting point
2. `$XDG_CONFIG_HOME/wezterm/wezterm.lua` (X11/Wayland)
3. `$HOME/.config/wezterm/wezterm.lua` — all other systems
4. Same directory as `wezterm.exe` (Windows thumb drive mode — not recommended)

## Quick Start

```lua
local wezterm = require 'wezterm'
local config = wezterm.config_builder()

config.initial_cols = 120
config.initial_rows = 28
config.font_size = 10
config.color_scheme = 'AdventureTime'

return config
```

- `wezterm.config_builder()` is the recommended way to build the config table — it provides better error messages than a plain `{}`.

## Live Reload

- WezTerm watches the config file and reloads on change automatically
- Force reload: `CTRL+SHIFT+R`
- **Warning:** the config file can be evaluated multiple times per process (startup + each reload). Avoid side effects in the top-level flow (e.g., spawning background processes unconditionally).

## CLI Config Overrides

Override any config key from the command line — these always win over file values, even after reload:

```bash
wezterm --config enable_scroll_bar=true
wezterm --config 'exit_behavior="Hold"'
```

Per-window overrides are possible via [`window:set_config_overrides()`](https://wezterm.org/config/lua/window/set_config_overrides.html) in Lua.

## Modular Config (Multiple Files)

Break config into Lua modules. `package.path` includes (in order):

- `~/.config/wezterm/`
- `~/.wezterm/`
- System Lua paths

**`~/.config/wezterm/helpers.lua`:**
```lua
local wezterm = require 'wezterm'
local module = {}

function module.apply_to_config(config)
  config.color_scheme = 'Batman'
end

return module
```

**`~/.config/wezterm/wezterm.lua`:**
```lua
local helpers = require 'helpers'
local config = {}
helpers.apply_to_config(config)
return config
```

Convention: modules export an `apply_to_config(config)` function that mutates the config table in place.

## Key Takeaways

- Config file is Lua — use full language features (functions, modules, conditionals)
- Use `wezterm.config_builder()` over raw `{}` for better error output
- Default config location: `~/.wezterm.lua` or `~/.config/wezterm/wezterm.lua`
- Auto-reloads on file change; `CTRL+SHIFT+R` for manual reload
- CLI `--config key=value` overrides always beat file values
- Split large configs into modules under `~/.config/wezterm/` using `require`
- Avoid side effects at the top level — config is evaluated multiple times

## Related

- [[wiki/dotfiles/wezterm-colors-appearance|WezTerm Colors & Appearance]] — color schemes, tab bar, opacity
- [[wiki/dotfiles/wezterm-cli-reference|WezTerm CLI Reference]] — CLI subcommands and scripting
- [[wiki/dotfiles/terminal-cheatsheet|Terminal Cheatsheet]] — daily WezTerm + Fish stack reference
- [[wiki/dotfiles/linux-terminal-ricing|Linux Terminal Ricing]] — full setup guide with themes

## Personal Setup (macOS — 2026-04-16)

Actual config applied to `~/.wezterm.lua` matching Ghostty/Kitty preferences:

```lua
local wezterm = require 'wezterm'
local config = wezterm.config_builder()

-- Appearance (matches Ghostty/Kitty stack)
config.color_scheme = 'Catppuccin Mocha'
config.font = wezterm.font('FiraCode Nerd Font Mono', { weight = 'Regular' })
config.font_size = 16
config.harfbuzz_features = { 'calt', 'clig', 'liga', 'ss01', 'ss02' }  -- FiraCode ligatures
config.window_background_opacity = 0.95
config.macos_window_background_blur = 20

-- Performance (Apple Silicon / ProMotion)
config.front_end = 'WebGpu'        -- requires full restart to take effect
config.max_fps = 120               -- ProMotion display
config.animation_fps = 120

-- Shell
config.default_prog = { '/opt/homebrew/bin/fish', '-l' }

-- Leader key (tmux-style)
config.leader = { key = 'a', mods = 'CTRL', timeout_milliseconds = 1000 }

-- Scrollback
config.scrollback_lines = 50000

return config
```

Notes:
- `front_end = 'WebGpu'` (Metal on macOS) — live reload doesn't apply; requires full WezTerm restart
- FiraCode ligatures via `harfbuzz_features` — not enabled by default
- Leader key `⌃A` chosen for tmux familiarity; 1 second timeout before it acts as literal Ctrl+A

## Sources

- `raw/Configuration - Wez's Terminal Emulator.md` (clipped from wezterm.org/config/files.html)
- [[daily/2026-04-16.md]] — personal WezTerm config created matching Catppuccin Mocha stack; extended with WebGpu renderer, leader key, workspace, 50k scrollback, status bar
