Hello! I made codes system and I want save already used codes by player in datastore! How I can make this? I must use RemoteEvent/Function?
You need metatables for that, that’s what I know.
You don’t… just simply create table in datastore and insert the used code there and then before giving the award in the server check if the code isn’t already in the saved table…
I have this script (it’s just a line)
experienceStore:SetAsync(Codes[Box.Text], true)
But I can’t use DataStore in LocalScript
You have to call DataStores on the server, the more easier approach would be is to just use a PlayerAdded
event, & set up your DataStores from there
Yes, you can use a RemoteEvent
to call from the client/server in order to save the data properly that way, you can pass the Codes[Box.Text]
& the bool value over for the server to receive and call SetAsync
that way
You’d want to fire a RemoteEvent
to the server with the Text
included in the TextBox
, then create an if
statement to check if the code is right and has been used using DataStore:GetAsync(userId).
If the code’s right and wasn’t used, create a DataStore:UpdateAsync(userId, function(oldValue)) to update the table
by adding in the code in the table (returning
the value to add for the oldValue
). Here’s a sample on how this works:
local codes = {"code1", "code2", "code3"}
RemoteEvent.OnServerEvent:Connect(function(plr, text)
if not table.find(codes, text) or DataStore:GetAsync(plr.UserId)[text] then
return end
DataStore:UpdateAsync(plr.UserId, function(oldValue) --{"code1", "code2"}
table.insert(oldValue, code) --inserting "code3" (example)
return oldValue --returning the table with the new value
end)
end)
Ok, I paste this example script but game think:
All codes are expired! (I made notification system for codes)
Do you want all scripts?
Sure, I’ll troubleshoot the issue in the code - I haven’t tested mine yet, so it could be the case, but I’ll see the source.
Scripts:
CodesHandler.lua (LocalScript)
local Codes = {
["babyshark"] = 50,
["CONSOLE"] = 343,
["Jarro"] = 300,
["alpha"] = 1000,
["devs"] = 2000,
["kromkowo.pl"] = 100000,
["Eurovision2021"] = 2021,
["ILikeDiscoteque"] = 2153,
["kasjmirr"] = 9000,
["kasjmirrhouse1_50Visits"] = 50,
["party"] = 984,
["watermelon"] = 5000
}
local Box = script.Parent.MainHandlerCode.TextBox
local code = Box.Text
local btn = script.Parent.MainHandlerCode.TextButton
local Value = game.Players.LocalPlayer.PlayerData.Credits -- I used this for example :D
btn.MouseButton1Up:Connect(function(player)
if Box.Text == Codes[Box.Text] then
local text = Box.Text
Value.Value += Codes[Box.Text]
btn.TextLabel.Text = "Successfully redeemed code ".. Box.Text .."!"
local Redeem = game.ReplicatedStorage.RedemCode
Redeem:FireServer(player, text)
local sgui = game.StarterGui
local textTit = "+".. Codes[Box.Text] .." Kas$"
sgui:SetCore("SendNotification", {
Title = textTit,
Text = "Redeemed code " .. Box.Text,
Duration = 2.5
}
)
wait(0.5)
btn.TextLabel.Text = "Redeem"
else
local sgui = game.StarterGui
local textTit = "Unable to reddem code ".. Box.Text
sgui:SetCore("SendNotification", {
Title = textTit,
Text = "Code " .. Box.Text .. " is expired or don't exist",
Duration = 2.5
}
)
end
end)
RedeemCode.lua (Server Script for Remote Event)
local RemoteEvent = game.ReplicatedStorage.RedemCode
local codes = {"codes"}
local DataStore = game:GetService("DataStoreService")
RemoteEvent.OnServerEvent:Connect(function(plr, text)
local userId = plr.UserId
if not table.find(codes, text) or DataStore:GetAsync(plr.UserId)[text] then
return end
DataStore:UpdateAsync(userId, function(oldValue) --{"code1", "code2"}
table.insert(oldValue, codes) --inserting "code3" (example)
return oldValue --returning the table with the new value
end)
end)
local dds = game:GetService("DataStoreService") --this is a service for DataStores
local DataStore = dds:GetDataStore("Codes") --DataStore is needed
You don’t have to define the userId - instead, use plr.UserId
in both of the parameters
DataStore:UpdateAsync(plr.UserId, function(oldValue)
DataStore:GetAsync(plr.UserId)[text]
Don’t increase the value (award) for the player in LocalScript - they’re exploitable and will cause security flaws. Instead, update (add) their value in the Script. Don’t check for the code in LocalScript either, as you’re leaking them (seen by exploiters), and they’re already being checked in the Script.
In what script I must paste this?
Above:
local codes = {"code1", "code2", "code3"}
Still game don’t want redeem code
Is there an error in the output? Are API services enabled in the game settings
?
No errors, and I have enabled API Service
--Script in ServerScriptService
local dds = game:GetService("DataStoreService")
local DataStore = dds:GetDataStore("Codes")
local rep = game:GetService("ReplicatedStorage")
local RemoteEvent = rep.RemoteEventName --replace "RemoteEventName"
local codes = {
["code1"] = 50,
["code2"] = 100,
["code3"] = 150
}
RemoteEvent.OnServerEvent:Connect(function(plr, text)
local hasRedeemed
local success, failed = pcall(function()
hasRedeemed = DataStore:GetAsync(plr.UserId)[text] or false
end)
if not codes[text] then --if code doesn't exist then
RemoteEvent:FireClient(plr, "invalid"); print("invalid"); return
elseif hasRedeemed then --if used then
RemoteEvent:FireClient(plr, "used"); print("used"); return
end
--if code is in table and hasn't been used then
plr.leaderstats.Points.Value += codes[text]
RemoteEvent:FireClient(plr, "redeemed"); print("redeemed")
--[ updating data ]
DataStore:UpdateAsync(plr.UserId, function(oldValue) --{"code1", "code2"}
if oldValue == nil then oldValue = {} end --if they're new then create a table
oldValue[text] = codes[text] --saves the code (with the value of points earned)
return oldValue --returning the table with the new value
end)
end)
With this script, you can use RemoteEvents
, locally (listening to :FireClient(msg)
), with these messages in the parameter (msg
):
- “invalid” - the code isn’t in the table,
- “used” - the code was already used by the player,
- “redeemed” - successfully redeemed.
RemoteEvent.OnClientEvent:Connect(function(msg)
print(msg)
if msg == "redeemed" then
print("the code was redeemed as well!")
--SetCore stuff
end
end)