Skip to main content

Minecraft Worlds

Quickstart: Bring a World Up

  1. Allocate IP, SNI Route, and DNS:

    sudo ipctl create <name> --dns
    

    (Or /data/minecraft/ipctl create <name> --dns. Allocates backend IPv6 fd77:7777:5010::1337:3c:d00d:<hex>/64, configures HAProxy SNI routing, adds <name>.drheck.dev in Unbound on danknasty, and syncs public A/AAAA records to deSEC).

  2. Configure the backend server: In your backend server's server.properties:

    server-ip=fd77:7777:5010::1337:3c:d00d:<hex>
    server-port=25565
    online-mode=true
    

    (Backend servers run stock vanilla Minecraft, online-mode=true, listening on standard port 25565).

  3. Start the server: Launch your Minecraft server on UL. It binds to its dedicated IPv6 address.

  4. Connect: Players connect using <name>.drheck.dev (standard port 25565). Microsoft account authentication takes place directly between the client and your backend server.


Quickstart: Take a World Down

  1. Stop the backend server: Run stop in the Minecraft server console or terminate its process.

  2. What Players See When Offline: HAProxy monitors backend health checks. If the server process is stopped:

    • In the Multiplayer Server List: The ping MOTD displays: [Server Name] is currently offline. Ping Luke
    When Clicking "Join Server": The client immediately disconnects with a clean red Minecraft disconnect screen: "[Server Name] is currently offline. Ping Luke" (No connection timeouts, hanging, or generic connection refused errors).

    Disable or remove router mapping & DNS:DNS (Teardown):

    • Temporary takedown (disable in router only):
      sudo ipctl route disable <name>
      
    • Complete teardown (release IP, remove HAProxy route, purge DNS):
      sudo ipctl delete <name> --dns
      

    Architecture & Design Details

    1. Unified Endpoint Model

    All public and LAN client connections resolve to the single Minecraft Router endpoint pair:

    • IPv4: 10.0.0.113
    • IPv6: fd77:7777:5010::1337:f1ac:d00d:3c

    Whether connecting via pokelovers.drheck.dev or any other server subdomain, players connect to this exact IP pair on standard port 25565.

    2. Transparent TCP SNI Handshake Routing & Offline Fallback (HAProxy)

    Rather than using an application-level proxy (which breaks vanilla Diffie-Hellman encryption and forces online-mode=false), HAProxy performs transparent pre-handshake packet inspection:

    1. HAProxy listens dual-stack on 10.0.0.113:25565 and [fd77:7777:5010::1337:f1ac:d00d:3c]:25565.
    2. When a player connects, HAProxy peeks at the initial unencrypted Minecraft handshake packet (0x00) via /etc/haproxy/minecraft.lua and extracts the requested hostname (e.g. pokelovers.drheck.dev) and connection state (Status vs Login).
    3. It looks upIf the target backend inserver /etc/haproxy/minecraft_hosts.map.
    is UP: It splices the raw TCP stream directly to that server's dedicated internal IPv6 address on port 25565. The client and backend perform native Microsoft/Mojang online-mode=true authentication directly over the spliced TCP connection. If the backend server is DOWN: HAProxy immediately handles the stream with Lua applet mc_offline which crafts and sends a valid Minecraft protocol packet:
      Status Ping: JSON MOTD with red text: <name> is currently offline. Ping Luke Login Join: Disconnect packet 0x00 rendering a red bold error screen: <name> is currently offline. Ping Luke

      3. Backend IPv6 Address Scheme

      Each backend Minecraft server is isolated on a dedicated Unique Local Address (ULA) on interface eth77 of ul:

      • Prefix: fd77:7777:5010::1337:3c:d00d:<hex>/64
      • Port: Each server binds to standard port 25565 on its assigned IPv6 address.
      • Security: Backend IPv6 addresses are completely internal and hidden behind the proxy router.

      4. Web Map (BlueMap) & Authentik Gated HTTPS

      Interactive 3D web mapping for Minecraft 26.3 is powered by BlueMap running in standalone watch mode:

      • Service: bluemap-pokelovers.service running from /data/minecraft/poke lovers/bluemap.
        • Automatically updates the rendered 3D map as chunks change in /data/minecraft/poke lovers/world.
        • Serves live map data & Server-Sent Events (SSE) updates on internal port 8100.
      • Reverse Proxy & Authentication: NGINX terminates SSL on port 443 at /etc/nginx/sites-available/pokelovers and gates access behind Authentik ForwardAuth (/outpost.goauthentik.io/auth/nginx).
        • GatedServes URL:directly at https://pokelovers.drheck.dev.
        • Unauthenticated visitors are automatically redirected to auth.drheck.dev to log in before viewing the 3D map.

      5. Network & DNS Automation (ipctl)

      The tool /data/minecraft/ipctl (symlinked in /home/luke/bin/ipctl) automates the entire lifecycle:

      • Local Network (ul): Appends or removes # <name> and Address=fd77:7777:5010::1337:3c:d00d:<hex>/64 in /etc/systemd/network/20-wired.network and triggers networkctl reload.
      • Router Configuration (ul): Updates /etc/haproxy/minecraft_hosts.map and backend stanzas (with health checks and offline responder) in /etc/haproxy/haproxy.cfg, then reloads haproxy.service.
      • SSH Key Verification: Verifies that key SHA256:7Xr0vCxgfpPhbKE3hN9fE2IC9y4x3Kj+kYmXwzgJY3s (ultra-arikui) is loaded in the agent before running remote router commands.
      • Router DNS (danknasty): When --dns is passed:
        1. Updates the git working tree at /home/luke/git/router_config/unbound.conf.
        2. Verifies syntax using doas unbound-checkconf.
        3. Deploys the configuration to /var/unbound/etc/unbound.conf.
        4. Restarts Unbound via doas rcctl restart unbound.
        5. Verifies local resolution via dig @10.0.0.1.
        6. Executes python3 /home/luke/git/router_config/dns_danger_sync.py --force to synchronize public A and AAAA records on deSEC.io.

      Backups & Disaster Recovery

      The router configurations, Lua scripts, mapping tables, network configurations, and the ipctl tool are integrated into the automated backup infrastructure:

      • Backup Script: /home/luke/git/backups/ul/scripts/backup/minecraft_router
        • Creates timestamped, ACL/xattr-preserved, par2-verified archives in /data/backups/services/current/minecraft_router/.
        • Automatically invoked during the global daily backup run (run_all_backups).
      • Restore Script: /home/luke/git/backups/ul/scripts/restore/minecraft_router [timestamp]
        • Verifies PAR2 checksums/parity.
        • Extracts configurations to / and triggers live reloads of systemd-networkd and haproxy.