Datastore script not working

Hey Everyone,
I’m making a datastore script for my wins for my story game.
It’s supposed to display the amount of wins under the player’s name.
The players name displays fine, but the wins don’t.
Here is my script:

local DataStoreService = game:GetService('DataStoreService')

local WinsDataStore = DataStoreService:GetDataStore('Wins')


script.Parent.UserId:GetPropertyChangedSignal('Value'):Connect(function()
	local PlayerName = game.Players:GetNameFromUserIdAsync(script.Parent.UserId.Value)
	local Player = game.Players:GetPlayerByUserId(script.Parent.UserId.Value)
	local Data = WinsDataStore:GetAsync(script.Parent.UserId.Value)
	
	if Data then

		script.Parent.Parent.Parent.Podium.MiddleBlock.SurfaceGui.PlayerName.Text = PlayerName
		script.Parent.Parent.Parent.Podium.MiddleBlock.SurfaceGui.WinsAmount.Text = Data.Stats
	end		
end)

I get no errors. Thanks for any help!

2 Likes

If you use :GetAsync() and the player does not already have a value stored, then the variable Data would return ‘nil’.

2 Likes

I would like to point out that you should really put GetAsync in a pcall if it fails.

Anyways, is the script.Parent.UserId.Value the key of the player?

It’s this:

local Players = game:GetService('Players')
local DataStoreService = game:GetService('DataStoreService')

local WinsDataStore = DataStoreService:GetDataStore('Wins')


Players.PlayerAdded:Connect(function(Player)
	
	local Stats = Instance.new('Folder')
	Stats.Name = 'leaderstats'
	Stats.Parent = Player
	
	local Wins = Instance.new('IntValue')
	Wins.Name = 'Wins'
	Wins.Parent = Stats
	
	
	local Data = WinsDataStore:GetAsync(Player.UserId)
	
	
	if Data then
		for name, value in pairs(Data.Stats) do
			Stats[name].Value = value
		end
		
	end
	
		
		
end)

Players.PlayerRemoving:Connect(function(Player)
	local SaveData = {Stats = {}}
	

	
	for _, stat in pairs(Player.leaderstats:GetChildren()) do
		SaveData.Stats[stat.Name] = stat.Value
	end
	

	
	
	
	WinsDataStore:SetAsync(Player.UserId,SaveData)
	
	
end)

game:BindToClose(function()
	for _, Player in pairs(game.Players:GetPlayers()) do
		local SaveData = {Stats = {}}
		

		
		for _,stat in pairs(Player.leaderstats:GetChildren()) do
			SaveData.Stats[stat.Name] = stat.Value
		end
		

		
		WinsDataStore:SetAsync(Player.UserId,SaveData)
		
	end
	
	wait(2)
end)

I’m bad at datastores(I made this with a video) This is my datastore script.

1 Like

I don’t see anything related to the UserId InstanceValue.

1 Like

I also get the error:
[12:04:16.746 - Workspace.Leaderboards.WinsLeaderboard.WinsPodium.NPCs.1.Script:14: invalid argument #3 (string expected, got table)

Where is this error pointing out? (Which line)

[12:04:16.747 - Script ‘Workspace.Leaderboards.WinsLeaderboard.WinsPodium.NPCs.1.Script’, Line 14]

1 Like

I mean in your code, I can’t tell which line is line 14. (You can add a comment in your code to point it out)

		script.Parent.Parent.Parent.Podium.MiddleBlock.SurfaceGui.WinsAmount.Text = Data.Stats

You saved a table in a table in your datastore.

Do you know how I can fix it? I’m quite bad

game:BindToClose(function()
	for _, Player in pairs(game.Players:GetPlayers()) do
		local SaveData = {}
		

		
		for _,stat in pairs(Player.leaderstats:GetChildren()) do
			SaveData[stat.Name] = stat.Value
		end
		

		
		WinsDataStore:SetAsync(Player.UserId,SaveData)
		
	end
	
	wait(2)
end)

Do I change that for the player removing function aswell, or just the bind to close?

Also, some data is already stored. Is there any way to clear a datastore?

Edit: The issue still appears I’m guessing because I already have 3 wins

1 Like

Another issue is, after setting my wins to 0, when I rejoin it still comes up as the old amount.
This is the edited script:

local Players = game:GetService('Players')
local DataStoreService = game:GetService('DataStoreService')

local WinsDataStore = DataStoreService:GetDataStore('Wins')


Players.PlayerAdded:Connect(function(Player)
	
	local Stats = Instance.new('Folder')
	Stats.Name = 'leaderstats'
	Stats.Parent = Player
	
	local Wins = Instance.new('IntValue')
	Wins.Name = 'Wins'
	Wins.Parent = Stats
	
	
	local Data = WinsDataStore:GetAsync(Player.UserId)
	
	
	if Data then
		for name, value in pairs(Data.Stats) do
			Stats[name].Value = value
		end
		
	end
	
		
		
end)

Players.PlayerRemoving:Connect(function(Player)
	for _, Player in pairs(game.Players:GetPlayers()) do
		local SaveData = {}
		

		
		for _,stat in pairs(Player.leaderstats:GetChildren()) do
			SaveData[stat.Name] = stat.Value
		end
		

		
		WinsDataStore:SetAsync(Player.UserId,SaveData)
		
	end
	
	wait(2)
end)
	
	

game:BindToClose(function()
	for _, Player in pairs(game.Players:GetPlayers()) do
		local SaveData = {}
		

		
		for _,stat in pairs(Player.leaderstats:GetChildren()) do
			SaveData[stat.Name] = stat.Value
		end
		

		
		WinsDataStore:SetAsync(Player.UserId,SaveData)
		
	end
	
	wait(2)
end)
1 Like

@Quwanterz Nevermind, I just changed my script to:

local DataStoreService = game:GetService('DataStoreService')

local WinsDataStore = DataStoreService:GetDataStore('Wins')


script.Parent.UserId:GetPropertyChangedSignal('Value'):Connect(function()
	local PlayerName = game.Players:GetNameFromUserIdAsync(script.Parent.UserId.Value)
	local Player = game.Players:GetPlayerByUserId(script.Parent.UserId.Value)
	local Data = WinsDataStore:GetAsync(script.Parent.UserId.Value)
	
	if Data then

		script.Parent.Parent.Parent.Podium.MiddleBlock.SurfaceGui.PlayerName.Text = PlayerName
		script.Parent.Parent.Parent.Podium.MiddleBlock.SurfaceGui.WinsAmount.Text = Data.Stats.Wins
	end		
end)

and kept the SaveData = {Stats = {}}
Thing

1 Like