tModLoader server with a web dashboard, Workshop mods, world management, and backups. AMD64/ARM64.
1.1K
Updated 2026-09-24 05:02 UTC · Refreshed hourly · Metric definitions
Run a modded Terraria server in Docker, with a built-in web dashboard for managing worlds, Workshop mods, players, and backups. Keep your server's data across container updates and manage it from your browser or Docker Compose.
This independently maintained project has its own features, fixes, and releases. It is not affiliated with Re-Logic or the tModLoader team.
Container images · Docker Hub · Releases · Changelog
Full changelog · All releases and preview notes
The release workflow also supports publishing verified images to Docker Hub. See Docker Hub publishing setup and retries.
| Tag | Behavior |
|---|---|
3.0.1 | Fixed stable release; matches the GitHub Release tag |
3.0.1-preview | Fixed preview release; marked as a GitHub prerelease |
latest | Follow the latest tested stable build |
preview | Follow the latest tested preview build |
Release notes identify the tModLoader version bundled as the initial runtime.
Numbered image tags are never overwritten. By default, the server can update its
persistent runtime at startup independently of the image; use TMOD_AUTO_UPDATE=0
to retain the selected runtime. Container releases still deliver dashboard,
security, system-library and downloader updates.
Container images publish when VERSION changes on master, or through a manual
workflow run. New upstream tModLoader releases are handled by the runtime updater;
they do not trigger scheduled image builds. Container releases still bundle an
initial stable or preview runtime.
With TMOD_AUTO_UPDATE=1, startup checks the image's stable or preview channel
for supported Terraria 1.4.4 releases. Set TMOD_UPDATE_CHANNEL to override the
channel, or TMOD_UPDATE_VERSION to pin an exact supported release. Pins may
advance the runtime; downgrades require a matching data checkpoint. Major
Terraria branch migrations are blocked until explicitly supported.
Downloads are cached in /data/.tmod-control/updates, including the original
runtime and its native .NET installation. Workshop updates happen in a separate
copy of the game data. The candidate must load every enabled mod and its
required dependencies, load or generate a copied world, reach server readiness,
and exit cleanly. Only then are the runtime and staged mods selected. The live
world is not replaced with the test copy. Startup checks cannot prove every mod
works throughout gameplay.
If download or compatibility checks fail, the installed runtime and live mods are retained together. The dashboard shows the available version, blocked-update reason, and Workshop/compatibility diagnostics. If live startup then fails, the pre-update runtime and world/mod checkpoint are restored automatically. Custom server configurations are not automatically updated because their external paths cannot be safely redirected for the compatibility test.
The overview checks for new releases in the background (cached for six hours; failed checks retry after fifteen minutes). Check for updates refreshes the notice, rate-limited to once per minute; it does not install anything. Startup is the installation point. Restart game and apply updates runs the same checks from the dashboard without restarting the container; it disconnects players and leaves saved drafts unapplied. Restore previous runtime and data queues recovery for the next game restart and requires confirmation: worlds, mods, mod configs and saved settings revert to the checkpoint. Current data is retained in another checkpoint until recovery passes its health check; both recovery copies are then deleted automatically. Failed recovery retains them. Credentials are preserved, and automatic updates are held until Restart game and apply updates is selected. Queued recovery can be performed with Restart game and restore checkpoint while the dashboard remains available. Compose values are not part of a checkpoint.
Staging needs free space for three copies of game data plus
TMOD_UPDATE_MIN_FREE_MB (default 1024 MiB). Runtime caches and update checkpoints
are excluded from ordinary backup archives and retained on the data volume;
backups record the actual selected runtime for compatibility checks. Keep an
independent backup of this volume for disaster recovery. Existing dashboard
Apply operations still intentionally refresh the selected Workshop mods;
the automatic compatibility gate applies to startup updates.
Set TMOD_UPDATE_TEST_TIMEOUT above the default 600 seconds if a large modded
world needs longer to test or start. A timeout blocks the update rather than
assuming compatibility.
For Drydock, use a numbered stable tag and opt into version updates with this Compose label (the double dollar sign escapes Compose interpolation):
labels:
- 'dd.tag.include=^[0-9]+\.[0-9]+\.[0-9]+$$'
This restricts updates to stable container versions. The image's source label points to this repository, where matching release tags provide release notes. See Drydock's getting started guide.
Captured from the current 3.2.0 dashboard interface with demonstration server data. Workshop cards show real public Steam titles and artwork in an illustrative results list. Select a screenshot to view it full size.
| Overview | Worlds |
|---|---|
![]() | ![]() |
| Health, players, settings, and backup status | World details, uptime, creation, and Journey permissions |
| Backups & recovery | Steam Workshop search |
|---|---|
![]() | ![]() |
| Archive contents, verification, and compatibility | Search controls, Steam preview artwork, and mod selection |
Enter a Steam API key on the Workshop page to unlock search and dependency checks. After validation, the key field is hidden; use Replace API key to change it. Adding a mod checks nested Workshop requirements and lists missing items in an Add / Cancel dialog before saving the selection as a draft. Client-only dependencies are excluded. Apply the draft when ready to restart. Importing a Workshop URL or ID works without a key; adding without a key requires acknowledging that dependencies have not been checked. Checks use Steam's declared requirements, so they cannot detect undeclared dependencies or version conflicts.
Keys entered on the page are encrypted in
/data/.tmod-control/workshop.key, with Linux permissions 0600. Authenticated
Workshop requests derive an encryption key from your admin token using Argon2id
and a random salt, and use Fernet authenticated encryption. The admin token and
derived encryption key are never saved with the ciphertext. Use a strong, unique
admin token: the protection of the encrypted Steam key depends on its strength.
Changing or resetting the admin token requires re-entering the Steam API key.
Previously saved plaintext keys are encrypted on the next authenticated settings
or Workshop request. The key is never returned by the dashboard API or included
in container backup archives. Keep the data volume to preserve it across
recreations; re-enter it when moving to a fresh volume.
An optional mounted TMOD_WORKSHOP_KEY_FILE remains an externally managed
plaintext input; a key saved on the page takes precedence. Use HTTPS for
administration over untrusted networks.
You need Docker Engine with Compose or Docker Desktop, a 64-bit AMD64 or ARM64 Linux container environment, and enough memory and disk space for your mod pack. Players need tModLoader clients compatible with the server's version and mods.
Clone this repository, or download docker-compose.yml and .env.example into the same folder.
git clone https://github.com/Crosis47/tmodloader.git
cd tmodloader
Copy .env.example to .env:
cp .env.example .env
On Windows PowerShell, use Copy-Item .env.example .env instead.
Open .env. For browser-based configuration, set:
TMOD_CONFIG_SOURCE=web
This enables settings edits, world selection, and loading profiles and playthroughs in the dashboard. Environment values seed the initial settings; afterward, saved web values take precedence. Save changes in the dashboard, then use Review & apply to apply them and restart the game.
Leave TMOD_CONFIG_SOURCE=env to manage settings through .env instead. The
dashboard still provides monitoring, console, and backup controls. Set
TMOD_WEB_ENABLED=0 if you want to run without the dashboard or its setup step.
Review the essential settings below before starting, particularly the game password, world name, and mods.
docker compose pull
docker compose up -d
docker compose logs --tail=100 --follow tmodloader
With the dashboard enabled, the game waits for first-run admin setup:
http://SERVER-IP:8080 from your home network, or
http://localhost:8080 on the Docker host.The container saves a hashed credential in the persistent data directory and
continues startup automatically. First-time mod downloads and world generation
can take several minutes. Press Ctrl+C to stop following logs without stopping
the server.
HTTP works for clients in 10.0.0.0/8, 172.16.0.0/12, and 192.168.0.0/16
(RFC 1918), plus loopback. Other sources, including non-loopback IPv6, require
HTTPS for setup and all dashboard access. HTTP traffic is unencrypted; use it
only on a trusted network. The server checks the client source IP, not the URL.
Leave TMOD_WEB_ORIGIN empty when opening the server IP. For a hostname, set it
to the exact browser origin. For HTTPS through a reverse proxy, also set
TMOD_WEB_TRUSTED_PROXY to that proxy's single IP as seen by the container.
The proxy must preserve Host and overwrite X-Forwarded-For with the actual
single client IP and X-Forwarded-Proto with http or https. Multi-proxy header
chains are rejected. Restrict backend access to the proxy when publishing it.
Docker forwarding or another gateway can hide the original source IP behind a private address. This rule can only classify the IP the container actually sees; do not directly port-forward the HTTP dashboard to the internet. Use the HTTPS proxy with the trusted-proxy setting to preserve the original client identity.
Check readiness in the dashboard or run:
docker compose ps
Once the server is healthy, connect from tModLoader to your Docker host's address
on port 7777 (or your chosen TMOD_HOST_PORT). Allow that TCP port through
the host firewall and forward it on your router if players connect over the internet.
The commented .env.example contains the full list of options. These are the main values to review for a new server:
| Setting | Purpose / default |
|---|---|
TMOD_CONFIG_SOURCE | env for .env settings; web for dashboard-managed settings. |
TMOD_WEB_ENABLED | 1 enables the dashboard; 0 disables it and skips admin setup. |
TMOD_PASS | Game password, separate from the admin token. Empty means no game password. |
TMOD_HOST_PORT | Port players connect to; defaults to 7777. |
TMOD_WORLDNAME | Selects a saved world or creates it if missing; defaults to Docker. |
TMOD_WORLDSIZE | New world size: 1 small, 2 medium, 3 large (default). |
TMOD_DIFFICULTY | New world difficulty: 0 Classic, 1 Expert (default), 2 Master, 3 Journey. |
TMOD_WORLDEVIL | New world evil: random (default), corruption, or crimson. |
TMOD_MODS | Comma-separated Workshop mod IDs and collection:ID entries; empty by default. |
TMOD_BACKUP_INTERVAL | Minutes between backups; 0 disables scheduling, 1440 means daily. |
World creation and Journey permissions live on Worlds. New World opens the creation form. For saved Journey worlds, Server Journey defaults sets shared permissions, and Set Journey permissions on a world lets you inherit those values or save an override. Controls are hidden for non-Journey worlds and unreadable world types. Existing global permissions seed the initial server defaults.
Saving permissions does not change the running game; they take effect when that world next starts. Review & apply stages the selected world and opens the usual restart confirmation. Per-world overrides survive switching worlds and container restarts. Applying a playthrough's different Journey snapshot records it as that world's override. Server defaults remain unchanged.
Review saved changes opens a running-versus-saved comparison, including fields edited outside Configuration. A draft identical to the running settings does not trigger the saved-changes reminder. Unsaved form edits are not part of this review.
Select a name in Saved worlds to expand details from its last save: dimensions, difficulty, evil, seed, creation date, Hardmode status, special seeds, spawn and dungeon coordinates, and file sizes. Expanded entries remain open across refreshes. The current world has a status badge; other worlds have a Switch button. Current session uptime starts when the world finishes loading and resets on a game restart or world switch. Total uptime accumulates loaded time across sessions and persists with the world data. Tracking begins with this feature; earlier sessions are not included. Totals are checkpointed every five seconds and on normal shutdown; an abrupt kill can lose up to five seconds. Inactive worlds display Not active for their current session and retain their total. This is not player playtime. Metadata currently supports world formats 194–279; unreadable or unsupported headers show an explanation while file details and existing world-selection controls remain available.
World generation settings only affect new worlds. Choose an unused world name to generate a different world. Profiles and playthroughs do not archive world files or pin mod versions; keep backups before changing a world's mods.
After editing .env, recreate the container with docker compose up -d.
In web mode, change saved settings in the dashboard. Docker ports, mounts,
credentials, and configuration mode remain managed outside the dashboard.
If you explicitly set TMOD_WEB_ORIGIN, update its port when changing the dashboard port.
The supplied Compose file keeps persistent files beside it:
| Host folder | Contents |
|---|---|
./data | Worlds, mods, mod configuration, dashboard settings, and logs. |
./backups | Backup archives created by the container. |
Startup prepares these directories for the runtime user, including changing
Linux host ownership to UID/GID 1000:1000. Use dedicated, writable local folders.
Keep both folders when replacing the container.
Use Backups & recovery in the dashboard for manual backups and restoration.
Scheduled backups are off by default. Keep a separate copy of your .env and
any external secret or custom configuration files; container backups do not
include them. Retain the original image version for recovery, since restores
check the container build that created the archive.
Expand an archive row to see its backup date, last running world (when recorded), world files, enabled mods, Workshop selections, sizes, and included settings/logs. Inspect & verify checks the actual archive and fills in details for older backups. A saved world selection in an old backup is labeled as such; it is not proof that that world was running.
When an inspected backup uses the same tModLoader release but a different container build, Prepare for Running Container Version creates a verified copy for the current build. The original and world data remain unchanged. After inspection, compatible archives show Restore this backup in their expanded details. This opens a review popup that verifies the archive and available space before you confirm the restore. Different or unknown game releases cannot be converted automatically: retain the matching original image. Normal retention preserves backups from other container builds, so these preserved copies may require additional storage.
For startup or connection problems, begin with docker compose ps and
docker compose logs --tail=200 tmodloader. Include relevant logs with an
issue report, removing private
information first.
Built on tModLoader for Terraria. Inspired by JACOBSMILE/tmodloader1.4. Thanks also to ldericher, rfvgyhn, guillheu, and FlorentLM for their earlier work.
Container code and scripts are distributed under LICENSE.md. Terraria, tModLoader, and bundled third-party tools retain their respective licenses.
The update card offers an opt-in Announce new tModLoader versions in game chat setting. It saves immediately without a restart, defaults to off, and sends one announcement per newly detected release while the game is healthy. The administration service checks in the background even without an open dashboard, using the existing release-check cache. Disabling and re-enabling the option does not repeat an already announced release.
Content type
Image
Digest
sha256:f4bd42b6e…
Size
327.3 MB
Last updated
2 days ago
docker pull crosis47/tmodloader