From 751f019580e210ff22fc1ac0eea72cece854534a Mon Sep 17 00:00:00 2001 From: Kaarle Ritvanen Date: Tue, 18 Mar 2014 00:52:30 +0200 Subject: move permission checking from server to model hide all model data and functions inaccessible to the user --- aconf/model/model.lua | 36 ++++++++++++++++++++++++++++-------- 1 file changed, 28 insertions(+), 8 deletions(-) (limited to 'aconf/model/model.lua') diff --git a/aconf/model/model.lua b/aconf/model/model.lua index 3f90450..5d4145f 100644 --- a/aconf/model/model.lua +++ b/aconf/model/model.lua @@ -153,6 +153,8 @@ function M.Model:init(context) assert(mt.txn) if isinstance(v, M.Action) then + mt.check_permission(k) + local f = v.field and BoundMember(self, k, v.field) if options.create then return f and f:load(options) end @@ -164,7 +166,7 @@ function M.Model:init(context) 'Action does not accept an input argument' ) end - local res = v.func(self, f and f:load()) + local res = v.func(mt.escalate, f and f:load()) if f then f:_save() end return res end @@ -174,9 +176,13 @@ function M.Model:init(context) end if self.is_removable then - function mt.removable() return self:is_removable() end + function mt.removable() + return mt.has_permission('delete') and self:is_removable() + end end + function mt.removing_permitted() return mt.has_permission('modify') end + local value_removable = mt.value_removable function mt.value_removable(v) return type(v) == 'table' and value_removable(v) @@ -190,7 +196,11 @@ function M.Model:init(context) function mt.save(k, v) k = normalize_name(k) local field = mt.member(k, false, Field) - if isinstance(field, fld.TreeNode) then mt.check_removable(k, v) end + + if v == nil and isinstance(field, fld.TreeNode) then + mt.check_removable(k) + else mt.check_permission('modify') end + return field:save(v) end @@ -199,7 +209,15 @@ function M.Model:init(context) end function mt.init_meta(meta) - util.update(meta, {fields=tmeta(Field), actions=tmeta(M.Action)}) + util.update( + meta, + { + fields=tmeta(Field), + actions=util.filter( + function(a) mt.has_permission(a.name) end, tmeta(M.Action) + ) + } + ) end function mt.members() @@ -215,12 +233,13 @@ function M.Model:init(context) end if self.has_permission then - function mt.has_permission(user, permission) - return self:has_permission(user, permission) + function mt.has_permission(permission) + return mt.privileged or self:has_permission(mt.txn.user, permission) end end - for _, f in ipairs(_members(Model)) do mt.load(f.name) end + local tload = getmetatable(mt.escalate).load + for _, f in ipairs(_members(Model)) do tload(f.name) end end function M.Model:fetch(path, create) @@ -228,8 +247,9 @@ function M.Model:fetch(path, create) end function M.Model:match(filter) + local tload = getmetatable(getmetatable(self).escalate).load for k, v in pairs(filter) do - if not util.contains(v, getmetatable(self).load(k)) then return false end + if not util.contains(v, tload(k)) then return false end end return true end -- cgit v1.2.3