1
\$\begingroup\$

I am kinda new to Multiplayer Games and I am really wondering how I should handle my data

Should each player send and update their data to the database (server) everytime one of their essential variables changes (like health or ingame currencies), or should they save the data as long as the game is running and then update the data all at once at the end of, lets say, each round?

I was thinking about using Firebase and Unity and here's a scenario:

Let's say 2 players connect to a game. Then one of them gets damage and the other one gets gold. Does the data change get sent to the FireBase Database immediatly or should I just update everything when the round ends/they disconnect?

\$\endgroup\$
  • 1
    \$\begingroup\$ It seems like this is a question you can answer for yourself simply by asking: "if one of my players suffers a power outage, am I OK with losing any data from the current round that was only cached locally?" or "am I willing to trust that the variable updates my players send me are legitimate, and not an attempt to cheat?" \$\endgroup\$ – DMGregory Mar 13 at 18:44
  • \$\begingroup\$ Thats a good way of thinking about it but I was wondering i was also wondering if Firebase + Unity actually exchange data fast enough to make the saving unnoticeable while playing. \$\endgroup\$ – Fvnex Mar 13 at 19:45
  • \$\begingroup\$ Do you plan to wait on server confirmation of the data change before drawing your next frame? If not, how would the player ever know that the database isn't updated yet? \$\endgroup\$ – DMGregory Mar 13 at 19:51
  • \$\begingroup\$ What do you mean with "updated yet". The problem i see with the server not sending a confirmation is that if the data gets lost on the way or something like that, the client doesnt know that and then data is lost. \$\endgroup\$ – Fvnex Mar 13 at 19:56
  • \$\begingroup\$ So you can use TCP or a reliability layer over UDP. In most cases, this can be handled by your netcode and never needs to manifest in your game logic or anything player-perceptible. \$\endgroup\$ – DMGregory Mar 13 at 20:00
0
\$\begingroup\$

I kind of cover this a little here. Let's see if I can expand it a bit for your situation.

Firebase Realtime Database has a couple of features you'll want to investigate. The first is that, by default, it tries to cache everything locally. That means that if you listen to the ValueChanged event, you'll always get the cached value first (sometimes null) and eventually get an update from the server when it syncs. You can also write data with a transaction, which works in concert with this cache. As data syncs to/from the server, you'll be able to first run your change against your local cache and eventually against the source of truth (the server) if it differs. If you're listening to ValueChanged to update your local game state and UI, you can minimize issues relating to users being offline (even for extended durations).

This won't be a silver bullet though, you still have to be able to construct transactions knowing that the user may have gotten into an impossible state and have some way to roll back gameplay (say if you tried to spend money you don't have).

It's worth also learning a bit about the rules system. You can get super complex with these, basically little JavaScript expressions that you can use to validate your database logic. It can get a little unwieldy if the rules get complex, but you can run them offline if you're wanting to write unit tests around critical rules (such as invalid changes to damage or gold).

One last trick is that you might want to build a sort of transaction log into your game. Rather than strictly saying "set player x's health to 2", say "at time x I'm dealing 2 damage" (and doing either both, or using a Cloud Function to turn the log into RTDB values to listen to). You can use ServerValue.Timestamp as a placeholder for "the time when this message syncs to the server" and use database rules as a way of figuring out the order actions resolve in (ex: "you can only write if the timestamp is newer than the last one in the log"). Then you can stop applying damage after one player dies, resolve rules with gold, &c monotonically. If a user was offline for a bit, this could get a little funky so it's entirely up to your game design.

Which (if any of these) work depends 100% on your game, but I hope I've helped a little!

| improve this answer | |
\$\endgroup\$
  • \$\begingroup\$ Thanks for the answer! I will have a look into that :) \$\endgroup\$ – Fvnex Mar 24 at 23:50

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.