mcp-config/hermes: make the gateway's context limits actually reach the clients
Folds in the in-flight local-checkout work and fixes the context accounting
on top of it. Both halves are the same bug seen from two ends: clients were
sending requests larger than the backend's window and getting hard
ContextWindowExceededError 400s, intermittently, in a way that looked like
the model or the GPU misbehaving.
Already in flight here (unchanged in intent):
- sync.sh prefers the LOCAL CHECKOUT over re-downloading from Gitea, and
install.sh records the checkout path so it can be found. That recording
is load-bearing: without it sync.sh cannot find the repo, silently falls
back to Gitea, and every local edit to opencode.gateway.json is ignored.
Observed on this box — ~/.config/mcp-sync/source did not exist, the
default ~/.dotfiles is not where the checkout lives, and the Gitea base
still served models:{}.
- the hermes custom-provider wiring.
Fixed on top:
opencode had NO context limit on ANY gateway model, not a wrong one. Two
faults compounded. /model/info 403s for a day-to-day virtual key (only
management-scoped keys may read it), which sync.sh treats as best-effort and
falls back to names-only — as designed and as commented. But the merge then
did `prov["models"] = models`, replacing the map wholesale, so limits
declared in the base config were discarded too and there was no floor left.
Base specs are now a floor that live /model/info overrides field by field:
discovery still wins where present, so this adds no drift, and a 403 no
longer strips the limits. Verified: ornith 195584/32768, the qwens
261120/32768.
hermes' model map named `qwen3-vl-30b-a3b` at 262144 — a model the gateway
stopped serving when Ornith replaced it — while ornith-1.0-35b, the model
actually on cg-1 AND the only one with a window smaller than its neighbours
(196608), had no entry at all and inherited Hermes' default. The one model
needing a lower ceiling was the one not declaring one, which is exactly the
shape that fails only once a session grows.
NOTE for other boxes: hermes reads ~/.hermes/config.yaml, which install.sh
produces by MERGING gateway.yaml. Editing gateway.yaml alone changes nothing
until install.sh re-runs — this machine's live config was patched by hand.
Not addressed here, deliberately: the gateway-side context_window_fallback
(ai-k8s-iac). It is wired but inert while cg-2 is scaled down, so preventing
the oversized request client-side is what actually works today.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01FoDK4wwB1Twty5gwiriYLf
This commit is contained in:
+31
-2
@@ -4,6 +4,10 @@
|
||||
#
|
||||
# curl -fsSL https://git.nic-oconnor.com/public/dotfiles/raw/branch/main/bootstrap.sh | sh
|
||||
# (or, from a checked-out clone: ./bootstrap.sh)
|
||||
#
|
||||
# If the repo is private, export GITEA_KEY first — the self-clone below uses it.
|
||||
# Without a key the clone falls back to git's credential.helper (set up by
|
||||
# git/), which prompts once and caches, so the interactive path still works.
|
||||
set -eu
|
||||
|
||||
REPO_URL="${DOTFILES_REPO:-https://git.nic-oconnor.com/public/dotfiles.git}"
|
||||
@@ -19,12 +23,27 @@ if [ ! -f "$SCRIPT_DIR/zsh/install.sh" ]; then
|
||||
echo "bootstrap: git is required to self-clone; install git first" >&2
|
||||
exit 1
|
||||
fi
|
||||
# Authenticated when we have a Gitea PAT, so a PRIVATE dotfiles repo
|
||||
# bootstraps without the repo having to be world-readable. The token goes
|
||||
# through the environment rather than `git -c ...` because argv shows up in
|
||||
# `ps`; it is also not written into .git/config, so the clone leaves no
|
||||
# credential behind on disk.
|
||||
git_auth() {
|
||||
if [ -n "${GITEA_KEY:-}" ]; then
|
||||
GIT_CONFIG_COUNT=1 \
|
||||
GIT_CONFIG_KEY_0=http.extraHeader \
|
||||
GIT_CONFIG_VALUE_0="Authorization: token $GITEA_KEY" \
|
||||
git "$@"
|
||||
else
|
||||
git "$@"
|
||||
fi
|
||||
}
|
||||
if [ -d "$DOTFILES_DIR/.git" ]; then
|
||||
echo "bootstrap: updating existing checkout at $DOTFILES_DIR"
|
||||
git -C "$DOTFILES_DIR" pull --ff-only
|
||||
git_auth -C "$DOTFILES_DIR" pull --ff-only
|
||||
else
|
||||
echo "bootstrap: cloning $REPO_URL into $DOTFILES_DIR"
|
||||
git clone "$REPO_URL" "$DOTFILES_DIR"
|
||||
git_auth clone "$REPO_URL" "$DOTFILES_DIR"
|
||||
fi
|
||||
exec "$DOTFILES_DIR/bootstrap.sh"
|
||||
fi
|
||||
@@ -66,6 +85,16 @@ run_module bin
|
||||
# Provides npx, which opencode needs to spawn the npm-based MCP servers in
|
||||
# mcp-config/. Without it every MCP server silently fails to start.
|
||||
run_module node
|
||||
# Deploys the mcp-sync hook and the LiteLLM key. Runs after node/ (the MCP
|
||||
# servers it configures are npx packages) and BEFORE hermes/, which needs
|
||||
# LITELLM_KEY exported to point its provider at the gateway.
|
||||
#
|
||||
# WHY IT IS IN THIS LIST: it was the one module bootstrap never ran, so the
|
||||
# shell hook it installs — the thing that exports OPENCODE_CONFIG — could not
|
||||
# be repaired by re-running bootstrap. Losing ~/.zshrc.local (or the hook line
|
||||
# in it) left opencode with no covert-gpt provider and no way to get it back
|
||||
# short of curl-ing this module by hand.
|
||||
run_module mcp-config
|
||||
# Hermes Agent (Nous Research) is distributed as an npm package with a Python
|
||||
# dependency. Runs after node/ ensures npx is available.
|
||||
run_module hermes
|
||||
|
||||
Reference in New Issue
Block a user