summaryrefslogtreecommitdiffstats
path: root/acf2/model/init.lua
diff options
context:
space:
mode:
Diffstat (limited to 'acf2/model/init.lua')
-rw-r--r--acf2/model/init.lua56
1 files changed, 36 insertions, 20 deletions
diff --git a/acf2/model/init.lua b/acf2/model/init.lua
index 62f114b..711626b 100644
--- a/acf2/model/init.lua
+++ b/acf2/model/init.lua
@@ -69,6 +69,7 @@ function M.Reference:init(params)
self.dtype = 'reference'
self.dereference = true
if not self.scope then self.scope = '/' end
+ self.filter = fld.conv_filter(self.filter)
end
function M.Reference:topology(context)
@@ -81,30 +82,43 @@ function M.Reference:abs_scope(context)
return pth.to_absolute(self.scope, node.path(context.parent))
end
-function M.Reference:meta(context)
- local res = super(self, M.Reference):meta(context)
- res.scope = self:abs_scope(context)
+-- assume one-level refs for now
+function M.Reference:_choice(context)
+ local res = {}
local txn = context.txn
- local obj = relabel('system', txn.fetch, txn, res.scope)
+ local obj = relabel('system', txn.fetch, txn, self:abs_scope(context))
assert(isinstance(obj, node.Collection))
- res.choice = {}
+
for k, v in node.pairs(obj) do
+ local ch = {enabled=true}
+
if isinstance(v, node.TreeNode) then
- v = node.path(v)
- local name = pth.name(v)
- v = not pth.is_subordinate(context.path, v) and {
- value=self.dereference and v or pth.escape(name),
- ['ui-value']=name,
- ref=v
- } or nil
- else v = {value=pth.escape(v), ['ui-value']=v} end
- if v then table.insert(res.choice, v) end
+ ch.ref = node.path(v)
+ if pth.is_subordinate(context.path, ch.ref) then ch = nil end
+ if ch then
+ ch['ui-value'] = pth.name(ch.ref)
+ ch.value = self.dereference and ch.ref or pth.escape(ch['ui-value'])
+ if self.filter then
+ assert(isinstance(v, model.Model))
+ if not node.match(v, self.filter) then ch.enabled = false end
+ end
+ end
+
+ else update(ch, {value=pth.escape(v), ['ui-value']=v}) end
+
+ if ch then table.insert(res, ch) end
end
return res
end
+function M.Reference:meta(context)
+ local res = super(self, M.Reference):meta(context)
+ res.scope = self:abs_scope(context)
+ return res
+end
+
function M.Reference:follow(context, value)
return context.txn:fetch(pth.rawjoin(self:abs_scope(context), value))
end
@@ -124,24 +138,26 @@ function M.Reference:normalize(context, value)
local path = context.path
if type(value) ~= 'string' then raise(path, 'Path name must be string') end
- if pth.is_absolute(value) then
+ local rel = value
+
+ if pth.is_absolute(rel) then
local scope = self:abs_scope(context)
local prefix = scope..'/'
- if not stringy.startswith(value, prefix) then
+ if not stringy.startswith(rel, prefix) then
raise(path, 'Reference out of scope ('..scope..')')
end
- value = value:sub(prefix:len() + 1, -1)
+ rel = rel:sub(prefix:len() + 1, -1)
end
-- assume one-level ref for now
- if #pth.split(value) > 1 then
+ if #pth.split(rel) > 1 then
raise(path, 'Subtree references not yet supported')
end
-- TODO check instance type
- relabel(path, self.follow, self, context, value)
+ relabel(path, self.follow, self, context, rel)
- return value
+ return self.dereference and value or rel, rel
end
function M.Reference:deleted(context, addr)