Hey there! So I’ve been inspired by Onett, who told me that he makes his developer messages by using a Datastore to get the message, but I can’t figure this out! What’s happening here? (The issue is that my Gui pops up with “None”)
local Datastore = game:GetService("DataStoreService"):GetDataStore("MessageTest")
local messageToDisplay = Datastore:GetAsync(1)
while true do
wait(5)
if Datastore:GetAsync(1) == "None" or Datastore:GetAsync(1) == "" then
for _, player in pairs(game.Players:GetPlayers()) do
player.PlayerGui:FindFirstChild("Message"):Destroy()
end
messageToDisplay = "None"
elseif Datastore:GetAsync(1) ~= "None" and Datastore:GetAsync(1) ~= "" then
print("''" .. Datastore:GetAsync(1) .. "''")
messageToDisplay = Datastore:GetAsync(1) or "None"
script.Message.TextLabel.Text = messageToDisplay
for _, player in pairs(game.Players:GetPlayers()) do
script.Message:Clone().Parent = player.PlayerGui
end
end
end
If the datastore is blank, it will always return “None” as the way it is set up in the first if statement, is that if the datastore is blank or equal to “None” then it returns “None”.
You will have to use :SetAsync() if you would like to make the data not blank.
Whew. You are making far too many DataStore GetAsync calls per iteration. Call GetAsync once per iteration and read that value instead of performing GetAsync several times over. Furthermore, you need to handle nil cases as well.
local Players = game:GetService("Players")
local MessageStore = game:GetService("DataStoreService"):GetDataStore("MessageTest")
while true do
local success, messageToDisplay = pcall(MessageStore.GetAsync, MessageStore, 1)
if success and messageToDisplay then
print(messageToDisplay)
script.Message.TextLabel.Text = messageToDisplay
for _, player in pairs(Players:GetPlayers()) do
script.Message:Clone().Parent = player.PlayerGui
end
end
wait(5)
end
Some commentary: I cut out quite a bit from your code and mutated it. It’s still not up to par and I think that work needs to be done on it, but for the sake of answering the question I’ve put this up. Here’s the additional commentary if it interests you:
I do not recommend a while loop for a message display unless it’s solely for testing. The message will constantly get displayed to the player and become disruptive to their gameplay.
Considering you’re working with Guis, clients should be requesting for potentially new messages via a RemoteFunction. When the server hears the request, it ensures that the player hasn’t previously requested for a message (to avoid abusing the remote and expending the budget). If the player is clear, the server sends them the message as a return.
Again, considering you’re working with Guis, the server should not be involved in anything beyond replication of the Gui. When a client closes a Gui, the server will still acknowledge the client has it because that change isn’t propagated to the server.
That being said, your original code would throw an error or should. If PlayerGui:FindFirstChild("Message") returns nil, you’ll be attempting to call nil:Destroy() which is obviously invalid.
Please get into the habit of using pcalls with DataStores! DataStore methods perform web calls internally and can fail for any given reason, especially if the endpoint goes down (a particularly prominent issue when there’s high traffic on Roblox).
My code attempts to resolve a few issues but it is lackluster. Please do not take it as a catch-all fix to your problem. There are several details about this piece of code that need work.