Limits and errors
Time and memory limits, and what happens when a plugin fails.
Each plugin has its own limits, so one plugin can't slow the game down or starve the others. Time is counted in Lua instructions.
task_budgetframe_budgetcallback_budgetmemory_limit_mbnot enough memory, which pcall can catch.The limits are set once for every Lua plugin, in the Lua Plugins host's own config file, config/lua-plugin.json in the injector's config folder. A plugin's own settings file (config/lua-<plugin>.json) doesn't hold them.
Long library calls
A single library call that calls back into Lua, like table.sort with a comparison function or string.gsub with a replacement function, can't be paused part way. One that runs far past the budget stops the plugin; split such work into smaller pieces.
Errors
An error nothing catches stops the plugin. It shows in the console with the file, line and a traceback, and the plugin's row turns red. on_stop("error") still runs. Fix the file and press reload.
Wrap code that may fail in pcall to handle the error yourself:
local ok, err = pcall(function()
-- something that may fail
end)
if not ok then warn("failed: " .. tostring(err)) endSafe UI
Every ui.begin_* and ui.push_* needs its ui.end_* or ui.pop_*. An end_* that doesn't match is a Lua error rather than a crash, and anything still open when on_render returns (or fails) is closed for you, with a warning. A script error can't take the game's interface down with it.