Game Hosting home

Valheim Docker server: a practical setup and restore guide

Run a Valheim Docker server with persistent volumes, a tested world restore, and clear limits for ports, updates, and backups.

Difficulty
HardDifficulty Hard
Time to do
45 min
Reading
9 min
Updated
By
Game Hosting team

You will need

  • A Docker Engine host with a compatible linux/amd64 runtime
  • Permission to create containers, named volumes, and UDP firewall rules
  • A Valheim world name and a separate place to keep recovery copies

Docker can keep a Valheim server’s configuration and world separate from the container that runs the game. That only works when the image mounts the right data path and you preserve its volumes during replacement. This walkthrough uses the maintained community-valheim-tools/valheim-server image, a pinned image digest, and Docker named volumes. We tested the setup by loading a copied Valheim 1.0.17 world, recreating its container, and restoring the copy into a separate volume. No game client joined or made a change, so the test proves server-side loading and storage behavior, not player access or recovery of gameplay progress.

If you would rather not maintain a Docker host, our recommended Valheim hosting from Game Hosting includes a game panel and free backups with its monthly plans. Docker remains a useful route when you want to manage the host, image, and storage yourself.

If you are still choosing how to run a dedicated server, compare this with the other Valheim server routes before you create a host to maintain.

Check the Docker host before choosing an image#

Choose an image whose maintainer publishes its storage paths, environment variables, update behavior, and supported architecture. The image used here is ghcr.io/community-valheim-tools/valheim-server. On October 11, 2026, its published multi-platform index included linux/amd64; Docker selected that platform on our test host. Do not assume an ARM NAS or single-board computer can run the same image natively. Confirm the current manifest for your host before installing it.

The example below pins the image index digest we tested. That keeps Docker from silently choosing a different image build when you recreate the container. It does not freeze the Valheim server files that the image downloads from Steam into /opt/valheim; treat the container image and game server update as separate things.

This is a single-server example. Give the machine a stable address, leave enough free disk for the image and game files, and decide who will maintain it. Docker handles packaging; you still own host updates, network rules, passwords, and world recovery.

Set up a Valheim Docker server with persistent volumes#

The maintainer documents two important paths: /config stores world and server configuration, while /opt/valheim can keep downloaded server files and Steam’s update cache. The Compose file gives each path a named volume. Docker manages those volumes beyond the lifetime of one container.

For the BepInEx plugin paths on this image and a check that they survive container recreation, see the guide to Valheim mods on Linux or Docker.

This walkthrough covers the tested generic setup; for the maintained community image’s current variable names, schedules and hooks, read the image-specific Valheim Docker settings reference.

Create a working directory and an environment file. Keep .env private: it holds the server password, and it should not go into a shared repository or public backup.

bash
mkdir -p "$HOME/valheim-docker"
cd "$HOME/valheim-docker"
umask 077
cat > .env <<'EOF'
SERVER_NAME=My Valheim World
WORLD_NAME=MyWorld
SERVER_PASS=replace-with-a-long-unique-password
EOF

Create compose.yaml:

yaml
services:
  valheim:
    image: ghcr.io/community-valheim-tools/valheim-server@sha256:f3ccde9a4e292663cf5096d502ff33cc9617015f6d70b6a9ca0968543f165ef2
    container_name: valheim-server
    restart: unless-stopped
    stop_grace_period: 120s
    ports:
      - "2456-2457:2456-2457/udp"
    volumes:
      - valheim_config:/config
      - valheim_install:/opt/valheim
    environment:
      SERVER_NAME: "${SERVER_NAME}"
      WORLD_NAME: "${WORLD_NAME}"
      SERVER_PASS: "${SERVER_PASS}"
      SERVER_PORT: "2456"
      SERVER_PUBLIC: "false"
      CROSSPLAY: "false"

volumes:
  valheim_config:
    name: valheim_config
  valheim_install:
    name: valheim_install

The fixed volume names make the later copy commands explicit. If you run several Valheim stacks on one Docker host, choose unique volume names for each world. The example selects the Steam backend and keeps the server out of the public browser list. The password in the maintainer’s current image must be at least five characters; use a longer unique value in practice.

Start the server and confirm it loaded the intended world#

Check Compose’s resolved configuration before starting. Then launch the service and follow its logs until Valheim reports that the server is connected. First startup downloads the dedicated server, so it can take longer than a container restart.

  1. Validate the Compose file

    bash
    docker compose config

    Resolve missing variables, YAML errors, or an unexpected image before creating the service. Keep the rendered output private because it includes the password.

  2. Start the container

    bash
    docker compose up -d

    Docker creates the named volumes if they do not exist and mounts them at /config and /opt/valheim.

  3. Check startup and world selection

    bash
    docker compose logs -f valheim

    Look for the selected world name, a completed world load, and Game server connected. Press Ctrl+C to leave the log view; that does not stop the service. If the container keeps running but reports another world or no world, stop and inspect WORLD_NAME and the contents of valheim_config before inviting anyone. If the configured save still is not the one that opens, trace the actual world directory and mount before restoring files.

The readiness line means the dedicated server is listening; it does not prove a client can reach it from your network. Check the configured world explicitly:

bash
docker exec valheim-server ls -la /config/worlds_local/MyWorld

If the image reports a missing directory, check the spelling of WORLD_NAME and whether the save is in Valheim’s current worlds_local/<WorldName>/ directory. For this example, the literal check is docker exec valheim-server ls -la /config/worlds_local/MyWorld. Valheim 1.0 worlds use a directory containing several files; copying only an older .db and .fwl pair is not a complete current-format world.

Open only the ports for the backend you selected#

