DataStore Saving Problem

Make sure you have API turned on, huge factor.

The reason I’m using another script is it’s less mess and it’s easier to do. I tried using SetAsync() but I didn’t know how to use it very well. So I used UpdateAsync() instead.

Set async is practically the same thing. Just the player that you want to save it to, then the arguments (data you want to save)

Something like this?

local p = game:GetService("Players"):GetPlayerByUserId(1)


game.Players.PlayerRemoving:Connect(function(plr)
	  
	local leaderstats = Instance.new("Folder")
	local a = plr.leaderstats.Time.Value  
	local datastore = game:GetService("DataStoreService")
	local ds1 = datastore:GetDataStore("TimeSave")
	
	ds1:SetAsync(p, a) ---Saves the data.
	
	
		
	
	
end)

Once again remove the leaderstats folder. Player already has one assuming that you have a leaderstats system.
local leaderstats = plr.leaderstats

Two, use a pcall to set the async since ROBLOX Api’s can still fail.

 local success, err = pcall(function()
  --- blah blah do stuff here
)

Three, you are saving the player’s data that is leaving, not the one that you defined. Why are you using p if that’s only saving data for that specific player?

Do ds1:SetAsync(plr, a)

1 Like

Firstly, I would also suggest putting all the code in one script, so its easier to manage and handle, unless you absolutely need to.

When you run the function connected with the PlayerRemoving event, you save the value of Time, yet you get the Value of gems when the player joins again. Could this be a possible mistake? You should try to save the gems Value if you want to retrieve it the next time the player joins the game.

Additionally, UpdateAsync accepts two parameters, the key it should update data in, and a function that actually updates the data (which it runs on its own). See here for more info. However, I think it makes little difference to use UpdateAsync in this case, and you could use SetAsync here. I made example code below to use as a guideline.

game.Players.PlayerRemoving:Connect(function(Player)
     local leaderstats = Player.leaderstats
     local Gems_Value = leaderstats.Gems.Value
     local datastore = game:GetService("DataStoreService")
     local ds1 = datastore:GetDataStore("TimeSave")

     local success, err = pcall(function()
        ds1:SetAsync(Player.UserId, Gems_Value)
    end)   

end)

@Syntheix UpdateAsync is actually more reliable of a saving method compared to SetAsync when use correctly. If you would like to learn more please read this great article.

1 Like

Thanks. Could I use the code you used in the example to save the data?

This would likely work if you were planning to save the Gems the player has. However, you save the Time in your original post, so I’m not sure if this would be what you need.

Wouldn’t it be the same though if I change Gems to Time in this line?

local Gems_Value = leaderstats.Time.Value

But isn’t time and gems value different? That would be over complicating it? Unless your planning to change Time.value to Gems.Value

It’s hard to tell because in your script you have written the following code.

local success, err = pcall(function()
      data = ds1:GetAsync(plr.UserId)
end)
 
if success then
     gems.Value = data
end 

If you don’t save the gems.Value, you will always be using default data and it will never properly save.

What is the Time data used for anyways?

1 Like

It’s made so I can award time badges, in other words, award a badge for staying in the game a curtain amount of time. I’m trying to make it save so you don’t have to restart everytime you rejoin.

Oh I see now, silly me.

Nevermind, this will work. Use leaderstats.Time.Value. Sorry, I did not see this.

2 Likes

Thanks. Sorry just want to double check, so something like this? For some reason it still won’t save in studio.


game.Players.PlayerRemoving:Connect(function(Player)
     local leaderstats = Player.leaderstats
     local timevalue = leaderstats.Time.Value
     local datastore = game:GetService("DataStoreService")
     local ds1 = datastore:GetDataStore("TimeSave")

     local success, err = pcall(function()
        ds1:SetAsync(Player.UserId, timevalue)
    end)   

end)
1 Like

All good, but make sure to remove these lines

     local datastore = game:GetService("DataStoreService")
     local ds1 = datastore:GetDataStore("TimeSave")

Since you will be putting all the code in one script instead of two. Use the variables defined at the top of your first script (datastore and ds1).

Before:
Screen Shot 2020-08-19 at 1.08.20 PM
After:
Screen Shot 2020-08-19 at 1.08.34 PM
I think I did something wrong, for some reason it won’t save when you leave. It just sets back to 0. I assume I put it in the wrong place.

local datastore = game:GetService("DataStoreService")
local ds1 = datastore:GetDataStore("TimeSave")
 
local badgeservice = game:GetService("BadgeService")
local badgeid = 2124575491
local badgeid2 = 2124565356
local badgeid3 = 2124565358
local badgeid4 = 2124565361
 
game.Players.PlayerAdded:Connect(function(plr)
    local m = 0
    local leaderstats = Instance.new("Folder")
    leaderstats.Parent = plr
    leaderstats.Name = "leaderstats"
 
 
    local gems = Instance.new("IntValue")
    gems.Parent = leaderstats
    gems.Name = "Time"
 
    local data
 
    local success, err = pcall(function()
        data = ds1:GetAsync(plr.UserId)
    end)
 ---Where is saves.
	  game.Players.PlayerRemoving:Connect(function(Player)
		local leaderstats = Player.leaderstats
     local timevalue = leaderstats.Time.Value   
		     
		local success, err = pcall(function()
        ds1:SetAsync(Player.UserId, timevalue)
    end)   

end)  
---End of where it saves.	
	
	
	
	
	if success then
        gems.Value = data
    end 
 
    repeat wait()
        m = m + 1
        if m == 2 then
            m = 0
            if plr.leaderstats.Time.Value >= 600 then 
            badgeservice:AwardBadge(plr.UserId, badgeid)
            if plr.leaderstats.Time.Value >= 3600 then 
 
                badgeservice:AwardBadge(plr.UserId, badgeid2)
 
                if plr.leaderstats.Time.Value >= 18000 then 
 
                    badgeservice:AwardBadge(plr.UserId, badgeid3)
 
                    if plr.leaderstats.Time.Value >= 36000 then 
 
                        badgeservice:AwardBadge(plr.UserId, badgeid4)
 
                    end
                end
            end
        end
        end
        wait(1)
        plr.leaderstats.Time.Value = plr.leaderstats.Time.Value + 1
    until plr == nil  
end)

Make sure to put this code at the very end, after game.Players.PlayerAdded.

Are there any errors in the output?


I think i see the problem, success is defined twice. Could that be a problem?

That should not be a problem, but as I suggested make sure the PlayerRemoving codeblock is placed at the end of the script.

local Players = game:GetService("Players")

Players.PlayerAdded:Connect(function(Player)
     -- get data
end)

Players.PlayerRemoving:Connect(function(Player)
     -- save data
end)

Are there any errors in the output?

No errors, I put it at the very end of the script and for some reason it won’t save.