Mercurial > prosody-hg
comparison plugins/mod_storage_memory.lua @ 10411:db2a06b9ff98
Merge 0.11->trunk
| author | Kim Alvefur <zash@zash.se> |
|---|---|
| date | Sat, 16 Nov 2019 16:52:31 +0100 |
| parents | 51f145094648 |
| children | 018acdaf374f |
comparison
equal
deleted
inserted
replaced
| 10410:659b577f280c | 10411:db2a06b9ff98 |
|---|---|
| 6 local new_id = require "util.id".medium; | 6 local new_id = require "util.id".medium; |
| 7 | 7 |
| 8 local auto_purge_enabled = module:get_option_boolean("storage_memory_temporary", false); | 8 local auto_purge_enabled = module:get_option_boolean("storage_memory_temporary", false); |
| 9 local auto_purge_stores = module:get_option_set("storage_memory_temporary_stores", {}); | 9 local auto_purge_stores = module:get_option_set("storage_memory_temporary_stores", {}); |
| 10 | 10 |
| 11 local archive_item_limit = module:get_option_number("storage_archive_item_limit", 1000); | |
| 12 | |
| 11 local memory = setmetatable({}, { | 13 local memory = setmetatable({}, { |
| 12 __index = function(t, k) | 14 __index = function(t, k) |
| 13 local store = module:shared(k) | 15 local store = module:shared(k) |
| 14 t[k] = store; | 16 t[k] = store; |
| 15 return store; | 17 return store; |
| 48 | 50 |
| 49 local archive_store = {}; | 51 local archive_store = {}; |
| 50 archive_store.__index = archive_store; | 52 archive_store.__index = archive_store; |
| 51 | 53 |
| 52 archive_store.users = _users; | 54 archive_store.users = _users; |
| 55 | |
| 56 archive_store.caps = { | |
| 57 total = true; | |
| 58 quota = archive_item_limit; | |
| 59 truncate = true; | |
| 60 }; | |
| 53 | 61 |
| 54 function archive_store:append(username, key, value, when, with) | 62 function archive_store:append(username, key, value, when, with) |
| 55 if is_stanza(value) then | 63 if is_stanza(value) then |
| 56 value = st.preserialize(value); | 64 value = st.preserialize(value); |
| 57 value = envload("return xml"..serialize(value), "=(stanza)", { xml = st.deserialize }) | 65 value = envload("return xml"..serialize(value), "=(stanza)", { xml = st.deserialize }) |
| 68 key = new_id(); | 76 key = new_id(); |
| 69 v.key = key; | 77 v.key = key; |
| 70 end | 78 end |
| 71 if a[key] then | 79 if a[key] then |
| 72 table.remove(a, a[key]); | 80 table.remove(a, a[key]); |
| 81 elseif #a >= archive_item_limit then | |
| 82 return nil, "quota-limit"; | |
| 73 end | 83 end |
| 74 local i = #a+1; | 84 local i = #a+1; |
| 75 a[i] = v; | 85 a[i] = v; |
| 76 a[key] = i; | 86 a[key] = i; |
| 77 return key; | 87 return key; |
| 78 end | 88 end |
| 79 | 89 |
| 80 function archive_store:find(username, query) | 90 function archive_store:find(username, query) |
| 81 local items = self.store[username or NULL]; | 91 local items = self.store[username or NULL]; |
| 82 if not items then | 92 if not items then |
| 83 return function () end, 0; | 93 if query then |
| 84 end | 94 if query.before or query.after then |
| 85 local count = #items; | 95 return nil, "item-not-found"; |
| 96 end | |
| 97 if query.total then | |
| 98 return function () end, 0; | |
| 99 end | |
| 100 end | |
| 101 return function () end; | |
| 102 end | |
| 103 local count = nil; | |
| 86 local i = 0; | 104 local i = 0; |
| 87 if query then | 105 if query then |
| 88 items = array():append(items); | 106 items = array():append(items); |
| 89 if query.key then | 107 if query.key then |
| 90 items:filter(function (item) | 108 items:filter(function (item) |
| 104 if query["end"] then | 122 if query["end"] then |
| 105 items:filter(function (item) | 123 items:filter(function (item) |
| 106 return item.when <= query["end"]; | 124 return item.when <= query["end"]; |
| 107 end); | 125 end); |
| 108 end | 126 end |
| 109 count = #items; | 127 if query.total then |
| 128 count = #items; | |
| 129 end | |
| 110 if query.reverse then | 130 if query.reverse then |
| 111 items:reverse(); | 131 items:reverse(); |
| 112 if query.before then | 132 if query.before then |
| 113 for j = 1, count do | 133 local found = false; |
| 134 for j = 1, #items do | |
| 114 if (items[j].key or tostring(j)) == query.before then | 135 if (items[j].key or tostring(j)) == query.before then |
| 136 found = true; | |
| 115 i = j; | 137 i = j; |
| 116 break; | 138 break; |
| 117 end | 139 end |
| 118 end | 140 end |
| 141 if not found then | |
| 142 return nil, "item-not-found"; | |
| 143 end | |
| 119 end | 144 end |
| 120 elseif query.after then | 145 elseif query.after then |
| 121 for j = 1, count do | 146 local found = false; |
| 147 for j = 1, #items do | |
| 122 if (items[j].key or tostring(j)) == query.after then | 148 if (items[j].key or tostring(j)) == query.after then |
| 149 found = true; | |
| 123 i = j; | 150 i = j; |
| 124 break; | 151 break; |
| 125 end | 152 end |
| 153 end | |
| 154 if not found then | |
| 155 return nil, "item-not-found"; | |
| 126 end | 156 end |
| 127 end | 157 end |
| 128 if query.limit and #items - i > query.limit then | 158 if query.limit and #items - i > query.limit then |
| 129 items[i+query.limit+1] = nil; | 159 items[i+query.limit+1] = nil; |
| 130 end | 160 end |
| 133 i = i + 1; | 163 i = i + 1; |
| 134 local item = items[i]; | 164 local item = items[i]; |
| 135 if not item then return; end | 165 if not item then return; end |
| 136 return item.key, item.value(), item.when, item.with; | 166 return item.key, item.value(), item.when, item.with; |
| 137 end, count; | 167 end, count; |
| 168 end | |
| 169 | |
| 170 function archive_store:summary(username, query) | |
| 171 local iter, err = self:find(username, query) | |
| 172 if not iter then return iter, err; end | |
| 173 local counts = {}; | |
| 174 local earliest = {}; | |
| 175 local latest = {}; | |
| 176 for _, _, when, with in iter do | |
| 177 counts[with] = (counts[with] or 0) + 1; | |
| 178 if earliest[with] == nil then | |
| 179 earliest[with] = when; | |
| 180 end | |
| 181 latest[with] = when; | |
| 182 end | |
| 183 return { | |
| 184 counts = counts; | |
| 185 earliest = earliest; | |
| 186 latest = latest; | |
| 187 }; | |
| 138 end | 188 end |
| 139 | 189 |
| 140 | 190 |
| 141 function archive_store:delete(username, query) | 191 function archive_store:delete(username, query) |
| 142 if not query or next(query) == nil then | 192 if not query or next(query) == nil then |
