Scripting HelpersARCHIVE
A little piece of Roblox history. Preserved for everyone, one question at a time.Read about the archive →
COMMUNITY QUESTION

What's wrong with this datastore code and how can I fix it?

I've been trying to make a character customization GUI in which all of the character values save. However, everything works fine until when the player leaves. When they leave, the values don't update, they stay the same as they were previously when I joined the game. When I use a datastore editor plugin, and change them, they load as the values I changed them to, but when I change them in studio or in the game, the values appear to change but they still don't save when I leave.

Here's my datastore code:

local DataStore = game:GetService("DataStoreService"):GetDataStore("CustomizationData")

game.Players.PlayerAdded:Connect(function(player)
	wait(1)
	--Creating the customization values for the player
	local Folder = Instance.new("Folder", player)
	Folder.Name = (player.Name.."Values")
	
	local SkinTone = Instance.new("IntValue", Folder)
	SkinTone.Name = "SkinTone"
	
	local HairOne = Instance.new("IntValue", Folder)
	HairOne.Name = "HairOne"
	
	local HairTwo = Instance.new("IntValue", Folder)
	HairTwo.Name = "HairTwo"
	
	local HairColour = Instance.new("IntValue", Folder)
	HairColour.Name = "HairColour"
	
	local Shirt = Instance.new("IntValue", Folder)
	Shirt.Name = "Shirt"
	
	local Pants = Instance.new("IntValue", Folder)
	Pants.Name = "Pants"
	
	local Key = (player.Name.."Data")
	
	--Setting the values based on the datastore
	local Get_Data = DataStore:GetAsync(Key)
	if Get_Data then
		SkinTone.Value = Get_Data[1]
		HairOne.Value = Get_Data[2]
		HairTwo.Value = Get_Data[3]
		HairColour.Value = Get_Data[4]
		Shirt.Value = Get_Data[5]
		Pants.Value = Get_Data[6]
	else
		SkinTone.Value = 1
		HairOne.Value = 1
		HairTwo.Value = 1
		HairColour.Value = 1
		Shirt.Value = 1
		Pants.Value = 1
	end
	for i, v in pairs(Folder:GetChildren()) do
		v.Changed:Connect(function()
			DataStore:SetAsync(Key, {SkinTone.Value, HairOne.Value, HairTwo.Value, HairColour.Value, Shirt.Value, Pants.Value})
			print("Data changed, set")
			print(SkinTone.Value)
		end)
	end
end)

game.Players.PlayerRemoving:Connect(function(player)
	local Key = (player.Name.."Data")
	local Folder = player:FindFirstChild(player.Name.."Values")
	local SkinTone = Folder.SkinTone
	print (SkinTone.Value)
	local HairOne = Folder.HairOne
	local HairTwo = Folder.HairTwo
	local HairColour = Folder.HairColour
	local Shirt = Folder.Shirt
	local Pants = Folder.Pants
	print(SkinTone.Value)
	print("Saved")
	DataStore:SetAsync(Key, {SkinTone.Value, HairOne.Value, HairTwo.Value, HairColour.Value, Shirt.Value, Pants.Value})
end)

1 comment

0

Use BindToClose

1 answer

I suggest making the function that begins at line 55 a variable for this, your problem is that the saving code doesn't run before the game closes when the last player of a server leaves. To fix this use the built in function BindToClose. BindToClose fully runs a code right before the server closes.

local function SavePlayerStats(player)
	    local Key = (player.Name.."Data")
	    local Folder = player:FindFirstChild(player.Name.."Values")
	    local SkinTone = Folder.SkinTone
	    print (SkinTone.Value)
	    local HairOne = Folder.HairOne
	    local HairTwo = Folder.HairTwo
	    local HairColour = Folder.HairColour
	    local Shirt = Folder.Shirt
	    local Pants = Folder.Pants
	    print(SkinTone.Value)
	    print("Saved")
	    DataStore:SetAsync(Key, {SkinTone.Value, HairOne.Value, HairTwo.Value, HairColour.Value, Shirt.Value, Pants.Value})
end

game:BindToClose(function()
	for i, player in pairs(game.Players:GetPlayers()) do
		SavePlayerStats(player)
	end
end) -- the BindToClose function will save the player's data before the server closes -- and also ensures that multiple player's data will save if there is a server crash or something (which is what the loop does)

game.Players.PlayerRemoving:Connect(function()
	SavePlayerStats(player)
end) -- when a player leaves but the server is not closing, their data will save

3 comments

0

SetAsync yields, so if it takes too long and there's a few players, some might not get their data saved; the solution's to use a coroutine.

0

Even after implementing this into it, it's still failing to save the data. Any other solutions?

0

This discussion is preserved as it was. New answers, comments, and votes are closed.