madelogdocs

Configuration

Every key in .madelog/config.toml with its type, default and the command that reads it; every environment variable; where the config and the device key live on macOS, Linux and Windows.

Settings live in .madelog/config.toml, one file per repository, written by madelog init and changed with madelog config set. A missing file means defaults. The file is TOML and you can edit it by hand; a key madelog does not know is an error when the file is read, so a typo fails loudly rather than silently doing nothing.

The file madelog init writes, plus the two keys madelog publish adds later:

# madelog configuration. `madelog config set <key> <value>` edits this file.
[llm]
provider = "auto"
model = "qwen3:4b"
remote = false
# host = "http://box.lan:11434"                      # optional, unset by default

[server]
url = "https://madelog-server-production.up.railway.app"
device_id = "5ea56900-b0d3-4683-aa32-fe1e3eca821c"   # written by madelog publish
slug = "north-fable-4xt3"                            # written by madelog publish

[privacy]
redact = []

[project]
name = "ledger"

Reading and changing keys

$ madelog config list
llm.provider = auto
llm.model = qwen3:4b
llm.host =
llm.remote = false
server.url = https://madelog-server-production.up.railway.app
server.device_id =
server.slug =
privacy.redact =
project.name = ledger
project.delivered_url =
project.screenshot =
$ madelog config get llm.model
qwen3:4b
$ madelog config set privacy.redact "^secrets/, [.]env$, credentials"
privacy.redact = ^secrets/, [.]env$, credentials

set prints the key and its new value, rewrites the whole file, and validates where there is something to validate. An empty value clears an optional key (llm.host, server.device_id, server.slug, project.delivered_url, project.screenshot); for a list it means an empty list.

