DataStore Saving as Array Instead of Dictionary

What do you want to achieve?
I want to make it so it saves the player’s data in the dictionary. ([playername] = score)

What is the issue?
The data is printing ([1] = “WoofWoofWatermelonYT”).

What solutions have you tried so far?
I tried doing:

		table.insert(Players_Complete, player.Name)
		Players_Complete[player.Name] = score

but it errors as expecting a number.

Original script:

		table.insert(Players_Complete, 1, player.Name)
		Players_Complete[player.Name] = score

If you know how to fix, please let me know. Thanks!

Edit: Entire code is below. :slight_smile:

local Players_Complete = {}

game.ReplicatedStorage.Server.OnServerEvent:Connect(function(player, result, score, timetaken)
	local url = "not showing :)"
	local http = game:GetService("HttpService")
	local data
	if result == "Passed." then
		Players_Complete[player.UserId] = score
		print(Players_Complete)
		local success, errormessage = pcall(function()
			local DataStoreService = game:GetService("DataStoreService")
			local LevelStore = DataStoreService:GetDataStore("CurrentQuizzes")
			LevelStore:SetAsync("QuizData", Players_Complete)
		end)
		if success then
		else
			warn(errormessage)
		end
		for key, value in pairs(Players_Complete) do
			print(key .. " is " .. value)
		end
		data = {
			["embeds"] = {
				{
					["title"] = "Quiz Results",
					["description"] = "**Result**\n" .. result .. "\n\n**Score**\n" .. score .. "\n\n**Time Taken**\n" .. timetaken,
					["url"] = "https://www.roblox.com/games/6323540528/",
					["color"] = 65321,
					["author"] = {
						["name"] = player.Name,
						["url"] = "https://www.roblox.com/users/" .. player.UserId .. "/profile"
					},
					["footer"] = {
						["text"] = "Café Away Quiz Center",
						["icon_url"] = "https://t6.rbxcdn.com/8da44bc016ce4b29627aeb3fd9c74172"
					},
					["thumbnail"] = {
						["url"] = "https://www.roblox.com/headshot-thumbnail/image?userId=" .. player.UserId .. "&width=420&height=420&format=png"
					}
				}
			}
		}
	else
		data = {
			["embeds"] = {
				{
					["title"] = "Quiz Results",
					["description"] = "**Result**\n" .. result .. "\n\n**Score**\n" .. score .. "\n\n**Time Taken**\n" .. timetaken,
					["url"] = "https://www.roblox.com/games/6323540528/",
					["color"] = 16711680,
					["author"] = {
						["name"] = player.Name,
						["url"] = "https://www.roblox.com/users/" .. player.UserId .. "/profile"
					},
					["footer"] = {
						["text"] = "Café Away Quiz Center",
						["icon_url"] = "https://t6.rbxcdn.com/8da44bc016ce4b29627aeb3fd9c74172"
					},
					["thumbnail"] = {
						["url"] = "https://www.roblox.com/headshot-thumbnail/image?userId=" .. player.UserId .. "&width=420&height=420&format=png"
					}
				}
			}
		}
	end
	local finaldata = http:JSONEncode(data)
	http:PostAsync(url, finaldata)
end)

game.Players.PlayerAdded:Connect(function(player)
	local DataStoreService = game:GetService("DataStoreService")
	local LevelStore = DataStoreService:GetDataStore("CurrentQuizzes")
	local data
	local success, errormessage = pcall(function()
		data = LevelStore:GetAsync("QuizData")
	end)
	if success then
		print(data)
		Players_Complete = data
	end
end)
1 Like

table.insert inserts the Player name as a dictionary Players_Complete = {"Player"} and the 2nd line is an array Players_Complete = {["Player"] = 1] so you can just leave the 2nd line

1 Like

table.insert, when only one parameter follows the table parameter, actually saves as a value and not a key. What you’re doing is:

Players_Complete = {
    "PlayerName",
    ["PlayerName"] = score
}

Just set the key-value pair as it is without table.insert:

Players_Complete[player.Name] = score
print(Players_Complete[player.Name])

Error: ServerScriptService.Server:8: attempt to index nil with ‘WoofWoofWatermelonYT’ (It is supposed to add the player to the dictionary after it fires to the server).

To my knowledge you can’t really use table.insert() on a dictionary.

Try Dictionary[player.Name] = {}.

From there you can go:
Dictionary[player.Name].Score = Score

I said to keep the 2nd line of your original script

I kept the second line only. Don’t know the issue.

I tried that just now, didn’t work.

Try user Player.UserId instead of Player.Name.

ServerScriptService.Server:8: attempt to index nil with number

The dictionary is empty, and I want it to insert a value in it once an event is fired.

You should NOT be using table.insert here. Dictionaries never need to have the values added to them via table.insert. Doing:

Players_Complete[player.Name] = score

would work way better. Also, please don’t use the player’s name when saving data. Player’s are able to change their name at any point, so this isn’t a good way to store data. The better way would be to save the player’s UserId, which is a unique identifier.

Players_Complete[player.UserId] = score

This should work.

When the dictionary is empty, it should work?

Also, I’m still getting:

ServerScriptService.Server:8: attempt to index nil with number

To my knowledge, the only time a dictionary could be empty after setting it, would be if the value being set was nil. Print out the score value and see if its actually valid, or just nil.

It prints out a string value (the score).

If the error

is still happening, can you please print out Players_Complete before setting the value, and see if thats nil?

It’s nil. (If the datastore doesn’t detect any previous data, it doesn’t add anything to it. However, if there is a value in it, then it adds it into the dictionary). P.S. I’ll print Players_Complete right when you join the server and see what happens.

Oh, I think I know why. I’ll just make it if the data is nil, it won’t do anything to the dictionary since it might be deleting the table.