Can you show us your script? That’ll help us all out a ton!
Okay
local function SaveData(plr,t)
if plr and t then
data:SetAsync(plr.UserId,t.Value)
end
end
game.Players.PlayerAdded:Connect(function(plr)
Instance.new("Folder",plr).Name = "leaderstats"
local stat
local function Getleaderstats()
wait(0.1)
if not plr:FindFirstChild("leaderstats") then
wait(1.5)
Getleaderstats()
else
stat = plr:WaitForChild("leaderstats")
return true;
end
end
Getleaderstats()
local function CreateStat(class,name,parent)
local i = Instance.new(class)
i.Name = tostring(name)
i.Parent = parent
return i
end
local money = CreateStat("IntValue","Gold",stat)
wait(0.03)
local SavedLevel = data:GetAsync(plr.UserId)
if SavedLevel then
money.Value = SavedLevel
else
money.Value = 1
wait(0.08)
SaveData(plr,money)
end
end)
game.Players.PlayerRemoving:Connect(function(plr)
if plr:FindFirstChild("leaderstats") and plr.leaderstats:FindFirstChild("Gold") then
SaveData(plr,plr.leaderstats["Gold"])
end
end)
if not game:GetService("RunService"):IsStudio() then
game:BindToClose(function()
for _,plr in pairs(game:GetService("Players")) do
if plr:FindFirstChild("leaderstats") and plr.leaderstats:FindFirstChild("Gold") then
SaveData(plr,plr.leaderstats["Gold"])
end
end
wait(10)
end)
end
---This is the first script, in ServerScriptService then then next is---
```game.Players.PlayerAdded:connect(function(player)
local DataStore = game:GetService("DataStoreService")
local leader = Instance.new("Folder",player)
leader.Name = "leaderstats"
for i,v in pairs(script:GetChildren()) do
local d = DataStore:GetDataStore(v.Name)
local x = Instance.new("NumberValue",leader)
x.Name = v.Name
x.Value = d:GetAsync(player.UserId) or v.Value
end
end)
game.Players.PlayerRemoving:Connect(function(player)
for i,v in pairs(script:GetChildren()) do
print("Getting")
local DataStore = game:GetService("DataStoreService")
local d = DataStore:GetDataStore(v.Name)
d:SetAsync(player.UserId, player.leaderstats[v.Name].Value)
print("Saved")
end
end)
---This is a seperate script in ServerScriptService---
First off if you are the last player in the game you should make a game:BindToClose function that will make it so if the server is ready to shutdown it must execute said code before it can shutdown
like kick every player left in the server and wait 5 seconds before shuting down use this code
local MDT = DTS:GetDataStore("CurrencyDT") -- Change you YOUR datastore name
local PS = game:GetService("Players")
local currencyName = "Currency" -- Change to your currency name
game.Players.PlayerAdded:Connect(function(plr)
local Folder = Instance.new("Folder")
Folder.Name = "leaderstats"
Folder.Parent = plr
local Value = Instance.new("IntValue")
Value.Name = currencyName
Value.Parent = Folder
local ID = currencyName.."-"..plr.UserId
local savedData = nil
pcall(function()
savedData = MDT:GetAsync(ID)
end)
if savedData ~= nil then
Value.Value = savedData
print(plr.Name.."'s data has loaded!")
elseif savedData == nil then
Value.Value = 200
print(plr.Name.." is a new player!")
end
end)
game.Players.PlayerRemoving:Connect(function(plr)
local ID = currencyName.."-"..plr.UserId
MDT:SetAsync(ID, plr.leaderstats[currencyName].Value)
end)
game:BindToClose(function()
for i, player in pairs(game.Players:GetPlayers()) do
if player then
player:Kick("This server is shutting down! Your data should be saved!")
end
end
wait(5)
end)
Okay thanks where would I replace that code to.
Thanks!
Studio is infamous for shutting down before the data gets saved, that’s why you have to use a BindToClose
function, if you’re also checking if your current game is inside studio you can solve this issue.
See this exampel:
local RunService = game:GetService("RunService")
local Players = game:GetService("Players")
game:BindToClose(function()
if RunService:IsStudio() then
for _,Player in ipairs(Players:GetPlayers()) do
local Success,ErrorMessage = pcall(function()
--Your data saving script comes into here
end)
if not Success then
warn("Error: "..ErrorMessage)
end
end
end
end)
I also suggest using a pcall
function since saving data can sometimes throw errors.
Okay Thanks where would I put this to at the end of my code?
It is up to you where you put it
Also, there is already a bindtoclose funciton at the end of my code
I don’t know how functions behave, if they do behave like events you’d need to put that script into your BindToClose
function as events have the problem of not running if they have have been used mutliple times in one script.
The code you have written could potentially lose data for a lot of users - most notably the use of SetAsync and lack of pcalls.
I suggest using a proper module like DataStore2 or ProfileService to handle data saving.
Okay how would I use DataStore2 using my currency I can not find the model for DataStore 2 and I can not find a real manual on hwo touse it
What you’re doing is pretty simple, just use a dictionary to store data.
local Players = game:GetService("Players")
local DataStoreService = game:GetService("DataStoreService")
local GoldData = DataStoreService:GetDataStore("Gold")
Players.PlayerAdded:Connect(function(player)
local leaderstats = Instance.new("Folder")
leaderstats.Name = "leaderstats"
leaderstats.Parent = player
local gold = Instance.new("IntValue")
gold.Name = "Gold"
local data = nil
local success, err = pcall(function()
data = GoldData:GetAsync(player.User.."-gold")
end)
if success then — if getting data was successful
if data then — if the player has data then...
gold.Value = data.Gold — looks into the dictionary, and grabs gold’s value
else — there’s no data, must be a new player
gold.Value = 100 — give the player 100 gold when they first join
end
else — getting data wasn’t successful
warn("There was an error whilst grabbing data!")
warn("Error:", err)
end
end)
Players.PlayerRemoving:Connect(function(player)
local gold = player:WaitForChild("leaderstats").Gold
local data = {
Gold = gold.Value — save a key called “Gold” to be referenced later
}
local success, err = pcall(function()
GoldData:UpdateAsync(player.UserId.."-gold", function()
return data — save the data
end)
end)
if not success then
warn("There was an error whilst saving data!")
warn("Error:", err)
end
end)
Would that be able to save most of the time?
Thanks! Because I do not want my game to make all players to lose their gold.
Also theres a problem with that I already have a different script that names my leaderstats that is named Gold. So how would I refer to that using your script?
is this happening in-game or in studio?
since im pretty sure when you hit close in a play-solo you kinda “force shut” the game. I think in real servers the server gets shut down after 2-3 seconds of the last player leaves (which gives the server time to save the data)
I made a DataStore2 and it works. But how would I add my currency that kills players for money inside of it?
Here is my DataStore2 code here. I know where to plug the script in just need to know how it would be plugged in.
local defaultValue = 100
game.Players.PlayerAdded:Connect(function(plr)
local goldDataStore = DataStore2("gold",plr)
local leaderstats = Instance.new("Folder", plr)
leaderstats.Name = "leaderstats"
local gold = Instance.new("IntValue", leaderstats)
gold.Name = "Gold"
local function goldUpdate(updatedValue)
gold.Value = goldDataStore:Get(updatedValue)
end
goldUpdate(defaultValue)
goldDataStore:OnUpdate(goldUpdate)
end)
game.Workspace:WaitForChild("ChickenO").ClickDetector.MouseClick:Connect(function(player)
local goldDataStore = DataStore2("gold", player)
goldDataStore:Increment(50, defaultValue)
end)
The data might not save properly in studio because the game leaves really fast, or the server shuts down in an unexpected way. But there is a really really useful function for that (as some people mentioned already.) game:BindOnClose()!
You can check more about this function or how to properly save here.
P.S. This thread helped a lot of people. Including me!
Okay Thanks, Everyone here for helping out so far. So right now I want to be able to add my kill player for money script, but I tried everything I can think of, and I can not replace it. I tried deleting the leaderstats and using my kill player for money script and this causes the whole leaderstats to break. I tried replacing an on player died function in place of the click detector workspace Chicken o function but it won’t work. Can anyone help me solve this?
Summary: Using the DataStore2 Script Above to add a kill player for money script to save the gold.
Thanks!