In most cases, when a non-string value is passed to the error
function, a generic “error occurred” message is thrown. Presumably, this is because whatever code handles errors internally does not work well with anything except strings.
error({})
--> Error occurred, no output from Lua.
This also happens with the pcall function, despite error messages having no destination other than being a value returned by pcall. It even returns a different generic message (An error occurred
vs Error occurred, no output from Lua.
), suggesting that this is an assertion unique to pcall.
print(pcall(error, {}))
--> false An error occurred
When handling errors with pcall, it can be difficult to create and process structured errors with only a single string as a medium. This can be improved by allowing any type of value to be passed through error
to pcall. Specifically tables, which can contain structured data.
local function HTTPRequest()
error({message = "Not found", code = 404}, 2)
end
local ok, status = pcall(HTTPRequest)
if not ok then
print(string.format("%d: %s", status.code, status.message))
end
For cases where an error is handled outside of pcall, and must be a string (e.g. logging, printing to output), there are several options:
- Convert the value to a string, respecting the
__tostring
metamethod.- Allows structured errors to interface with the string-based system.
- The security of the metamethod must be considered.
- Convert the value to a string, without metamethods.
- While not being as detailed, still provides a bit of information.
- Continue to throw a generic error as usual.
- Message fails normally, but succeeds when wrapped in pcall, which could be considered inconsistent.