I am trying to figure out what game architecture to use. I have settled on OOP and I’m now working on classes.
For the classes, what I’m currently doing is have a module script in Replicated Storage that goes like this:
local ClassBase = {Server = {}, Client = {}}
ClassBase.Server.__index = ClassBase.Server
ClassBase.Client.__index = ClassBase.Client
local function getClassType()
if RunService:IsServer() then
return ClassBase.Server
elseif RunService:IsClient() then
return ClassBase.Client
end
end
--< SERVER >--
function ClassBase.Server.new(player: Player, module: ModuleScript)
if not player then return end
if not module then return end
local self = setmetatable({}, ClassBase)
return self
end
--< CLIENT >--
function ClassBase.Client.new()
local self = setmetatable({}, ClassBase)
return self
end
return getClassType()
Is this safe from exploiters? Both server and client methods and key value pairs are in the same place, but when the module is required, it only returns server stuff if it’s a server script, it only returns client if it’s a local script.
The reason I want to do this is too avoid having two class folders.
When it comes to modular classes, I always recommend creating module scripts and those module scripts only consisting of that particular class.
You have a ClassBase table that contains your two classes. It is not good practice to do it this way. Separate both classes into module scripts, then require them both and add them to the ClassBase table.
Assuming from the usage case here, I recommend just having some shared module script that inputs particular variables and outputs a wrapper for it, that way you can use it across the game and have everything consistent and tidy.
Other than all of that, it’s excellent.
If you make a module script, or any script for that matter, that only the server will be using, never store it in a location the client can access. This is one of the worst mistake you can make. Store the Server module script someplace like ServerStorage or ServerScriptService, then have the requiring script automatically add the server information in. I recommend also making a module script for this usage case, but instead of it being shared, it’s stored in a place only the server can access.
Since it’s replicated to the client, they can modify the entire module if they wanted to. It’s why server checks are of upmost importance when you have to verify anything the client sends. Even if you check something on the client, you should also check it on the server to verify. That’s just the rule of thumb. Anyways, whatever you modify on the client is only changed for that particular client. It is not replicated to the server or other clients. If the exploiter deleted or modified this module on their client, the only person it effects is themselves. The server still sees the original module and so do the other clients.
The client can’t necessarily modify the module and it apply to the server, but the client can see what the server will be doing and potentially make educated and effective attacks against your game and it’s server methods.
In general, your game isn’t “less secure” by definition by exposing server methods, it just gives exploiters an upper-hand as they can see what the server will be doing for given situations.