HydraNeck

Getting Started Overview
Onboarding New Venue

Mesh Participation

How HydraNeck joins the HydraGuard WireGuard mesh and reads partner-managed venue routers (Citymesh MikroTik) over the tunnel — instead of over the public internet.

Companion to the Partner Network Design (high-level shared document) and the hydraguard runbooks for venue enrollment (citymesh-venue.md, omada-venue.md).

Why HydraNeck is on the mesh

Partner-managed routers (Citymesh MikroTik at cloud-seven, rupelmonde) do not accept API calls from the public internet. The design avoids public-internet API exposure entirely by routing operator-side access through the WireGuard mesh:

hydraneck.experiencenet.com (Hetzner nbg1)
   │  air peer in mesh
   ▼
HydraGuard Hub (Brussels, 10.10.0.1)
   │  WG tunnel
   ▼
Citymesh MikroTik @ cloud-seven (10.10.2.1)
   │  routes venue LAN
   ▼
Venue LAN 10.0.X.0/24

Side benefits:

Enrollment as an Air peer

HydraNeck is enrolled once as a Hydra Air peer (10.10.100.x range). It doesn't bridge a LAN of its own; it just consumes the mesh.

Step 1: Add the Air peer on the hub

ssh ubuntu@hydraguard.experiencenet.com
hydraguard air add hydraneck
hydraguard apply
hydraguard air config hydraneck > /tmp/hydraneck.wg.conf

The private key is printed to stdout once on air add; save it. air config includes it in the generated file.

Step 2: Install on hydraneck.experiencenet.com

ssh root@hydraneck.experiencenet.com
apt-get install -y wireguard
install -m 600 /path/to/hydraneck.wg.conf /etc/wireguard/wg0.conf
systemctl enable --now wg-quick@wg0
wg show                      # expect handshake with the hub
ping -c1 10.10.0.1           # hub

Step 3: Verify mesh reach

Once at least one venue peer is installed by the partner:

ping -c1 10.10.2.1                                   # cloud-seven MikroTik (WG side)
curl -sk https://10.10.2.1/rest/system/resource      # MikroTik REST over WG

If hydraneck can ping the venue but the venue cannot ping hydraneck, the issue is a missing MikroTik route — MikroTik does not auto-derive routes from WireGuard AllowedIPs. Citymesh must add /ip route add dst-address=10.10.0.0/16 gateway=<wg-interface> manually. This is always the Citymesh side; hydraneck and the hub are open to all wg0→wg0 traffic.

Per-venue MikroTik configuration

Once HydraNeck has mesh reach, point per-venue MikroTik credentials at the WG-side address (NOT a public WAN IP). Edit /root/.hydraneck/config.yaml.

Before doing so, confirm with the partner that HydraNeck's WG address is allowlisted in the MikroTik firewall for inbound TCP 443 (REST) and optionally TCP 8729 (legacy binary). The hub does pure routing with no NAT — the MikroTik sees HydraNeck's WG IP (10.10.100.14 for the current air-hydraneck enrollment) as the source, not the hub IP. No public internet IP needs to be whitelisted.

venues:
  cloud-seven:
    mikrotik:
      host: 10.10.2.1            # WG tunnel address, not public WAN
      user: <readonly-user-from-partner>
      pass: <password-from-partner>
      transport: rest             # REST on :443 — preferred
      # transport: legacy        # legacy binary on :8729 — fallback
  rupelmonde:
    mikrotik:
      host: 10.10.3.1
      user: <readonly>
      pass: <password>
      transport: rest

The exact WG addresses (10.10.2.1, 10.10.3.1, …) are whatever hydraguard apply assigned — confirm via hydraguard status on the hub or the venue's row in mesh.yaml.

Self-signed TLS certs on RouterOS are the normal posture; the REST client in pkg/mikrotik/rest handles this — no extra configuration required on the consumer side.

After updating the config, restart hydraneck:

systemctl restart hydraneck
hydraneck scan cloud-seven       # expect non-empty Clients() and Bandwidth()

Graceful degradation

If a venue's partner peer isn't installed yet, HydraNeck sees only the hub and any already-installed peers. Scans for the missing venue return connect-refused; the venue's tile in the admin dashboard shows offline; no crash, no cascading failures. Existing healthy venues are unaffected.

Multi-district future

Today there is one district (Brussels). When a second district opens, two options:

No decision required until a second district is real. The single-hydraneck path is simpler and works fine if interface counts stay manageable.

Verification

End-to-end smoke after a fresh enrollment:

  1. ssh root@hydraneck.experiencenet.com wg show — handshake with the hub.
  2. ping -c1 10.10.0.1 from the hydraneck server.
  3. curl -sk https://<venue-WG-IP>/rest/system/resource — RouterOS responds with system info JSON.
  4. hydraneck scan <venue>clients and bandwidth populated.
  5. Web UI /admin/venues/<venue> — correlation table populated, no red rows for known bodies.

See also