Skip to content

Instantly share code, notes, and snippets.

@nefftd
Created October 7, 2014 16:59
Show Gist options
  • Save nefftd/37bd509d8a856e6f0940 to your computer and use it in GitHub Desktop.
Save nefftd/37bd509d8a856e6f0940 to your computer and use it in GitHub Desktop.
-- READ ONLY FORM
local mt = {} -- The real metatable
local mt_proxy = {} -- The object returned by getmetatable()
setmetatable(mt_proxy,{
__index = function(self,k) return mt[k] end, -- Allow the proxy to read fields. use a function so it's opaque (user cannot access real metatable)
__newindex = function() end -- But writing is a nop (otherwise we may accidentally barr access to __index)
})
mt.__metatable = mt_proxy -- Make getmetatable() return the proxy
test = {}
setmetatable(test,mt)
mt.__newindex = print -- insert into real metatable
assert(getmetatable(test).__newindex ~= nil) -- we can access the field
getmetatable(test).__newindex = function(...)
print('overruled',...)
end -- this should be discarded because this form is read-only
test[1]=1 -- should invoke the standard print, not 'overruled'
assert(not pcall(setmetatable,test,nil)) -- setting metatable should error
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment