Lua Configuration
Crucible loads Lua configuration from ~/.config/crucible/init.lua at startup. This file can configure the TUI, define keybindings, and customize behavior.
Quick Start
Section titled “Quick Start”Create ~/.config/crucible/init.lua:
-- Configure the statusline (cru.* is canonical, crucible.* still works)cru.statusline.setup({ left = { cru.statusline.mode(), cru.statusline.model({ max_length = 25 }), }, right = { cru.statusline.notification({ fallback = cru.statusline.context(), }), },})Config Locations
Section titled “Config Locations”| Location | Purpose |
|---|---|
~/.config/crucible/init.lua | Global config (always loaded) |
<kiln>/.crucible/init.lua | Kiln-specific config (loaded after global) |
Kiln config runs after global config, so it can override settings.
Built-in Modules
Section titled “Built-in Modules”All built-in modules are under the cru namespace (canonical). The crucible namespace is a backwards-compatible alias.
-- Canonical namespace (preferred)cru.statusline -- Statusline configurationcru.log(level, msg) -- Logging (debug, info, warn, error)cru.json.encode(tbl) -- Convert table to JSON stringcru.json.decode(str) -- Parse JSON string to tablecru.include -- Load another config file
-- Also available via cru.*cru.http -- HTTP requests (GET, POST, PUT, etc.)cru.fs -- Filesystem operationscru.shell -- Shell command executioncru.oq -- Data query/transform (parse, json, etc.)cru.paths -- Path utilitiescru.ws -- WebSocket clientcru.kiln -- Kiln accesscru.graph -- Knowledge graph queries
-- Utility modulescru.timer -- sleep(secs), timeout(secs, fn), clock()cru.ratelimit -- Rate limiter: new({capacity, interval})cru.retry(fn, opts) -- Exponential backoff retrycru.emitter.new() -- Event emitter (:on, :once, :off, :emit)cru.check -- Argument validation (.string, .number, .boolean, .table, .func, .one_of)cru.spawn(fn) -- Spawn async task (daemon context only, requires send feature)
-- Daemon-side modules (available when running as a plugin in the daemon)cru.sessions -- Session management: create, get, list, send_message, subscribe, etc.
-- Legacy aliases (still work)crucible.statusline -- same as cru.statuslinecrucible.log -- same as cru.logcrucible.json_encode -- same as cru.json.encodecrucible.json_decode -- same as cru.json.decodecrucible.include -- same as cru.include-- Standalone globals: http, fs, shell, oq, paths (backwards-compat)Statusline Configuration
Section titled “Statusline Configuration”The statusline appears at the bottom of the TUI. Configure it with cru.statusline.setup():
cru.statusline.setup({ left = { ... }, -- Left-aligned components center = { ... }, -- Center-aligned components right = { ... }, -- Right-aligned components separator = " ", -- Between components (default: space)})Components
Section titled “Components”mode()
Section titled “mode()”Shows the current chat mode (Normal/Plan/Auto):
-- With defaultscru.statusline.mode()
-- With custom stylingcru.statusline.mode({ normal = { text = " NORMAL ", bg = "green", fg = "black" }, plan = { text = " PLAN ", bg = "blue", fg = "black" }, auto = { text = " AUTO ", bg = "yellow", fg = "black" },})model()
Section titled “model()”Shows the current model name:
-- With defaultscru.statusline.model()
-- With optionscru.statusline.model({ max_length = 20, -- Truncate long names fallback = "...", -- Show when no model fg = "cyan", -- Text color})context()
Section titled “context()”Shows context window usage:
-- With defaults (shows "42% ctx")cru.statusline.context()
-- With custom formatcru.statusline.context({ format = "{percent}%", fg = "gray",})text()
Section titled “text()”Static text with optional styling:
cru.statusline.text(" | ", { fg = "gray" })cru.statusline.text("Crucible", { fg = "cyan", bold = true })spacer()
Section titled “spacer()”Flexible space that pushes components apart:
cru.statusline.spacer()notification()
Section titled “notification()”Shows transient notifications (toasts and warning/error counts). Supports an optional fallback component that renders when no notifications are active:
-- Simple notification areacru.statusline.notification({ fg = "yellow" })
-- With fallback to context usage when idlecru.statusline.notification({ fg = "yellow", fallback = cru.statusline.context({ fg = "gray" }),})When a toast or warning counts are active, the notification component renders them. When idle, it renders the fallback component (if set) or nothing.
Colors
Section titled “Colors”Named colors: black, red, green, yellow, blue, magenta, cyan, white, gray, darkgray
Hex colors: #ff5500, #1a1a1a
Including Other Files
Section titled “Including Other Files”Split your config into multiple files:
-- ~/.config/crucible/init.luacru.include("statusline.lua") -- loads ~/.config/crucible/statusline.luacru.include("keymaps.lua") -- loads ~/.config/crucible/keymaps.luaExample: Full Configuration
Section titled “Example: Full Configuration”-- ~/.config/crucible/init.lua
-- Statusline with all featurescru.statusline.setup({ left = { cru.statusline.mode({ normal = { text = " N ", bg = "#98c379", fg = "black" }, plan = { text = " P ", bg = "#61afef", fg = "black" }, auto = { text = " A ", bg = "#e5c07b", fg = "black" }, }), }, center = { cru.statusline.model({ max_length = 25, fg = "cyan" }), }, right = { cru.statusline.notification({ fg = "yellow", fallback = cru.statusline.context({ fg = "gray" }), }), },})
cru.log("info", "Config loaded!")Troubleshooting
Section titled “Troubleshooting”Config not loading?
- Check file exists:
ls ~/.config/crucible/init.lua - Check for syntax errors: run
lua ~/.config/crucible/init.lua - Check logs:
cru chatwithRUST_LOG=crucible_lua=debug
Statusline not changing?
- Ensure your
init.luaruns before the TUI starts (check for syntax errors first) cru.statusline.setup()is loaded at TUI startup — changes require restarting the chat session- Crucible ships an embedded Lua default that runs before your
init.lua. Your config overrides it — you don’t need to configure everything from scratch - If the Lua runtime fails entirely, a minimal emergency statusline (mode + model) renders in pure Rust
- Check logs with
RUST_LOG=crucible_lua=debugto verify config was loaded
See Also
Section titled “See Also”- Scripting Languages - Overview of Lua in Crucible
- Creating Plugins - Writing Lua plugins