~/home/blogs/zomboid-plus-discord.md

Hosting a Private Zomboid Server + Discord

Deployed a private Project Zomboid server and added death notifications and online list to my discord server.

- Raul G.
2024-06-01

Introduction

The other day, I was hanging out with some friends and we started talking about Project Zomboid. It's a survival horror game that genuinely attempts to emulate surviving in the zombie apocalyse. This means your character gets hungry, bored, depresssed, and you have to manage things like your temperature and calories/weight else you risk getting sick and weak. I've played the game before and it can be somewhat depressing, but only in single player mode.

Multiplayer mode is a lot more fun. So, I decided to spin up a 24/7 zomboid server so that we can all play together even if our schedules don't overlap.I'd highly recommend the game to anyone who enjoys survival crafting games and the lore of The Walking Dead

Zomboid Server

Notable Configs

After playing for a week and learning the ropes, we decided to add mods and customize the sandbox settings to make the experience more engaging and challenging. I still wanted to keep the vanilla feeling though, so we only added mods that improved the QoL of the game or otherwise kept the theme of Zomboid intact.

Check out the list of mods here. This is a note that I prepared to send to my friends in a CHANGELOG-style discord message.

After installing those mods, I updated the server so that we all spawn randomly around the map (Which is huge). There are 4x as many zombies too, but they respawn very slowly. They form larger groups, and there is a 3% change that one of the zombies is a running zombies. Those are actually pretty spooky to encounter.

Note: I also made the zombies hit harder, but that was a silent patch. If you're reading this, I'm sorry but it makes the game more fun šŸ™ƒ

Server Management

Luckily for me, setting up the server was rather simple thanks to the folks maintaining LinuxGSM. You can follow the instructions for setting up the server in the link I provided.

Once I had the LinuxGSM scripts installed, it became super easy to manage the server. I just SSH into it and run commands to start the game up, shut it down, check for updates, etc.

su - pzserver # Change to the server admin Linux user.

./pzserver start # This command starts the server up
./pzserver stop # This one obviously stops the server
./pzserver update # Checks for updates from SteamCMD and applies them
./pzserver backup # Stores a backup of the game files locally

Modifying the game's rules and sandbox settings are simple, too. All of the game's settings are managed by some .ini and .lua files in the ~/Zomboid/Server/ directory.

I actually just edit the server configs using Zomboid's "Host" config editor. Those files are stored in the same directory locally on my gaming machine(Windows=%USERPROFILE%\Zomboid\).

Then I just upload those files up to the server using WinSCP and ./pzserver start. Works pretty well.

Note: When I initially spun up the Zombid server, I had to use ./pzserver console to set an admin password. That was only for the first run.

Idea #1: Death Notifications

My fiancee came up with the idea that we should alert the discord server whenever someone dies. I thought it was a great idea! It would be really cool if we could all collectively "mourn" these characters, and give players the opportunity to vent their frustrations in the chat.

I decided to check that out and look through the log files or any other things I could "subscribe" to so that we get real-time notifications. Luckily for me, I found the PerkLog file under ~/Zomboid/Logs. This file is updated whenever a character logs in, levels up a skill, or dies.

So, I wrote a script to subscribe to it. The script monitors the Zomboid log files to detect player deaths (and record the events in a database). To extract death events from the other events, I used a regular expression to identify and capture relevant information from the line.

const deadLinePattern = /\[[\d\- :\.]+\] \[\d+\]\[(.+)\]\[\d+,\d+,\d+\]\[Died\]\[Hours Survived: (\d+)\]\./;

If it's the right file & the right line pattern, then we log the death information in an sqlite database and send a notification to a Discord channel via webhook.

To avoid re-processing log entries & prevent any redundent line processing, we also maintains a file to track the last processed line in each log file.

sequenceDiagram
    participant ZomboidServer
    participant LogDirectory
    participant Script
    participant SQLite
    participant DiscordWebhook

    Script->>LogDirectory: Watch for changes
    LogDirectory-->>Script: 

    ZomboidServer->>LogDirectory: Update log file
    LogDirectory->>Script: 
    Script->>LogDirectory: Check file and read new lines
    LogDirectory-->>Script: 
    alt Right file and matching line
        Script->>SQLite: Update with player death info
        Script->>DiscordWebhook: Send death notification
    end

Check out the script here :)

Idea #2: Leaderboards

If you noticed, we store the death event in a database. This is because my fiancee' next idea was to create a sort of leaderboard. Genius! šŸ’„

The leaderboard script queries the database to retrieve the top 10 players with the most deaths and the total hours they survived. This is done with some raw SQL, no ORMs here lol.

It then formats this information into a Discord embed and sends out the leaderboard! It's kinda fun to see just how much time has been lost to zombie bites šŸ§Ÿā€ā™‚ļø

I just set the script to run weekly via cron, and ta-da. A weekly leaderboard.

See the code here. It basically outputs the code like this:

šŸ† Zombie-Darwin Awards

Check out the players with the most deaths šŸ§Ÿā€ā™‚ļø

Rank Player Name Deaths Hours Lost
1 Player1 10 120
2 Player2 9 110
3 Player3 8 105
4 Player4 7 100
5 Player5 6 95

Idea #3: /online Discord Command

This idea was suggested by my good friend. He just wanted to be able to see who was online at any given time, and I took that as a coding challenge, haha.

For this one, I had to dive into the lua scripts for Zomboid. I ended up writing a zomboid mod that logs the list of online players as well as some information about the player like the profession, zombie kills, and hours alive every 15 seconds to a log file. Then, I wrote a script that reads this log file and saves the information to a JSON file when it detects a change.

Finally, I wrote a discord bot that can respond to the /online command by reading the JSON file and sending the list of online players to the channel. So, technically speaking, the bot is not really "live" but it's close enough. I'm happy with it.

sequenceDiagram
    participant ZomboidMod
    participant LogFile
    participant WatcherScript
    participant JSONFile
    participant DiscordBot
    participant DiscordChannel

    Note over ZomboidMod,JSONFile: Log online players every 15 seconds

    WatcherScript->>LogFile: Monitor for changes
    activate WatcherScript
    LogFile-->>WatcherScript: 

    ZomboidMod->>LogFile: Every 900 ticks, log online players
    LogFile-->>WatcherScript: 
    activate WatcherScript
    WatcherScript->>JSONFile: Save updated player info to JSON
    deactivate WatcherScript

    Note over JSONFile,DiscordChannel: Respond with player info
    DiscordChannel->>DiscordBot: /online command received
    activate DiscordBot
    DiscordBot->>JSONFile: Read updated player info
    activate DiscordBot
    JSONFile-->>DiscordBot: 
    deactivate DiscordBot
    DiscordBot->>DiscordChannel: Respond with player info
    deactivate DiscordBot

    deactivate WatcherScript

See the Lua mod code here, and the Discord bot code here

Conclusion

It was a fun challenge for me and a fun addition to the zomboid experience. I had an idea for implementing permadeath with a "three strikes and you're out" rule, but I think I might save that one until the Build 42 update comes out. I hear they're changing the way the game handles modding, so I might have to rewrite a lot of the scripts anyway. šŸ˜…

I'll make another update when that happens. Until then, I hope you enjoyed reading about my little project or the code snippets I shared. If you have any questions or suggestions, feel free to reach out to me on Twitter.

šŸ‘‹

Share this post