Minecraft Server From Scratch (Proxmox LXC, Docker Compose + itzg)

#minecraft #server #docker #docker-compose #lxc #itzg

Table of Contents

Just a smol lil guide for myself to set up a minecraft server from scratch, as I cannot count the number of times I’ve had to re-learn this when I migrate from server to server.

I’ve opted for services that should (for the most part) be supported long-term and are relatively secure & lightweight. However, as any good netizen should do, please take my advice with a granule of sugar

- Set up LXC Container in Proxmox

  1. Create new container in proxmox using the Ubuntu 24.04 LXC image (or your desired flavour, noting commands may differ slightly depending on package managers) - allocating at least 4GB RAM & 2-4 CPU cores to the machine.
  2. Once logged in, create a sudo-enabled user with: adduser myuser Set the password, then: usermod -aG sudo myuser su myuser
  3. Harden SSH - ensuring the following values are changed & set within /etc/sshd_config.
Port 22
PermitRootLogin no
MaxAuthTries 4
MaxSessions 2

PubkeyAuthentication yes

PasswordAuthentication no
PermitEmptyPasswords no

KbdInteractiveAuthentication no

UsePAM no

X11Forwarding no
PrintMotd no
ClientAliveInterval 600
ClientAliveCountMax 2
  1. Add your local machine’s ed25519_pub key to the ~/.ssh/authorized_keys file (creating it, if it doesn’t exist). This will allow key-based login for user myuser.

Be careful not to lock yourself out here, test with password based login first! For example, by setting PasswordAuthentication yes and logging in, before changing it to PasswordAuthentication no.

  1. Ensure DNS is setup properly - check /etc/resolv.conf. Basic internet functionality can be tested & achieved by having the line nameserver 8.8.8.8, but configure to your use case.

  2. Login from local machine with ssh [email protected]. Test your sudo privileges with sudo ls /root.

  3. Lock root account with sudo passwd root -l.

  4. Run sudo apt update && sudo apt upgrade -y.

  5. Find the current IP with ip -a (typically on the eth interface) and set it as static (in proxmox and/or on your router).

- Install Docker (Compose) & itzg Minecraft Server

  1. Install Docker Engine - follow steps (distro-specific) here, as you will need to configure your package repository properly.

  2. Install Docker Compose - following steps here. sudo apt install docker-compose worked for me.

  3. Make a new directory for the Minecraft server to sit in: ~/minecraft.

  4. Inside, create a docker-compose.yml, generated with something like setupmc.com to specify server version, plugins, etc.

My example docker-compose.yml file is below (for a 1.18 server, replacing Timezone (TZ) accordingly):

services:
	mc:    
		image: itzg/minecraft-server:java17    
		tty: true    
		stdin_open: true    
		ports:       
			- "25565:25565"     
		environment:       
			EULA: "TRUE"       
			TYPE: "PAPER"       
			VERSION: "1.18"       
			PAPER_CHANNEL: "experimental"       
			MEMORY: "4096M"       
			MOTD: "welcome, traveller, to an older time...
			USE_AIKAR_FLAGS: "true"       
			TZ: "[YOUR-TIMEZONE]"     
		volumes:       
			- "./data:/data"
  1. Start the container from within the same directory as docker-compose.yml with sudo docker compose up -d. After the image is finished being pulled from the itzg minecraft server repo, watch the logs as the server starts with sudo docker compose logs -f.

  2. If you get an error message about the “class file version” after starting the server, check this table to see which Java version corresponds to the respective class file version. Then adjust the Docker image tag in the setupmc.com](https://setupmc.com/java-server/) configurator accordingly.

  3. To stop the server, run sudo docker compose down.

  4. To migrate a world save file over (if applicable), copy the following files (at minimum) over from your old server (using something like scp, or via a GUI if you install something like webmin):

    • server.properties
    • /world
    • /world_the_nether (if exists)
    • /world_the_end (if exists)
    • whitelist.json (if applicable)

Ensure to tweak server-specific configurations within server.properties if needed!

  1. As you’re running through docker, it should handle the local network ports on the lxc for you nicely (if on a fresh linux install). Also, before I continue, it would be remiss of me to exclude the obligatory ***do this so at your own risk, and please consider the below server hardening methods:

  2. With that out of the way, now time to open up a port on your local router/modem. For me, I’ve opted for a little “security through obscurity” (a contentious topic, but given my threat model) by mapping my router’s external port, 43456 to the default minecraft listening port (25565 - specified in server.properties) on my lxc machine:

    Additionally, I’ve set up a DNS A record for the domain I own to point at my router’s public IP, so I can access my server (and share it) with my-domain:43456.

Now, you should be all up and running! :3

- For any further troubleshooting