I’ve been using the same exact DataStore script all the time, but for some reason, this time it isn’t saving my data. I have no idea why, all the values just reset back to 0 when I leave the game and rejoin. Here’s my script:
local DataStoreService = game:GetService("DataStoreService")
local Players = game:GetService("Players")
local playerDataStore = DataStoreService:GetDataStore("PlayerData")
local function playerAdded(player)
local leaderstats = Instance.new("Folder")
leaderstats.Name = "leaderstats"
leaderstats.Parent = player
local rebirths = Instance.new("IntValue")
rebirths.Name = "Rebirths"
rebirths.Parent = leaderstats
local level = Instance.new("IntValue")
level.Name = "Level"
level.Parent = leaderstats
local gems = Instance.new("IntValue")
gems.Name = "Gems"
gems.Parent = leaderstats
local coins = Instance.new("IntValue")
coins.Name = "Coins"
coins.Parent = leaderstats
local playerUserId = player.UserId
local playerData
local success, errorMessage = pcall(function()
playerData = playerDataStore:GetAsync(playerUserId)
end)
if success then
if playerData then
rebirths.Value = playerData[1]
level.Value = playerData[2]
gems.Value = playerData[3]
coins.Value = playerData[4]
print("Player "..playerUserId.."'s data was loaded.")
end
elseif errorMessage then
warn("Player "..playerUserId.."'s data was not loaded.")
end
end
local function playerRemoving(player)
local playerUserId = player.UserId
local leaderstats = player:FindFirstChild("leaderstats")
local playerData = {
Rebirths = leaderstats.Rebirths.Value,
Level = leaderstats.Level.Value,
Gems = leaderstats.Gems.Value,
Coins = leaderstats.Coins.Value
}
local success, errorMessage = pcall(function()
playerDataStore:SetAsync(playerUserId, playerData)
end)
if success then
print("Player "..playerUserId.."'s data was saved.")
elseif errorMessage then
warn("Player "..playerUserId.."'s data was not saved.")
end
end
local function bindToClose()
for _, player in pairs(Players:GetPlayers()) do
warn("Server shutdown commencing in 5 seconds.")
end
task.wait(5)
end
Players.PlayerAdded:Connect(playerAdded)
Players.PlayerRemoving:Connect(playerRemoving)
game:BindToClose(bindToClose)
I have no idea what the issue is. I don’t get any errors, everything seems to be working fine. I do have Enable Studio Access to API Services turned on. Maybe I accidentally changed something in my code by accident?
Try saving player data on bindtoclose. If its the last player in a server and they leave, the server may shut down too fast before it can save the players data.
local DataStoreService = game:GetService("DataStoreService")
local Players = game:GetService("Players")
local playerDataStore = DataStoreService:GetDataStore("PlayerData")
local function playerAdded(player)
local leaderstats = Instance.new("Folder")
leaderstats.Name = "leaderstats"
leaderstats.Parent = player
local rebirths = Instance.new("IntValue")
rebirths.Name = "Rebirths"
rebirths.Parent = leaderstats
local level = Instance.new("IntValue")
level.Name = "Level"
level.Parent = leaderstats
local gems = Instance.new("IntValue")
gems.Name = "Gems"
gems.Parent = leaderstats
local coins = Instance.new("IntValue")
coins.Name = "Coins"
coins.Parent = leaderstats
local playerUserId = player.UserId
local playerData
local success, errorMessage = pcall(function()
playerData = playerDataStore:GetAsync(playerUserId)
end)
if success then
if playerData then
rebirths.Value = playerData[1]
level.Value = playerData[2]
gems.Value = playerData[3]
coins.Value = playerData[4]
print("Player "..playerUserId.."'s data was loaded.")
end
elseif errorMessage then
warn("Player "..playerUserId.."'s data was not loaded.")
end
end
local function playerRemoving(player)
local playerUserId = player.UserId
local leaderstats = player:FindFirstChild("leaderstats")
local playerData = {
Rebirths = leaderstats.Rebirths.Value,
Level = leaderstats.Level.Value,
Gems = leaderstats.Gems.Value,
Coins = leaderstats.Coins.Value
}
local success, errorMessage = pcall(function()
playerDataStore:SetAsync(playerUserId, playerData)
end)
if success then
print("Player "..playerUserId.."'s data was saved.")
elseif errorMessage then
warn("Player "..playerUserId.."'s data was not saved.")
end
end
local function bindToClose()
local playerUserId = player.UserId
local leaderstats = player:FindFirstChild("leaderstats")
local playerData = {
Rebirths = leaderstats.Rebirths.Value,
Level = leaderstats.Level.Value,
Gems = leaderstats.Gems.Value,
Coins = leaderstats.Coins.Value
}
local success, errorMessage = pcall(function()
playerDataStore:SetAsync(playerUserId, playerData)
end)
if success then
print("Player "..playerUserId.."'s data was saved.")
elseif errorMessage then
warn("Player "..playerUserId.."'s data was not saved.")
end
for _, player in pairs(Players:GetPlayers()) do
warn("Server shutdown commencing in 5 seconds.")
end
task.wait(5)
end
Players.PlayerAdded:Connect(playerAdded)
Players.PlayerRemoving:Connect(playerRemoving)
game:BindToClose(bindToClose)
As suggested here, it’s a great idea to save your data on a BindToClose in correlation with saving via a PlayerRemoving. UnderCity21 sums this up pretty good on why this is the case and I’m sure this in theory would probably work, although in terms of you testing this out and debugging I thought I’d add a bit of useful information onto this.
Under the assumption you’re doing this in Studio, and this simply isn’t saving to the datastore in studio, a debugging tool I used to use is simply simulating a PlayerRemoving while in studio. The simpliest way to do this in my opinion is, in the command bar, kick LocalPlayer with the following line: game.Players.LocalPlayer:Kick(), then end the studio play session as usual. Studio is pretty notorious for issues with PlayerRemoving simply because of how it works.
Hopefully this helps with the concept better. If not, other potential issues could be the way you’re obtaining the stats (ie. you’re simply editing the IntValues on the client rather than the server.)
I have seen that if player removing and bindtoclose both runs on server close then studio will freeze for about 30 seconds. This is prob because its saving those values twice within 30 seconds which then adds that value to wait 30 seconds before it will save it again and then studio freezes for 30 seconds until it can save again. Mabey add a debounce. like if player removing runs then save data and debounce to true then wait 30 then debounce to false though that would cause it not to save for every other player that leaves. Mabey track it by the player name. Just some tips! But my scipt that i put above should work and save every time! Note: Running a server on the TEST Tab then cleaning up that server won’t save data cause its a server running in studio.