Getting started

panto

terminal agentziglua

panto is a terminal coding agent: a Zig host you extend with Lua. Run it as a TUI, for one turn in print mode, or as an Anthropic Messages-compatible proxy (panto serve).

Quick start

Install, bootstrap, authenticate, then choose a model.

1. Install

Fetch the latest release (options).

shellbash
curl -fsSL https://tjp.lol/pantograph/install.sh | sh

2. Bootstrap

Set up config and the Lua runtime (details).

shellbash
panto bootstrap

3. Set an API key

Export your provider's key and confirm panto sees it (details).

shellbash
export ANTHROPIC_API_KEY="YOUR_ANTHROPIC_API_KEY"
panto auth list

4. Start a session

Fetch model aliases, pick one, and launch in your project.

shellbash
panto models sync
panto models list
cd ~/code/my-project
panto -m anthropic:<alias>

Install

The script fetches your platform's release and verifies its checksum.

ItemBehavior
PlatformsmacOS arm64, Linux x86_64 (glibc 2.28+), FreeBSD amd64
Destination/usr/local/bin; override with PANTO_INSTALL_DIR
sudoUsed if the destination or its nearest existing parent isn't writable
PATHWarns if the destination isn't on it
shellbash
curl -fsSL https://tjp.lol/pantograph/install.sh | PANTO_INSTALL_DIR="$HOME/.local/bin" sh

First run

Bootstrap a fresh install before starting a session.

Bootstrap

StepResult
Data home$XDG_DATA_HOME/panto, or ~/.local/share/panto
Base config.tomlDefines the default OpenAI and Anthropic providers
luv rockDownloads and builds with LuaRocks; needs CMake and a C compiler
panto bootstrap --forceWipe this Lua version's rocks tree and reinstall.

Normal startup also bootstraps, but needs a provider and model first. With no provider/model config on a fresh data home, plain panto exits with a model or provider error.

Model selection

For ordinary sessions, choose a startup model in this order:

#Source
1-m/--model
2[defaults] model in config.toml
3Your last Ctrl+T pick (state.toml)
4The only models.toml alias of the only remaining provider (unset API keys drop API-key providers)
  • No model setting or single-alias fallback: panto exits with no model selected.
  • In provider:name, an unlisted name becomes the wire model name.
  • panto models sync rebuilds the base models.toml from models.dev.

Other ways to start

shellbash
# Start the TUI with a first message
panto -- "Summarize this project."

# Resume latest here; use panto resume <id-prefix> for a specific session
panto resume

# Run one turn without the TUI
panto -p -- "Summarize this project."
  • Quote the prompt: -- takes exactly one argument.
  • Fresh sessions without a prompt or rig open an empty TUI.
  • Print mode requires a prompt; it also reads piped stdin.
-m, --model <provider:alias>
Model for this run; a unique bare alias works.
-r, --reasoning <level>
Reasoning level; same labels as Ctrl+R.
--theme <name>
Startup theme; same names as Ctrl+Y.
-p, --print
One turn without the TUI; prints the reply, exits 0 or 1.
--rig <file.rig|dir>
Use a rig's config, models, and extensions.
  • ZIP archives extract privately; the extracted files are removed on exit, not the archive.
  • Directory rigs persist in place.
  • Fresh sessions use PROMPT.md only without an explicit prompt or piped stdin.
See Rigs.
--ignore-rig-prompt
Skip the rig's PROMPT.md; requires --rig.
--no-extensions
Built-ins only: no Lua runtime, so no tools.

References: Command line, Key bindings, Configuration, Lua extensions.

Authenticate

Export your provider's key; the generated base config defines these API-key sessions.

Auth sessionKey from
openaiOPENAI_API_KEY
anthropicANTHROPIC_API_KEY
panto auth list [filter]Show key resolution or OAuth login state.
panto auth login <name>Device login for a configured oauth_device session; API-key sessions use their key source.
panto auth logout <name>Forget a stored OAuth token.

Authentication setup

  • The base config has commented-out GitHub Copilot and OpenAI Codex examples.
  • No stored token for that provider? Your first TUI turn starts device login; print mode fails.
MessageAction
no auth sessions configuredNo sessions are configured; bootstrap a fresh install first
Setup: [auth.<name>].

Updating

Self-update replaces only the panto binary.

CommandEffect
panto updateDownload, verify, and atomically swap in the latest release
panto update --checkOnly report whether an update exists
panto extensions updateUpdate git extensions and reinstall configured rocks

Seeing permission denied? Rerun with sudo.

Versions

Find published binaries on Codeberg releases; tags use semantic versions with a v prefix.

panto versionPrint the installed version.

Build from source

Build unreleased changes or a sibling libpantograph with mise.toml's pinned tools:

ToolVersion
zig0.16.0
rust1.97.1; macOS arm64 and Linux/FreeBSD x86_64 targets
cargo-zigbuild0.22.1
shellbash
mise install
mise run build:release
CommandBuildsOutput
mise run build:releaseAll three platforms, pinned depszig-out/release/panto-<ver>-macos-arm64
zig-out/release/panto-<ver>-linux-x86_64
zig-out/release/panto-<ver>-freebsd-x86_64
zig-out/release/SHA256SUMS
mise run build:localAgainst ../libpantographzig-out/local/bin/panto

Cross-target release builds are verified from macOS arm64. Linux-to-macOS builds need a macOS SDK and remain unverified.