Welcome coders!
I have found a method to make properties of self
(the table that returns from module.new()
in OOP) read-only.
This method is not 100% convenient for everyone as it uses a function instead of directly accessing the property through self.Property
, but it does work 100% of the time.
I’ll be making an OOP class called “Person” and using it as an example to show you what I mean, through code. Feel free to copy any of the code below.
Here is my setup for the OOP class “Person” written in a ModuleScript. Feel free to set it up any other way you would like:
-- ModuleScript
local Person = {}
function Person.new(firstName: string, lastName: string)
local self = {}
self.FirstName = firstName
self.LastName = lastName
return self
end
return Person
As you might see I am not type checking anything and will not be doing it in this post as it is irrelevant.
For the ModuleScript we will also need to add a Script. Let’s name the ModuleScript “Person” and put both inside ServerScriptService. Inside the explorer it should look something like this:
- ServerScriptService
– Script
– Person
Let’s write the code for the Script and print()
both chosen names:
-- Script
local Person = require(script.Parent.Person)
local person = Person.new("Bob", "Billysson")
print(person.FirstName, person.LastName)
Output: Bob Billysson
None of these properties are read-only. We can still change them as demonstrated:
-- Script
local Person = require(script.Parent.Person)
local person = Person.new("Bob", "Billysson")
person.FirstName = "Hello"
print(person.FirstName, person.LastName)
Output: Hello Billysson
Let’s make both properties read-only by adding a function that returns a property of a hidden table that can not be accessed by any other code than the code inside of Person.new()
:
-- ModuleScript(Person)
local Person = {}
function Person.new(firstName: string, lastName: string)
local self = {}
local privateProperties = {
FirstName = firstName,
LastName = lastName,
}
function self:GetReadOnlyProperty(propertyName: string)
return privateProperties[propertyName]
end
return self
end
return Person
Now if we try to reach FirstName or LastName in our script without the newly added function it won’t work:
-- Script
local Person = require(script.Parent.Person)
local person = Person.new("Bob", "Billysson")
person.FirstName = "Hello"
print(person.FirstName, person.LastName)
Output: Hello nil
This code still outputs “Hello” as person.FirstName has been set to “Hello” instide of the Script.
But if we use the function we will get:
local Person = require(script.Parent.Person)
local person = Person.new("Bob", "Billysson")
local firstName = person:GetReadOnlyProperty("FirstName")
local lastName = person:GetReadOnlyProperty("LastName")
print(firstName, lastName)
Output: Bob Billysson
That was all I wanted to share. If you find a better or simpler way to do this it would be much appreciated by myself and probably many others.
Positive and negative feedback is much appreciated.