comparison mod_cloud_notify/mod_cloud_notify.lua @ 2791:008cf272b7ea

mod_cloud_notify: Fix regression in error handling The last commit made push error handling not working at all.
author tmolitor <thilo@eightysoft.de>
date Wed, 11 Oct 2017 03:10:40 +0200
parents 6b710a8bdf03
children 7622ec165cdd
comparison
equal deleted inserted replaced
2790:5163f7905371 2791:008cf272b7ea
18 local include_sender = module:get_option_boolean("push_notification_with_sender", false); 18 local include_sender = module:get_option_boolean("push_notification_with_sender", false);
19 local max_push_errors = module:get_option_number("push_max_errors", 50); 19 local max_push_errors = module:get_option_number("push_max_errors", 50);
20 20
21 local host_sessions = prosody.hosts[module.host].sessions; 21 local host_sessions = prosody.hosts[module.host].sessions;
22 local push_errors = {}; 22 local push_errors = {};
23 local id2node = {};
23 24
24 -- For keeping state across reloads while caching reads 25 -- For keeping state across reloads while caching reads
25 local push_store = (function() 26 local push_store = (function()
26 local store = module:open_store(); 27 local store = module:open_store();
27 local push_services = {}; 28 local push_services = {};
60 local handle_push_success, handle_push_error; 61 local handle_push_success, handle_push_error;
61 62
62 function handle_push_error(event) 63 function handle_push_error(event)
63 local stanza = event.stanza; 64 local stanza = event.stanza;
64 local error_type, condition = stanza:get_error(); 65 local error_type, condition = stanza:get_error();
65 local node = jid.split(stanza.attr.to); 66 local node = id2node[stanza.attr.id];
67 if node == nil then return false; end -- unknown stanza? Ignore for now!
66 local from = stanza.attr.from; 68 local from = stanza.attr.from;
67 local user_push_services = push_store:get(node); 69 local user_push_services = push_store:get(node);
68 70
69 for push_identifier, _ in pairs(user_push_services) do 71 for push_identifier, _ in pairs(user_push_services) do
70 local stanza_id = hashes.sha256(push_identifier, true); 72 local stanza_id = hashes.sha256(push_identifier, true);
71 if stanza_id == stanza.attr.id then 73 if stanza_id == stanza.attr.id then
72 if user_push_services[push_identifier] and user_push_services[push_identifier].jid == from and error_type ~= "wait" then 74 if user_push_services[push_identifier] and user_push_services[push_identifier].jid == from and error_type ~= "wait" then
73 push_errors[push_identifier] = push_errors[push_identifier] + 1; 75 push_errors[push_identifier] = push_errors[push_identifier] + 1;
88 -- save changed global config 90 -- save changed global config
89 push_store:set_identifier(node, push_identifier, nil); 91 push_store:set_identifier(node, push_identifier, nil);
90 push_errors[push_identifier] = nil; 92 push_errors[push_identifier] = nil;
91 -- unhook iq handlers for this identifier (if possible) 93 -- unhook iq handlers for this identifier (if possible)
92 if module.unhook then 94 if module.unhook then
93 module:unhook("iq-error/bare/"..stanza_id, handle_push_error); 95 module:unhook("iq-error/host/"..stanza_id, handle_push_error);
94 module:unhook("iq-result/bare/"..stanza_id, handle_push_success); 96 module:unhook("iq-result/host/"..stanza_id, handle_push_success);
97 id2node[stanza_id] = nil;
95 end 98 end
96 end 99 end
97 elseif user_push_services[push_identifier] and user_push_services[push_identifier].jid == from and error_type == "wait" then 100 elseif user_push_services[push_identifier] and user_push_services[push_identifier].jid == from and error_type == "wait" then
98 module:log("debug", "Got error of type '%s' (%s) for identifier '%s': " 101 module:log("debug", "Got error of type '%s' (%s) for identifier '%s': "
99 .."NOT increasing error count for this identifier", error_type, condition, push_identifier); 102 .."NOT increasing error count for this identifier", error_type, condition, push_identifier);
103 return true; 106 return true;
104 end 107 end
105 108
106 function handle_push_success(event) 109 function handle_push_success(event)
107 local stanza = event.stanza; 110 local stanza = event.stanza;
108 local node = jid.split(stanza.attr.to); 111 local node = id2node[stanza.attr.id];
112 if node == nil then return false; end -- unknown stanza? Ignore for now!
109 local from = stanza.attr.from; 113 local from = stanza.attr.from;
110 local user_push_services = push_store:get(node); 114 local user_push_services = push_store:get(node);
111 115
112 for push_identifier, _ in pairs(user_push_services) do 116 for push_identifier, _ in pairs(user_push_services) do
113 if hashes.sha256(push_identifier, true) == stanza.attr.id then 117 if hashes.sha256(push_identifier, true) == stanza.attr.id then
114 if user_push_services[push_identifier] and user_push_services[push_identifier].jid == from and push_errors[push_identifier] > 0 then 118 if user_push_services[push_identifier] and user_push_services[push_identifier].jid == from and push_errors[push_identifier] > 0 then
115 push_errors[push_identifier] = 0; 119 push_errors[push_identifier] = 0;
116 module:log("debug", "Push succeeded, error count for identifier '%s' is now at %s again", push_identifier, tostring(push_errors[push_identifier])); 120 module:log("debug", "Push succeeded, error count for identifier '%s' is now at %s again", push_identifier, tostring(push_errors[push_identifier]));
186 origin.push_settings = nil; 190 origin.push_settings = nil;
187 end 191 end
188 user_push_services[key] = nil; 192 user_push_services[key] = nil;
189 push_errors[key] = nil; 193 push_errors[key] = nil;
190 if module.unhook then 194 if module.unhook then
191 module:unhook("iq-error/bare/"..key, handle_push_error); 195 module:unhook("iq-error/host/"..key, handle_push_error);
192 module:unhook("iq-result/bare/"..key, handle_push_success); 196 module:unhook("iq-result/host/"..key, handle_push_success);
197 id2node[key] = nil;
193 end 198 end
194 end 199 end
195 end 200 end
196 local ok = push_store:set(origin.username, user_push_services); 201 local ok = push_store:set(origin.username, user_push_services);
197 if not ok then 202 if not ok then
224 { name = "FORM_TYPE"; type = "hidden"; value = "urn:xmpp:push:summary"; }; 229 { name = "FORM_TYPE"; type = "hidden"; value = "urn:xmpp:push:summary"; };
225 { name = "message-count"; type = "text-single"; }; 230 { name = "message-count"; type = "text-single"; };
226 { name = "pending-subscription-count"; type = "text-single"; }; 231 { name = "pending-subscription-count"; type = "text-single"; };
227 { name = "last-message-sender"; type = "jid-single"; }; 232 { name = "last-message-sender"; type = "jid-single"; };
228 { name = "last-message-body"; type = "text-single"; }; 233 { name = "last-message-body"; type = "text-single"; };
234 { name = "last-message-priority"; type = "text-single"; };
229 }; 235 };
230 236
231 -- http://xmpp.org/extensions/xep-0357.html#publishing 237 -- http://xmpp.org/extensions/xep-0357.html#publishing
232 local function handle_notify_request(stanza, node, user_push_services) 238 local function handle_notify_request(stanza, node, user_push_services)
233 local pushes = 0; 239 local pushes = 0;
262 form_data["last-message-sender"] = stanza.attr.from; 268 form_data["last-message-sender"] = stanza.attr.from;
263 end 269 end
264 if stanza and include_body then 270 if stanza and include_body then
265 form_data["last-message-body"] = stanza:get_child_text("body"); 271 form_data["last-message-body"] = stanza:get_child_text("body");
266 end 272 end
273 if stanza then
274 if stanza:get_child("body") or stanza:get_child("encrypted", "eu.siacs.conversations.axolotl") then
275 form_data["last-message-priority"] = "high";
276 else
277 form_data["last-message-priority"] = "low";
278 end
279 end
267 push_publish:add_child(push_form:form(form_data)); 280 push_publish:add_child(push_form:form(form_data));
268 if stanza and push_info.include_payload == "stripped" then 281 if stanza and push_info.include_payload == "stripped" then
269 push_publish:tag("payload", { type = "stripped" }) 282 push_publish:tag("payload", { type = "stripped" })
270 :add_child(strip_stanza(stanza)); 283 :add_child(strip_stanza(stanza));
271 push_publish:up(); -- / payload 284 push_publish:up(); -- / payload
285 module:log("debug", "Sending push notification for %s@%s to %s (%s)", node, module.host, push_info.jid, tostring(push_info.node)); 298 module:log("debug", "Sending push notification for %s@%s to %s (%s)", node, module.host, push_info.jid, tostring(push_info.node));
286 -- module:log("debug", "PUSH STANZA: %s", tostring(push_publish)); 299 -- module:log("debug", "PUSH STANZA: %s", tostring(push_publish));
287 -- handle push errors for this node 300 -- handle push errors for this node
288 if push_errors[push_identifier] == nil then 301 if push_errors[push_identifier] == nil then
289 push_errors[push_identifier] = 0; 302 push_errors[push_identifier] = 0;
290 module:hook("iq-error/bare/"..stanza_id, handle_push_error); 303 module:hook("iq-error/host/"..stanza_id, handle_push_error);
291 module:hook("iq-result/bare/"..stanza_id, handle_push_success); 304 module:hook("iq-result/host/"..stanza_id, handle_push_success);
305 id2node[stanza_id] = node;
292 end 306 end
293 module:send(push_publish); 307 module:send(push_publish);
294 pushes = pushes + 1; 308 pushes = pushes + 1;
295 end 309 end
296 end 310 end
432 module:unhook("archive-message-added", archive_message_added); 446 module:unhook("archive-message-added", archive_message_added);
433 module:unhook("cloud-notify-ping", send_ping); 447 module:unhook("cloud-notify-ping", send_ping);
434 448
435 for push_identifier, _ in pairs(push_errors) do 449 for push_identifier, _ in pairs(push_errors) do
436 local stanza_id = hashes.sha256(push_identifier, true); 450 local stanza_id = hashes.sha256(push_identifier, true);
437 module:unhook("iq-error/bare/"..stanza_id, handle_push_error); 451 module:unhook("iq-error/host/"..stanza_id, handle_push_error);
438 module:unhook("iq-result/bare/"..stanza_id, handle_push_success); 452 module:unhook("iq-result/host/"..stanza_id, handle_push_success);
453 id2node[stanza_id] = nil;
439 end 454 end
440 end 455 end
441 456
442 module:log("info", "Module unloaded"); 457 module:log("info", "Module unloaded");
443 end 458 end