rein-openweights acquires its OpenRouter credential directly (OpenBao/ops-warden), consistent with rein-aharness's existing credential-holder principle — glas-harness does not broker LLM-provider credentials. Confirmed llm-connect itself never brokers credentials either (resolve_api_key() only reads an already-materialized key from explicit/env/file), so routing through llm-connect vs. a leaner wrapper doesn't change this. Composable reins as middleware (monitoring/eval/optimization) is recorded as a separate, deliberately deferred question in the same ADR — one candidate capability isn't evidence of a recurring pattern yet. GLAS-WP-0001-T06 done; T05 (bootstrap rein-openweights) unblocked. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
94 lines
4.6 KiB
Markdown
94 lines
4.6 KiB
Markdown
# ADR-001: The "rein" harness family, routed by glas-harness
|
|
|
|
- Status: accepted
|
|
- Date: 2026-07-26
|
|
- Deciders: Bernd Worsch
|
|
|
|
## Context
|
|
|
|
Two harness efforts existed in parallel with no relationship documented
|
|
between them:
|
|
|
|
- **agent-harness** — a working v0.1 runtime, deployed on Railiance,
|
|
driving Claude Code CLI sessions for one tenant (`binky-control`). Its
|
|
only isolation is a `--allowedTools` allow-list string plus cwd-pinning;
|
|
it has no OS-level sandbox and no awareness of glas-harness or
|
|
sand-boxer.
|
|
- **glas-harness** — a charter-only meta-framework (`INTENT.md` plus a CI
|
|
smoke stub) that names sand-boxer as its sandbox provider but has no
|
|
gateway, session loop, or tool dispatch implemented yet.
|
|
|
|
Neither repo referenced the other. Left alone, this heads toward "two
|
|
harnesses that both think they're the runtime," with no shared contract
|
|
and duplicated wiring to `kaizen-agentic`, `activity-core`, and
|
|
`llm-connect`.
|
|
|
|
Separately: every current agent-facing harness in the ecosystem (Claude
|
|
Code, Grok's CLI, GPT/Codex's CLI) is a **frontier-model-vendor harness**
|
|
— it only drives that vendor's own model. There is no harness in the
|
|
ecosystem today that can run a current open-weight model (via OpenRouter)
|
|
through an equivalent agentic tool-use loop.
|
|
|
|
## Decision
|
|
|
|
1. **glas-harness is the framework.** It owns the harness *contract*
|
|
(session lifecycle, tool dispatch, actor attribution, sandbox
|
|
consumption via sand-boxer) and routes between pluggable, concrete
|
|
harness backends — mirroring how sand-boxer owns a sandbox contract
|
|
and routes between pluggable extensions (`ext.compose-ssh`,
|
|
`ext.vm-packer`, `ext.e2b`, ...).
|
|
|
|
2. **Concrete harness backends are called "reins."** The name mirrors
|
|
"rails" (operations models for running workloads): different reins
|
|
suit different circumstances, and more can be added without changing
|
|
the framework. Each rein is its own repo, prefixed `rein-*`.
|
|
|
|
3. **`agent-harness` is renamed `rein-aharness`** and becomes the first
|
|
rein: the Claude-Code-CLI-driven harness for governed, unattended/
|
|
scheduled tenant work (its existing `binky-control` role is unchanged).
|
|
Repo and Forgejo remote already renamed
|
|
(`coulomb/rein-aharness.git`); local directory, git remote, and
|
|
self-referencing docs (`README.md`, `INTENT.md`, `pyproject.toml`
|
|
project name) are updated as part of this ADR landing. The CLI command
|
|
name, Python package name, and deploy artifacts (Docker image tag, k8s
|
|
namespace, Railiance host paths) are **deliberately left unrenamed for
|
|
now** — see `rein-aharness/workplans/HARNESS-WP-0002` — because they
|
|
touch a live deployment and deserve their own reviewed change, not a
|
|
silent mechanical rename bundled into an architecture decision.
|
|
|
|
4. **A new rein, `rein-openweights`, is chartered** to close the
|
|
frontier-vendor-harness gap: an agentic tool-use loop that drives
|
|
current open-weight models via OpenRouter (through `llm-connect`) as
|
|
an alternative to Claude Code / Grok CLI / Codex, usable wherever a
|
|
rein-aharness-equivalent session is wanted but a frontier vendor
|
|
dependency is not. Scaffolded at `~/rein-openweights` (local only —
|
|
no Forgejo remote yet).
|
|
|
|
## Consequences
|
|
|
|
- glas-harness's first implementation milestone is now concrete: define
|
|
the harness contract that both `rein-aharness` and `rein-openweights`
|
|
implement, plus a minimal router, rather than an abstract charter with
|
|
no consumer.
|
|
- `rein-aharness` keeps running unchanged in production (`binky-control`)
|
|
while glas-harness matures — no forced cutover, no risk to the live
|
|
Railiance deployment.
|
|
- The "retire agent-harness" question raised earlier is superseded: it
|
|
isn't retired, it's incorporated as a rein. Whether it's ever folded
|
|
directly into glas-harness's own process (vs. staying a separate
|
|
routed repo) is deferred until glas-harness's contract exists and at
|
|
least two reins have implemented it.
|
|
- Future reins (e.g. a channel-bot rein, a subagent-delegation rein) slot
|
|
into the same contract without new framework work, the same way a new
|
|
sand-boxer extension doesn't require sand-boxer's core API to change.
|
|
|
|
## Open questions (for the workplans below)
|
|
|
|
- Does the harness contract abstract scheduling/blueprint-sourcing
|
|
(kaizen-agentic, activity-core), or does only `rein-aharness` depend on
|
|
those while `rein-openweights` is triggered differently (e.g. directly
|
|
by glas-harness channels)?
|
|
- ~~Where does credential brokering for `rein-openweights`'s OpenRouter/
|
|
llm-connect calls live~~ — resolved in
|
|
`docs/adr/ADR-002-credential-brokering-and-composable-reins.md`: the
|
|
rein itself (Option B), not glas-harness.
|