← home  ·  the blueprint
// free blueprint

The Always-On Modded Server Blueprint

How to run a private modded Minecraft world your crew can hop on any time, without it eating your gaming PC or turning you into 24/7 tech support.


How to run a private modded Minecraft world your crew can hop on any time, day or night, without it eating your gaming PC or turning you into the group's 24/7 tech support


Somebody drops the trailer for the new pack in the group chat. ATM10. A fresh Create run. A brutal RLCraft season. Everyone's suddenly fired up, everyone's in.

And then, like it always does, the chat turns and looks at you.

Because you're the computer person. Hosting is your job now, whether you signed up for it or not.

I've been that person. I run modded servers, and I've made every mistake in this Blueprint at least once. So before you spend another two weeks staring at a wall of red crash-log text, let me save you the whole thing. This is the exact path from "I have a modpack I want to play with my friends" to "the world is up 24/7 and I never think about it," written by someone who actually games and actually runs these servers.

No fluff. No content-farm "top 5 hosts" nonsense. Just the build.

First, which one are you?

Whichever one you are, you're in the right place. Read the bold and you'll get the whole build in about five minutes. Read every line and you'll have a server that runs for months.

Why this actually matters (and it's not the server)

Here's the thing nobody says out loud. The server isn't the point. The server is the path.

What you're really building is the one place your crew keeps coming back to. Think about how these groups die. Not in a fight. They just drift. Someone can't get the pack to install, someone else can't join, the host is asleep so the world is down, and one quiet week turns into a dead Discord and a world nobody ever loaded again.

An always-on server kills that death. When the world is up 24/7, your friends play when they want, not when you happen to be at your desk. Somebody logs on at 1am and the base is exactly where they left it. The person in the other time zone finally gets to build. The world keeps its momentum, and the group keeps coming back to it.

So what? So the crew stays together. And you're the reason. You get to be the one who built the world that just runs, instead of the one everybody pings when it breaks. That feeling, being the quiet MVP instead of the on-call help desk, is the whole reason to do this right. That is what we're actually building.

The one decision you have to make first

Everything downstream forks here, so make this call before anything else.

Do you want to run it yourself on a cheap box, or pay someone to handle the sysadmin part?

Neither one is wrong. I'll give you the full self-host build now, then lay out the no-terminal path near the end so you can pick with your eyes open. Both beat hosting off your bedroom PC.


The build, step by step

Step 1: Read the pack's spec sheet before you touch anything

This is thirty seconds that saves you a weekend. Open your modpack's page on CurseForge or Modrinth and write down four things:

  1. The exact Minecraft version (like 1.20.1, or 1.21.1).
  2. The modloader (Forge, NeoForge, or Fabric).
  3. The loader version.
  4. The recommended server RAM.

That one line dictates every choice after it: which Java you install, which loader you run, how much memory you give it. Guess here and you'll be debugging phantom crashes for hours.

A quick word on loaders in 2026, because this trips up a lot of people:

The trap: from 1.20.2 onward, Forge and NeoForge are separate universes and their mods are NOT cross-compatible. A Forge mod dropped into a NeoForge server silently fails or crashes. So every single time you grab a mod, check that its page lists your exact loader AND your exact Minecraft version. Not "close enough." Exact.

Step 2: Get the box (and get it right-sized)

For 3 to 8 friends on a heavy pack, you want two things: enough RAM, and strong single-core CPU. Hold onto that second one, because it's the thing everybody gets wrong, and I'll come back to it.

Rough RAM targets:

One honest warning that will save you a lot of grief: a pack's advertised "minimum RAM" is for one person on a brand-new world. You and five friends exploring in different directions is two to three times that load. If a host tells you "4GB is plenty for ATM9," they're wrong, and you'll crash constantly. Size for the real thing, not the brochure number.

For a VPS, I run these on Hostinger's KVM plans, and here's why they fit modded specifically: the KVM tiers give you dedicated vCPU (not the cheap shared-core stuff), which is exactly what a single-threaded game like Minecraft needs, plus enough RAM to actually breathe.

You can grab one here: crewworlds.com/go/host. Spin up Ubuntu or Debian (the latest LTS), and you've got an always-on box with a public IP, which (spoiler for Step 8) is what quietly deletes the entire "my friends can't join" nightmare before it ever starts.

Do not cheap out on a shared-vCPU box just because it lists 16 GB for a few bucks. A weak shared core with tons of RAM will still stutter on chunk generation, because RAM was never your bottleneck. A strong core with 8 GB won't. Spend on the CPU.

Step 3: Install the correct Java

Here's the rule that ends the UnsupportedClassVersion crashes: Java version tracks the Minecraft version, not the loader, and newer is not always better.

Minecraft version Java you need
1.16.5 and older Java 8
1.17.x Java 16
1.18 through 1.20.4 Java 17
1.20.5 through 1.21.x Java 21

Use Eclipse Temurin (Adoptium) builds, they're the community standard and they're free. Grabbing "the latest Java" for an old Forge pack will throw cryptic class-loading errors, so match the table, don't chase the newest number.

Confirm it took with java -version before you move on. Evidence over assumption, always.

While you're in the terminal, create a dedicated non-root user for this (call it minecraft) and run everything as that user. Never run a game server as root.

Step 4: Get the SERVER pack, not the client pack

This is the single most common "my server won't start" cause, and it's a five-second fix once you know it.

The big green Download button on CurseForge or Modrinth gives you the CLIENT pack. That's the version you install in the launcher to play. Upload it to a server and it won't run, or it'll crash, because it's stuffed with mods that only make sense on your own machine.

What you want is the Server Pack, from the Files tab (CurseForge labels it exactly that). On Modrinth, grab the .mrpack and deploy it with a tool like mrpack-install. The server pack is the same content minus the client-only mods, plus the loader installer and a run.sh script.

Client-only mods are the visual and quality-of-life stuff that runs on your machine and does nothing (or actively crashes) on a headless server: Sodium, Iris and shaders, minimaps, HUD tweaks, controller mods, Controlling, TrashSlot, Clumps. If your server boots fine when you test it solo but dies when it's actually running as a server, a client-only mod snuck into the server's /mods folder. Pull it out. It belongs only in your friends' clients.

If no server pack was published, you build one: copy the client instance's /mods and /config, delete the client-only mods listed above, and install the matching loader's server files.

One heads-up that trips up auto-installers: CurseForge requires API-key authentication for automated file downloads (that rule went into force back in mid-2025), and some mod authors turn off third-party distribution entirely. If an auto-installer chokes on a specific mod, that's usually why, and you'll need to grab that one by hand. Not a big deal, just don't let it confuse you.

Step 5: Unzip, install the loader, accept the EULA, tune the settings

Drop the server pack into a clean directory and run the bundled loader installer (something like java -jar neoforge-<version>-installer.jar --installServer, or the Forge equivalent). You should end up with /mods, /config, the loader libraries, and a run.sh.

Open server.properties and set:

Then add your crew to the whitelist. Once the server's running you just type whitelist add <username> in the console for each person, or edit whitelist.json. A whitelist is not optional for a private server. It's the difference between "our world" and "some rando griefed the base while we slept."

Step 6: Set your RAM and JVM flags (and do NOT just max out the memory)

Here's the counterintuitive truth that separates people who understand modded from people who don't: throwing more RAM at the server can make it worse.

A bigger heap means the garbage collector has more memory to scan, which means longer pauses, which shows up in-game as stutter and TPS drops. Past what your pack actually needs, extra RAM buys you close to nothing on performance. It only prevents out-of-memory crashes.

So do two things:

1. Set -Xms equal to -Xmx, and leave headroom. On a 16 GB box, give the server 12 GB, not 16. That ~2 GB you held back is for the operating system and the JVM's own off-heap memory. Hand the JVM everything and Linux's out-of-memory killer will silently execute your server mid-session, and you'll have no idea why it "just died."

2. Use Aikar's flags. These are the community-standard G1GC tuning, and they genuinely help. Modern Forge and NeoForge put your memory settings in a user_jvm_args.txt file next to run.sh. Here's the standard set:

-Xms10G
-Xmx10G
-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

If your heap is larger than 12 GB, switch to the large-heap variant: G1NewSizePercent=40, G1MaxNewSizePercent=50, G1HeapRegionSize=16M, G1ReservePercent=15, InitiatingHeapOccupancyPercent=20, G1MixedGCCountTarget=8.

Step 7: First boot, then pre-generate the world

Start the server by hand the first time and watch the log scroll to a clean Done with no fatal errors. Then have one friend connect, on the exact same pack version, to confirm the mod lists match and nobody gets a mismatch kick. (More on that in the port section.)

Now the move that fixes the mystery lag before it happens. Remember how I said single-core CPU is the real bottleneck? The most CPU-punishing thing your server ever does is generate new chunks, and it does it on the main thread while your friends stand there watching the world stutter into existence.

So generate it in advance, while nobody's playing. Install the Chunky mod and pre-generate a reasonable radius around spawn (a few thousand blocks). It front-loads the heavy work into the quiet hours, and most of your in-play lag vanishes. Add the Spark mod too, so you can type /spark and actually see your TPS and GC behavior instead of guessing.

If you ever see Can't keep up! Is the server overloaded? in the console with TPS dropping below 20, and your RAM and CPU graphs look half-empty, this is why. It's one core doing chunk work, not a memory shortage. Pre-gen and lower view distance, in that order, before you ever think about paying for a bigger box.

Step 8: Make it ACTUALLY always-on with systemd

This is the step that turns "a server I start when I feel like it" into "a world that's just always there." You want it to launch on boot, come back automatically after a reboot, and, critically, shut down gracefully so it never corrupts your world mid-save. (True crash auto-restart with this pattern is finicky, since systemd is tracking the tmux session rather than the Java process itself. Getting that part bulletproof is one of the things the Deploy Pack handles for you.)

You run the server inside a tmux session (so you can attach to the live console any time), and you wrap it in a systemd service. Here's the shape of it:

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

[Service]
User=minecraft
Type=forking
WorkingDirectory=/home/minecraft/server
ExecStart=/usr/bin/tmux new-session -d -s mc '/home/minecraft/server/run.sh'

# Graceful stop: save the world, wait, then stop the server, wait
ExecStop=/usr/bin/tmux send-keys -t mc 'save-all' Enter
ExecStop=/bin/sleep 10
ExecStop=/usr/bin/tmux send-keys -t mc 'stop' Enter
ExecStop=/bin/sleep 20

# The setting that matters most: stop systemd from SIGKILLing the JVM mid-write
KillMode=none
Restart=on-failure
RestartSec=15

[Install]
WantedBy=multi-user.target

Then systemctl enable --now minecraft and it survives reboots.

Read that KillMode line twice. Without a graceful stop, a plain systemctl stop or a server reboot sends a hard kill to the JVM while it's in the middle of writing chunks to disk, and a half-written region file is one of the classic ways people corrupt a world. The save-all then stop then wait sequence is what keeps your world intact every time the box restarts.

⭐ Step 9: Add, swap, and remove mods WITHOUT breaking the world

This is the section worth the whole Blueprint. It's the thing that terrifies every host, the question that gets asked a thousand times in every modded forum, phrased as a plea:

"Will it break my world?"

Here's the honest answer, and it's the most important thing you'll read today: adding and removing mods are not the same risk. Not even close. Getting them mixed up is how people lose bases.

Let me break it into the three moves.

Adding a mod: usually safe

New mods bring new blocks, items, mobs, and recipes. They don't touch what's already generated, and new content mostly shows up in freshly generated chunks. So adding is the low-risk move. But two things still bite people:

Swapping a mod (or updating one): medium risk

A swap is a remove plus an add, so it inherits the removal risk below. Version-matching a mod up or down can also change how it stored data. Treat it like a removal: back up first.

Removing a mod: THIS is the dangerous one

When you delete a mod that already wrote blocks or items into your world, the game restarts and finds references to content that no longer exists. On Forge and NeoForge you'll see:

Fatally missing registry entries

Here's what almost nobody understands until it's too late: this is not a crash you can just click through. On Forge (and its NeoForge descendants) you get past it by confirming: type /fml confirm in the console, or, since a headless server usually refuses to boot without an answer, pass -Dfml.queryResult=confirm as a JVM argument. Either way the world loads. But confirming permanently deletes every block and item that mod added. Those blocks become air (holes in your base), and those items vanish out of chests and inventories. Gone. Forge writes an automatic backup alongside your world folder when it does this, but never, ever rely on that. Make your own first.

And then there's the truly dangerous case, the one that doesn't just delete items but actually corrupts terrain:

Removing a worldgen, biome, or dimension mod after that terrain has already generated. Your existing chunks reference biomes, features, or whole dimensions that no longer exist. That can produce genuinely corrupt chunks, cascading worldgen errors, or hard crashes on load. This isn't "I lost some items," this is "the world won't open." Sometimes the only fix is deleting and regenerating the affected dimension's region folders. Treat pulling a worldgen mod like open-heart surgery, and never do it on your only copy.

The repeatable loop that makes all of it safe

Here's the workflow I run every single time, no exceptions. Follow it and you can experiment freely, because a mistake is never permanent:

  1. Announce it and stop the server. Never edit /mods on a live world.
  2. Back up the WHOLE instance, not just /world. The full folder. (Step 10 automates this. Before it's automated, do it by hand.)
  3. Make the change on the server. Add dependencies too. For a removal, know first whether the mod wrote to the world, and especially whether it touched worldgen.
  4. Mirror the exact change on every client, same versions, for every content mod. This is non-negotiable, it's the "it works on my machine but nobody can join" fix.
  5. Restart and watch the log. If you hit missing registry entries, only confirm past it (/fml confirm in the console, or the -Dfml.queryResult=confirm JVM arg on a headless box) after you know your backup exists.
  6. Verify everyone can join and the base is intact.
  7. Keep it, or roll back to the backup you made in step 2. That last option is the whole reason this is safe.

That's it. That's the fear, solved. You're not "risking the world" every time you want to try a mod. You're making a backup and running a checklist. The base becomes a place you can renovate, not a fragile thing you're scared to touch.

Step 10: Backups that actually restore

A backup you've never tested is a rumor, not a safety net. Two rules make backups real:

1. Never copy the world while the server is writing to it. You'll get a torn, unrestorable file. Either stop the server, or run save-off then save-all in the console, copy or tar the files, then save-on to resume writes.

2. Automate it and get a copy off the box. A cron job that runs the save-off/save-all dance, tars /world (plus world/serverconfig, where a lot of packs keep per-world settings) with a timestamp, prunes old archives with find -mtime, and rsyncs a copy somewhere else. If the whole VPS dies, a backup that only lived on that VPS died with it. There's a ready-made script, nicolaschan/minecraft-backup, that handles the tmux/RCON save dance and tar or restic out of the box.

And the part everyone skips: actually restore one, once, on purpose. Prove to yourself the file opens into a working world. Do it before you need it, not the night your base is a smoking crater.

Keep a "sticky" snapshot right before every mod change and every pack update. Those are the ones that save you.

Quick note on updating the whole pack: snapshot first, keep your /world, replace /mods and the loader with the new version's server pack, then re-apply any custom edits to /config (the update usually overwrites that folder, so note your tweaks before you start). Make sure every friend updates to the identical version. If the world won't load on the new pack, restore the snapshot and stay put. There's no shame in staying a version behind on a world you love.


The port-forwarding myth, killed for good

Now let me hand you the reason to never host off your bedroom PC again.

Half the "my friends can't join" agony out there is one problem: port forwarding. The endless spiral of connection timed out, "is it my router," "is it my ISP," "do we have to use Hamachi." People burn days on it and end up blaming their router in defeat.

Here's the thing. That entire class of pain only exists when you host behind a home router. Your home network hides your PC behind one shared address, so you have to poke a hole through the router to let strangers reach it, and a dozen things can go wrong.

A VPS has none of that. It's a box sitting on the open internet with its own public IP and no router in front of it. So there's nothing to "forward." You just open the game port in the box's firewall:

sudo ufw allow 25565/tcp
sudo ufw allow OpenSSH

Then you hand your friends the server's IP address and they connect. Done. No router settings, no Hamachi, no port-forwarding tutorials, no calling your ISP.

One security note: open port 25565 (the game) and your SSH port, and nothing else. Do NOT expose RCON (port 25575) to the internet. Leave it bound to localhost.

And to be clear about the other "can't join" cause, the mod-version mismatch kick: that's not a network problem at all. That's the mod-list-must-match rule from Step 9. Everyone on the identical pack version, and that error disappears too.


The honest money math

No spin. Here's what this actually costs.

Self-host on a VPS: a 16 GB dedicated-vCPU box runs roughly $15 to $25 a month depending on how long a term you lock in. Split across five friends, that's three to five bucks each. Cheaper than one coffee, for a world that's up every hour of every day. You own the ops (Java, systemd, backups), which this Blueprint just handed you.

Managed host: budget around $3.75 per gigabyte, so an 8 GB heavy-modded plan lands near $30 a month, and a 10 to 12 GB plan closer to $35 to $45. More expensive per gigabyte, but the price buys back your time: one-click installs, correct Java, backups, and DDoS protection, all handled.

The math that actually matters isn't the monthly number, though. It's this: a corrupted world with fifty hours of your crew's builds in it costs more than any of these plans, and it costs it all at once. Whichever path you pick, the backups in Step 10 are the real bargain.


The no-terminal path (if systemd made your eyes glaze over)

If you read Step 8 and thought "absolutely not," that's a completely valid answer, and there's a clean path for you.

A managed modded host does the sysadmin work so you don't. You pick your pack from a library, it installs in one click, the correct Java is already set, backups run on a schedule, and there's a web panel instead of a command line. You skip Steps 3, 5, 6, 8, and 10 entirely, and you point your friends at an address the host gives you.

For the no-terminal route I'd point you at Apex Hosting (apexminecrafthosting.com). They've got a strong reputation for a clean panel, one-click modpack installs, automatic Java, and offsite backups, which is exactly the "I just want to play, not administrate" package. Their pricing is a flat rate across the mid-range (roughly $7.49 for 2 GB, $29.99 for 8 GB), so you can right-size to your pack.

You lose some control and pay a bit more per gigabyte. You gain your evenings back. For a lot of people, that's the right trade, and there's nothing wrong with making it.


Do it tonight: the checklist

You can have this running before you go to bed. Work down the list:

Tick all twelve and you've got what you came for: a private modded world your friends can hop on any hour of the day, that survives reboots, that you're not scared to change, and that you're not on call to babysit.


The easy button

Everything above works. I run it. You can run it. It's genuinely the full build, and if you follow it you will have a real always-on modded server, no strings.

But I'll be straight with you, because that's the whole point of this thing. Steps 3 through 10 are a couple of hours of careful terminal work the first time, and every one of them has a spot where a small mistake means a confusing crash or a lost afternoon. Correct Java. The exact right flags for your heap size. A systemd unit that shuts down gracefully instead of corrupting your world. Backups that actually restore. It's all doable. It's also all the stuff that "usually wastes the first night of a modded server."

So we built the shortcut, for the nights you'd rather be playing than configuring.

Here's the honest pitch, elephant in the room and all: we make our money whether you build it by hand or hit the easy button. This Blueprint is free because we'd rather earn your trust with something that actually works than gate it behind an email and a sales page. If you build the whole thing yourself off these steps, genuinely, good. That was the point. And if you'd rather have your first modded night be playing instead of configuring, the Deploy Pack and Server Butler are sitting right there at crewworlds.com when you want them.

Either way, you get to be the one who built the world that just runs.

Now go get the box. Your crew's waiting.

CrewWorlds

// the easy button

Want the whole thing done for you? The Deploy Pack runs Steps 3 through 10 in one command, and Server Butler keeps it alive from Discord.

Back to CrewWorlds  →