-- A simple index fallback implementation for tables.-- Useful for template argument aliasing.-- Hmm, what about __newindex?
local function makeFallback(args, arg_aliases) local oldArgsMeta = getmetatable(args) or local newArgsMeta = -- Forget about thread-safety. -- States kept to avoid strange loops. local referencedKeys = -- dataType:Set/hashtable-impl local attemptDepth = 0 -- useful for "last nil" case -- Start the new metatable as a copy of the old metatable. for k, v in ipairs(oldArgsMeta) do newArgsMeta[k] = v end
-- Change the __index metamethod to our implementation. -- See https://www.lua.org/pil/13.4.1.html. newArgsMeta.__index = function (t, k) -- My friend, why are you here again? if referencedKeys[k] then -- You have to be drunk. Go home. return nil end referencedKeys[k] = true -- Try the old metamethod first. -- Thanks to closures, this whole oldArgsMeta object will stay. if oldArgsMeta.__index ~= nil then local val = oldArgsMeta.__index(t, k) if val ~= nil then referencedKeys = return val end end attemptDepth = attemptDepth + 1 -- Now try use the aliases given. for _, v in ipairs(arg_aliases[k] or) do -- If a working value is found, use it. -- Note: mw-argument-specific empty str chk. if t[v] ~= nil and t[v] ~= then referencedKeys = return t[v] end end attemptDepth = attemptDepth - 1 if attemptDepth
return makeFallback
----