Creating a custom global function in Roblox Studio (without modules or _G)

TLDR, it was possible but due to security reasons I’m pretty confident you intentionally cannot do this anymore.

First of all, generally from reading around the the dev forum as a whole it seems like the luau nerds agree that _G is generally bad just like using globals in many programming languages is a fair amount worse than managing to avoid it. However _G is from my understanding safe enough to be used and is bad due to performance. From looking around it also seems to say that using require on module scripts is simply a way better solution than using _G and is absolutely what you should go with.
Regarding making what you want work, there is a very much deprecated function called “setfenv” which from my understanding did exactly what you wanted. However this was not only (from my understanding) much worse in performance than _G, it was also a big security risk. I think it has to do with running scripts in a sandbox or something, if you care about it then there’s a lot of googling you can do about it. It seems that setfenv was in Roblox because it was in Lua and it looks like it is also deprecated in Lua. I tried to use the setfenv function which couldn’t find it in other scripts and in the same script it seems it just breaks all default functions…? So I guess if you are desperate you could maybe rewrite all default functions or atleast the once you need because I have a feeling all of them might not be possible, then you need the setfenv in each script once.
You basically can’t do it, but if you wanna try out setfenv my best result came from setfenv(1,{kill = function() print("test") end}) (The 1 is to make it global instead of putting it in an “enviroment”)

Removed from the documentations?

Removed/deleted post about using setfenv
https://devforum.roblox.com/t/how-to-use-getfenv-and-setfenv/402621

Lua documentation on setfenv
https://www.lua.org/manual/5.1/manual.html#pdf-setfenv

Post about it potentionally being deprecated in Lua (could probably be verified with some more googling if interested)
https://lua-l.lua.narkive.com/IsC41Yvb/deprecating-setfenv

1 Like

Thanks for the post!

The issue is that setfenv() is deprecated and cannot be used in Roblox Studio.

My goal is to create my own custom keyword, similar to print().
I want to be able to type something like kill(character) without having to use _G before it, or without requiring it in every script.

Create one modulescript that requires every single modulescript with your global functions:

-- Modulescript
local modules = {} 
for index, module in pairs(moduleScriptLocation:GetChildren() do 
    table.insert(modules, require(module)) 
end
return modules

Example module:

local module = {}
function module:someGlobalFunction(...)
    -- Do some code in here
    local something = table.pack(...) -- <- Some code
    return something
end
return module

Then, all you have to do to access these global functions is use one single require at the top of a script:

local global = require(masterGlobalFunctions)

global:someGlobalFunctions(1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 10)

There is (as far as I know), no way to do it without using _G or without using this method. You might be able to do something using setfenv(), and getfenv(), but I don’t think these functions work very well in roblox, and I am not very familiar with how they are supposed to be used.

You’d probably have to modify luau itself, and recompile it, to have your own global functions. Let’s say that isn’t really possible to do on roblox

As others suggested, use a “Global” module script where you have all your “global” functions. Simple and effective
Yes you will have to require it in every script, but that really isn’t much of a problem, as someone who uses module scripts extensively

2 Likes

Atleast you could remove the need to actually typing this yourself with a plugin that sets the source of new scripts to requiring the MS instead of the print(“Hello world!”)

unfortunately no, but i dont think that should be a huge problem (its kind of just 3 extra characters. not really that big a deal)

you could alternatively make yourself a plugin using ScriptEditorService to automatically set that stuff up for you, but that feels like more effort than its worth- again, going _G.Kill(chr) compared to kill(chr) isnt that different

theres a lot more that can be said about best practice and such but ya. without recompiling a modified luau thered be no way to establish builtins on your own without it being tedious to share across scripts; using _G is the best solution i can think of that wont require a whole bunch of extra effort