Skip to content

Instantly share code, notes, and snippets.

@justincjahn
Last active January 16, 2024 20:15
Show Gist options
  • Save justincjahn/4fe65b552b0622662420928cc8ffc7c0 to your computer and use it in GitHub Desktop.
Save justincjahn/4fe65b552b0622662420928cc8ffc7c0 to your computer and use it in GitHub Desktop.
Minecraft server(s) using systemd and screen.

Install

# Install dependencies
sudo yum install -y java-1.8.0-openjdk screen

# Create a new unprivileged user for minecraft
useradd -r -m -d /opt/minecraft minecraft

# Create the directory that will house our minecraft instances
sudo su --shell /bin/bash minecraft
mkdir instances
exit

# Copy the minecraft@.service file into the correct place.
sudo vi /etc/systemd/system/minecraft@.service

# Reload systemd units
sudo systemctl daemon-reload

Provision a new server

# Sudo into the minecraft user's shell
sudo su --shell /bin/bash minecraft

# Move into the instances directory
cd instances

# Create a new folder to house your instance
mkdir server1

# Install your minecraft instance, and make sure there is a minecraft_server.jar file.
# If you use Forge servers, you can use the following:
ln -s forge*.jar minecraft_server.jar

# Start and enable (start after boot) the server.
sudo systemctl start minecraft@server1
sudo systemctl enable minecraft@server1
[Unit]
Description=Minecraft Server: %i
After=network.target
[Service]
WorkingDirectory=/opt/minecraft/instances/%i
User=minecraft
Group=minecraft
Restart=always
ExecStart=/usr/bin/screen -DmS mc-%i /usr/bin/java -Xmx2G -jar minecraft_server.jar nogui
ExecStop=/usr/bin/screen -p 0 -S mc-%i -X eval 'stuff "say SERVER SHUTTING DOWN IN 15 SECONDS..."\015'
ExecStop=/bin/sleep 5
ExecStop=/usr/bin/screen -p 0 -S mc-%i -X eval 'stuff "say SERVER SHUTTING DOWN IN 10 SECONDS..."\015'
ExecStop=/bin/sleep 5
ExecStop=/usr/bin/screen -p 0 -S mc-%i -X eval 'stuff "say SERVER SHUTTING DOWN IN 5 SECONDS..."\015'
ExecStop=/bin/sleep 5
ExecStop=/usr/bin/screen -p 0 -S mc-%i -X eval 'stuff "save-all"\015'
ExecStop=/usr/bin/screen -p 0 -S mc-%i -X eval 'stuff "stop"\015'
[Install]
WantedBy=multi-user.target
@cbytestech
Copy link

How does this handle the server.Properties file? If setting this up for each user to have their own, wouldn't they each need their own copy?

@waaynee
Copy link

waaynee commented Jul 6, 2021

So I copied your service unit, modified it to fit my server and added recommendations from comments.
This is my first systemd unit and if I start it the ExecStop commands all immediatly execute?

[Unit]
Description=Minecraft Forge Server
After=network.target

[Service]
WorkingDirectory=/home/niclas/forge

User=niclas
Group=niclas

Restart=always
KillMode=none

ExecStart=/usr/bin/screen -dmS forge /usr/lib/jvm/java-11-openjdk-amd64/bin/java -Xms1G -Xmx8G -jar forge-1.16.5-36.1.32.jar nogui

ExecStop=/usr/bin/screen -p 0 -S forge -X eval 'stuff "say SERVER SHUTTING DOWN IN 5 SECONDS..."\015'
ExecStop=/bin/sleep 5
ExecStop=/usr/bin/screen -p 0 -S forge -X eval 'stuff "save-all"\015'
ExecStop=/usr/bin/screen -p 0 -S forge -X eval 'stuff "stop"\015'
ExecStop=/bin/sleep 10

[Install]
WantedBy=multi-user.target

@MaxSMoke-KillSZ-Official
Copy link

MaxSMoke-KillSZ-Official commented Jul 26, 2021

What is or who is a "stuff"?

@Maxgamerboy1
Copy link

@MaxSMoke-KillSZ-Official I was wondering what this did too. It's a screen command for inputting text or keyboard commands to a running screen session.
https://www.gnu.org/software/screen/manual/screen.html#:~:text=Stuff%20a%20string%20in%20the%20input%20buffer%20of%20a%20window
\015 is the ASCII keycode for a carriage return, the Enter key

@Aviatorpaal
Copy link

Aviatorpaal commented Sep 8, 2021

I had to add "Type=forking" to the file for systemctl to interpret it correctly, and not start/stop-loop the minecraft@survival.service

[Unit]
Description=Minecraft Unmodded: %i
After=network.target

[Service]
Type=forking
WorkingDirectory=/opt/survival
User=minecraft
Group=minecraft
Restart=always
ExecStart=/usr/bin/screen -dmS mc%i /usr/bin/java -Xmx4G -jar minecraft_server.jar nogui
ExecStop=/usr/bin/screen -p 0 -S mc%i -X eval 'stuff "say SERVER SHUTTING DOWN IN 10 SECONDS..."\015'
ExecStop=/bin/sleep 10
ExecStop=/usr/bin/screen -p 0 -S mc%i -X eval 'stuff "save-all"\015'
ExecStop=/usr/bin/screen -p 0 -S mc%i -X eval 'stuff "stop"\015'
ExecStop=/bin/sleep 25

[Install]
WantedBy=multi-user.target

@GwynethLlewelyn
Copy link

I'm using systemd + screen to launch a different application (similar in concept to launching a Minecraft server) so I tried to adapt things to my own purposes. This was not easy, but I've encountered the same issue as @Aviatorpaal and had to use Type=forking as well. There were also some slight differences in the parameters sent to screen, some of them not obvious. Ultimately, I got my own setup working using the skeleton framework suggestion posted on the Unix StackExchange (see point 2.), which worked quite well for me. It should also work fine for Minecraft or any kind of interactive server application that benefits from having a console.

@Fiwi1265
Copy link

Thanks this thread is exactly what I needed.

@Dominik-Gubrynowicz
Copy link

Hi, I have an error: screen[2355]: No screen session found. Any ideas what might be wrong? (Ubuntu 20.04)

@sublok
Copy link

sublok commented Jan 24, 2022

Will this work with 1.18.1 java @user_jvm_args.txt @libraries/net/minecraftforge/forge/1.18.1-39.0.45/unix_args.txt "$@"?

@RAD750
Copy link

RAD750 commented Mar 16, 2022

To view the console su to minecraft with:

sudo su minecraft

then

screen -R mc-server1

Don't use sudo su. Instead, do sudo -u minecraft -s, or directly sudo -u minecraft screen -R mc-server1

Cheers

@mitcherthewitcher
Copy link

This thread helped me out. Thanks 👍

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment