This past weekend I was finally able to (re)build my homelab server. I said I'd write about it so here it is:

I had one of my best friends, who is a programmer, and my brother, who works in tech repair, over since we all generally enjoy building computers and they had some experience with this stuff.
The machine's specs are nothing too impressive, because it's an old HP Z230 that my brother got for basically free as an abandoned machine at work. He gave it to me because he wasn't using it and had better hardware. The specs are:
- Intel Code i5-4570 CPU running at 3.2Ghz
- 32Gb DDR3 Corsair Vengeance RAM
- Integrated graphics
- 3x 8Tb WD Red's for storage
- 1x 120Gb SSD for the proxmox install

There is a caveat: I discovered I didn't have enough sata power connectors available to plug all 3 WD Reds in... so right now it's just running two in RAID 0. LOL I'll have to get a molex to sata connector in a bit. The ultimate goal is to have all 3 in RAID 5.
One of the first hurdles was that I was swapping in the new RAM I got second hand (also from a friend), and somehow the computer was not happy at all. We thought we might have a dead stick or dead slot but eventually as we were testing each stick one by one, the computer decided to post with all 4 sticks in. Hurray.
We initialized it, flashed proxmox onto it, and then I disconnected it from the monitor we were using and just stuck it in the closet, as proxmox can run headless on the network. Problem was, we allowed the computer to auto-designate its IP and it's gateway while not plugged into the network, so it used the wrong gateways. We had to take it out of the closet, plug it back into the peripherals on my desk, and reconfigure everything so that we could see the UI in the browser on my other computer finally.
Once that was done, it was time for my friend and brother to leave, so I was left with initializing portainer, docker, docker compose, and ultimately the minecraft server image that I found through this video tutorial from Raid Owl. The video uses a docker image created by itzg, which is a very popular docker image for minecraft servers and has support for every modloader I've ever heard of. It was helpful to have both the videos and the documentation for the image on github as I created this.
I started by creating a vanilla server using the quick start docker-compose.yml from the github page, and it just immediately worked. It actually took longer for me to set up the volumes and containers than it did to get the actual server up and running. Once I got there, I started modifying the compose file to use a custom mod-pack my girlfriend had made on CurseForge. I had all sorts of problems with that. At first, I didn't want to use the AUTO_CURSEFORGE feature from the docker image because I really really didn't want to have to create a curseforge account to get the required API key, but the other setups I was working with were just not working.
In no particular order I tried:
- Uploading the individual mod .jar files to the containers 'mods' folder and using 'MODPACK' in the compose file
- Uploading the CurseForge-created client pack .zip file for the custom modpack and using 'GENERIC_PACK' in the compose file
- Some frankenstinian combination of the above as I got more frustrated
What ended up working for me ultimately was the AUTO_CURSEFORGE variation while only uploading the 'manifest.json' from the CurseForge pack and mounting it to the 'manifests' folder in the container. Initially, this caused me a ton of issues where the server was still trying to load client-only mods like 'Oculus' and then crashing. I frankly do not know why this was being caused and I made a Discussion post on Github for it. However, after completely deleting the container, attached volumes, all the mounted folders, and pinning the image to Java 17, the server just worked.
For the curious, below is the (truncated) docker-compose.yml I ended up using:
services:
minecraft:
image: itzg/minecraft-server:java17
volumes:
- minecraftdata:/data
- /home/Minecraft/manifests:/manifests:ro
ports:
- 25565:25565
tty: true
stdin_open: true
restart: unless-stopped
stop_grace_period: 120s
environment:
EULA: "TRUE"
SERVER_NAME: _______
MOD_PLATFORM: AUTO_CURSEFORGE
OPS: _______
MEMORY: 12G
MOTD: "Hello, gamers!"
ENABLE_WHITELIST: "TRUE"
ENFORCE_WHITELIST: "TRUE"
WHITELIST: __________
VERSION: 1.20.1
CF_API_KEY: ${CF_API_KEY}
CF_SLUG: "custom"
CF_MODPACK_MANIFEST: /manifests/manifest.json
CF_EXCLUDE_MODS: |
oculus
journeymap-integration
RCON_PASSWORD: ______
volumes:
minecraftdata:
external: true
You can see that I keep my api key in a .env file so that it can be a bit more secure and the java17 section was added to designate the java version used. This was something I saw in a few of the example compose files for other modpacks that use Minecraft 1.20.1, so I just tried it on a whim. I sincerely don't know if this was the primary issue - all I saw in the logs was that 'Oculus' was being loaded and it was not a server mod.
Regardless, very happy to have the server working. My girlfriend and I were able to play last night for a few hours and the server remained very stable. I am hoping the backup cron job works well but haven't really tested it, as I am not the most experienced with cron. My ultimate aim with the server is to securely open it to the world so my friends can play on it remotely as well, and I can ensure nothing weird happens since I'm not super knowledgable on security.
My next idea for the server, since I bought all that storage for it, is to run Jellyfin as a media vault as well as streamer, and the arr suite for maintaining it. I still need to figure that out so if you have any really good guides please send them my way! Right now I am looking at this Github Repo MediaStack Project (Docker). And also at YAMS since it seems super quick to set up.
_ _ _
Thoughts? Send me an email!
kagumail.uselessly535@passinbox.com
Feel free to remain anonymous and send it from a secure mailer!