claudeers.
// Claude Skills

nanopi

Tiny Rust port of Pi — a ~4 MB statically-linked coding agent CLI for old/low-resource Linux boxes. OpenAI + Anthropic providers, streaming tool calls (read/…

// Claude Skills[ cli ][ api ][ claude ]#claude#agent-skills#ai-agent#anthropic#claude-code#cli#coding-agent#deepseek#skills◷ MIT$open-sourceupdated about 1 month ago
Actively maintained
100/100
last commit 7 days ago
last release 26 days ago
releases 8
open issues 0
// star history

Install with your AI

Paste into Claude Code, Cursor, or any agent — it reads the repo and wires the tool into your project.

Install and set up nanopi (release-binary project) into my current project.
Found on https://claudeers.com/nanopi
Repo: https://github.com/ChrisZhangJin/nanopi
Homepage/docs: —
Detected install method: release-binary → inspect the README
Category: skills. Platforms: cli, api.
Read the repo's README for exact setup and env vars, then install it and wire it into my project.

Claudeers Health Verdict:
active; community-verified: false. Confirm the source before running anything.
// or install directly (release-binary)

Grab the latest release asset from GitHub.

# download a build from https://github.com/ChrisZhangJin/nanopi/releases
// or clone
git clone https://github.com/ChrisZhangJin/nanopi

// compatibility

Platformscli, api
Operating systems—
AI compatibilityclaude
LicenseMIT
Pricingopen-source
LanguageRust

Get your FREE $2.50 API credits to access TickAtlas financial data ↗

nanopi

No Node. No Python. No node_modules.

A coding-agent CLI you can scp onto a box that has no runtime — a single ~4 MB static Rust binary, ported from Pi. Runs on Alpine, on CentOS 6, and anywhere npm install isn't an option.

English · 简体中文


nanopi TUI screenshot

Why nanopi?

  • 🚫 Zero runtime dependencies — no Node, no Python, no package manager. Download one file, chmod +x, run.
  • 🖥 Runs on ancient boxes — glibc 2.12+ (CentOS 6), or the fully static musl build on Alpine and anything else
  • 🪶 ~4 MB static binary — musl + LTO + strip (the download is 1.6 MB, UPX-packed)
  • 🧬 PI-parity — mirrors Pi's surface: JSONL sessions, hooks, skills, -p, /fork, /resume
  • 🔌 Multi-provider — any OpenAI-compatible endpoint (DeepSeek, ollama, vLLM, …) plus native Anthropic
  • 🛠 Streaming tool calls — read / write / edit / bash, rendered live in a ratatui TUI
  • 🪝 Claude Code hooks — PreToolUse / PostToolUse / UserPromptSubmit shell hooks
  • 🧠 Agent Skills — spec-compliant SKILL.md discovery + /skill:name expansion

Background — why nanopi exists

Pi is a great coding agent, but its upstream chose not to support certain environments that real users need:

Upstream issueUser requestUpstream status
pi#8591musl-linked builds for Alpinenot planned
pi#6546Avoid glibc version mismatch on older Linuxnot planned
pi#6075Startup time is too slownot planned

Three separate people asked for musl builds, old-glibc compatibility and a lighter startup; upstream closed all three as not planned. That is a reasonable call for them — Pi targets modern machines — but it leaves the old-hardware case unserved. nanopi is a Rust rewrite for exactly that case:

  • Static musl build — zero runtime deps, runs in Alpine containers (see release.yml for the CI matrix)
  • glibc 2.12+ (CentOS 6) — the dynamic build covers old servers; the musl build covers everything else
  • ~4 MB — Rust + LTO + opt-level = "z" + panic = abort + strip; the published binary is UPX-packed down to 1.6 MB
  • Prebuilt for linux-x86_64, linux-x86_64-musl, macos-aarch64 and windows-x86_64. Linux ARM is not prebuilt yet — build from source with cargo build --release --target aarch64-unknown-linux-musl.

Install

Prebuilt binaries

Grab a build from Releases:

# Adjust VERSION to the tag you want (e.g. v0.9.1)
VERSION=v0.9.1
curl -L -o nanopi \
  "https://github.com/ChrisZhangJin/nanopi/releases/download/${VERSION}/nanopi-${VERSION}-linux-x86_64-musl"
chmod +x nanopi
./nanopi --version

Per release, prebuilt binaries ship for:

  • nanopi-<ver>-linux-x86_64-musl — fully static Linux, works on anything (recommended)
  • nanopi-<ver>-linux-x86_64 — dynamic glibc Linux, slightly smaller
  • nanopi-<ver>-macos-aarch64 — Apple Silicon (M1+)
  • nanopi-<ver>-windows-x86_64.exe — Windows 10/11

macOS Intel isn't prebuilt (GitHub runner supply is scarce); build from source with cargo build --target x86_64-apple-darwin.

Build from source

# One-time host setup
curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s -- -y --default-toolchain stable --profile minimal
source "$HOME/.cargo/env"
rustup target add x86_64-unknown-linux-musl
sudo apt install -y musl-tools build-essential   # Debian/Ubuntu

# Build
cargo build --release --target x86_64-unknown-linux-musl
./target/x86_64-unknown-linux-musl/release/nanopi --version

Quick start

export OPENAI_API_KEY=sk-...
export OPENAI_BASE_URL=https://api.deepseek.com/v1
export OPENAI_MODEL=deepseek-v4-flash

# Interactive TUI (default)
nanopi

# One-shot -p mode (Claude Code semantics)
nanopi -p "read /etc/hostname and tell me what you see"

# JSON output for scripting
nanopi -p --output json "say hi"

# Prompt piped on stdin
echo "explain this error" | nanopi -p

# Resume: last session / by id / fork
nanopi --continue
nanopi --session <id>
nanopi --fork <id>

CLI

FlagDefaultPurpose
--base-urlhttps://api.openai.com/v1OpenAI-compatible API root
--model(required)Model id
--api-key$OPENAI_API_KEYBearer token
-m, --message(piped stdin)User message; first positional arg also accepted. In -p mode, falls back to piped stdin
-p, --printfalseNon-interactive mode
--outputtext-p output: text | json
--continuefalseResume the most recent session
--session <id>—Resume by session id
--fork <id>—Fork an existing session
--no-hooksfalseDisable all hooks
-a, --approvefalseTrust project resources for this run
-N, --distrustfalseDistrust project resources
--skill <path>—Load a skill file/dir (repeatable)
-S, --no-skillsfalseDisable skill discovery
-C, --no-context-filesfalseDisable AGENTS.md / CLAUDE.md discovery
--system-prompt <text|path>—Replace the built-in system prompt
--append-system-prompt <text|path>—Append to the system prompt (repeatable)

Skills

Nanopi implements the Agent Skills spec. Drop a SKILL.md into ~/.nanopi/skills/<name>/:

---
name: greet
description: Greet the user warmly. Use for hellos.
---
Say "hi, friend" — nothing else.

Invoke explicitly, or let the model discover it via the auto-appended <available_skills> block in the system prompt:

/skill:greet             # expands SKILL.md into the message
/skill:greet in french   # extra args are appended

Locations (earlier wins on name collisions):

  • User: ~/.nanopi/skills/
  • Project: <cwd>/.nanopi/skills/ (only when trusted via -a or persisted decision)
  • CLI: --skill <path> (files or dirs; loads even with --no-skills)

Custom system prompt

--system-prompt <text|path> replaces the built-in identity/guidelines prompt; --append-system-prompt <text|path> (repeatable, values joined by a blank line) adds text after it. Both accept literal text OR a path to an existing file. Either flag suppresses the matching file discovery below entirely — no merge.

Without a flag, nanopi discovers:

  • <cwd>/.nanopi/SYSTEM.md (only when the project is trusted via -a or a persisted decision), then ~/.nanopi/SYSTEM.md — for --system-prompt.
  • <cwd>/.nanopi/APPEND_SYSTEM.md (same trust rule), then ~/.nanopi/APPEND_SYSTEM.md — for --append-system-prompt.

Project beats global; the global file needs no trust gate (it's your own machine, not a cloned repo). Context files, skills, and the "Current working directory: …" line still apply on top of a custom prompt — only the identity/tools/guidelines section is replaced. Caveat: a replaced prompt drops the auto-generated "Available tools: …" line, and some models skip tool calls without it, so mention the tools you expect the model to use.

Hooks

Shell hooks fire around tool calls, matching Claude Code's PreToolUse / PostToolUse / UserPromptSubmit protocol. Configure in ~/.nanopi/settings.toml:

[[hooks.pre_tool_use]]
matcher = "^bash$"
command = "logger 'nanopi about to shell out'"

Keys are snake_case (pre_tool_use, not PreToolUse). Full protocol in docs/v0.5-research.md §6.

Versions

VersionStatusSizeNotes
v0.10.0current1.6 MBCustom system prompt (--system-prompt, SYSTEM.md); explicit api_kind beats the vendor sniff; readable tool failures in -p; UPX-packed release
v0.9.xreleased~3.9 MBFirst-run wizard, /settings + /keybindings, 8-vendor dispatch, retry envelope (0.9.2–0.9.3); v0.9.1 fixed the v0.9.0 tool loop
v0.9.0released~4.0 MBSkills (PI-parity), --skill/--no-skills, folded TUI card, UserPromptSubmit hook
v0.8.xreleased~3.9 MBFull ratatui TUI, /fork, --continue/--session, hooks, JSONL sessions
v0.5.0released~3.0 MBTools (read/write/edit/bash), -p mode, JSON output, hooks
v0.1.0released2.4 MBSingle-file OpenAI streaming demo (kept as nanopi_v0_1 binary)

Sizes are the published musl artifact. From v0.10.0 that artifact is UPX-packed (make), so 1.6 MB is not comparable to the unpacked figures above it — the same build is 4.4 MB before packing.

Roadmap

  • v1.0 — full PI parity: themes, compaction, extension system
  • Linux aarch64 not yet in the CI matrix (see cargo build --release --target aarch64-unknown-linux-musl above)

Cargo mirror (China)

Add to ~/.cargo/config.toml for faster crate downloads:

[source.crates-io]
replace-with = "rsproxy-sparse"

[source.rsproxy-sparse]
registry = "sparse+https://rsproxy.cn/index/"

[target.x86_64-unknown-linux-musl]
linker = "musl-gcc"

Design notes

  • musl + LTO + panic=abort + strip → small static binary. rustls avoids the OpenSSL dep.
  • Hand-written SSE parser — no reqwest-eventsource, keeps the dep tree lean.
  • JSONL over JSON — append-only files survive crashes mid-write.
  • Provider abstraction landed in v0.6; native Anthropic + any OpenAI-compatible endpoint.

See docs/v0.5-research.md and docs/PLAN.md for design + implementation notes.

Credits

  • Pi — the upstream TypeScript agent nanopi ports.
  • Claude Code — hook protocol, -p mode, skills spec.
  • ratatui & crossterm — the TUI foundation.

License

MIT © Chris Zhang

// faq

What is nanopi?

Tiny Rust port of Pi — a ~4 MB statically-linked coding agent CLI for old/low-resource Linux boxes. OpenAI + Anthropic providers, streaming tool calls (read/write/edit/bash), JSONL sessions, ratatui TUI, Agent Skills, Claude Code-style hooks, -p print mode.. It is open-source on GitHub.

Is nanopi free to use?

nanopi is open-source under the MIT license, so it is free to use.

What category does nanopi belong to?

nanopi is listed under skills in the Claudeers registry of Claude-compatible tools.

6 views
★ 30 stars
unclaimed
updated about 1 month ago

// embed badge

nanopi on Claudeers
[![Claudeers](https://claudeers.com/api/badge/nanopi.svg)](https://claudeers.com/nanopi)

// retro hit counter

nanopi hit counter
[![Hits](https://claudeers.com/api/counter/nanopi.svg)](https://claudeers.com/nanopi)

// reviews

// guestbook

0/500

// related in Claude Skills

🔓

An agentic skills framework & software development methodology that works.

// skillsobra/⟨Shell⟩★ 292,190◷ MIT[ claude ]
🔓

Public repository for Agent Skills

// skillsanthropics/⟨Python⟩★ 178,324[ claude ]
🔓

💫 Toolkit to help you get started with Spec-Driven Development

// skillsgithub/⟨Python⟩★ 138,919◷ MIT[ claude ]
🔓

AI coding assistant skill (Claude Code, Codex, OpenCode, Cursor, Gemini CLI, and more). Turn any folder of code, SQL schemas, R scripts, shell scripts, docs,…

// skillsGraphify-Labs/⟨Python⟩★ 123,800◷ MIT[ claude ]
→ see how nanopi connects across the ecosystem