78 lines
3.1 KiB
Markdown
78 lines
3.1 KiB
Markdown
# Ulicraft Server
|
||
|
||
Self-hosted modded Minecraft (NeoForge 1.21.1) for a LAN party, designed to run
|
||
**fully offline**. Self-hosted auth/skins (Drasl), a packwiz modpack, a guest
|
||
landing page, and a transparent mirror of Mojang/launcher assets so guest
|
||
laptops need no internet.
|
||
|
||
## Stack
|
||
|
||
| Service | Image | Role |
|
||
|---|---|---|
|
||
| `minecraft` | itzg/minecraft-server | NeoForge 1.21.1 server, `:25565` |
|
||
| `drasl` | unmojang/drasl | Yggdrasil auth + skins (password login) |
|
||
| `caddy` | caddy:alpine | ingress: landing page, auth/packwiz proxy, asset mirror |
|
||
| `dnsmasq` | jpillora/dnsmasq | LAN DNS `*.ulicraft.local` + Minecraft SRV |
|
||
| `mc-backup` | itzg/mc-backup | world backups every 6h via RCON |
|
||
|
||
Everything keys off two vars in `.env`: `BASE_DOMAIN` (default `ulicraft.local`)
|
||
and `HOST_LAN_IP`. Services are subdomains: `auth.`, `packwiz.`, plus the apex
|
||
landing page.
|
||
|
||
## Prerequisites
|
||
|
||
Docker + Docker Compose, and for prep: `pnpm`, `packwiz`, `jq`, `curl`,
|
||
`envsubst`, `sha1sum`.
|
||
|
||
## Setup
|
||
|
||
```sh
|
||
cp .env.example .env # set BASE_DOMAIN, HOST_LAN_IP, RCON_PASSWORD
|
||
```
|
||
|
||
Point guest laptops' DNS at `HOST_LAN_IP` (resolves `*.ulicraft.local`). On the
|
||
Docker host, free port 53 if `systemd-resolved` holds it (dnsmasq binds the LAN
|
||
IP only).
|
||
|
||
## Launch
|
||
|
||
```sh
|
||
tooling/build-stack.sh --prep # ONLINE, run once: render configs, build
|
||
# landing, mirror mods+assets, fetch
|
||
# launcher, pre-bake the server volume
|
||
|
||
tooling/build-stack.sh --up [mode] # bring the stack up
|
||
# core base only (no static site, no mirror)
|
||
# static + apex landing page + launcher downloads
|
||
# mirror + full air-gap asset mirror (HTTPS :443)
|
||
# full static + mirror (default)
|
||
```
|
||
|
||
Down: `docker compose -f docker-compose.yml -f docker-compose.static.yml -f docker-compose.mirror.yml down`
|
||
|
||
## Join (guests)
|
||
|
||
1. Open `http://ulicraft.local`, download FjordLauncherUnlocked for your OS.
|
||
2. Add an **authlib-injector** account, URL `http://auth.ulicraft.local/authlib-injector`
|
||
(register/login at `http://auth.ulicraft.local`).
|
||
3. (Air-gap) Trust the Caddy root CA; in Settings → APIs set **Assets Server**
|
||
to the mirror if not using DNS spoofing.
|
||
4. Import the pack: `http://packwiz.ulicraft.local/pack.toml`.
|
||
5. Connect to **`mc.ulicraft.local`** (no port — SRV record).
|
||
|
||
## Layout
|
||
|
||
```
|
||
docker-compose.yml + .static.yml + .mirror.yml # core + optional layers
|
||
caddy/Caddyfile + conf.d/*.caddy # ingress vhost snippets
|
||
drasl/config/config.toml.tmpl # auth config (rendered)
|
||
dnsmasq/dnsmasq.conf.tmpl # LAN DNS + SRV (rendered)
|
||
pack/ # packwiz modpack source
|
||
landing/ # Astro site → www/
|
||
tooling/ # build-stack + render/mirror/fetch scripts
|
||
mirror/ # vendored jars + launcher + asset mirror (gitignored)
|
||
plan/ # full design docs (00–12)
|
||
```
|
||
|
||
See `plan/00-overview.md` for the full design.
|