diff options
-rw-r--r-- | acf/model/field.lua | 5 | ||||
-rw-r--r-- | acf/model/init.lua | 8 | ||||
-rw-r--r-- | acf/model/node.lua | 4 | ||||
-rw-r--r-- | acf/persistence/backends/augeas.lua | 2 | ||||
-rw-r--r-- | acf/persistence/backends/files.lua | 4 | ||||
-rw-r--r-- | acf/persistence/backends/json.lua | 4 | ||||
-rw-r--r-- | acf/persistence/backends/null.lua | 2 | ||||
-rw-r--r-- | acf/persistence/backends/volatile.lua | 2 | ||||
-rw-r--r-- | acf/persistence/init.lua | 22 | ||||
-rw-r--r-- | acf/transaction/backend.lua | 12 | ||||
-rw-r--r-- | acf/transaction/init.lua | 6 |
11 files changed, 48 insertions, 23 deletions
diff --git a/acf/model/field.lua b/acf/model/field.lua index 26d4621..7af0698 100644 --- a/acf/model/field.lua +++ b/acf/model/field.lua @@ -75,7 +75,7 @@ function Field:meta(context) end function Field:load(context) - local value = context.txn:get(context.addr) + local value = context.txn:get(context.addr, self.dtype) if value == nil then return self.default end return value end @@ -94,7 +94,6 @@ end function Field:validate(context, value) end function Field:save(context, value) - -- 2nd argument currenly not much used by backends context.txn:set(context.addr, self.dtype, self:_validate(context, value)) end @@ -150,6 +149,6 @@ function Model:init(params) end function Model:load(context, create) - if not create and not context.txn:get(context.addr) then return end + if not (create or context.txn:get(context.addr, 'table')) then return end return self.model(context) end diff --git a/acf/model/init.lua b/acf/model/init.lua index 00fc7aa..1bc190d 100644 --- a/acf/model/init.lua +++ b/acf/model/init.lua @@ -129,7 +129,8 @@ function Reference:meta(context) local txn = context.txn local objs = txn:get( - node.addr(relabel('system', txn.search, txn, res.scope)) + node.addr(relabel('system', txn.search, txn, res.scope)), + 'table' ) or {} res.choice = map(function(p) return pth.join(res.scope, p) end, objs) res['ui-choice'] = objs @@ -209,15 +210,16 @@ Mixed = class(Collection) function Mixed:init(params) params.type = Mixed super(self, Mixed):init(params, node.Mixed) + self.pfield = Field() end function Mixed:load(context) - local value = Primitive.load(self, context) + local value = self.pfield:load(context) if type(value) == 'table' then return super(self, Mixed):load(context) end return value end function Mixed:save(context, value) if type(value) == 'table' then super(self, Mixed):save(context, value) - else Primitive.save(self, context, value) end + else self.pfield:save(context, value) end end diff --git a/acf/model/node.lua b/acf/model/node.lua index 8028bcb..afc3e0f 100644 --- a/acf/model/node.lua +++ b/acf/model/node.lua @@ -114,10 +114,10 @@ function Collection:init(context, params) function mt.valid_member(name) return true end function mt.mmeta(name) return mt.meta.members end - function mt.members() return mt.txn:get(mt.addr) or {} end + function mt.members() return mt.txn:get(mt.addr, 'table') or {} end function mt.validate() - if params.required and #mt.txn:get(mt.addr) == 0 then + if params.required and #mt.members() == 0 then raise(mt.path, 'Collection cannot be empty') end end diff --git a/acf/persistence/backends/augeas.lua b/acf/persistence/backends/augeas.lua index cf4614f..c33e09a 100644 --- a/acf/persistence/backends/augeas.lua +++ b/acf/persistence/backends/augeas.lua @@ -12,7 +12,7 @@ backend = require('acf.object').class() function backend:init() self.aug = require('augeas').init() end -function backend:get(path) +function backend:get(path, tpe) path = '/'..pth.mjoin(unpack(path)) local _, count = self.aug:match(path) if count == 0 then return end diff --git a/acf/persistence/backends/files.lua b/acf/persistence/backends/files.lua index 31058a7..03eadff 100644 --- a/acf/persistence/backends/files.lua +++ b/acf/persistence/backends/files.lua @@ -16,7 +16,7 @@ backend = require('acf.object').class() -- TODO cache expiration function backend:init() self.cache = {} end -function backend:get(path) +function backend:get(path, tpe) local name = pth.mjoin('/', unpack(path)) if not self.cache[name] then @@ -59,7 +59,7 @@ function backend:set(mods) else local file = util.open_file(name, 'w') - file:write(value) + file:write(tostring(value)) file:close() self.cache[name] = value diff --git a/acf/persistence/backends/json.lua b/acf/persistence/backends/json.lua index 1ac977e..57352d8 100644 --- a/acf/persistence/backends/json.lua +++ b/acf/persistence/backends/json.lua @@ -51,12 +51,12 @@ function backend:split_path(path) end end -function backend:get(path) +function backend:get(path, tpe) local fpath, jpath = self:split_path(path) if not self.cache[fpath] then self.cache[fpath] = Cache(json.decode(util.read_file(fpath))) end - return self.cache[fpath]:get(jpath) + return self.cache[fpath]:get(jpath, tpe) end function backend:set(mods) diff --git a/acf/persistence/backends/null.lua b/acf/persistence/backends/null.lua index 62a793f..45b6f22 100644 --- a/acf/persistence/backends/null.lua +++ b/acf/persistence/backends/null.lua @@ -6,5 +6,5 @@ See LICENSE file for license details module(..., package.seeall) backend = require('acf.object').class() -function backend:get(path) if #path == 0 then return {} end end +function backend:get(path, tpe) if #path == 0 then return {} end end function backend:set(mods) end diff --git a/acf/persistence/backends/volatile.lua b/acf/persistence/backends/volatile.lua index 63d7265..165e7fc 100644 --- a/acf/persistence/backends/volatile.lua +++ b/acf/persistence/backends/volatile.lua @@ -29,7 +29,7 @@ function backend:_get(path) return res end -function backend:get(path) +function backend:get(path, tpe) local res = self:_get(path) return type(res) == 'table' and keys(res) or res end diff --git a/acf/persistence/init.lua b/acf/persistence/init.lua index de23a68..7b10002 100644 --- a/acf/persistence/init.lua +++ b/acf/persistence/init.lua @@ -29,9 +29,27 @@ function DataStore:split_path(path) return backend, comps end -function DataStore:get(path) +function DataStore:get(path, t) local backend, comps = self:split_path(path) - return util.copy(backend:get(comps)), self.mod_time[path] or 0 + local res = backend:get(comps, t) + + if t ~= nil and res ~= nil then + local atype = type(res) + + if t == 'table' then assert(atype == 'table') + + else + assert(atype ~= 'table') + + if t == 'string' then res = tostring(res) + elseif t == 'number' then res = tonumber(res) + elseif t == 'boolean' then res = res and true or false + elseif t == 'reference' then assert(atype == 'string') + else assert(false) end + end + end + + return util.copy(res), self.mod_time[path] or 0 end function DataStore:_set_multiple(mods) diff --git a/acf/transaction/backend.lua b/acf/transaction/backend.lua index a8ecfe0..d778a40 100644 --- a/acf/transaction/backend.lua +++ b/acf/transaction/backend.lua @@ -23,8 +23,8 @@ TransactionBackend = require('acf.object').class() function TransactionBackend:init() self.mod_time = {} end -function TransactionBackend:get_if_older(path, timestamp) - local value, ts = self:get(path) +function TransactionBackend:get_if_older(path, timestamp, t) + local value, ts = self:get(path, t) if ts > timestamp then err.raise('conflict', path) end return value, ts end @@ -38,9 +38,15 @@ function TransactionBackend:set_multiple(mods) local timestamp = gen_number() local effective = {} + local function tostr(s) return s ~= nil and tostring(s) or nil end + for _, mod in ipairs(mods) do local path, t, value = unpack(mod) - if t == 'table' or value ~= self:get(path) then + + if t == 'table' or type( + self:get(path) + ) == 'table' or self:get(path, t) ~= value then + table.insert(effective, mod) self.mod_time[path] = timestamp end diff --git a/acf/transaction/init.lua b/acf/transaction/init.lua index 0afad48..ec83aae 100644 --- a/acf/transaction/init.lua +++ b/acf/transaction/init.lua @@ -53,7 +53,7 @@ function Transaction:check() if not self.backend then error('Transaction already committed') end end -function Transaction:get(path) +function Transaction:get(path, t) self:check() if self.deleted[path] then return nil, self.mod_time[path] end @@ -63,7 +63,7 @@ function Transaction:get(path) end end - local value, timestamp = self.backend:get_if_older(path, self.started) + local value, timestamp = self.backend:get_if_older(path, self.started, t) self.access_time[path] = timestamp return value, timestamp end @@ -84,7 +84,7 @@ function Transaction:_set_multiple(mods) local path, t, value = unpack(mod) local ppath = pth.parent(path) - local parent = self:get(ppath) + local parent = self:get(ppath, 'table') if parent == nil then self:set(ppath, 'table', true) parent = {} |