$ madelog config set llm.provider openai
madelog: llm.provider must be one of auto, ollama, none (got `openai`)
$ madelog config set llm.remote maybe
madelog: expected true or false, got `maybe`
$ madelog config set privacy.redact "(unclosed"
madelog: privacy.redact pattern `(unclosed` is not a valid regex: regex parse error:
    (unclosed
    ^
error: unclosed group
$ madelog config get nope
madelog: unknown config key `nope`. Known keys: llm.provider, llm.model, llm.host, llm.remote, server.url, server.device_id, server.slug, privacy.redact, project.name, project.delivered_url, project.screenshot

Each of these exits 1 and changes nothing. A key that is in the file but not in that list stops every command that reads the config:

$ madelog config list
madelog: parsing /Users/ana/projects/ledger/.madelog/config.toml: TOML parse error at line 6, column 1
  |
6 | temperature = 0.2
  | ^^^^^^^^^^^
unknown field `temperature`, expected one of `provider`, `model`, `host`, `remote`

Keys

KeyType, default, exampleRead by
llm.providerauto, ollama or none. Default auto. Example nonesummarize, and publish through it. See Summaries
llm.modelstring. Default qwen3:4b. Example llama3.1:8bsummarize. A blank value means the default. Any name Ollama has pulled; a bare name matches its :latest tag
llm.hoststring, optional. Unset by default. Example http://box.lan:11434summarize, and publish through it. Where Ollama listens. A bare host gets http://; a trailing slash is dropped. It wins over OLLAMA_HOST; unset or blank, OLLAMA_HOST decides, then http://localhost:11434
llm.remotebool: true, false, yes, no, y, n, 1, 0, on, off. Default falsesummarize. true prints a notice and uses the template; no remote provider exists in this version
server.urlstring. Default: the hosted server, shown in the file above. Example http://localhost:8080publish, unpublish. A bare host gets https://; a trailing slash is dropped. --server <url> overrides it for one run
server.device_idUUID, optional. Unset by default; the file above shows onepublish, unpublish, which also write it. The id the server gave this machine's public key; a public identifier, not a secret. Cleared, it is registered again on the next publish
server.slugstring, optional. Unset by default. Example north-fable-4xt3publish (re-publishes to it), unpublish (deletes it and clears the key). Written by publish
privacy.redactlist of regular expressions, set as a comma-separated string. Default empty. Example ^secrets/, [.]env$The post-commit hook, for diff excerpts and prompts. Every pattern must compile; Rust regex syntax, matched anywhere in the path or prompt. See Privacy
project.namestring. Default: the repository directory name, written by init. Example ledgerpublish (the page header and title), the preview
project.delivered_urlstring, optional. Unset by default. Example https://ledger.examplepublish: the "Delivered" link on the page
project.screenshotstring, optional. Unset by default. Example docs/screenshot.pngpublish: a link on the page. The path is written into the page as given; nothing is copied or uploaded

server.device_id and server.slug belong to one server. When you move a repository to another server, clear both so the next publish registers afresh.

Two more values are stored outside this file. The answers to madelog init live in the newest intent event, which the page and the hook read, and in .madelog/intent.md, which is a copy for you; editing the Markdown file changes nothing on the page. Whether AI sessions are recorded is record_ai_sessions in that event. The device key lives outside the repository entirely.

Environment variables

VariableRead byEffect
MADELOG_CONFIG_DIRevery command that touches the device key: init, onboard, publish, unpublishReplaces ~/.config/madelog as the directory of device.key
MADELOG_EXEinit, onboardThe path the post-commit hook should call. The hook names the binary by path only when that path sits under <repo>/.madelog/bin/; anywhere else the hook line says madelog and relies on PATH. The per-project installer sets it
MADELOG_EDITORsummary edit, the preview's e keyThe editor, before EDITOR and VISUAL. The value stdin reads the new text from standard input instead
MADELOG_CLAUDE_PROJECTS_DIRthe post-commit hookReplaces ~/.claude/projects as the directory searched for Claude Code transcripts
OLLAMA_HOSTsummarize, publishThe Ollama address, as Ollama itself reads it. Consulted only when llm.host is unset or blank. Default http://localhost:11434
EDITOR, VISUALsummary edit, the previewConsulted in that order when MADELOG_EDITOR is unset; vi when all three are
TERM, WT_SESSION, LC_ALL, LC_CTYPE, LANGonboardDecide whether the banner is drawn with box characters or ASCII
PATH, PATHEXTonboard, init, the hookWhere git, git-ai and ollama are looked for; PATHEXT on Windows
MADELOG_INSTALL_DIR, MADELOG_INSTALL_URLthe install scripts onlySee Installation

No variable turns on a network call. server.url and --server are the only ways to choose where a page goes, and madelog publish --local ignores both. An empty --server "" is refused rather than silently falling back to server.url. OLLAMA_HOST only changes where a local model is looked for, and llm.host overrides it.

File locations

WhatmacOS and LinuxWindows
Per-repository state<repo>/.madelog/<repo>\.madelog\
Device key~/.config/madelog/device.keyC:\Users\<you>\.config\madelog\device.key
Claude Code transcripts (read only)~/.claude/projects/C:\Users\<you>\.claude\projects\
Summary being edited$TMPDIR/madelog-summary-<uuid>.md (macOS), /tmp/madelog-summary-<uuid>.md (Linux)%TEMP%\madelog-summary-<uuid>.md
System-wide binary~/.local/bin/madelog%LOCALAPPDATA%\madelog\bin\madelog.exe

madelog does not use XDG_CONFIG_HOME or %APPDATA%; the config directory is .config/madelog under the home directory on every platform, unless MADELOG_CONFIG_DIR says otherwise. Inside <repo>/.madelog/:

FileWritten byNotes
log.dbinit, then every recording commandSQLite, WAL mode; log.db-wal and log.db-shm appear next to it while it is open
config.tomlinit, config set, publish, unpublishThis page
intent.mdinitYour answers as Markdown. Rewritten only when init records a new intent
site/index.htmlpublish, with or without --localThe rendered page, overwritten each time
bin/madelogthe per-project installerOnly in a per-project install

The device key

device.key is 64 hex characters plus a newline: the 32-byte ed25519 secret key. The directory is created with mode 0700 and the file with 0600 on macOS and Linux; on Windows the user profile's ACL applies. It is created by the first madelog init (or onboard) on the machine, through a temporary file that is hard-linked into place, so two concurrent runs cannot leave a half-written key. It is loaded, never rewritten, by publish and unpublish.

The public half is what the server knows. POST /v1/devices maps it to a device_id, the same id every time for the same key, and that id is what server.device_id stores. The secret never leaves the file. A page belongs to the key that published it: to replace or remove it from another machine, copy device.key there, or run madelog unpublish first and publish afresh. A corrupt file is reported by path: madelog: /Users/ana/.config/madelog/device.key is not a hex device key.