41 lines
1.3 KiB
Lua
41 lines
1.3 KiB
Lua
do -- Require luajit __pairs metamethod to be enabled
|
|
local enabled
|
|
local t = setmetatable({}, { __pairs = function() enabled = true; return function() end end })
|
|
for _ in pairs(t) do
|
|
end
|
|
if not enabled then
|
|
error("This thing requires luajit with __pairs metamethod enabled")
|
|
end
|
|
end
|
|
|
|
|
|
local function make_proxy(actual, name)
|
|
local function fmt(...) print(string.format(...)) end
|
|
local function get_trace(label)
|
|
return debug.traceback(label,3):gsub("([^\n]+)", "| %1")
|
|
end
|
|
|
|
local proxy = {} -- this must be empty to intercept every access
|
|
local mt = {
|
|
__index = function (_self, k)
|
|
fmt("* %s.self.%s -- %s", name, k, get_trace('read'))
|
|
return actual[k] -- access the original table
|
|
end,
|
|
|
|
__newindex = function (_self, k, v)
|
|
fmt("* %s.self.%s = %s -- %s", name, k, v, get_trace('write'))
|
|
actual[k] = v -- update original table
|
|
end,
|
|
__pairs = function (self)
|
|
-- wrap `next` to enable proxy hits during traversal
|
|
return function (tab, key)
|
|
local index, value = next(actual, key)
|
|
return index, value ~= nil and self[index]
|
|
end, self, nil
|
|
end,
|
|
}
|
|
return setmetatable(proxy, mt)
|
|
end
|
|
|
|
return make_proxy
|