The Compose example publishes UDP 2456 and 2457 for the Steam backend. If friends connect from outside the Docker host’s LAN, allow those ports through the host firewall and forward the same UDP pair at the router. The container port mapping alone does not configure either device. Iron Gate’s dedicated-server manual documents the selected port plus the next one; the Steam port and crossplay guide explains how the relay changes that network step.

For cross-platform play, the image supports CROSSPLAY=true. Iron Gate says the crossplay backend uses a relay and does not need router forwarding. Change the backend intentionally, restart the container, and follow the current joining instructions for your crew’s platforms. We did not join this test server from a game client, so treat a real client join from each required platform as your own acceptance check.

Stop cleanly and keep a separate world copy#

The image’s README documents automatic backups under /config/backups by default, with an hourly schedule and three days of age retention. Those backups share the config volume with the live world. They can help with a local rollback, but they are not an independent copy; a failed disk or deleted volume can take both with it. The maintainer also warns that backups run while the server is active and can overlap a save. Read its current backup notes before changing retention or relying on an automatic snapshot.

For a simple manual copy, stop the container cleanly first. Copy the entire world directory, not selected save files, into a second volume. This example keeps that copy on the same Docker host, so move another copy to a separate device or backup service if you need protection from host loss.

bash
docker compose stop
docker volume create valheim_restore_config
docker run --rm \
  --platform linux/amd64 \
  --mount source=valheim_config,target=/source,readonly \
  --mount source=valheim_restore_config,target=/destination \
  alpine:3.22 sh -c \
  'mkdir -p /destination/worlds_local && cp -a /source/worlds_local/MyWorld /destination/worlds_local/'

The source and destination must be different volumes. Confirm that the complete MyWorld directory exists in valheim_restore_config; a successful cp message alone is not enough. For a full restore exercise, start a separate disposable container using valheim_restore_config at /config, point WORLD_NAME to MyWorld, and keep its UDP ports bound to localhost or unused test ports. Start with the same compatible server version, check that the world loads, then stop and remove only the test container. Keep the original server stopped during the exercise so the two processes cannot write to one world concurrently. Compare the source and restored directories with Docker’s lightweight helper:

bash
docker run --rm --platform linux/amd64 \
  --mount source=valheim_config,target=/source,readonly \
  --mount source=valheim_restore_config,target=/restored,readonly \
  alpine:3.22 sh -c \
  'diff -r /source/worlds_local/MyWorld /restored/worlds_local/MyWorld'

No output and exit status 0 means the files compare equal. diff here checks the copy, not whether a player can enter the world.

Here is a local-only restore container using the same image and server-install volume. The second config volume contains the copied world; the host ports 2466–2467 are loopback-only and remain distinct from the live server pair:

bash
docker run -d --name valheim-restore \
  --stop-timeout 120 \
  --publish 127.0.0.1:2466:2466/udp \
  --publish 127.0.0.1:2467:2467/udp \
  --mount source=valheim_restore_config,target=/config \
  --mount source=valheim_install,target=/opt/valheim \
  --env-file .env \
  --env SERVER_NAME='Restore test' \
  --env SERVER_PORT=2466 \
  --env SERVER_PUBLIC=false \
  ghcr.io/community-valheim-tools/valheim-server@sha256:f3ccde9a4e292663cf5096d502ff33cc9617015f6d70b6a9ca0968543f165ef2

Check docker logs valheim-restore for ZNet.LoadWorld: MyWorld and Game server connected. The official manual identifies that message as ready to accept connections; it is not an external-player join test. Stop the restore service cleanly. Remove the restore container and volume only after you have recorded the result.

Our test followed that sequence with a copied empty 1.0.17 world. The original container shut down cleanly, the replacement loaded the same named-volume world, and a new container loaded a copy from a separate config volume. Five source and restore file hashes matched. That confirms a headless server can load those copies; there was no player-made progress to recover, and no client joined. Add a second device or backup service if you also need protection from loss of the Docker host.

Replace the container without replacing the world#

The container is disposable; valheim_config and valheim_install are not. When you deliberately replace the container, keep the same volume mounts and verify the selected image and server version before reopening play. A changed digest may change the container software, while the image’s updater may separately download a different Valheim server build into the install volume.

Use a short maintenance window. Stop the current server, confirm it shut down cleanly, make a separate world copy, then recreate the container while leaving named volumes in place:

bash
docker compose stop
docker compose rm -f valheim
docker compose up -d valheim
docker compose logs -f valheim

Do not use docker compose down -v in this sequence. After recreation, check that the logs name the expected world and reach Game server connected; then join with an authorized client and confirm the crew’s actual platforms before reopening the campaign. If the world is missing, stop the new process before restoring the copied directory. Never point two running servers at the same writable world volume.

If you prefer full control of the Linux host and its volumes, the Docker route works—keep its update, independent-copy, and restore checks on your own schedule.

Quest complete

Before you invite your friends, check that the intended world loaded and that each player can connect. If those checks pass, you're ready for a session; if you'd rather not keep a PC on, that's what we're here for.

Quick answers

Will deleting a Docker container delete my Valheim world?

Not when your world lives in a persistent volume mounted at the image’s documented `/config` path. Removing that volume does delete the data, so check the Compose command and keep a separate copy before cleanup.

Does Docker remove the need for Valheim backups?

No. Docker volumes keep data outside a container, but they are still on the Docker host. Keep a separate copy and rehearse restoring it into an isolated server.

Does a Valheim crossplay server in Docker need router port forwarding?

Iron Gate’s manual says the crossplay relay does not require router forwarding. The Steam backend uses the configured UDP port and the next port, usually 2456–2457; check the backend you selected.