local form = {} -- form to produce the target with super functional table and integrating multi-interface implement feature function form.build(tag, super) super = super or form local target = {_tag = tag, _super = super} return setmetatable(target, form._meta()) end -- specification on the target function form.on(target, spec) local handler = {} function handler.function(target, spec) return function ( ... ) return spec(target, ...) end end function handler.table(target, spec) local tar = {} for k,v in pairs(spec) do if type(v) == ‘function‘ then tar[k] = function ( ... ) spec[k](target, ...) end else tar[k] = v end end return tar end local handler_spec = handler[type(spec)] if handler_spec then print(target._tag..‘[‘..prop..‘] target binding form produced‘) end return handler_spec and handler_spec(target, spec) end --[[ function form:spec(prop, target) end local p1 -- protocol specification local p2 -- protocol specification local px -- any interface spec -- Future init style local Future = form.build(‘Future‘):spec(‘proto_xxx‘, p1) :spec(‘proto_xx2‘, p2) :spec(px) -- protocol usecase, assume implemented on target ‘Future‘ -- assume there p1:funcall defined Future:spec(‘proto_xxx‘).funcall() -- assume there px:funcall defined Future:funcall() --]] function form:spec(prop, target) local handler = {} function handler.string(self, prop, target) if target ~= nil then print(self._tag..‘[‘..prop..‘] setter/getter produced‘) local property = ‘_‘..prop local function prop_(self, target) if target ~= nil then self[property] = target return self end return self[property] end prop_(self, target)[prop] = prop_ end return form.on(self, self[prop](self)) end function handler.table(self, prop) local target = prop local interface = self._interface or {} if self._interface == nil then self._interface = interface end table.insert(interface, target) if type(target._tag)==‘string‘ then print(self._tag..‘ interface[‘..target._tag..‘] specified‘) end return self end local handler_prop = handler[type(prop)] return handler_prop and handler_prop(self, prop, target) end function form._meta() local meta = {} function meta.__index(target, key) local v = target._super[key] if v == nil then local interface = target._interface or {} for i=1, #interface do v = interface[i][key] if v ~= nil then return v end end end return v end return meta end return form
form.test
local p1 -- protocol specification local p2 -- protocol specification local px -- any interface spec -- Future init style local Future = form.build(‘Future‘):spec(‘proto_xxx‘, p1) :spec(‘proto_xx2‘, p2) :spec(px) -- protocol usecase, assume implemented on target ‘Future‘ -- assume there p1:funcall defined Future:spec(‘proto_xxx‘).funcall() -- assume there px:funcall defined Future:funcall()-- using property getterFuture:proto_xx2()==p2
时间: 2024-10-12 14:26:40