Comparison

plugins/mod_pep.lua @ 12091:7a48ccb084dd

Merge 0.11->trunk
author Kim Alvefur <zash@zash.se>
date Mon, 20 Dec 2021 23:12:08 +0100
parent 12022:eedd3eff0768
parent 12089:76b4e3f12b53
child 12153:26af75c20163
comparison
equal deleted inserted replaced
12083:ec21e379c145 12091:7a48ccb084dd
4 local jid_join = require "util.jid".join; 4 local jid_join = require "util.jid".join;
5 local set_new = require "util.set".new; 5 local set_new = require "util.set".new;
6 local st = require "util.stanza"; 6 local st = require "util.stanza";
7 local calculate_hash = require "util.caps".calculate_hash; 7 local calculate_hash = require "util.caps".calculate_hash;
8 local is_contact_subscribed = require "core.rostermanager".is_contact_subscribed; 8 local is_contact_subscribed = require "core.rostermanager".is_contact_subscribed;
9 local cache = require "util.cache";
9 local set = require "util.set"; 10 local set = require "util.set";
10 local new_id = require "util.id".medium; 11 local new_id = require "util.id".medium;
11 local storagemanager = require "core.storagemanager"; 12 local storagemanager = require "core.storagemanager";
13 local usermanager = require "core.usermanager";
12 14
13 local xmlns_pubsub = "http://jabber.org/protocol/pubsub"; 15 local xmlns_pubsub = "http://jabber.org/protocol/pubsub";
14 local xmlns_pubsub_event = "http://jabber.org/protocol/pubsub#event"; 16 local xmlns_pubsub_event = "http://jabber.org/protocol/pubsub#event";
15 local xmlns_pubsub_owner = "http://jabber.org/protocol/pubsub#owner"; 17 local xmlns_pubsub_owner = "http://jabber.org/protocol/pubsub#owner";
16 18
17 local lib_pubsub = module:require "pubsub"; 19 local lib_pubsub = module:require "pubsub";
18 20
19 local empty_set = set_new(); 21 local empty_set = set_new();
20 22
23 -- username -> object passed to module:add_items()
24 local pep_service_items = {};
25
26 -- size of caches with full pubsub service objects
27 local service_cache_size = module:get_option_number("pep_service_cache_size", 1000);
28
21 -- username -> util.pubsub service object 29 -- username -> util.pubsub service object
22 local services = {}; 30 local services = cache.new(service_cache_size, function (username, _)
31 local item = pep_service_items[username];
32 pep_service_items[username] = nil;
33 if item then
34 module:remove_item("pep-service", item);
35 end
36 end):table();
37
38 -- size of caches with smaller objects
39 local info_cache_size = module:get_option_number("pep_info_cache_size", 10000);
23 40
24 -- username -> recipient -> set of nodes 41 -- username -> recipient -> set of nodes
25 local recipients = {}; 42 local recipients = cache.new(info_cache_size):table();
26 43
27 -- caps hash -> set of nodes 44 -- caps hash -> set of nodes
28 local hash_map = {}; 45 local hash_map = cache.new(info_cache_size):table();
29 46
30 local host = module.host; 47 local host = module.host;
31 48
32 local node_config = module:open_store("pep", "map"); 49 local node_config = module:open_store("pep", "map");
33 local known_nodes = module:open_store("pep"); 50 local known_nodes = module:open_store("pep");
48 end 65 end
49 end 66 end
50 67
51 function module.save() 68 function module.save()
52 return { 69 return {
53 services = services;
54 recipients = recipients; 70 recipients = recipients;
55 }; 71 };
56 end 72 end
57 73
58 function module.restore(data) 74 function module.restore(data)
59 services = data.services;
60 recipients = data.recipients; 75 recipients = data.recipients;
61 for username, service in pairs(services) do
62 local user_bare = jid_join(username, host);
63 module:add_item("pep-service", { service = service, jid = user_bare });
64 end
65 end 76 end
66 77
67 function is_item_stanza(item) 78 function is_item_stanza(item)
68 return st.is_stanza(item) and item.attr.xmlns == xmlns_pubsub and item.name == "item" and #item.tags == 1; 79 return st.is_stanza(item) and item.attr.xmlns == xmlns_pubsub and item.name == "item" and #item.tags == 1;
69 end 80 end
179 end 190 end
180 return broadcast_to; 191 return broadcast_to;
181 end 192 end
182 end 193 end
183 194
195 local nobody_service = pubsub.new({
196 service = pubsub.new({
197 node_defaults = {
198 ["max_items"] = 1;
199 ["persist_items"] = false;
200 ["access_model"] = "presence";
201 ["send_last_published_item"] = "on_sub_and_presence";
202 };
203 });
204 });
205
184 function get_pep_service(username) 206 function get_pep_service(username)
185 local user_bare = jid_join(username, host); 207 local user_bare = jid_join(username, host);
186 local service = services[username]; 208 local service = services[username];
187 if service then 209 if service then
188 return service; 210 return service;
211 end
212 if not usermanager.user_exists(username, host) then
213 return nobody_service;
189 end 214 end
190 module:log("debug", "Creating pubsub service for user %q", username); 215 module:log("debug", "Creating pubsub service for user %q", username);
191 service = pubsub.new({ 216 service = pubsub.new({
192 pep_username = username; 217 pep_username = username;
193 node_defaults = { 218 node_defaults = {
224 normalize_jid = jid_bare; 249 normalize_jid = jid_bare;
225 250
226 check_node_config = check_node_config; 251 check_node_config = check_node_config;
227 }); 252 });
228 services[username] = service; 253 services[username] = service;
229 module:add_item("pep-service", { service = service, jid = user_bare }); 254 local item = { service = service, jid = user_bare }
255 pep_service_items[username] = item;
256 module:add_item("pep-service", item);
230 return service; 257 return service;
231 end 258 end
232 259
233 function handle_pubsub_iq(event) 260 function handle_pubsub_iq(event)
234 local origin, stanza = event.origin, event.stanza; 261 local origin, stanza = event.origin, event.stanza;
457 484
458 for node, node_obj in pairs(ret) do 485 for node, node_obj in pairs(ret) do
459 reply:tag("item", { jid = user_bare, node = node, name = node_obj.config.title }):up(); 486 reply:tag("item", { jid = user_bare, node = node, name = node_obj.config.title }):up();
460 end 487 end
461 end); 488 end);
489
490 module:hook_global("user-deleted", function(event)
491 if event.host ~= host then return end
492 local username = event.username;
493 local service = services[username];
494 if not service then return end
495 for node in pairs(service.nodes) do service:delete(node, true); end
496
497 local item = pep_service_items[username];
498 pep_service_items[username] = nil;
499 if item then module:remove_item("pep-service", item); end
500
501 recipients[username] = nil;
502 end);
503