Tutorial by: eult


skNetwork shares Skript variables between every server on a BungeeCord or Velocity network. Put a ? in front of a variable name and it exists everywhere.

# on the lobby
set {?coins::%player%} to 100

# on survival, no extra code
send "You have %{?coins::%player%}% coins"

Reading is free. Your server answers from its own copy in memory, so nothing goes over the network when a script reads. Only writes go to the proxy.

This tutorial takes you from nothing to that working. Ten minutes if your servers are already running.

What you need

Version
Java 25
Minecraft 1.21 to 26.2
Skript 2.16.0 or newer
Proxy BungeeCord or Velocity

The proxy does not need Skript. Only the game servers do.

One jar, two halves

You download a single skNetwork.jar and put the same file on the proxy and on every game server. It works out where it is running and turns on the right half.

The proxy holds the real data. Every game server holds a copy in memory. Writes travel to the proxy, and the proxy tells every server about the change.

Step 1: the proxy

Drop skNetwork.jar into the plugins folder of your BungeeCord or Velocity proxy. Start the proxy once, then stop it. That creates plugins/skNetwork/config.yml.

Open it:

bind: 127.0.0.1
port: 25580
token: "change-me"

Change token to your own password. Any text works. Every game server has to use the same one.

Step 2: each game server

Put the same jar into the plugins folder of every game server. Skript has to already be there or skNetwork will not start.

Start each server once, stop it, then open its plugins/skNetwork/config.yml:

server-name: "lobby"

proxy:
  host: 127.0.0.1
  port: 25580
  token: "change-me"

prefix: "?"

server-name is a short name for this server. Give every server a different one. Your scripts can read it back with network server name, so one script can behave differently on each server.

token has to match the proxy exactly. If it does not, the proxy refuses the connection and says so in the console.

prefix decides which variables are shared. With ?, {?coins} goes to the network and {coins} stays local.

Do the same on your other servers. Only server-name should be different.

Step 3: Skript's config

Skript needs to know that ? variables belong to skNetwork. skNetwork writes that for you at startup, so normally there is nothing to do here.

If you want to see what it added, open plugins/Skript/config.sk and look under databases::

    network:
        type: skNetwork

        pattern: [?].*

That block has to sit above the default: block at the bottom of the file. Skript saves a variable to the first database whose pattern matches. Below default:, your network variables would also get written into variables.csv on that server. skNetwork places it in the right spot by itself.

On a brand new server, Skript has not created config.sk yet when skNetwork starts. It writes the block after startup instead and tells you in the console. Restart that server once and it works from then on.

Step 4: start everything and check

Start the servers and the proxy. The order does not matter, because game servers keep retrying until the proxy answers.

Run /sknetproxy in the proxy console:

skNetwork  │  0.2.0  ·  protocol 8
│
│ Backends   2 servers
│ Variables  0  seq 0
│ Scripts    off
│

Backends is how many game servers are connected. If it says 0, check the token and the port.

Then run /sknet on a game server:

skNetwork  │  0.2.0  ·  protocol 8
│
│ State      READY
│ Server     lobby
│ Proxy      127.0.0.1:25580  1ms
│ Storage    ?  routing [?].*
│ Mirror     0 variables  seq 0
│

You want State to say READY in green, and a Storage line saying routing. A red NOT CONFIGURED means Skript never picked up the block from step 3.

Step 5: try it

Put this on one server:

command /setcoins <number>:
    trigger:
        set {?coins::%player%} to arg-1
        send "Set to %arg-1%"

And this on another:

command /getcoins:
    trigger:
        send "You have %{?coins::%player%} ? 0% coins"

Run /setcoins 100, walk to the other server, run /getcoins. It says 100.

The rule that will bite you

When a server starts, its copy is empty until the proxy sends everything. Empty is not the same as "the network has nothing". During that gap, every is not set check says yes, even for players who already have money.

So guard anything that runs early:

on join:
    if network is not synced:
        stop
    atomically set {?coins::%player%} to 500 if it is not set

skNetwork refuses writes until the first sync finishes rather than let you wipe real data, and it logs every refused write. But your script should still check.

The other thing worth knowing on day one: never read a network variable and then change it based on what you read.

# WRONG on a network
if {?coins::%player%} >= 100:
    remove 100 from {?coins::%player%}

Two servers can run that at the same moment, both read 100, and both subtract. Let the proxy do the check and the subtraction together instead:

atomically remove 100 from {?coins::%player%} without going below 0 and wait
if the atomic change succeeded:
    give player a diamond
else:
    send "Not enough coins."

Where to go next

The wiki covers the rest: atomic changes, cross-server messaging and player lookup, the sync events, pushing .sk files from the proxy, and everything skNetwork cannot do.

https://github.com/ahmadmsaleem/skNetwork/wiki


Did you find eult's tutorial helpful?


You must be logged in to comment