Hacker News new | ask | show | jobs
by quenix 717 days ago
I’m confused about one thing.

It doesn’t follow to me, that since all clients are running their own simulation, Lua scripts must run on every client too.

If a client runs a Lua script, why can’t we just run it on their machine and propagate any game state changes (if the script adds an inserted, for example,) as if the player made those changes themselves?

5 comments

> why can’t we just run it on their machine and propagate any game state changes (if the script adds an inserter, for example,)

Because that's an unbounded amount of traffic. You can reliably write data into RAM at many gigabits per second, whereas network connections are variable and many of them won't carry more than a few kilobits at the 99th percentile (note that you roll that 100-sided die like 30 times per second, so "1% situation" lag spikes are something you'd run into constantly)

I sometimes use Lua commands in single player to clear biters from a certain region for example, which removes many entities. Propagating those sorts of changes on multiplayer (or take a more plausible example: wave defense that eventually spawns loads of entities at once) would cause a big lag spike if you have a few players that all need to receive this data, whereas simulating it locally on each machine is no problem

Factorio multiplayer bandwidth is like a dozen kilobytes per second from what I remember, and this post agrees https://forums.factorio.com/viewtopic.php?p=125328#p125328 (couldn't quickly find an exact number though it must surely be out there). If you make it O(n) for every lua-touched entity in the game, it would quickly balloon into the megabits constantly and many mods would just not be viable for multiplayer for most people

The mechanism Factorio uses is to sync user inputs, not game state changes (the reason isn’t explained, but I strongly suspect it’s because user inputs are less data; small inputs can cause big game state changes, but not vice versa).

If the user types a command, in order to preserve synchronization, the game must:

- Run the command on all other clients.

- OR it could sync changes made to the game for just commands; in other words, the other clients apply the changes caused by the command instead of running the command directly. But that would be an unreasonable amount of extra work just for a small feature and to make exploits harder.

- OR the server simply disallows clients from running Lua commands, which is the case for some servers.

I don’t get the second part though: why a map can store arbitrary Lua code that runs when the map loads.

Scenarios that don't require a mod ?

(Some time ago, Factorio did not have a built-in mod synchronization system for multiplayer, with the result that the most popular servers did not run any mods, but rather used complicated scenarios instead.)

> If a client runs a Lua script, why can’t we just run it on their machine and propagate any game state changes (if the script adds an inserted, for example,) as if the player made those changes themselves?

The game already has to run Lua scripts as part of the simulation, potentially as part of in-game events which aren't directly triggered by players. A player running a script from the console is handled by that same interpreter -- making it run in a completely different operating mode where any changes to game state are replicated would be much more complicated and prone to error.

Or, from the other direction: the game's multiplayer model is all based around a replicated simulation where player inputs are fed into the simulation. Treating a player running a script as a special kind of event involving the text of that script is the simplest and most obviously correct way to implement that.

Running the scripts outside the simulation and syncing their commands alongside user input would definitely work on a technical level.

But I think you're massively underestimating how much these scripts can do. Many mods would flood the network connections. And there would also be an awkward delay for all script actions.

If clients don't run the same code they will desync the moment their state diverges. I haven't played multiplayer factorio but I expect you can't even join a server unless you're running the same factorio version and mods as other players.