diff options
author | Kim Alvefur <zash@zash.se> | 2020-05-11 21:56:19 +0200 |
---|---|---|
committer | Kim Alvefur <zash@zash.se> | 2020-05-11 21:56:19 +0200 |
commit | b9bb7cca20ac53685a13fd096a74abd1ae5eb3d3 (patch) | |
tree | d3c52660aea85e97cb676dad5994bc6613834fd2 | |
parent | c3058505713cfbad76812f7797d52cc32e626fea (diff) | |
download | prosody-b9bb7cca20ac53685a13fd096a74abd1ae5eb3d3.tar.gz prosody-b9bb7cca20ac53685a13fd096a74abd1ae5eb3d3.zip |
mod_storage_internal: Implement key-value API
-rw-r--r-- | plugins/mod_storage_internal.lua | 40 | ||||
-rw-r--r-- | spec/core_storagemanager_spec.lua | 15 |
2 files changed, 55 insertions, 0 deletions
diff --git a/plugins/mod_storage_internal.lua b/plugins/mod_storage_internal.lua index c8b902cf..586ea10f 100644 --- a/plugins/mod_storage_internal.lua +++ b/plugins/mod_storage_internal.lua @@ -208,6 +208,46 @@ function archive:find(username, query) end, count; end +function archive:get(username, wanted_key) + local iter, err = self:find(username, { key = wanted_key }) + if not iter then return iter, err; end + for key, stanza, when, with in iter do + if key == wanted_key then + return stanza, when, with; + end + end + return nil, "item-not-found"; +end + +function archive:set(username, key, new_value, new_when, new_with) + local items, err = datamanager.list_load(username, host, self.store); + if not items then + if err then + return items, err; + else + return nil, "item-not-found"; + end + end + + for i = 1, #items do + local old_item = items[i]; + if old_item.key == key then + local item = st.preserialize(st.clone(new_value)); + + local when = new_when or item.when or datetime.parse(item.attr.stamp); + item.key = key; + item.when = when; + item.with = new_with or old_item.with; + item.attr.stamp = datetime.datetime(when); + item.attr.stamp_legacy = datetime.legacy(when); + items[i] = item; + return datamanager.list_store(username, host, self.store, items); + end + end + + return nil, "item-not-found"; +end + function archive:dates(username) local items, err = datamanager.list_load(username, host, self.store); if not items then return items, err; end diff --git a/spec/core_storagemanager_spec.lua b/spec/core_storagemanager_spec.lua index 29ab014f..96ccceb6 100644 --- a/spec/core_storagemanager_spec.lua +++ b/spec/core_storagemanager_spec.lua @@ -439,6 +439,21 @@ describe("storagemanager", function () assert.equal(2, count); assert(archive:delete("user-issue1073")); end); + + it("can be treated as a map store", function () + assert.falsy(archive:get("mapuser", "no-such-id")); + assert.falsy(archive:set("mapuser", "no-such-id", test_stanza)); + + local id = archive:append("mapuser", nil, test_stanza, test_time, "contact@example.com"); + assert.same(test_stanza, archive:get("mapuser", id)); + + local replacement_stanza = st.stanza("test", { xmlns = "urn:example:foo" }) + :tag("bar"):up() + :reset(); + assert(archive:set("mapuser", id, replacement_stanza)); + assert.same(replacement_stanza, archive:get("mapuser", id)); + end); + end); end); end |