UGREEN NAS Stack
Consolidated compose stack for the UGREEN NAS (UGREEN-NAS-MKP, 192.168.1.29, user
unknown224).
Migrated from twelve independent compose projects that lived in
/volume1/docker-ssd/<app>/ and /volume2/docker/<app>/, each with its own
docker-compose.yaml and hardcoded secrets.
Layout
Section titled “Layout”| Path | Contents |
|---|---|
docker-compose.yml | include: list — the only file compose is invoked on |
host/arcane.yaml | Arcane agent, extends ../../arcane/arcane-agent.yaml |
host/deunhealth.yaml | Watchdog restarting unhealthy gluetun-namespace sharers |
apps/<name>/<name>.yaml | One file per application |
dozzle-agent comes from the shared ../dozzle/dozzle-agent.yaml.
Services
Section titled “Services”| Service | Port(s) | Data location |
|---|---|---|
gluetun | 21287, 21265, 6881-6882, 21478 | /home/unknown224/Apps/gluetun |
gluetun-webui | 65258 | — |
qbittorrent1 | via gluetun (21287) | /volume1/docker-ssd/qbittorrent/appdata |
rustatio | via gluetun (21478) | volume rustatio_data |
qbitwebui | 26610 | /volume1/docker-ssd/qbitwebui/data |
qui | 7476 | /volume1/docker-ssd/qui-bittorrent/qui |
anibridge | 4848 | /volume1/docker-ssd/anibridge/data |
metube | 8081 | /volume2/metube/{downloads,audio-downloads} |
speedtest-tracker | 8899, 8793 | /volume1/docker-ssd/speedtest-tracker/config |
upsnap | host network | /volume1/docker-ssd/upsnap/data |
dozzle-agent | 7007 | — |
arcane-agent | 3553 | volume arcane-agent-data |
deunhealth | none | — |
backup2 | none | /volume2/docker-apps-backup (archives) |
Registry
Section titled “Registry”Every image is pulled through the internal Harbor at harbor.toolsera.lan, using the
proxy-cache project that matches its upstream registry:
| Upstream | Harbor project |
|---|---|
| Docker Hub | docker_proxy_cache |
ghcr.io | ghcr_proxy_cache |
lscr.io | lscr_proxy_cache |
The registry host is stripped and the rest of the path is preserved, e.g.
ghcr.io/autobrr/qui:latest becomes
harbor.toolsera.lan/ghcr_proxy_cache/autobrr/qui:latest.
Harbor requires authentication, which the Docker daemon holds as root — so
docker manifest inspect as unknown224 fails on the CA file’s permissions while daemon
pulls work fine.
Conventions in this stack
Section titled “Conventions in this stack”- No secret has a value here. Every credential is a
${VAR}placeholder documented in.env.example. - Bind mounts are absolute. A relative
./datawould resolve against this project directory rather than the app’s original one, silently repointing it at an empty directory. network_mode: service:gluetunonqbittorrentandrustatio, gated behinddepends_on: condition: service_healthy, with orphan-detecting healthchecks and thedeunhealthwatchdog — a gluetun restart otherwise strands both in a dead network namespace. Seeapps/qbittorrent/README.md.- gluetun’s control server uses apikey auth, passed as valid JSON in
HTTP_CONTROL_SERVER_AUTH_DEFAULT_ROLE. Anything polling:8000without the key gets 401 —gluetun-webuialready sends it.
Not migrated
Section titled “Not migrated”firefox lives at /volume2/@appstore/com.ugreen.docker.firefox/ and is managed by the
UGREEN app store, which owns its lifecycle and rewrites its compose file. Bringing it
into this stack would fight the appliance. Left in place.
watchtower and portainer_agent are running on the NAS but are deliberately not part
of this stack. They stay under whatever manages them today.
Cutting over from the old projects (one-time)
Section titled “Cutting over from the old projects (one-time)”- Rotate every secret — the old compose files held the Arcane token, VPN credentials,
gluetun API key, qbitwebui encryption key and the speedtest-tracker
APP_KEYin plaintext on disk. - Stop the old projects first. Container names collide.
- Named volumes are renamed by the project switch (
rustatio_rustatio_data→ugreen-nas_rustatio_data, and the same for the Arcane agent’s), so both start empty. Copy the old volumes across first if that state matters; the agent needs re-pairing either way. - Check the Arcane manager URL — the shared
arcane/arcane-agent.yamland the NAS agent point at different addresses; one is stale.
Running
Section titled “Running”cd /volume1/docker-ssd/infrastructure-toolkit/docker-compose-apps/ugreen-nasbws run --access-token "$BWS_ACCESS_TOKEN" -- docker compose up -dFootnotes
Section titled “Footnotes”-
https://github.com/markkpamy/infrastructure-toolkit/blob/main/docker-compose-apps/ugreen-nas/Pinned to an exact build and upgraded one-way — back up
appdatabefore any version bump. Seeapps/qbittorrent/README.md. ↩ -
https://github.com/markkpamy/infrastructure-toolkit/blob/main/docker-compose-apps/ugreen-nas/Nightly config/state backup of every app above. Adding an app to this stack means adding its data path to
apps/backup/backup.yaml— coverage is not automatic. Seeapps/backup/README.mdfor the restore procedure and the encryption-key constraint. ↩