Datastore error: Unable to assign property value. string expected, got nil

trying to create a datastore script that handles how many credits a player has, and what trains they have. everything in this code works, except for the line in the image below. would really appreciate a solution

----{ Variables
--{ Main

--{ Services
local Players = game:GetService("Players")
local DataStoreService = game:GetService("DataStoreService")
local RunService = game:GetService("RunService")

--{ Objects
local PlayerData_Folder = script.PlayerData
local Database = DataStoreService:GetDataStore("PlayerData")
local sessionData = {}

local RailCredits_Handler = require(script:WaitForChild("RailCredits_Handler"))

--{ Values

----{ Code
function PlayerAdded(player)
	local DataFolder = Instance.new("Folder")
	DataFolder.Name = "PlayerData"
	
	local RailCredits = Instance.new("IntValue")
	RailCredits.Name = "RailCredits"
	RailCredits.Parent = DataFolder
	local TrainsOwned = Instance.new("StringValue")
	TrainsOwned.Name = "TrainsOwned"
	TrainsOwned.Parent = DataFolder

	local success = nil
	local playerData = nil
	local attempt = 1

	success, playerData = pcall(function()
		return Database:GetAsync(player.UserId)
	end)

	if success then
		print("Connected to database")
		if not playerData then
			print("Assigning default data")
			playerData = {
				["RailCredits"] = 50,
				["TrainsOwned"] = "Nul"
			}
		end
		sessionData[player.UserId] = playerData
	else
		warn("Unable to get data for " .. player.UserId)
		player:Kick("Unable to load data.")
	end

	RailCredits.Value = sessionData[player.UserId].RailCredits
	RailCredits.Changed:Connect(function()
		sessionData[player.UserId].RailCredits = RailCredits.Value
	end)

	TrainsOwned.Value = sessionData[player.UserId].TrainsOwned
	TrainsOwned.Changed:Connect(function()
		sessionData[player.UserId].TrainsOwned = TrainsOwned.Value
	end)

	DataFolder.Parent = player
end

function PlayerLeaving(player)
	if sessionData[player.UserId] then
		local success = nil
		local errorMessage = nil
		local attempt = 1

		repeat
			success, errorMessage = pcall(function()
				Database:SetAsync(player.UserId, sessionData[player.UserId])
			end)

			attempt += 1

			if not success then
				warn(errorMessage)
				task.wait(2)
			end
		until success or attempt == 5

		if success then
			print("Data saved for " .. player.Name)
		else
			warn("Unable to save data for " .. player.Name)
		end
	end
end

function ServerShutdown()
	if RunService:IsStudio() then
		return
	end
	
	for i, player in ipairs(Players:GetPlayers()) do
		task.spawn(function()
			PlayerLeaving(player)
		end)
	end
end

Players.PlayerAdded:Connect(function(player)
	PlayerAdded(player)
end)

Players.PlayerRemoving:Connect(function(player)
	PlayerLeaving(player)
end)

game:BindToClose(ServerShutdown)

image
image

This error is likely occurring as sessionData[player.UserId] does not contain TrainsOwned. Have you tried printing sessionData[player.UserId] and seeing the output?

1 Like

The error message suggests that you are trying to assign a nil value to a property that expects a string. Looking at your code, the issue seems to be with the line:

TrainsOwned.Value = sessionData[player.UserId].TrainsOwned

In the PlayerAdded function, you’re assigning the sessionData[player.UserId].TrainsOwned value directly to the Value property of TrainsOwned. However, if sessionData[player.UserId].TrainsOwned is nil, it will cause an error because the Value property expects a string.

To fix this issue, you can modify the code to handle the nil case and provide a default value. Here’s an updated version of the line:

TrainsOwned.Value = sessionData[player.UserId].TrainsOwned or ""

In this updated line, if sessionData[player.UserId].TrainsOwned is nil, it will be replaced with an empty string "". This ensures that the Value property of TrainsOwned always receives a string value and avoids the error.

Make sure to apply this fix to the line mentioned above and see if it resolves the issue.

(Whoops, replied to the wrong message.)