Roblox security guides
43 problems that show up in Roblox games, what an exploiter could do with each one, and how to fix it in Luau. They're the same checks Luaudit gives your AI when it audits your game.
Remote events
How the server handles RemoteEvents, UnreliableRemoteEvents and RemoteFunctions. Every remote is a door into the server, and an exploiter can fire it at any time with any arguments.
When a remote sends a price, reward or damage value, the client decides it. How to send only the player's choice and look everything else up on the server.
How to filter player text in Roblox with TextServicecriticalPet names, signs and plot names typed by players must be filtered before others see them. How to use FilterStringAsync and the right TextFilterResult method on the server.
How to range-check numbers sent to RemoteEventscriticalA typeof check alone lets negative numbers, NaN and infinity through. How to write range checks for amounts, quantities and stock that reject all three.
How to validate RemoteEvent arguments in RobloxcriticalEvery argument after the player in OnServerEvent comes from the client. How to check types with typeof, use allowlists and reject bad values before they reach saved data.
How to check Instances sent through RemoteEventscriticalChecking an Instance's class doesn't prove the player may use it. How to check a tool, part or model sent by the client belongs to that player.
How to rate limit RemoteEvents in RobloxwarningA remote that spawns parts, plays effects or calls data stores can be fired far faster than any button. How to add a per-player cooldown on the server.
How to keep roles and answers hidden from exploiterswarningAnything sent to a client or left in ReplicatedStorage can be read. How to send each player only what they're allowed to know.
Why the server shouldn't wait on InvokeClientwarningRemoteFunction:InvokeClient lets a client stall or break server code. How to replace it with two RemoteEvents and a timeout the server controls.
Server validation
Whether the server checks that an action is allowed before it happens: that the player owns or has unlocked what they picked, hasn't claimed a reward already, is close enough to what they're using and could really have landed a hit, and that the round or their state allows it. It also covers values that only look server-side, such as teleport data and parts a client simulates, and making sure nothing can slip in between a check and the change it guards.
An unanchored part near a player is simulated by their client. How to stop balls, crates and carts deciding rewards from client physics.
Why teleport data can't be trusted in RobloxcriticalTeleportData passes through the client, even with a SourcePlaceId check. How to carry coins, boosts and entry fees between places safely.
How to check the round state before allowing an actioncriticalBets after the winner is known and answers after the reveal. How to keep round and player state on the server and check it in every handler.
How to check a player owns the item or zone they pickcriticalChecking that an id exists isn't the same as checking the player has it. How to check pets, skins, classes and zones against the player's own data.
How to stop daily rewards and codes being claimed twicecriticalDaily rewards, promo codes and quest prizes that pay out again on every call or rejoin. How to record claims in saved data before paying.
How to validate combat hits on the server in RobloxcriticalIf the client reports hits and the server just applies damage, hits can land from anywhere. How to check range, cooldowns and ranged shots on the server.
How to stop yields letting players claim or spend twicecriticalA yield between a check and the change it guards lets the same remote pass the check twice. How to order handlers so the change happens first.
How to add server-side distance checks in RobloxwarningChests, shops and sell pads that work from anywhere on the map. How to check on the server that the player's character is close enough to use them.
Data stores
How the game loads and saves with DataStoreService: what happens when a load or save fails, whether two servers can hold the same player's data at once, whether servers can overwrite each other's writes, whether keys are tied to the player's UserId and chosen by the server, whether UpdateAsync callbacks stay pure, and whether saving stays within Roblox's request budgets and size limits.
Building a data store key from a user id or slot the client sent lets one player read or overwrite another's data. How to build keys on the server.
How to stop a failed data store load wiping player datacriticalTreating a failed load as a new player hands out default data, which is then saved over the real data. How to keep failed loads apart from new players.
How to session-lock player data in RobloxcriticalWithout a session lock, two servers can hold the same player's data and the later save wins. How session locking with UpdateAsync works.
Why Roblox player data should be saved by UserIdcriticalData store keys built from a player's name or display name break when they change it, and display names aren't unique. How to key saves by UserId instead.
How to use UpdateAsync for values many servers changecriticalGetAsync followed by SetAsync lets two servers overwrite each other's changes to a bank, counter or limited stock. How to use UpdateAsync and IncrementAsync instead.
How to write a safe UpdateAsync callbackcriticalGranting coins or items inside an UpdateAsync callback can pay twice when the write fails. How to keep the callback pure and grant after it succeeds.
How to stay within data store request limitswarningSaving on every coin, kill or second played uses up the server's data store budget and gets saves dropped. How to keep values in memory and save on a timer.
How to stop player data outgrowing the data store size limitwarningBuilds, drawings and lists with no cap can grow past the 4 MB limit and stop a profile saving. How to cap and bound what players add to saved data.
How to save player data when a Roblox server shuts downwarningSaving only in PlayerRemoving can lose data when a server closes. How to use BindToClose to wait for every save to finish.
Anti-exploit
How the game spots and handles exploiters: whether its checks run where an exploiter can't switch them off, whether the server watches the things a client controls, such as its own character's movement and touches, and whether moderation and admin powers are protected on the server.
Report buttons, vote-kicks and client anti-cheat that let one client punish another. How to keep punishment decisions on the server or with moderators.
How to secure Touched rewards in RobloxcriticalCoins, checkpoints and finish lines that pay on Touched without checking the character is there. How to add distance checks and debounces on the server.
How to secure admin commands and admin remotescriticalAdmin panels that are only hidden on the client leave their remotes open to everyone. How to check the caller on the server in every admin handler.
Why client-side anti-cheat isn't enough in RobloxwarningAn exploiter controls their own client, so checks that only run there can be switched off. How to move movement checks to the server.
How to ban players properly in RobloxwarningBans kept in a script table or saved by username don't stop anyone for long. How to use Players:BanAsync or save bans by UserId.
Monetisation
How the game handles Robux purchases: developer products granted through ProcessReceipt, game pass and subscription checks, paid random items, and whether every purchase grants exactly what was bought, once, to the right player, and only after Roblox confirms it.
Granting products from PromptProductPurchaseFinished or a client remote isn't reliable. Why every grant belongs in ProcessReceipt.
Why ProcessReceipt should grant by ProductIdcriticalGranting the item a player picked before the prompt, instead of the product they paid for, lets them pay for a cheap item and get an expensive one. How to map products to rewards.
How to write a safe ProcessReceipt callbackcriticalA ProcessReceipt that grants twice, or returns PurchaseGranted before saving, loses or repeats purchases. How to record PurchaseIds and grant exactly once.
How to check game pass ownership safelywarningTrusting the client, skipping pcall or checking only on join all break game pass perks. How to check ownership on the server and update it after a purchase.
Why ProcessReceipt must be set in one placewarningProcessReceipt is a single callback, so each script that sets it replaces the last. How to handle every developer product from one script.
How to handle paid random items and PolicyServicewarningCrates, eggs and spins bought with Robux or Robux-bought currency must respect ArePaidRandomItemsRestricted. How to check it on the server and show odds.
How to grant Roblox subscription perks correctlywarningSubscription perks saved forever, checked once or trusted from the client. How to check GetUserSubscriptionStatusAsync on the server and keep perks in step.
Backdoors
Code that lets someone outside the team run things in the game: modules loaded from the Roblox catalogue by id, code run from strings, hidden or scrambled scripts, and scripts tucked inside models, often from the Creator Store, that do more than the model needs.
require(id) loads code from outside your game that its owner can change at any time. How to find these calls and what to replace them with.
Why loadstring is a backdoor risk in RobloxcriticalRunning code from strings with loadstring lets whoever controls the string run code on your server. How to remove it and use data instead.
How to find hidden admin backdoors in your gamecriticalFree models that give commands to their maker's UserId or group, or add a second handler to your staff remotes. How to find them and remove them.
How to spot hidden or obfuscated code in your gamecriticalCode pushed off-screen, strings built from character codes and getfenv lookups are common signs of a backdoor. How to find them and clean them out.
How to spot scripts sending your server details elsewherewarningScripts that post your JobId, PlaceId and player list to outside addresses help backdoor makers find your servers. How to find these requests and remove them.
How to find scripts hidden in free modelswarningScripts inside models, parts and tools, often from free models, can create remotes or copy themselves. How to find them and check models before use.
Each guide covers one problem. Fixing every one of them makes a game harder to exploit, but it doesn't make it secure on its own: review your own game logic too.