How to add data saving to my script?

so im making guess the anime game and i have problem with the leaderstats.
I have two leaderstats: Stage and Points.
Stage is show u what stage u are and you can purchase for skip stage.
Points is how much door/stage u did opened so far.
I want to save the data points only but i dont know how.
How do i save the data of the points without broke the stages or the checkpoints script.
anyway this is the scripts:

Checkpoints(Script in ServerScriptService):

local Players = game:GetService("Players")
local MarketplaceService = game:GetService("MarketplaceService")
local ReplicatedStorage = game:GetService("ReplicatedStorage")
local SkipStage = ReplicatedStorage:WaitForChild("SkipStage")

local Checkpoints = workspace:WaitForChild("Checkpoints")
local inGameStartupPlayers = {}
local CurrentStage = {}
local CurrentPoints = {}
local TouchDb = {}

local ProductId = 1145455293
local Products = {
	{
		ProductPrice = 5, --The price from the Developer Product.
		ProductId = 1141211330 -- The ID from the Developer Product.	
	},
	{
		ProductPrice = 25, --The price from the Developer Product.
		ProductId = 1141214738 -- The ID from the Developer Product.	
	},
	{
		ProductPrice = 50, --The price from the Developer Product.
		ProductId = 1141214866 -- The ID from the Developer Product.	
	},
	{
		ProductPrice = 100, --The price from the Developer Product.
		ProductId = 1141214989 -- The ID from the Developer Product.	
	},
	{
		ProductPrice = 1000, --The price from the Developer Product.
		ProductId = 1141215192 -- The ID from the Developer Product.	
	},
	
}


local function NewCharacter(player, char)
	local TempCurrentStage = CurrentStage[player.UserId]
	if TempCurrentStage ~= nil then
		local TempCheckpoint = Checkpoints:FindFirstChild(TempCurrentStage)
		if TempCheckpoint ~= nil then
			repeat wait(0.1) until char.PrimaryPart ~= nil
			char:SetPrimaryPartCFrame(CFrame.new(TempCheckpoint.Position + Vector3.new(0, 3, 0)) * CFrame.Angles(0, math.rad(TempCheckpoint.Orientation.Y) + math.rad(90), 0))
		end
	end
end

local function NewPlayer(player)
	CurrentStage[player.UserId] = 1

	local leaderstats = Instance.new("Folder", player)
	leaderstats.Name = "leaderstats"
	local Stage = Instance.new("IntValue", leaderstats)
	Stage.Name = "Stage"
	Stage.Value = 1
	
	local Points = Instance.new("IntValue", leaderstats)
	Points.Name = "Points"
	Points.Value = 0
	
	local TempChar = player.Character
	if TempChar ~= nil then
		NewCharacter(player, TempChar)
	end
	player.CharacterAdded:Connect(function(char)
		NewCharacter(player, char)
	end)
end

Players.PlayerAdded:Connect(function(player)
	if inGameStartupPlayers[player] == nil then
		NewPlayer(player)
	end
end)

Players.PlayerRemoving:Connect(function(player)
	CurrentStage[player.UserId] = nil
end)

SkipStage.OnServerInvoke = function(player)
	local connection
	local leaderstats = player:FindFirstChild("leaderstats")
	if leaderstats ~= nil then
		local Stage = leaderstats:FindFirstChild("Stage")
		if Stage ~= nil then
			if #Checkpoints:GetChildren() ~= Stage.Value then
				local PurchaseResult = "Purchase Failed"
				connection = MarketplaceService.PromptProductPurchaseFinished:Connect(function(userId, productId, purchased)
					if player.UserId == userId and productId == ProductId then
						if purchased == true then
							PurchaseResult = "Success"
						end
					end
					connection:Disconnect()
				end)
				MarketplaceService:PromptProductPurchase(player, ProductId)
				repeat wait(0.1) until connection.Connected == false or Players:GetPlayerByUserId(player.UserId) == nil
				return PurchaseResult
			else
				return "You have reached the highest stage!"
			end
		end
	end
end

