What isn't the dev agent's moves to nisse-core, unchanged in behaviour,
with its tests: canonical, render, render_anthropic, llm, catalog, probe,
context, views, state, reconcile, worker, cancel, dump, transport, matrix,
execution, testing, vault, memory, oplog, envfile and gitea (whole).
- nisse_core.state.StateStore holds the tables every agent has; an
agent's subclass adds its tables (version, migrations), roles and
views. nisse_dev.state.StateStore adds the build VM blocks (v5).
- views.project takes what each role is shown, rather than a fixed table.
- Vault takes the agent's name (agent=), for provenance.
- A test that nisse_core never imports an agent.
- The loop, config, git, delegation, expert, tools and evals stay in
nisse-dev until nisse-ops has a loop to share.
Docs: the Development Plan marks M7.1 done and notes that Phase 6 waits on
the agent host and Terraform; Architecture Part L names the package.
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01J5Utyfzw7gF7UhjRDEtjTk
- Every PR: lint, unit tests across the runner's cores (pytest-xdist), 16
property walks from a seed that moves with the run number, integration
tests, and the end-to-end smoke tests (the slice, a conversation filed
as work, a question; `smoke` marker).
- A PR labelled e2e:full, a push to main, or a manual run: all 48 walks and
the whole end-to-end suite. Adding e2e:full to a PR runs it; any other
label runs nothing.
- A published release runs the full set before its image is built.
- The walk's seeds come from NISSE_WALK_SEEDS / NISSE_WALK_FIRST (48 from 0
by default).
Measured here: the unit tier on 2 workers took 3m49s against 6-8 minutes
serially.
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01PPQ14L3LikyefCMFBqEbKE
The thresholds Part H says to tune on the real inference hardware were
hardcoded, so every adjustment would have been a PR. They now live in a
`tuning:` section of a YAML config file, which also replaces flat
environment variables as the home for structure (#32).
- The file (NISSE_CONFIG, default ./nisse-dev.yaml) carries structure
and holds no secrets: credentials are ${VAR} references resolved from
the environment, and a reference to an unset variable is an error
- The environment still wins: every existing NISSE_* variable overrides
its key, and the file is optional, so .env and CI work unchanged
- Validation stays fail-fast and reports every problem at once; unknown
keys are errors, so a misspelt knob fails at startup instead of
silently doing nothing
- The config file joins the state store and .env in the check that
refuses to start when they sit inside the workspace clone
- Tuning covers the executor's turn and failure limits, the consult
budget, the delegation caps, the command timeout and the tool output
limit, which Workspace now takes as a setting; the defaults are the
values the agent already ran with
- llm.max_output_tokens reaches both LLM clients from the config
docs/Tuning-Guide.md explains the knobs for someone learning local
model tuning: how weights, quantization and the KV cache spend VRAM,
what each knob does and what goes wrong at either extreme, and an order
to tune in. nisse-dev.example.yaml documents every key and is checked
by a test so it cannot drift.
Closes#32
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
PR 2 of the steps-3/4 plan.
- llm.py: LLMClient protocol — complete(events, tools, model) ->
canonical events — present from the first real LLM call.
LiteLLMClient renders requests via the A10 renderer, targets the
proxy's OpenAI-compatible route, and maps provider tool-call IDs
to locally-minted canonical IDs at the boundary
- RoleMap (A11): executor/planner/delegate/consultant resolved from
env; pinned() returns the mapping to record at task start
- Config strictly from env: NISSE_LLM_BASE_URL, NISSE_LLM_TOKEN;
envfile.py is a minimal .env loader where real env wins; .env now
gitignored with a committed .env.example documenting all variables
(Matrix ones included for the upcoming transport PR)
- Live smoke test against the proxy is integration-marked and skips
without credentials — CI stays credential-free per operator
decision; the test runs locally once .env exists
- httpx added as nisse-dev's HTTP client
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
- uv workspace tying nisse-core, nisse-dev, nisse-ops together
(src layouts, workspace-sourced nisse-core dependency)
- Placeholder hello-world entry points for both agents, calling
through nisse-core to exercise the package boundary
- pytest unit tests per package; integration tests (marker-gated)
running the installed console scripts as subprocesses
- ruff lint + format, nisse_* declared first-party
- Gitea Actions workflow running lint, format check, unit and
integration tests; scripts/check.sh mirrors it locally
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>