Commit Graph
4 Commits
Author SHA1 Message Date
Ilker ManapandClaude Opus 5.5 9b61bbc983 Revoke a removed node's certificate, and require --api-client with a mirror's mutual TLS
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
2026-10-04 10:34:35 +02:00
Ilker ManapandClaude Opus 5 cd7eedf09e Give the mirror a page, so managing it is not a curl command
/admin/mirror, behind the same admin session as the other admin pages. What is
held, what is arriving with its byte count, what failed and why; start a fetch,
retry a failed one, remove a version.

Not mounted at all without a mirror configured. The right page for a deployment
with no mirror is no page, rather than an empty one pointing at nothing.

It reloads itself only while something is downloading. A reload at any other
moment takes with it whatever is half-typed into the fetch form, and there is
nothing to watch when nothing is moving.

A failed row offers Retry, not Remove. A fetch that failed left nothing on disk,
so the remove could only answer "the mirror holds nothing for this" — a button
whose single outcome is a confusing error. Starting the same download again is
what somebody looking at that row wants, and the mirror allows it: only a
download still running is refused.

An unreachable mirror is said outright instead of rendering as an empty table.
The two look nearly identical and mean opposite things: one is a mirror waiting
to be filled, the other is a machine to go and look at.

Dashboard takes NavExtras rather than a second bool. Two adjacent booleans at a
call site get swapped silently and are discovered by somebody clicking the
wrong link.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-27 10:17:12 +02:00
Ilker ManapandClaude Opus 5 afb3797e57 Document the mirror that exists rather than the one you assemble
The page described nginx and a curl loop, which was accurate when the mirror
was a directory somebody kept by hand. It is a subcommand now, so it says so:
the two listeners and why they are two, the API and what each endpoint answers,
and the certificates coming from the authority the fleet already has.

nginx stays, further down. It serves a directory perfectly well and anyone
already running it should not be told to install something to replace it.

The systemd unit spells out --base in a comment because it is the flag that
goes wrong quietly: it ends up in catalog entries, and a wrong one makes
`mirror unused` call files unreferenced while they are in use.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-27 09:43:02 +02:00
Ilker ManapandClaude Opus 5 e86457cf02 Make the model mirror a file you can copy, not an idea you have to have
"Set up a local mirror" was advice. This is the nginx config, the directory
layout and the reason the layout has a date in it — a repository that changes
upstream changes what you are running, and the first sign is a prompt that
worked last week answering differently this week.

It says what the mirror is not, because both mistakes are easy. It is not a
caching proxy: nothing populates it on demand, deliberately, since a mirror
that reaches the internet at the least convenient moment fails in a way that
looks like llmgw being broken. And it is not needed at all if you already run
a shared filesystem — put the models there, use a path, and nothing is fetched.

It also says when a mirror stops being enough, and that llmgw is positioned to
distribute between nodes because it already knows which of them hold which
weights. That is not built, and the page says so rather than implying it is
coming.

Every behaviour it relies on was checked against the source: an http:// source
is fetched and a path is not, a killed download resumes, a partial file is
never visible under the model's name, and a shared filesystem is not counted
once per node.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-27 08:20:50 +02:00