(Server -> Client -> Server) Communication

Does anyone know the most efficient way for a Server to send a request to a Client (through a GUI Pop-up) and for the Client to respond to the Server without the Client being able to just make the GUI visible and firing the RemoteEvent/Function without even receiving the request from the Server.

This might seem easy but I know there are multiple ways, just want to know the easiest. Thanks :slightly_smiling_face:

Just check that the server is requesting input on the server before doing anything with it. There isn’t really a reliable way to do it other than that.

Any particular way you would suggest doing this?

In the OnServerEvent include a variable as a key, then use said key in the :FireServer() ?

I think that’d work, just make sure you randomly generate the key and you’re good!

If its player specific you can just create a bool value in the player and change it to true when a request is needed.

Eh, I don’t think that is very reliable and also a waste of server resources to have a instance for every single request/communication I have with the client.

I mean just create one when the player joins and set it to true when the request is needed for the player and use an if statement? This isnt a waste of server resources.

Hm, that isn’t 100% though. If the Event/Function is very important, exploiters could potentially use anti-exploits to randomally generate numbers until it’s the same as one you created - unless you have a cooldown.

Well, here is some really simple code that should give you some ideas.

local inputrequested = false
--Hooking Inputs
game:GetService("ReplicatedStorage").Remote.OnServerEvent:Connect(function()
    if inputrequested then
        --code
    end
end)
--Requesting Input
game:GetService("ReplicatedStorage").Remote:FireAllClients
inputrequested = true
wait(100)
inputrequested = false
2 Likes

Exactly like this only if its player specific just have the the variable as bool value in player instead.

Server Side:

local randomSeed =  Random.new()
local randomKey

function keysend()
     randomKey = randomSeed:NextInteger(1,999999999)
     remote:FireClient(plr, value, randomKey)
end

remote.OnServerEvent:Connect(function(player,val,key)
    if key == randomKey then
        -- blah blah blah
    else
        player:Kick("Invalid Key")
    end
end)

Client Side

remote.OnClientEvent:Connect(function(val,key)

-- blah blah blah

remote:FireServer:(value,key)
end)
1 Like

It doesn’t reset the key until the next time the server requests input. Exploiters can theoretically wait till the server asks for input then exploit using that key.

Ontop of that, the code wouldn’t even work in general, as the key changes for each player, so only the last player will have the right key.

This isn’t needed you can just do what @mistrustfully has done also I am sure this is flawed so that exploiters can receive a request and reuse the key.

It generates a new key whenever there is a new valid request. there’s no way to reuse the old one. The only problem I think this might have is when you use it with multiple people.

oops you’re right, I’ll fix it

You’re right of course, but I’ve just written it down to just give the general idea how it’d look like, I haven’t tested it.

You can reuse the key because it only generates a new one when a new player joins which also brings up problems as only the recently joined player would have the right key.

Of course it could be tweaked to work but a simple bool value would do for this case. You want to avoid things like this (key systems) as much as possible.

what are you on about? it creates a new key whenever the function fires.

The random seed isn’t in a function.

the random seed is in a function, and the variable gets re-defined every time the function fires. I haven’t assigned the function.