Skip to content

Sandbox ​

Scripts run in a restricted Lua 5.4 environment. Only a subset of the standard library is loaded. Anything that touches the filesystem, OS, or arbitrary module loading is blocked. Network access goes through a separate API that can be disabled from the menu.

Loaded libraries ​

  • base: core language functions (type, pairs, pcall, tostring, error, etc.)
  • math: math functions (sin, cos, sqrt, floor, random, etc.)
  • string: string manipulation (find, format, sub, gsub, match, etc.)
  • table: table operations (insert, remove, sort, concat, unpack, etc.)
  • coroutine: coroutine control (yield, resume, create, wrap, etc.)
  • utf8: Unicode string handling (len, codes, char, codepoint, etc.)

Blocked libraries ​

  • io: no file read/write
  • os: no os.execute, os.remove, os.clock, etc.
  • package: no require paths or module loading
  • debug: no debug.getinfo, debug.sethook or stack inspection

Common replacements ​

  • To persist data, use Storage instead of io.
  • For timing, use the global clock() function instead of os.clock.
  • For network access, use the HTTP library. It is opt-in and can be turned off from the menu.
  • For modular code, use export and import. require is blocked, but these two globals let scripts share modules with each other:
lua
-- In your library script (e.g. utils.lua):
export("utils", {
    clamp = function(v, lo, hi) return math.max(lo, math.min(hi, v)) end,
})

-- In any other script:
local utils = import("utils")
if utils then
    local x = utils.clamp(value, 0, 100)
end

export(name, module) registers a table under a name. import(name) fetches it and returns nil if the exporting script hasn't loaded yet, so check the result with an if.