A self-hosted, single-user, one-instance-per-domain playbook. playmaker turns a stream of sources into a living, self-maintaining playbook of discrete, actionable plays (e.g. "How to use AI in Software Product Engineering").
playmaker is a thin, non-invasive superset over VectifyAI OpenKB
— the Apache-2.0 implementation of the Karpathy LLM-wiki pattern. OpenKB does
the heavy lifting (ingest → compile → query → lint, cross-document enrichment,
contradiction synthesis, dedup, [[wikilinks]], PageIndex long-PDF handling,
LiteLLM provider, Obsidian-compatible markdown). playmaker adds only what makes
it a playbook.
OpenKB is pinned to v0.4.1 (playmaker.OPENKB_PIN); upgrades are
deliberate.
| Concern | OpenKB | playmaker |
|---|---|---|
| Page shape | concept/entity pages | plays (WHY-led, Kind, When/How/Outcome/Caveats, category-first tools) via a custom wiki/AGENTS.md |
| Frontmatter | managed in code | a sidecar (.playmaker/plays-meta.json) for human-set maturity + typed links (prerequisite / alternative / counters) |
| Contradictions | reconciled silently | flagged as contested for human review |
| Log | thin ingest | filename |
a richer changelog (+N plays, enriched M, linked K) |
The layer is non-invasive: it steers OpenKB via config (AGENTS.md,
config.yaml), keeps its own state outside OpenKB's directories, and wraps the
openkb CLI as a black box (playmaker.engine). Nothing in OpenKB is forked or
patched.
Prerequisites: Python ≥ 3.10 and git (OpenKB is pinned as a git+https
dependency). uv is used if present.
git clone <this-repo> playmaker && cd playmaker
./scripts/install.sh # creates ./.venv, installs playmaker + OpenKB (pinned v0.4.1)
source .venv/bin/activate
# add --dev to also install test deps and run the suite:
# ./scripts/install.sh --devManual equivalent:
python3 -m venv .venv && source .venv/bin/activate
pip install -e . # pulls OpenKB (pinned v0.4.1) + its depsThe install pulls the engine and its dependency tree (litellm, pageindex, markitdown, …) from source — it needs network access. Playbook instances are data, not code: create them outside the repo (see Quick start). Nothing secret or instance-specific is in the repo.
# 1. Initialize an instance for one domain
playmaker init ./my-playbook --model openai/<your-model>
# 2. Configure the gateway: copy .env.example -> .env and fill in
# LLM_API_KEY + OPENAI_API_BASE; set the model/headers in
# .openkb/config.yaml (User-Agent workaround is pre-filled).
# 3. Ingest sources — get a per-changeset summary back
playmaker --kb-dir ./my-playbook ingest https://example.com/some-article
playmaker --kb-dir ./my-playbook ingest ./notes/
# 4. Ask the playbook
playmaker --kb-dir ./my-playbook query "How should I do X well?"playmaker set-maturity <play> established # experimental|emerging|established
playmaker assert-link <a> prerequisite <b> # prerequisite|alternative|counters
playmaker conflicts # list contested plays
playmaker resolve-conflict <play> --note "..." # clear + record
playmaker reconcile [--repair <old> <new>] # heal sidecar after rename/removeplaymaker plays --kind procedure --tool "coding agent" --maturity established<play> accepts a slug (tdd) or full key (concepts/tdd).
playmaker publish --kb-dir <kb-root> --out ./site renders a read-only static
snapshot — one page per play, a unified search/ask command bar, faceted browse,
and a grounded Ask (/api/query) function — then deploy ./site to Vercel
behind a shared-password gate. publish is read-only over the wiki, so it also
works on a plain OpenKB wiki (play metadata just renders empty).
- Bundle deploy notes:
playmaker/publish/deploy/DEPLOY.md - Step-by-step agent runbook (publish an existing OpenKB + deploy to Vercel,
with verification and failure modes):
docs/deploy-existing-openkb.md
playmaker routes the LLM through a LiteLLM-compatible gateway:
model: openai/<name> + OPENAI_API_BASE + LLM_API_KEY. Some gateways' WAFs
reject LiteLLM's default User-Agent — config.yaml ships an extra_headers
User-Agent override (forwarded to LiteLLM by OpenKB). Reasoning models need a
generous max_tokens budget.
The repo is the tool, not any deployed playbook. The split:
Committed (the solution — clone this to redeploy):
| Path | What |
|---|---|
playmaker/ |
the Python package (incl. templates/config.yaml, templates/env.example — packaged data) |
pyproject.toml |
dependencies + the pinned OpenKB version (git@v0.4.1) |
scripts/ |
install.sh (redeploy) and smoke_test.py (live check) |
tests/ |
the offline suite |
docs/, README.md |
docs (incl. precision/recall + conflict-detection tuning) |
openspec/ |
the proposal, design decisions, and specs |
.gitignore |
this policy, enforced |
Not committed (.gitignore):
| Path | Why |
|---|---|
.venv/, __pycache__/, *.egg-info/, .pytest_cache/, build/ |
regenerated by install.sh — and large (~500 MB venv) |
.env, **/.env |
secrets (API key, gateway URL) |
.openkb/, .playmaker/, /wiki/, /raw/ |
a deployed instance's data — per machine/domain, not part of the tool |
.claude/ |
local agent config (commit openspec/ instead; delete this ignore line to share OpenSpec slash-commands) |
.DS_Store |
macOS noise |
Instances live outside the repo. A playbook (e.g.
~/playbooks/ai-swe) is data you build withplaymaker init; it is not redeployed via git. To move a playbook between machines, copy its directory (it's self-contained:wiki/+raw/+.openkb/+.playmaker/), and recreate its.envfrom.env.example— never copy the secret.
my-playbook/
├── raw/ OpenKB: original sources
├── wiki/ OpenKB: the compiled playbook (Obsidian-browsable)
│ ├── AGENTS.md playmaker: the play-shaped compiler prompt
│ ├── concepts/<slug>.md the PLAYS
│ └── log.md OpenKB: thin log
├── .openkb/ OpenKB: config.yaml, hashes.json, pageindex.db
├── .env gateway secret + base URL (you create this)
└── .playmaker/ playmaker: sidecar + changelog (engine never writes here)
├── plays-meta.json
└── changelog.md
The offline suite (sidecar, changelog/diff, wiki parser, reconciliation, CLI) needs no LLM or OpenKB install:
pip install pytest pyyaml click && pytestThe live integration is exercised by scripts/smoke_test.py (a tiny gateway
call + a one-source end-to-end ingest), which requires gateway credentials.
See openspec/changes/playmaker/ for the full proposal, design decisions, and
specs. Precision/recall trade-off: docs/precision-recall.md.
A Firecrawl source fetcher for JS-heavy pages, a play-tuned Skill Factory export, and an upstream OpenKB PR adding a pluggable page-type so plays are first-class rather than repurposed concepts.