Hi everyone,
I’ve been working on a system to manage player data using ProfileStore
by loleris, and I’d love some feedback on it. The system handles things like saving/loading inventory data and managing player sessions. It works, but I feel like there’s room for improvement, and I want to make sure I’m doing things the right way.
What I Need Help With:
-
Better Practices: Am I using
ProfileStore
the way it’s meant to be used? - General Feedback: Anything else you see that could be improved or cleaned up?
--<Services>--
local runService = game:GetService("RunService")
local players = game:GetService("Players")
--<Modules>--
local profileStoreModule = require(script.Parent:FindFirstChild("ProfileStore"))
local defaultData = require(script.Parent.Default_Data)
--<Variables>--
local playersInventoryFolder = script.Parent.Parent.Parent.Players_Inventories
local inventoryTemplate = playersInventoryFolder:FindFirstChild("Inventory_Temp")
local key = "MainKey"
if runService:IsStudio() then
key = "StudioKey"
end
local profileStore = profileStoreModule.New(key, defaultData)
local Profiles: {[player]: typeof(playerStore:StartSessionAsync())} = {}
local Player = {}
Player.__index = Player
function Player.new(newPlayer: Player)
local self = setmetatable({}, Player)
self.Player = newPlayer
self.Character = newPlayer.Character
self.Player.CharacterAdded:Connect(function(character: Model)
self.Character = character
end)
--Extra variables
self.CurrentlySaving = false
self.CurrentlyLoading = false
self.UnLoading = false
self.UserId = self.Player.UserId
self:CreateProfile(self.Player)
return self
end
function Player:CreateProfile(player: Player)
print("Data key name: "..profileStore.Name)
local profile = profileStore:StartSessionAsync(`{player.UserId}`, {
Cancel = function()
return player.Parent ~= players
end,
})
if profile ~= nil then
profile:AddUserId(player.UserId)
profile:Reconcile()
profile.OnSessionEnd:Connect(function()
Profiles[player] = nil
player:Kick("Profile session end - Please rejoin")
end)
if player.Parent == players then
Profiles[player] = profile
print(`Profile loaded for {player.DisplayName}!`)
self:CloneDefaultInventory()
task.wait()
self:LoadData(player)
else
profile:EndSession()
end
else
player:Kick("Profile load fail - Please rejoin")
end
end
function Player:LoadData(player: Player)
local playerInventoryModule = require(playersInventoryFolder:FindFirstChild(player.UserId))
if not playerInventoryModule then
return false
end
local profile = Profiles[player]
if profile and profile.Data then
local success, errorMsg = pcall(function()
playerInventoryModule.SendInventoryData(profile.Data.Inventory)
end)
if success then
print(profile.Data)
--task.wait(3)
--for _, player in ipairs(players:GetPlayers()) do
-- playerInventoryModule.AddItem("Wooden Axe")
-- print(playerInventoryModule["Inventory"])
--end
else
warn("Failed to save data for " .. player.DisplayName .. ": " .. errorMsg)
end
else
warn("No profile found for "..player.DisplayName)
end
end
function Player:SaveData(player: Player)
local profile = Profiles[player]
if profile ~= nil then
local success, errorMsg = pcall(function()
profile.Data.Inventory = self:GetPlayerInventory(player)
end)
if success then
profile:EndSession()
print(player.DisplayName .. "'s data successfully saved!")
end
end
end
function Player:CloneDefaultInventory()
if not inventoryTemplate then
return
end
local defaultInventory = inventoryTemplate:Clone()
defaultInventory.Name = self.UserId
defaultInventory.Parent = playersInventoryFolder
end
function Player:GetPlayerInventory(player: Player)
local playerInventoryModule = require(playersInventoryFolder:FindFirstChild(player.UserId))
if not playerInventoryModule then
return
end
return playerInventoryModule.GetInventoryData()
end
return Player
I appreciate any tips or suggestions you can provide—I’m continually learning and eager to improve, so your insights would be incredibly valuable.