Typer¶
Type Checker and Function Signature Assigner
Library API¶
Typer.AssignSignature¶
function Typer.AssignSignature([number ParameterIndexToStartChecking = 1, ] types ... , function Callback)
Returns a function which checks to make sure the arguments passed in exactly match the parameters specified. If they match, it will call Callback
, otherwise it will error, stating which parameter caused the error and what was expected.
Each parameter corresponds to the parameter with which the function is being called. Parameters should be arrays containing all valid strings which may be returned by typeof(parameter)
. For example: {"string", "number", "nil"}
would allow the corresponding parameter to be a string
, number
, or nil
. Optionally, a table may have a [string TypeNameKey] = function Callback
which may be called to determine whether a parameter is of the type TypeNameKey
.
The first parameter may optionally be a positive integer which is the first parameter AssignSignature
should start checking.
Example
local Typer = Resources:LoadLibrary("Typer") local function IsButton(Value, TypeOfString) -- Value is the Parameter -- TypeOfString is the string returned by typeof(Value) return TypeOfString == "Instance" and (Value:IsA("TextButton") or Value:IsA("ImageButton")) end local foo = Typer.AssignSignature({"string", "number", "nil", Button = IsButton}, function(s) -- s can be a string, number, nil, or Button (TextButton or ImageButton) -- Will error if `s` is none of the aforementioned -- Will error if 2 or more parameters are passed in return s end) foo(2) -- 2 foo("Hello") -- Hello foo({}) -- [Typer] {Foo} bad argument #1: expected Button or string or number or nil, got table {} local bar = Typer.AssignSignature(2, {"string"}, {"number"}, function(p1, p2, p3) -- The 2 signifies that the first checked parameter will be the second one -- Makes sure the 2nd parameter is a string, 3rd is a number -- The first parameter is not checked print(p1, p2, p3) end) bar(false, "", 1)
Typer.Check¶
boolean Typer.Check(table PotentialType, any Parameter [, <string, number> ArgumentName])
Checks if an individual Parameter matches a PotentialType in the same way Typer.AssignSignature
does. Returns Parameter
if it's a truthy value. If it isn't a truthy value, return true. ArgumentName is just the name or number of the argument being Checked which can be used in the error message.
Example
local Debug = Resources:LoadLibrary("Debug") local Typer = Resources:LoadLibrary("Typer") local function foo(a) -- `assert` can be used instead of Debug.Assert return Debug.Assert(Typer.Check({"number"}, a, 1)) end foo(2) -- 2 foo("Noodle") -- [Script] {Foo} bad argument #1: expected number, got string Noodle
Typer.MapDefinition¶
function Typer.MapDefinition(table Definition)
Returns a function which returns the table if it matches the definition, or false, errorMessage
if it doesn't.
Example
local PlayerDefinition = Typer.MapDefinition { Name = Typer.String; UserId = Typer.PositiveInteger; } local Player1 = { Name = "Validark"; UserId = 2966752; } Player1 = assert(PlayerDefinition(Player1)) -- Can also be used with AssignSignature Typer.AssignSignature({Player = PlayerDefinition}, function(...) print(...) end)(Player1)
Typer.TYPE¶
table Typer.TypeString
Typer will procedurally generate tables which can be cast to valid types. These may be used with Typer.AssignSignature
or Typer.Check
to avoid duplicate table definitions. These tables may also be called directly, since their metatable __call
is set to Typer.Check
assert(Typer.String("Yup")) assert(Typer.String(1)) assert(Typer.Number(1)) assert(Typer.Boolean(true)) assert(Typer.Function(function() end) assert(Typer.Userdata(newproxy(false))) local foo = Typer.AssignSignature(Typer.String, function(a) print(a) end) foo("Hello, world!")
Built-in Types¶
Key | Matches |
---|---|
Nil | type(Object) = "nil" |
Boolean | type(Object) = "boolean" |
Number | type(Object) = "number" |
String | type(Object) = "string" |
Userdata | type(Object) = "userdata" |
Function | type(Object) = "function" |
Thread | type(Object) = "thread" |
Table | type(Object) = "table" |
Typer accepts anything returned by typeof
Custom Types¶
Key | Matches |
---|---|
Any | Anything |
Array | A non-empty table with only numeric keys |
Dictionary | A non-empty table with only non-numeric keys |
EmptyTable | An empty table |
NonNil | Any value which isn't nil |
Integer | Any whole number |
PositiveInteger | An integer higher than 0 |
NegativeInteger | An integer lower than 0 |
NonPositiveInteger | An integer lower than 0 or 0 |
NonNegativeInteger | An integer higher than 0 or 0 |
PositiveNumber | A number higher than 0 |
NegativeNumber | A number lower than 0 |
NonPositiveNumber | A number lower than 0 or 0 |
NonNegativeNumber | A number higher than 0 or 0 |
Truthy | Any value which isn't false or nil |
Falsy | False or nil |
Enum | An EnumType or EnumItem |
EnumType | A roblox EnumType |
EnumItem | An EnumItem |
True | true |
False | false |
Types from parsed strings¶
Types separated by "Or" will function as expected.
assert(Typer.NumberOrString(2)) assert(Typer.OptionalBooleanOrNumberOrString(2))
Prefixes¶
Prefix | Matches |
---|---|
Optional | Accepts nil as well |
InstanceOfClass | Returns Object.ClassName == ClassName |
InstanceWhichIsA | Returns Object:IsA(ClassName) |
EnumOfType | Returns the (Roblox) Enum if it can be cast to it via its string, number, or reference |
EnumerationOfType | Returns EnumerationType:Cast(Object) |
DictionaryOf | Ensures it's a dictionary with values of a given type |
ArrayOf | Ensures it's an array with values of a given type |
TableOf | Ensures it's a table with values of a given type |
Warning
You may not nest prefixes, but you may use multiple on the top level using "Or"
Example
assert(Typer.ArrayOfStringsOrDictionaryOfNumbers{"a", "b", "c"}) assert(Typer.ArrayOfStringsOrDictionaryOfNumbers{ a = 1; b = 2; c = 3; })