What are some tips for a reliable datastore?

Hello everyone, im a wannabe developer trying to get some tips on making a good datastore. I currently have made a basic one that i use, but it completely crashes and stops saving if i have 4 or more values being saved.

So, can anybody share tips and the basics of making a more reliable datastore so that i can save more values for more complex game ideas?

1 Like

How are you saving your values? Realistically you should be putting your values which you want to save in a dictionary, then saving that dictionary in the datastore.

3 Likes

Well something I have implemented, (which I try my best to make the most performant) is a data validation check whenever I set the data of a key. I essentially check to make sure the data exists, and that it’s valid, if it doesn’t it’ll revert to the last data.

3 Likes

Honestly, just use already made modules like ProfileService. Unless your goal is to make a public datastore module someday, or you have a unique scenario that requires a custom datastore, it’s better to rely on people that know what they’re doing and have already built a module.

It will save you lots of time and headaches in the long run. I specifically prefer ProfileService because of how versatile it is compared to other modules like DataStore2.

You also compromise your game’s wellbeing and players’ data if you don’t know what you’re doing.

1 Like

Thanks for the replies already, ill look into each method individually and hopefully get a better script

Personally, I’ve never really been into using external modules for datastores, because I don’t see the issue with DataStoreService, or real benefit behind other modules. (Just me personally tho.)

Once you start using them you’ll realize how beneficial they are. Open sourced modules are tested by thousands of developers, unlike one that would be made by yourself. This means there is bound to be way less, if not zero, bugs. It also just saves you time that can be put towards the actual completion of the game. ProfileService also includes useful functions that you may not even have thought of. Also, in the game that I used it in, there was not 1 single data loss, and it gives you the peace of mind that everything is working smoothly.

I use open sourced modules, you didn’t read my reply.

I said, specifically for datastores, I’m a web developer ofcourse I’m using open sourced modules. :skull:

Hey there,

Sorry for the late response, but i have the current datastore i’m using. It was about a year ago when i made this (i believe i may have been following a tutorial, those were not my brightest days) but i’ve been using it because i can’t wrap my head around datastores.

local DSS = game:GetService("DataStoreService")
local MyStore = DSS:GetDataStore("GOAWv1")

game.Players.PlayerAdded:Connect(function(player)
	wait()
	
	local playerKey = "id_"..player.UserId
	
	local saveValue1 = player.Coins
	local saveValue2 = player.Checkpoint
	
	local GetSaved = MyStore:GetAsync(playerKey)
	if GetSaved then
		saveValue1.Value = GetSaved[1]
		saveValue2.Value = GetSaved[2]
	else
		local valuestosave = {saveValue1.Value, saveValue2.Value}
		MyStore:GetAsync(playerKey, valuestosave)
	end
end)

game.Players.PlayerRemoving:Connect(function(player)
	local saveItems = {player.Coins.Value, player.Checkpoint.Value}
	MyStore:SetAsync("id_"..player.UserId, saveItems)
end)

game:BindToClose(function()
	for i, plr in pairs(game.Players:GetChildren()) do
		plr:Kick("All data has been saved! Yippe!")
	end
end)

It works fine until i add more than three values, no errors, just doesn’t save

How are you adding your third value to save? It looks fine as is, to save more values you’d have to put them in the saveItems array
local saveItems = {player.Coins.Value, player.Checkpoint.Value, thirdValue, fourthValue} etc…

Yes, this is how i’m doing it. Like i said: no errors it just stops saving after i add 4 or more and im really confused

It is recommended to use a pcall function when retrieving or saving a players data, a pcall stands for a “Protected Call”, you can learn more about it here: Pcalls

the reason why we use them in datastores is because Roblox servers sometimes tend to shutdown/go down, and usually that can also have an impact on datastores. If there’s no datastore to fetch data from, then the function will give an error, consequently also stopping the rest of the script from continuing. So use a pcall for both GetAsync() and SetAsync()

Another thing I recommend is to save their data manually when using game:BindToClose. Ofcourse, what you did does look right, but playeremoving connection when kicking the players during a shutdown might fail, I’d recommend use :SetAsync() inside the game:BindToClose function too, we could have a function you can use for both playerRemoving and game:BindToClose

your code should look something like this:

--Inside PlayerAdded Event
local GetSaved
local success,errormessage = pcall(function()
	GetSaved = MyStore:GetAsync(playerKey)
end)

if success then
	if GetSaved then
		saveValue1.Value = GetSaved[1]
		saveValue2.Value = GetSaved[2]
	else -- success but the data retrieved is nil, meaning it is a new player.
		print(`New Player: {player.Name}`)
	end
elseif errormessage then
	print(`ERR: {errormessage}`)
end
function savePlayersData(player)
	local saveItems = {player.Coins.Value, player.Checkpoint.Value}
	local success,errormessage = pcall(function()
		MyStore:SetAsync("id_"..player.UserId, saveItems)
	end)
	if success then
		print(`Successfully saved {player.Name}s data!`)
	elseif errormessage then
		print(`ERR: {errormessage}`)
	end
end

game.Players.PlayerRemoving:Connect(savePlayersData)

---bindToClose
game:BindToClose(function()
	for i, plr in pairs(game.Players:GetPlayers()) do
		savePlayersData(plr)
        --plr:Kick("Your data has been saved.")
	end
end)

Hope this makes sense, the code you’re using will def work, I am just giving you a better version, in case of large servers, it is important to always use the most efficient way, making no mistakes and making sure that there would be no errors that could stop the rest of the script. Good Luck!

1 Like

Wow, thanks a lot for this. I have heard of pcalls and their use, but this helped me understand better! :+1:

1 Like

Here’s just a few bullet points for reliable data stores…

  • data versioning
  • session locking
  • retry logic and UpdateAsync
  • request budgeting
  • autosaving
  • BindToClose yielding (not saving)
  • data corruption checking and restoration
  • data validation during saving
  • detection and appropriate action for internal errors

yeah ive never really been into using other modules, I prefer to make my own because I can tailor it more to my needs.

1 Like

Thanks, this will help for sure! :+1:

1 Like