fix(mesh): route ordering shadowed /api/mesh/register; initiator side never got a self-entry
Two real bugs found while live-testing the new GET /api/mesh/self
endpoint with two actual jump-host containers (mesh-joined for real,
not mocked):
1. routes/api.js mounted `/` (routes/jump.js, admin-session-gated)
before `/mesh`. Since router.use('/', ...) matches every /api/*
path, EVERY /api/mesh/* request -- including /register, which is
authenticated by a bearer mesh join token, not an admin session --
hit that admin gate first and 401'd before routes/mesh.js ever ran.
Confirmed live: a real gateway-to-gateway /join call failed with a
checkApiToken/LoginFailed error instead of ever reaching /register.
Reordered so /mesh is mounted first.
2. POST /register (the receiving side of a join) persists a `(self)`
registry entry via ensureOwnMeshIndex(), but POST /join (the
initiating side) never did -- so GET /api/mesh/self and the mesh
UI's own-entry handling silently saw nothing on whichever gateway
called /join. Fixed by registering a self-entry there too, using
the exact meshIndex the remote assigned (models/mesh_gateway.js's
register() now accepts an explicit meshIndex instead of always
auto-picking one from the local registry, which has no reason to
agree with what's actually configured on the live wg0 interface).
Verified with two real containers joined over a live network: both
sides now report their own correct mesh IP via GET /api/mesh/self,
and both appear correctly in GET /api/mesh/gateways.
This commit is contained in:
@@ -142,6 +142,15 @@ router.post('/join', middleware.auth, middleware.requireJumpAdmin, async (req, r
|
||||
const data = await resp.json();
|
||||
|
||||
wgIface.setAddress(IFACE, meshCidrFor(data.meshIndex));
|
||||
// Persist OUR OWN identity too, not just the remote peer's -- the
|
||||
// receiving side of /register does this via ensureOwnMeshIndex(), but
|
||||
// the initiating side (here) never did, so GET /api/mesh/self and the
|
||||
// mesh UI's own-entry/"(self)" handling both silently saw nothing on
|
||||
// whichever gateway called /join. register() is upsert-by-publicKey
|
||||
// and reuses an existing entry's index, so this is safe to call even
|
||||
// if a self-entry from a PRIOR /register (as the receiving side of a
|
||||
// different peer) already exists.
|
||||
await meshGateway.register({ publicKey: self.serverPublicKey, endpoint: self.serverEndpoint || '', siteSlug: '(self)', meshIndex: data.meshIndex });
|
||||
await meshGateway.register({ publicKey: data.gateway.publicKey, endpoint: data.gateway.endpoint, siteSlug: '(remote master)' });
|
||||
wgIface.setPeer(IFACE, {
|
||||
publicKey: data.gateway.publicKey,
|
||||
|
||||
Reference in New Issue
Block a user