luagame-enginerobloxdatastore

How to use Datastore to save player Values? (Roblox Studio)


Kylaaa's advice fixed something but now I get a new error in the Output after running this code on joining the game, I've never done datastore before so all the help is very much appreciated thank you!

local UpgradeDataStore = DataStoreService:GetDataStore("UpgradeDataStore")

game.Players.PlayerAdded:Connect(function(player)
    local playerData ={clickValue = 0,}

    -- Load data from DataStore
    local success, result = pcall(function()
        return UpgradeDataStore:GetAsync(tostring(player.UserId))
    end)
    
    -- only load if the player has previous data
    if success and result then
        playerData = result
    else

    -- Handle loading errors
    
        warn("Failed to load data for player " .. player.Name .. ": " .. errorMessage)
        
    end






local  clickNum = Instance.new("IntValue")
clickNum.Name = "clickValue"
clickNum.Value = clickNum or 1
clickNum.Parent = player



-- Save the clicker upgrade when the player leaves
player.CharacterRemoving:Connect(function()
    local success, errorMessage = pcall(function()
        playerData.clickValue = clickNum.Value
        UpgradeDataStore:SetAsync(tostring(player.UserId), playerData)
    end)

    -- Handle saving errors
    if not success then
        warn("Failed to save data for player " .. player.Name .. ": " .. errorMessage)
    end
end)
end)

Now Everytime this script runs I get this error: ServerScriptService.OnPlayerAdded:56: attempt to concatenate string with nil


Solution

  • The error is telling you that when the player's character dies or is removed from the workspace, for some reason playerData is nil.

    When you initialize playerData, you only assign an empty table if the data store fails to load, but you haven't accounted for the case that the data store successfully returns nothing. You really should give it a default value that the data store overrides.

        -- initialize playerData with default values
        local playerData = {
            clickValue = 0,
        }
    
        -- Load data from DataStore
        local success, result = pcall(function()
            return UpgradeDataStore:GetAsync(tostring(player.UserId))
        end)
    
        -- only load if the player has previous data
        if success and result then
            playerData = result
        elseif not success then
            -- Handle loading errors
            warn(string.format("Failed to load data for %s : %s", player.Name, result))
        end