How Omarchy Filters User Theme Overlays: A Technical Deep Dive
Omarchy uses a contextual two-step overlay system that applies full file replacement for manually created themes but enforces a security denylist for Git-cloned themes, blocking executable configuration files like alacritty.toml and kitty.conf.
When activating a theme, Omarchy balances customization flexibility with security by examining how a user theme was installed. The omarchy-theme-set command orchestrates this process, handling everything from staging to final activation in ~/.local/state/omarchy/current/theme.
The Two-Step Overlay Architecture
Omarchy's theme activation follows a predictable pipeline. First, it copies built-in theme files from themes/<name>/. Then it overlays user-provided files from ~/.config/omarchy/themes/<name>/ according to trust boundaries.
This design allows users to override any aspect of a built-in theme while protecting against supply-chain attacks from untrusted Git repositories.
Full Overlay for Manually Created Themes
When a user creates a theme directory by hand—without initializing a Git repository—Omarchy applies the overlay without restriction. Every file placed in ~/.config/omarchy/themes/<name>/ replaces its counterpart in the base theme.
This mode trusts the user as the sole author, giving complete control over terminal emulators, editors, and shell configurations.
Filtered Overlay for Git-Cloned Themes
If the theme directory contains a .git folder, Omarchy treats it as potentially untrusted. The overlay logic switches to filtered mode, selectively copying only safe files and omitting any that could execute arbitrary code.
The INSTALLED_THEME_DENIED Denylist
The security boundary is defined in bin/omarchy-theme-set as a bash array:
# Inspect the denylist in bin/omarchy-theme-set
grep -A5 "INSTALLED_THEME_DENIED=" bin/omarchy-theme-set
As of the current implementation, INSTALLED_THEME_DENIED contains:
alacritty.toml– Alacritty terminal configurationfoot.ini– Foot terminal configurationghostty.conf– Ghostty terminal configurationkitty.conf– Kitty terminal configurationvscode.json– VS Code settings that may trigger extensions
When the overlay loop encounters any filename matching this array, it prints a warning to stderr and excludes the file from staging. Only color-related and non-executable resources survive the filter.
Theme Activation Flow
The complete sequence in omarchy-theme-set <name> follows three phases:
- Staging – Base theme copies to a temporary directory, then user overlay applies (full or filtered depending on
.gitpresence) - Template Rendering – If
colors.tomlexists, dynamic templates are processed - Activation – Final theme moves to
~/.local/state/omarchy/current/theme, and the running shell reloads
# Activate a manually created theme - full overlay applies
omarchy-theme-set my-custom-theme
# Install and activate a theme from Git - filtered overlay applies
omarchy theme install https://github.com/example/omarchy-theme.git
omarchy-theme-set example
# stderr warning: "Skipping dangerous file: kitty.conf"
Verifying the Filtering Behavior
The test suite test/shell.d/theme-staging-test.sh validates that cloned themes cannot smuggle executable configurations. It asserts that:
- Color definitions and static assets pass through unchanged
- Files matching
INSTALLED_THEME_DENIEDare absent from the final staged theme - Warnings appear for each dropped file
# Run the overlay filtering test
./test/shell.d/theme-staging-test.sh
This test ensures the denylist mechanism remains functional across refactors.
Security Design Rationale
Omarchy's filtering strategy acknowledges two threat models. Trusted authors (manual theme creators) maintain full control over their environment. Untrusted sources (any Git repository) are sandboxed from executing code through terminal or editor configurations.
The denylist approach prioritizes explicit safety over completeness—new dangerous file types can be added to INSTALLED_THEME_DENIED as the ecosystem evolves.
Summary
- Two overlay modes exist: full (manual themes) and filtered (Git-cloned themes)
INSTALLED_THEME_DENIEDinbin/omarchy-theme-setdefines blocked files for cloned themes- Five terminal/editor configs are currently denied:
alacritty.toml,foot.ini,ghostty.conf,kitty.conf,vscode.json .gitdirectory presence triggers the security filter automaticallytest/shell.d/theme-staging-test.shvalidates correct filtering behavior
Frequently Asked Questions
How does Omarchy detect whether to use full or filtered overlay?
Omarchy checks for a .git directory inside ~/.config/omarchy/themes/<name>/. If present, the theme is treated as cloned and the filtered overlay applies. Absence of .git indicates a manually created theme receiving full overlay privileges.
Can I override the denylist for a cloned theme?
No—the denylist is hardcoded in bin/omarchy-theme-set and applies uniformly to all Git-cloned themes. To use denied configurations, manually create the theme directory without Git initialization, or fork the theme and maintain it outside version control.
Where are filtered themes ultimately stored?
After staging and any template rendering, the finalized theme moves to ~/.local/state/omarchy/current/theme. This location is read by the shell environment and application launchers to apply the active theme.
Why are terminal configurations specifically targeted?
Terminal emulators execute shell commands through features like shell, startup_script, or command directives. By denying these files from untrusted sources, Omarchy prevents a malicious theme from triggering arbitrary code execution when the user opens a new terminal window.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →