Motivation
Today the tool layer is built from a spec extracted from a live Dockhand instance
(api:extract → docs/dockhand-openapi.json), pinned via PINNED_DOCKHAND_OPENAPI_COMMIT.
Consequences: CI can't refresh it (no live instance), and every new Dockhand release needs a
manual review of the API diff to spot new/changed endpoints.
Dockhand now commits its generated spec to the repo: src/lib/openapi.generated.json
(raw-fetchable, ~250 paths, info.version per release), regenerated from the route tree on every
build (prebuild → generate:openapi) and drift-checked (generate:openapi:check). Every
operation is 100% annotated. It's the same document served at GET /api/docs when
FEAT_API_DOCS=true, and the upstream manual now references this MCP server as driving the API
from that document.
Proposal — change the spec SOURCE, not the curation
- Fetch
src/lib/openapi.generated.json from the pinned upstream commit via
raw.githubusercontent.com/Finsys/dockhand/<PINNED_DOCKHAND_OPENAPI_COMMIT>/src/lib/openapi.generated.json
instead of extracting from a live instance. Reproducible (pinned to a commit), CI-friendly
(just an HTTP GET), no FEAT_API_DOCS/running instance needed.
- Keep the entire curation layer unchanged: body-contract gate, tool-endpoint-map,
EXPLICIT_OVERRIDES, omission-registry, and the business-logic tools that don't 1:1-proxy REST
(e.g. update_stack_env's get-merge-put) — none of which a spec can express.
- Add drift automation: a Renovate/CI check that bumps the pin toward upstream
main; the
bump PR's CI (body-contract gate + tool-endpoint-map against the new spec) surfaces new/changed
endpoints automatically — replacing the manual release-diff review.
Non-goals
- Not full live tool-generation. Auto-converted raw specs measurably underperform curated MCP
servers; the curation is the value and stays.
- Not reading from a running instance at runtime — a pinned committed spec is reproducible; a
live instance is not.
To validate during implementation
- Does the raw upstream spec carry everything the current handler-source extraction
(extract-dockhand-api.mjs) adds — in particular query-param required flags — so that separate
extraction can be retired? Evidence-based check, not assumed.
- Renovate ergonomics for a "raw file at a pinned commit" dependency.
Process
This issue is the intake of the initiative (decided to take it on, likely soon). Implementation
goes through brainstorming → plan first — the source swap plus drift automation is a real design
step, not a mechanical change.
Motivation
Today the tool layer is built from a spec extracted from a live Dockhand instance
(
api:extract→docs/dockhand-openapi.json), pinned viaPINNED_DOCKHAND_OPENAPI_COMMIT.Consequences: CI can't refresh it (no live instance), and every new Dockhand release needs a
manual review of the API diff to spot new/changed endpoints.
Dockhand now commits its generated spec to the repo:
src/lib/openapi.generated.json(raw-fetchable, ~250 paths,
info.versionper release), regenerated from the route tree on everybuild (
prebuild→generate:openapi) and drift-checked (generate:openapi:check). Everyoperation is 100% annotated. It's the same document served at
GET /api/docswhenFEAT_API_DOCS=true, and the upstream manual now references this MCP server as driving the APIfrom that document.
Proposal — change the spec SOURCE, not the curation
src/lib/openapi.generated.jsonfrom the pinned upstream commit viaraw.githubusercontent.com/Finsys/dockhand/<PINNED_DOCKHAND_OPENAPI_COMMIT>/src/lib/openapi.generated.jsoninstead of extracting from a live instance. Reproducible (pinned to a commit), CI-friendly
(just an HTTP GET), no
FEAT_API_DOCS/running instance needed.EXPLICIT_OVERRIDES, omission-registry, and the business-logic tools that don't 1:1-proxy REST(e.g.
update_stack_env's get-merge-put) — none of which a spec can express.main; thebump PR's CI (body-contract gate + tool-endpoint-map against the new spec) surfaces new/changed
endpoints automatically — replacing the manual release-diff review.
Non-goals
servers; the curation is the value and stays.
live instance is not.
To validate during implementation
(
extract-dockhand-api.mjs) adds — in particular query-paramrequiredflags — so that separateextraction can be retired? Evidence-based check, not assumed.
Process
This issue is the intake of the initiative (decided to take it on, likely soon). Implementation
goes through brainstorming → plan first — the source swap plus drift automation is a real design
step, not a mechanical change.