Desert Forge IT — Arizona IT · Field-tested tools & guidesFree consult →

How to Self-Host a Minecraft Server (Paper or Spigot) on Proxmox LXC

Intermediate 30 min — Run a Paper or Spigot Minecraft server in a lightweight Proxmox container with Aikar's JVM flags.

Prerequisites

  • Proxmox VE 7+ installed and accessible via web UI
  • A Debian 12 (Bookworm) LXC template downloaded in Proxmox
  • Java 21 (we'll install Eclipse Temurin 21 in step 3)
  • Basic Linux command-line knowledge
  • Network access to port 25565 from player clients

1. Create the LXC Container

From the Proxmox shell (or SSH into your host), create a new container. Adjust the storage and ID as needed:

pct create 210 local:vztmpl/debian-12-standard_12.2-1_amd64.tar.zst \
  --hostname minecraft \
  --cores 2 \
  --memory 4096 \
  --swap 1024 \
  --rootfs local-lvm:20 \
  --net0 name=eth0,bridge=vmbr0,ip=dhcp \
  --unprivileged 1 \
  --start 1

This creates a container with 2 CPU cores, 4GB RAM, and 20GB disk. Minecraft benefits from multiple cores (GC runs on separate threads), and 4GB gives the JVM enough heap for a smooth experience with 10-20 players.

2. Install Java 21

Enter the container and install Eclipse Temurin 21 from the Adoptium apt repository:

pct enter 210
apt update && apt upgrade -y
apt install -y wget apt-transport-https gpg

Add the Adoptium GPG key and repository:

wget -qO - https://packages.adoptium.net/artifactory/api/gpg/key/public | gpg --dearmor -o /etc/apt/keyrings/adoptium.gpg

echo "deb [signed-by=/etc/apt/keyrings/adoptium.gpg] https://packages.adoptium.net/artifactory/deb bookworm main" | tee /etc/apt/sources.list.d/adoptium.list

apt update
apt install -y temurin-21-jdk

Verify the installation:

java -version
# Expected: openjdk version "21.x.x" ... Temurin

3. Download the Server Jar (Paper or Spigot)

You have two solid choices for the server software. Both run the same world files, support the same plugins (Spigot plugins run on Paper), and use the same systemd unit later in this guide — only the jar download differs.

  • Paper — high-performance fork of Spigot with significant optimizations, better default configs, and easier plugin tuning. Best for most servers. Latest stable: 1.21.11 (experimental builds for 26.1.1 available).
  • Spigot — the upstream the Bukkit ecosystem is built on. Closer to vanilla behavior and often releases for new Minecraft versions sooner than Paper. Choose this if you need the newest MC version before Paper ships a stable build. Latest stable: 26.1.2.

Pick one of the two options below. Either way you'll end up with a file at /opt/minecraft/server.jar, and the rest of the guide refers to that filename.

Option A — Paper (recommended)

Set the version you want and pull the latest build from the PaperMC API:

mkdir -p /opt/minecraft && cd /opt/minecraft

# Change this to whichever version you want (e.g. 1.21.11)
MC_VERSION=1.21.11

# Get the latest build number for that version
PAPER_BUILD=$(wget -qO - https://api.papermc.io/v2/projects/paper/versions/${MC_VERSION}/builds | \
  grep -o '"build":[0-9]*' | tail -1 | cut -d: -f2)

# Download the jar as server.jar
wget -O server.jar \
  "https://api.papermc.io/v2/projects/paper/versions/${MC_VERSION}/builds/${PAPER_BUILD}/downloads/paper-${MC_VERSION}-${PAPER_BUILD}.jar"

echo "Downloaded Paper ${MC_VERSION} build ${PAPER_BUILD}"

Option B — Spigot (newest MC versions)

Spigot doesn't distribute prebuilt jars — you compile it locally with BuildTools. This takes 3–5 minutes the first time. You'll need git installed:

apt install -y git
mkdir -p /opt/minecraft/build && cd /opt/minecraft/build

# Download BuildTools
wget -O BuildTools.jar https://hub.spigotmc.org/jenkins/job/BuildTools/lastSuccessfulBuild/artifact/target/BuildTools.jar

# Compile Spigot for the version you want (e.g. 26.1.2)
MC_VERSION=26.1.2
java -jar BuildTools.jar --rev ${MC_VERSION}

# Move the compiled jar into place as server.jar
mv spigot-${MC_VERSION}.jar /opt/minecraft/server.jar

cd /opt/minecraft
echo "Built Spigot ${MC_VERSION}"

To upgrade Spigot later, re-run BuildTools with the new version and replace server.jar. Keep the build/ directory around — subsequent compiles reuse the cached sources and finish much faster.

4. First Run & EULA

Run the server once to generate the configuration files:

cd /opt/minecraft
java -jar server.jar --nogui

The server will stop immediately and ask you to accept the Minecraft EULA. Open the generated eula.txt and set it to true:

sed -i 's/eula=false/eula=true/' /opt/minecraft/eula.txt

By changing this to true, you agree to the Minecraft End User License Agreement.

5. Configure server.properties

The first run generated server.properties. Edit it with the key settings:

cat > /opt/minecraft/server.properties << 'EOF'
# Minecraft Server Properties
server-port=25565
max-players=20
motd=A Minecraft Server
view-distance=10
simulation-distance=8
online-mode=true
difficulty=normal
gamemode=survival
level-name=world
spawn-protection=0
max-tick-time=60000
enable-command-block=true
enforce-whitelist=false
white-list=false
EOF

Key settings:

  • view-distance=10 — number of chunks sent to the client. Lower values reduce RAM and CPU usage
  • simulation-distance=8 — how far from the player entities and redstone are ticked. Keep this at or below view-distance
  • online-mode=true — verifies player accounts with Mojang. Set to false only if running behind a proxy like Velocity
  • max-players — adjust based on your RAM. With 4GB heap, 20 players is comfortable

6. JVM Flags (Aikar's Flags)

Aikar's flags are the community-standard JVM tuning for Minecraft servers. They optimize the G1 garbage collector to reduce lag spikes:

java -Xms4G -Xmx4G \
  -XX:+UseG1GC \
  -XX:+ParallelRefProcEnabled \
  -XX:MaxGCPauseMillis=200 \
  -XX:+UnlockExperimentalVMOptions \
  -XX:+DisableExplicitGC \
  -XX:+AlwaysPreTouch \
  -XX:G1NewSizePercent=30 \
  -XX:G1MaxNewSizePercent=40 \
  -XX:G1HeapRegionSize=8M \
  -XX:G1ReservePercent=20 \
  -XX:G1HeapWastePercent=5 \
  -XX:G1MixedGCCountTarget=4 \
  -XX:InitiatingHeapOccupancyPercent=15 \
  -XX:G1MixedGCLiveThresholdPercent=90 \
  -XX:G1RSetUpdatingPauseTimePercent=5 \
  -XX:SurvivorRatio=32 \
  -XX:+PerfDisableSharedMem \
  -XX:MaxTenuringThreshold=1 \
  -Dusing.aikars.flags=https://mcflags.emc.gs \
  -Daikars.new.flags=true \
  -jar server.jar --nogui

Important: -Xms and -Xmx should be the same value. This pre-allocates the full heap and avoids resize pauses. With a 4GB container, use -Xms4G -Xmx4G (leave ~512MB for the OS if your container has 4.5GB+, but 4G/4G works in a 4GB container since the OS overhead in LXC is minimal).

7. Create a systemd Service

Create a systemd unit so the server starts on boot and restarts on crash:

cat > /etc/systemd/system/minecraft.service << 'EOF'
[Unit]
Description=Minecraft Server
After=network.target

[Service]
Type=simple
User=root
WorkingDirectory=/opt/minecraft
ExecStart=/usr/bin/java \
  -Xms4G -Xmx4G \
  -XX:+UseG1GC \
  -XX:+ParallelRefProcEnabled \
  -XX:MaxGCPauseMillis=200 \
  -XX:+UnlockExperimentalVMOptions \
  -XX:+DisableExplicitGC \
  -XX:+AlwaysPreTouch \
  -XX:G1NewSizePercent=30 \
  -XX:G1MaxNewSizePercent=40 \
  -XX:G1HeapRegionSize=8M \
  -XX:G1ReservePercent=20 \
  -XX:G1HeapWastePercent=5 \
  -XX:G1MixedGCCountTarget=4 \
  -XX:InitiatingHeapOccupancyPercent=15 \
  -XX:G1MixedGCLiveThresholdPercent=90 \
  -XX:G1RSetUpdatingPauseTimePercent=5 \
  -XX:SurvivorRatio=32 \
  -XX:+PerfDisableSharedMem \
  -XX:MaxTenuringThreshold=1 \
  -Dusing.aikars.flags=https://mcflags.emc.gs \
  -Daikars.new.flags=true \
  -jar server.jar --nogui
ExecStop=/bin/kill -SIGINT $MAINPID
Restart=on-failure
RestartSec=10
StandardInput=null

[Install]
WantedBy=multi-user.target
EOF

systemctl daemon-reload
systemctl enable minecraft

8. Start and Connect

systemctl start minecraft
systemctl status minecraft

Watch the logs to confirm the server starts successfully:

journalctl -u minecraft -f

You should see output like Done (12.345s)! For help, type "help" once the server is ready. Open Minecraft Java Edition (matching the server version you installed), go to Multiplayer > Add Server, and enter your container's IP address. The default port is 25565 so you don't need to specify it.

9. Firewall Rules

If you're using Proxmox's built-in firewall or ufw, allow port 25565:

# On the Proxmox host (if using host firewall)
iptables -A INPUT -p tcp --dport 25565 -j ACCEPT

# Or if using ufw inside the container
ufw allow 25565/tcp

If your server is behind a NAT router, forward port 25565 TCP to the container's IP address.

10. Backups

Your world files live in /opt/minecraft/world/ (with world_nether/ and world_the_end/ for other dimensions). Back these up regularly. A simple cron job:

mkdir -p /opt/minecraft/backups

crontab -e
# Add this line to back up every 6 hours:
0 */6 * * * tar czf /opt/minecraft/backups/world-$(date +\%Y\%m\%d-\%H\%M).tar.gz /opt/minecraft/world/ /opt/minecraft/world_nether/ /opt/minecraft/world_the_end/

Consider stopping the server briefly before backup to avoid corrupted chunks, or use Paper's built-in save-off/save-all commands via RCON.

Want automatic backups?

Desert Forge Backup handles world file backups automatically with AES-256 encryption and zero egress fees.

Set up Backup

11. Troubleshooting

  • Wrong Java version: Modern Paper and Spigot builds require Java 21. Run java -version to verify. If you see Java 17 or lower, make sure Temurin 21 is installed and check update-alternatives --config java to select the correct version.
  • EULA not accepted: The server will refuse to start and log You need to agree to the EULA. Verify /opt/minecraft/eula.txt contains eula=true (no spaces around the equals sign).
  • Can't connect: Check the firewall, verify the container has network access (ping 8.8.8.8), and confirm the server is listening (ss -tlnp | grep 25565). Make sure your Minecraft client version matches the server version you installed.
  • Low TPS / lag spikes: Run /tps in-game or from console. If TPS is below 20, lower view-distance and simulation-distance in server.properties. Check /timings for detailed performance reports. Paper also has tuning options in config/paper-global.yml and config/paper-world-defaults.yml.
  • Out of memory: If the server crashes with OOM errors, increase the container memory in Proxmox (pct set 210 --memory 6144) and update -Xms/-Xmx in the systemd unit.
  • Server won't start after update: Check journalctl -u minecraft -e for errors. Plugin incompatibility is common after version upgrades. Remove plugins from /opt/minecraft/plugins/ one at a time to isolate the issue.
Don't want to manage all this?

Desert Forge Game Hosting gives you a Minecraft server with one click — from $2/week, no Linux required.

Get a server

← Back to all guides