Want Children of Folder to save when player leaves

I have a script that whenever a player purchases a sword, a new StringValue gets put into a folder called “OwnedSwords”. When the StringValue gets added, I want to adjust the script so that when the player leaves the game, then all the children get saved and then get reput into the “OwnedSwords” when the player rejoins. This is the script that adds the StringValue when the player purchases a sword;

local ReplicatedStorage = game:GetService("ReplicatedStorage")
local swordPurchasedEvent = ReplicatedStorage.Events:WaitForChild("SwordPurchasedEvent")

local swordPrices = {
	["Spartan Sword"] = 500,
	["Steampunk Sword"] = 1000,
	["Skelly Slayer"] = 1500,
	["Signifier Sword"] = 2000,
	["Darkheart"] = 2750,
	["Overseer Wrath"] = 5000,
	["Serpent Sword"] = 6000,
	["Light Blade"] = 7500,
	["Plated Sword"] = 9250,
	["Uppercut Sword"] = 11000,
	["Evil Knight"] = 13450,
	["Arabian Knight"] = 16000,
	["Spec Elipson"] = 19000,
	["Interstellar Sword"] = 23500,
	["RGB Sword"] = 31000,
	["Violet Sword"] = 40000,
	["Gilded Sword"] = 52500,
	["Omi Odachi Sword"] = 65000,
	["Orc Blade"] = 80000,
	["Sorcus Sword"] = 97500,
	["Sword Of Darkness"] = 111000,
	["Amethyst Rock Sword"] = 125000,
	["Blood Sword"] = 200000,
	["Molten Scythe"] = 250000,
}

swordPurchasedEvent.OnServerEvent:Connect(function(player, sword)
	print("Received sword:", sword)
	local price = swordPrices[tostring(sword)]
	print("Price:", price)
	if price then
		if player.leaderstats.Gems.Value >= price then
			print("Deducting gems...")
			player.leaderstats.Gems.Value = player.leaderstats.Gems.Value - price
			print("Gems deducted successfully.")
			local stringValue = Instance.new('StringValue', player)
			stringValue.Parent = player.OwnedSwords
			stringValue.Name = tostring(sword)
		else
			print("Player does not have enough gems to purchase.")
		end
	else
		print("Sword price not found.")
	end
end)

And the script that creates the folder when the player joins is:

game.Players.PlayerAdded:Connect(function(player)
	local swordFolder = Instance.new('Folder', player)
	swordFolder.Name = "OwnedSwords"
end)

Any help or guidance would be appreciated, thanks alot.

You can use Folders for a DataStore.

Here is a good video that explains how:

1 Like

Hey, thanks alot. I watched through the video for a bit and got a bit lost along the way. I think I’m struggling on how to understand it since the video showcases datastore for values inside of the folders folders children, if you see what I mean.

This is what I’ve written so far from the video, any additional help or insight would be really appreciated. I stopped midway through the PlayerRemoving since that’s where the video starting tracking a bit off my needs and where I got a bit confused. The script is below, thanks! :happy3:

local dataStoreService = game:GetService("DataStoreService")
local dataStore = dataStoreService:GetDataStore("Player")

game.Players.PlayerAdded:Connect(function(player)
	local success, data = pcall(dataStore.GetAsync, dataStore, player.UserId)
	if success == false then player:Kick("Failed to load data, please rejoin") return end
	print("Loaded:", data)
	data = data or {}
	
	local folder = game.ServerStorage.OwnedSwords
	local subData = folder:GetChildren() or {}
		local clone = folder:Clone()
		clone.Parent = player
end)

game.Players.PlayerRemoving:Connect(function(player)
	local data = {}
	local folder = game.ServerStorage.OwnedSwords
end)

Resolved! Found a script that works perfectly fine.

local DataStore = game.DataStoreService:GetDataStore("InstanceSave")

local function SaveItems(plr: Player)
	local FolderToSave = plr:WaitForChild("OwnedSwords")
	local Data = {}
	for i,v: BoolValue in ipairs(FolderToSave:GetChildren()) do
		table.insert(Data,{
			v.Name,
		})
	end
	local s,e
	repeat
		s,e = pcall(function()
			DataStore:UpdateAsync("Items_"..plr.UserId,function()
				return Data
			end)
		end)
		task.wait()
	until s
	if not s then
		warn("Failed To Save Items, error: "..e)
	end
end


local function LoadItems(plr : Player)
	local FolderToSave = plr:WaitForChild("OwnedSwords") 
	local s,e
	local Data
	repeat
		s,e = pcall(function()
			Data = DataStore:GetAsync("Items_"..plr.UserId)
		end)
	until s or not game.Players:FindFirstChild(plr.Name)
	if not Data then return end
	if s then
		for i,v in ipairs(Data) do
			local NewBool = Instance.new("StringValue",plr:WaitForChild("OwnedSwords"))
			NewBool.Name = v[1]
		end
	else
		warn("Failed To Save Items, error: "..e)
	end
end

game.Players.PlayerAdded:Connect(LoadItems)
game.Players.PlayerRemoving:Connect(SaveItems)

game:BindToClose(function()
	for i, plr: Player in ipairs(game.Players:GetChildren()) do
		SaveItems(plr)
	end
end)