Datastore Session Locking

I was wondering if Roblox’s DataStores have built in Session Locking, or if that is something that I would have to implement myself. Recently loleris released ProfileService, with its most prominent feature being session locking, but shouldn’t Roblox handle this internally.
By the way, I am using UpdateAsync, instead of SetAsync to save my data.

From how I understand it, session locking is used to prevent two servers from editing the same key at the same time. Without this someone could perform a data changing action, quickly rejoin and have the data before that action be loaded, overwriting the change. This can lead to item duplication because old data is overwriting new data.

If Roblox doesn’t handle this internally, what would be the easiest, but most effective way to create my own system of session locking?

5 Likes

Every single time ProfileService writes OR fetches data (or interacts with Roblox Datastores in ANY way), it uses something similar to this:

datastore:updateasync(key, function(currentData)
    if currentData == nil then
        currentData = {}
    elseif currentData.SessionJobId ~= game.JobId then
        return nil -- This doesn't actually save nil, it just cancels the UpdateAsync query. Be careful though because your UpdateAsync call will return nil!
    end
    
    currentData.SessionJobId = game.JobId -- Apply the session lock
    --If you're fetching, you can just do this:
    --return currentData

    --If you're writing, just return the updated data:
    --currentData.Coins += 100
    --return currentData
end)

It also has systems to manually override the session locks if it tries to fetch a profile and there’s still a lock after 90 seconds or so. This is just the bare minimum code that makes it work.

9 Likes

I know ProfileService doesn’t use MessagingService, but do you think it would cut loading times if I were to implement MessagingService into my session locking system? I remember reading there are certain cases where the data could take over a minute to load which isn’t very good.

1 Like

I think if you broadcasted 5-10 MessagingService messages every 1-2 seconds when you detect a session lock, you could be fairly sure that the profile has a dead session lock if you don’t get a response within that 10-20 second window. Keep in mind that MessagingService can still fail periodically and even for long periods of time if Roblox has an outage. These small windows of time would be hard for a cheater to take advantage of so this should still be a decent and interesting solution.

1 Like

What do you do if a player is leaving the game and saves the data? How do you unlock the session?