MarketplaceService.ProcessReceipt = function(recieptInfo)
	local player = Players:GetPlayerByUserId(recieptInfo.PlayerId)

	-- Don't grant purchase if the player left or is not here for whatever reason
	if not player then
		return Enum.ProductPurchaseDecision.NotProcessedYet
	end

	if recieptInfo.ProductId == ProductId then
		CurrentStage[player.UserId] = CurrentStage[player.UserId] + 1
		local leaderstats = player:FindFirstChild("leaderstats")
		if leaderstats ~= nil then
			local Stage = leaderstats:FindFirstChild("Stage")
			if Stage ~= nil then
				Stage.Value = CurrentStage[player.UserId]
			end
		end
		local TempChar = player.Character
		if TempChar ~= nil then
			NewCharacter(player, TempChar)
		end
		return Enum.ProductPurchaseDecision.PurchaseGranted
	end

	-- Loop through the product data
	for _, productData in ipairs(Products) do
		-- if the productData's productId matches the prouct being purchased's id then continue
		if productData.ProductId == recieptInfo.ProductId then
			-- Since IncrementAsync can error we wrap it in a pcall (protected call)
			local success, err = pcall(function()
				game:GetService("DataStoreService"):GetOrderedDataStore("TopDonators"):IncrementAsync(player.UserId, productData.ProductPrice)
			end)
			-- If it errored we wanna know what went wrong
			if success then
				return Enum.ProductPurchaseDecision.PurchaseGranted
			else
				warn("Failed to increment amount donated. Error thrown: " .. err)
				return Enum.ProductPurchaseDecision.NotProcessedYet
			end
		end
	end

	return Enum.ProductPurchaseDecision.NotProcessedYet
end

for i,v in pairs(Checkpoints:GetChildren()) do
	local StageNum = tonumber(v.Name)
	v.Touched:Connect(function(hit)
		local char = hit.Parent
		if char ~= nil then
			local Humanoid = char:FindFirstChildOfClass("Humanoid")
			if Humanoid ~= nil and Humanoid.Health > 0 then
				local player = Players:GetPlayerFromCharacter(char)
				if player ~= nil and (TouchDb[player.UserId] or 0) + 1 <= os.time() then
					TouchDb[player.UserId] = os.time()
					local TempCurrentStage = CurrentStage[player.UserId]
					if TempCurrentStage == StageNum - 1 then
						CurrentStage[player.UserId] = StageNum
						local TempLeaderstats = player:FindFirstChild("leaderstats")
						if TempLeaderstats ~= nil then
							local TempStage = TempLeaderstats:FindFirstChild("Stage")
							if TempStage ~= nil then
								TempStage.Value = StageNum
							end
						end
					end
				end
			end
		end
	end)
end

inGameStartupPlayers = Players:GetPlayers()
for i,v in pairs(inGameStartupPlayers) do
	spawn(function()
		NewPlayer(v)
	end)
end

inGameStartupPlayers = {}

SaveData(Script in ServerScriptService)

local DataStoreService = game:GetService("DataStoreService")
local dataStore = DataStoreService:GetDataStore("MyDataStore") -- This can be changed to whatever you want

local function saveData(player) -- The functions that saves data

	local tableToSave = {
		player.leaderstats.Points.Value; -- First value from the table
		 
	}

	local success, err = pcall(function()
		dataStore:SetAsync(player.UserId, tableToSave) -- Save the data with the player UserId, and the table we wanna save
	end)

	if success then -- If the data has been saved
		print("Data has been saved!")
	else -- Else if the save failed
		print("Data hasn't been saved!")
		warn(err)		
	end
end

game.Players.PlayerAdded:Connect(function(player) -- When a player joins the game

	-- // Assigning player stats //
	local leaderstats = Instance.new("Folder")
	leaderstats.Name = "leaderstats"
	leaderstats.Parent = player

	local Points = Instance.new("IntValue")
	Points.Name = "Points"
	Points.Parent = leaderstats

	

	local data -- We will define the data here so we can use it later, this data is the table we saved
	local success, err = pcall(function()

		data = dataStore:GetAsync(player.UserId) -- Get the data from the datastore

	end)

	if success then -- If there were no errors and player loaded the data

		Points.Value = data[1] -- Set the money to the first value of the table (data)
		 -- Set the coins to the second value of the table (data)

	else -- The player didn't load in the data, and probably is a new player
		print("The player has no data!") -- The default will be set to 0
	end

end)

game.Players.PlayerRemoving:Connect(function(player) -- When a player leaves
	local success, err  = pcall(function()
		saveData(player) -- Save the data
	end)

	if success then
		print("Data has been saved")
	else
		print("Data has not been saved!")
	end
end)

game:BindToClose(function() -- When the server shuts down
	for _, player in pairs(game.Players:GetPlayers()) do -- Loop through all the players
		local success, err  = pcall(function()
			saveData(player) -- Save the data
		end)

		if success then
			print("Data has been saved")
		else
			print("Data has not been saved!")
		end
	end
end)