annotate mod_muc_cloud_notify/mod_muc_cloud_notify.lua @ 5401:c8d04ac200fc

mod_http_oauth2: Reject loopback URIs as client_uri This really should be a proper website with info, https://localhost is not good enough. Ideally we'd validate that it's got proper DNS and is actually reachable, but triggering HTTP or even DNS lookups seems like it would carry abuse potential that would best to avoid.
author Kim Alvefur <zash@zash.se>
date Tue, 02 May 2023 16:20:55 +0200
parents 524a9103fb45
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
1 -- XEP-XXX: MUC Push Notifications
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
2 -- Copyright (C) 2015-2016 Kim Alvefur
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
3 -- Copyright (C) 2017-2018 Thilo Molitor
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
4 --
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
5 -- This file is MIT/X11 licensed.
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
6
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
7 local s_match = string.match;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
8 local s_sub = string.sub;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
9 local os_time = os.time;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
10 local next = next;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
11 local st = require"util.stanza";
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
12 local jid = require"util.jid";
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
13 local dataform = require"util.dataforms".new;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
14 local hashes = require"util.hashes";
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
15
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
16 local xmlns_push = "urn:xmpp:push:0";
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
17
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
18 -- configuration
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
19 local include_body = module:get_option_boolean("push_notification_with_body", false);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
20 local include_sender = module:get_option_boolean("push_notification_with_sender", false);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
21 local max_push_errors = module:get_option_number("push_max_errors", 16);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
22 local max_push_devices = module:get_option_number("push_max_devices", 5);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
23 local dummy_body = module:get_option_string("push_notification_important_body", "New Message!");
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
24
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
25 local host_sessions = prosody.hosts[module.host].sessions;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
26 local push_errors = {};
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
27 local id2node = {};
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
28
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
29 module:depends("muc");
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
30
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
31 -- ordered table iterator, allow to iterate on the natural order of the keys of a table,
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
32 -- see http://lua-users.org/wiki/SortedIteration
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
33 local function __genOrderedIndex( t )
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
34 local orderedIndex = {}
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
35 for key in pairs(t) do
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
36 table.insert( orderedIndex, key )
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
37 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
38 -- sort in reverse order (newest one first)
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
39 table.sort( orderedIndex, function(a, b)
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
40 if a == nil or t[a] == nil or b == nil or t[b] == nil then return false end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
41 -- only one timestamp given, this is the newer one
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
42 if t[a].timestamp ~= nil and t[b].timestamp == nil then return true end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
43 if t[a].timestamp == nil and t[b].timestamp ~= nil then return false end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
44 -- both timestamps given, sort normally
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
45 if t[a].timestamp ~= nil and t[b].timestamp ~= nil then return t[a].timestamp > t[b].timestamp end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
46 return false -- normally not reached
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
47 end)
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
48 return orderedIndex
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
49 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
50 local function orderedNext(t, state)
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
51 -- Equivalent of the next function, but returns the keys in timestamp
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
52 -- order. We use a temporary ordered key table that is stored in the
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
53 -- table being iterated.
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
54
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
55 local key = nil
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
56 --print("orderedNext: state = "..tostring(state) )
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
57 if state == nil then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
58 -- the first time, generate the index
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
59 t.__orderedIndex = __genOrderedIndex( t )
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
60 key = t.__orderedIndex[1]
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
61 else
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
62 -- fetch the next value
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
63 for i = 1, #t.__orderedIndex do
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
64 if t.__orderedIndex[i] == state then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
65 key = t.__orderedIndex[i+1]
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
66 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
67 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
68 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
69
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
70 if key then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
71 return key, t[key]
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
72 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
73
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
74 -- no more value to return, cleanup
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
75 t.__orderedIndex = nil
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
76 return
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
77 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
78 local function orderedPairs(t)
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
79 -- Equivalent of the pairs() function on tables. Allows to iterate
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
80 -- in order
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
81 return orderedNext, t, nil
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
82 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
83
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
84 -- small helper function to return new table with only "maximum" elements containing only the newest entries
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
85 local function reduce_table(table, maximum)
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
86 local count = 0;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
87 local result = {};
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
88 for key, value in orderedPairs(table) do
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
89 count = count + 1;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
90 if count > maximum then break end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
91 result[key] = value;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
92 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
93 return result;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
94 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
95
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
96 -- For keeping state across reloads while caching reads
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
97 local push_store = (function()
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
98 local store = module:open_store();
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
99 local push_services = {};
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
100 local api = {};
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
101 function api:get(user)
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
102 if not push_services[user] then
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
103 local err;
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
104 push_services[user], err = store:get(user);
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
105 if not push_services[user] and err then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
106 module:log("warn", "Error reading push notification storage for user '%s': %s", user, tostring(err));
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
107 push_services[user] = {};
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
108 return push_services[user], false;
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
109 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
110 end
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
111 if not push_services[user] then push_services[user] = {} end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
112 return push_services[user], true;
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
113 end
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
114 function api:set(user, data)
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
115 push_services[user] = reduce_table(data, max_push_devices);
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
116 local ok, err = store:set(user, push_services[user]);
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
117 if not ok then
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
118 module:log("error", "Error writing push notification storage for user '%s': %s", user, tostring(err));
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
119 return false;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
120 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
121 return true;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
122 end
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
123 function api:set_identifier(user, push_identifier, data)
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
124 local services = self:get(user);
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
125 services[push_identifier] = data;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
126 return self:set(user, services);
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
127 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
128 return api;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
129 end)();
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
130
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
131
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
132 -- Forward declarations, as both functions need to reference each other
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
133 local handle_push_success, handle_push_error;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
134
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
135 function handle_push_error(event)
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
136 local stanza = event.stanza;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
137 local error_type, condition = stanza:get_error();
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
138 local node = id2node[stanza.attr.id];
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
139 if node == nil then return false; end -- unknown stanza? Ignore for now!
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
140 local from = stanza.attr.from;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
141 local user_push_services = push_store:get(node);
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
142 local changed = false;
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
143
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
144 for push_identifier, _ in pairs(user_push_services) do
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
145 local stanza_id = hashes.sha256(push_identifier, true);
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
146 if stanza_id == stanza.attr.id then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
147 if user_push_services[push_identifier] and user_push_services[push_identifier].jid == from and error_type ~= "wait" then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
148 push_errors[push_identifier] = push_errors[push_identifier] + 1;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
149 module:log("info", "Got error of type '%s' (%s) for identifier '%s': "
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
150 .."error count for this identifier is now at %s", error_type, condition, push_identifier,
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
151 tostring(push_errors[push_identifier]));
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
152 if push_errors[push_identifier] >= max_push_errors then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
153 module:log("warn", "Disabling push notifications for identifier '%s'", push_identifier);
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
154 -- remove push settings from sessions
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
155 if host_sessions[node] then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
156 for _, session in pairs(host_sessions[node].sessions) do
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
157 if session.push_identifier == push_identifier then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
158 session.push_identifier = nil;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
159 session.push_settings = nil;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
160 session.first_hibernated_push = nil;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
161 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
162 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
163 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
164 -- save changed global config
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
165 changed = true;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
166 user_push_services[push_identifier] = nil
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
167 push_errors[push_identifier] = nil;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
168 -- unhook iq handlers for this identifier (if possible)
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
169 if module.unhook then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
170 module:unhook("iq-error/host/"..stanza_id, handle_push_error);
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
171 module:unhook("iq-result/host/"..stanza_id, handle_push_success);
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
172 id2node[stanza_id] = nil;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
173 end
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
174 end
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
175 elseif user_push_services[push_identifier] and user_push_services[push_identifier].jid == from and error_type == "wait" then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
176 module:log("debug", "Got error of type '%s' (%s) for identifier '%s': "
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
177 .."NOT increasing error count for this identifier", error_type, condition, push_identifier);
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
178 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
179 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
180 end
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
181 if changed then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
182 push_store:set(node, user_push_services);
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
183 end
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
184 return true;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
185 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
186
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
187 function handle_push_success(event)
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
188 local stanza = event.stanza;
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
189 local node = id2node[stanza.attr.id];
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
190 if node == nil then return false; end -- unknown stanza? Ignore for now!
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
191 local from = stanza.attr.from;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
192 local user_push_services = push_store:get(node);
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
193
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
194 for push_identifier, _ in pairs(user_push_services) do
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
195 if hashes.sha256(push_identifier, true) == stanza.attr.id then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
196 if user_push_services[push_identifier] and user_push_services[push_identifier].jid == from and push_errors[push_identifier] > 0 then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
197 push_errors[push_identifier] = 0;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
198 module:log("debug", "Push succeeded, error count for identifier '%s' is now at %s again", push_identifier, tostring(push_errors[push_identifier]));
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
199 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
200 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
201 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
202 return true;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
203 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
204
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
205 -- http://xmpp.org/extensions/xep-0357.html#disco
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
206 local function account_dico_info(event)
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
207 (event.reply or event.stanza):tag("feature", {var=xmlns_push}):up();
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
208 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
209 module:hook("account-disco-info", account_dico_info);
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
210
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
211 -- http://xmpp.org/extensions/xep-0357.html#enabling
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
212 local function push_enable(event)
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
213 local origin, stanza = event.origin, event.stanza;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
214 local enable = stanza.tags[1];
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
215 origin.log("debug", "Attempting to enable push notifications");
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
216 -- MUST contain a 'jid' attribute of the XMPP Push Service being enabled
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
217 local push_jid = enable.attr.jid;
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
218 -- SHOULD contain a 'node' attribute
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
219 local push_node = enable.attr.node;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
220 -- CAN contain a 'include_payload' attribute
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
221 local include_payload = enable.attr.include_payload;
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
222 if not push_jid then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
223 origin.log("debug", "MUC Push notification enable request missing the 'jid' field");
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
224 origin.send(st.error_reply(stanza, "modify", "bad-request", "Missing jid"));
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
225 return true;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
226 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
227 local publish_options = enable:get_child("x", "jabber:x:data");
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
228 if not publish_options then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
229 -- Could be intentional
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
230 origin.log("debug", "No publish options in request");
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
231 end
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
232 local push_identifier = push_jid .. "<" .. (push_node or "");
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
233 local push_service = {
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
234 jid = push_jid;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
235 node = push_node;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
236 include_payload = include_payload;
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
237 options = publish_options and st.preserialize(publish_options);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
238 timestamp = os_time();
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
239 };
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
240 local ok = push_store:set_identifier(origin.username.."@"..origin.host, push_identifier, push_service);
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
241 if not ok then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
242 origin.send(st.error_reply(stanza, "wait", "internal-server-error"));
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
243 else
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
244 origin.push_identifier = push_identifier;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
245 origin.push_settings = push_service;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
246 origin.first_hibernated_push = nil;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
247 origin.log("info", "MUC Push notifications enabled for %s by %s (%s)",
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
248 tostring(stanza.attr.to),
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
249 tostring(stanza.attr.from),
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
250 tostring(origin.push_identifier)
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
251 );
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
252 origin.send(st.reply(stanza));
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
253 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
254 return true;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
255 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
256 module:hook("iq-set/host/"..xmlns_push..":enable", push_enable);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
257
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
258
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
259 -- http://xmpp.org/extensions/xep-0357.html#disabling
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
260 local function push_disable(event)
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
261 local origin, stanza = event.origin, event.stanza;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
262 local push_jid = stanza.tags[1].attr.jid; -- MUST include a 'jid' attribute
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
263 local push_node = stanza.tags[1].attr.node; -- A 'node' attribute MAY be included
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
264 if not push_jid then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
265 origin.send(st.error_reply(stanza, "modify", "bad-request", "Missing jid"));
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
266 return true;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
267 end
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
268 local user_push_services = push_store:get(origin.username);
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
269 for key, push_info in pairs(user_push_services) do
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
270 if push_info.jid == push_jid and (not push_node or push_info.node == push_node) then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
271 origin.log("info", "Push notifications disabled (%s)", tostring(key));
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
272 if origin.push_identifier == key then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
273 origin.push_identifier = nil;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
274 origin.push_settings = nil;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
275 origin.first_hibernated_push = nil;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
276 end
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
277 user_push_services[key] = nil;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
278 push_errors[key] = nil;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
279 if module.unhook then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
280 module:unhook("iq-error/host/"..key, handle_push_error);
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
281 module:unhook("iq-result/host/"..key, handle_push_success);
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
282 id2node[key] = nil;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
283 end
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
284 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
285 end
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
286 local ok = push_store:set(origin.username, user_push_services);
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
287 if not ok then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
288 origin.send(st.error_reply(stanza, "wait", "internal-server-error"));
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
289 else
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
290 origin.send(st.reply(stanza));
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
291 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
292 return true;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
293 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
294 module:hook("iq-set/host/"..xmlns_push..":disable", push_disable);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
295
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
296 -- Patched version of util.stanza:find() that supports giving stanza names
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
297 -- without their namespace, allowing for every namespace.
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
298 local function find(self, path)
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
299 local pos = 1;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
300 local len = #path + 1;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
301
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
302 repeat
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
303 local xmlns, name, text;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
304 local char = s_sub(path, pos, pos);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
305 if char == "@" then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
306 return self.attr[s_sub(path, pos + 1)];
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
307 elseif char == "{" then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
308 xmlns, pos = s_match(path, "^([^}]+)}()", pos + 1);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
309 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
310 name, text, pos = s_match(path, "^([^@/#]*)([/#]?)()", pos);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
311 name = name ~= "" and name or nil;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
312 if pos == len then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
313 if text == "#" then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
314 local child = xmlns ~= nil and self:get_child(name, xmlns) or self:child_with_name(name);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
315 return child and child:get_text() or nil;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
316 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
317 return xmlns ~= nil and self:get_child(name, xmlns) or self:child_with_name(name);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
318 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
319 self = xmlns ~= nil and self:get_child(name, xmlns) or self:child_with_name(name);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
320 until not self
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
321 return nil;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
322 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
323
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
324 -- is this push a high priority one (this is needed for ios apps not using voip pushes)
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
325 local function is_important(stanza)
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
326 local st_name = stanza and stanza.name or nil;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
327 if not st_name then return false; end -- nonzas are never important here
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
328 if st_name == "presence" then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
329 return false; -- same for presences
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
330 elseif st_name == "message" then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
331 -- unpack carbon copies
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
332 local stanza_direction = "in";
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
333 local carbon;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
334 local st_type;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
335 -- support carbon copied message stanzas having an arbitrary message-namespace or no message-namespace at all
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
336 if not carbon then carbon = find(stanza, "{urn:xmpp:carbons:2}/forwarded/message"); end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
337 if not carbon then carbon = find(stanza, "{urn:xmpp:carbons:1}/forwarded/message"); end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
338 stanza_direction = carbon and stanza:child_with_name("sent") and "out" or "in";
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
339 if carbon then stanza = carbon; end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
340 st_type = stanza.attr.type;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
341
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
342 -- headline message are always not important
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
343 if st_type == "headline" then return false; end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
344
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
345 -- carbon copied outgoing messages are not important
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
346 if carbon and stanza_direction == "out" then return false; end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
347
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
348 -- We can't check for body contents in encrypted messages, so let's treat them as important
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
349 -- Some clients don't even set a body or an empty body for encrypted messages
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
350
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
351 -- check omemo https://xmpp.org/extensions/inbox/omemo.html
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
352 if stanza:get_child("encrypted", "eu.siacs.conversations.axolotl") or stanza:get_child("encrypted", "urn:xmpp:omemo:0") then return true; end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
353
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
354 -- check xep27 pgp https://xmpp.org/extensions/xep-0027.html
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
355 if stanza:get_child("x", "jabber:x:encrypted") then return true; end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
356
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
357 -- check xep373 pgp (OX) https://xmpp.org/extensions/xep-0373.html
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
358 if stanza:get_child("openpgp", "urn:xmpp:openpgp:0") then return true; end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
359
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
360 local body = stanza:get_child_text("body");
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
361 if st_type == "groupchat" and stanza:get_child_text("subject") then return false; end -- groupchat subjects are not important here
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
362 return body ~= nil and body ~= ""; -- empty bodies are not important
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
363 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
364 return false; -- this stanza wasn't one of the above cases --> it is not important, too
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
365 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
366
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
367 local push_form = dataform {
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
368 { name = "FORM_TYPE"; type = "hidden"; value = "urn:xmpp:push:summary"; };
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
369 { name = "message-count"; type = "text-single"; };
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
370 { name = "pending-subscription-count"; type = "text-single"; };
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
371 { name = "last-message-sender"; type = "jid-single"; };
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
372 { name = "last-message-body"; type = "text-single"; };
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
373 };
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
374
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
375 -- http://xmpp.org/extensions/xep-0357.html#publishing
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
376 local function handle_notify_request(stanza, node, user_push_services, log_push_decline)
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
377 local pushes = 0;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
378 if not user_push_services or next(user_push_services) == nil then return pushes end
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
379
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
380 -- XXX: customized
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
381 local body = stanza:get_child_text("body");
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
382 if not body then
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
383 return pushes;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
384 end
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
385
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
386 for push_identifier, push_info in pairs(user_push_services) do
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
387 local send_push = true; -- only send push to this node when not already done for this stanza or if no stanza is given at all
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
388 if stanza then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
389 if not stanza._push_notify then stanza._push_notify = {}; end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
390 if stanza._push_notify[push_identifier] then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
391 if log_push_decline then
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
392 module:log("debug", "Already sent push notification for %s@%s to %s (%s)", node, module.host, push_info.jid, tostring(push_info.node));
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
393 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
394 send_push = false;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
395 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
396 stanza._push_notify[push_identifier] = true;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
397 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
398
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
399 if send_push then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
400 -- construct push stanza
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
401 local stanza_id = hashes.sha256(push_identifier, true);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
402 local push_publish = st.iq({ to = push_info.jid, from = module.host, type = "set", id = stanza_id })
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
403 :tag("pubsub", { xmlns = "http://jabber.org/protocol/pubsub" })
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
404 :tag("publish", { node = push_info.node })
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
405 :tag("item")
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
406 :tag("notification", { xmlns = xmlns_push });
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
407 local form_data = {
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
408 -- hardcode to 1 because other numbers are just meaningless (the XEP does not specify *what exactly* to count)
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
409 ["message-count"] = "1";
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
410 };
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
411 if stanza and include_sender then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
412 form_data["last-message-sender"] = stanza.attr.from;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
413 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
414 if stanza and include_body then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
415 form_data["last-message-body"] = stanza:get_child_text("body");
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
416 elseif stanza and dummy_body and is_important(stanza) then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
417 form_data["last-message-body"] = tostring(dummy_body);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
418 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
419 push_publish:add_child(push_form:form(form_data));
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
420 push_publish:up(); -- / notification
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
421 push_publish:up(); -- / publish
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
422 push_publish:up(); -- / pubsub
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
423 if push_info.options then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
424 push_publish:tag("publish-options"):add_child(st.deserialize(push_info.options));
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
425 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
426 -- send out push
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
427 module:log("debug", "Sending%s push notification for %s@%s to %s (%s)", form_data["last-message-body"] and " important" or "", node, module.host, push_info.jid, tostring(push_info.node));
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
428 -- module:log("debug", "PUSH STANZA: %s", tostring(push_publish));
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
429 -- handle push errors for this node
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
430 if push_errors[push_identifier] == nil then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
431 push_errors[push_identifier] = 0;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
432 module:hook("iq-error/host/"..stanza_id, handle_push_error);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
433 module:hook("iq-result/host/"..stanza_id, handle_push_success);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
434 id2node[stanza_id] = node;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
435 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
436 module:send(push_publish);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
437 pushes = pushes + 1;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
438 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
439 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
440 return pushes;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
441 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
442
3570
8a93af85f319 mod_muc_cloud_notify: Count codepoints instead of bytes
Matthew Wild <mwild1@gmail.com>
parents: 3319
diff changeset
443 local function extract_reference(text, i, j)
8a93af85f319 mod_muc_cloud_notify: Count codepoints instead of bytes
Matthew Wild <mwild1@gmail.com>
parents: 3319
diff changeset
444 -- COMPAT w/ pre-Lua 5.3
8a93af85f319 mod_muc_cloud_notify: Count codepoints instead of bytes
Matthew Wild <mwild1@gmail.com>
parents: 3319
diff changeset
445 local c, pos, p1 = 0, 0, nil;
8a93af85f319 mod_muc_cloud_notify: Count codepoints instead of bytes
Matthew Wild <mwild1@gmail.com>
parents: 3319
diff changeset
446 for char in text:gmatch("([%z\1-\127\194-\244][\128-\191]*)") do
8a93af85f319 mod_muc_cloud_notify: Count codepoints instead of bytes
Matthew Wild <mwild1@gmail.com>
parents: 3319
diff changeset
447 c, pos = c + 1, pos + #char;
8a93af85f319 mod_muc_cloud_notify: Count codepoints instead of bytes
Matthew Wild <mwild1@gmail.com>
parents: 3319
diff changeset
448 if not p1 and i < c then
8a93af85f319 mod_muc_cloud_notify: Count codepoints instead of bytes
Matthew Wild <mwild1@gmail.com>
parents: 3319
diff changeset
449 p1 = pos;
8a93af85f319 mod_muc_cloud_notify: Count codepoints instead of bytes
Matthew Wild <mwild1@gmail.com>
parents: 3319
diff changeset
450 end
8a93af85f319 mod_muc_cloud_notify: Count codepoints instead of bytes
Matthew Wild <mwild1@gmail.com>
parents: 3319
diff changeset
451 if c == j then
8a93af85f319 mod_muc_cloud_notify: Count codepoints instead of bytes
Matthew Wild <mwild1@gmail.com>
parents: 3319
diff changeset
452 return text:sub(p1, pos);
8a93af85f319 mod_muc_cloud_notify: Count codepoints instead of bytes
Matthew Wild <mwild1@gmail.com>
parents: 3319
diff changeset
453 end
8a93af85f319 mod_muc_cloud_notify: Count codepoints instead of bytes
Matthew Wild <mwild1@gmail.com>
parents: 3319
diff changeset
454 end
8a93af85f319 mod_muc_cloud_notify: Count codepoints instead of bytes
Matthew Wild <mwild1@gmail.com>
parents: 3319
diff changeset
455 end
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
456
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
457 -- archive message added
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
458 local function archive_message_added(event)
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
459 -- event is: { origin = origin, stanza = stanza, for_user = store_user, id = id }
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
460 -- only notify for new mam messages when at least one device is online
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
461 local room = event.room;
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
462 local stanza = event.stanza;
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
463 local body = stanza:get_child_text('body');
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
464
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
465 for reference in stanza:childtags("reference", "urn:xmpp:reference:0") do
4664
524a9103fb45 mod_muc_cloud_notify: Fix comparison between string and number in reference extraction. Fixes #1681.
Matthew Wild <mwild1@gmail.com>
parents: 3883
diff changeset
466 local ref_begin, ref_end = tonumber(reference.attr['begin']), tonumber(reference.attr['end']);
524a9103fb45 mod_muc_cloud_notify: Fix comparison between string and number in reference extraction. Fixes #1681.
Matthew Wild <mwild1@gmail.com>
parents: 3883
diff changeset
467 if reference.attr['type'] == 'mention' and ref_begin and ref_end then
524a9103fb45 mod_muc_cloud_notify: Fix comparison between string and number in reference extraction. Fixes #1681.
Matthew Wild <mwild1@gmail.com>
parents: 3883
diff changeset
468 local nick = extract_reference(body, ref_begin, ref_end);
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
469 local jid = room:get_registered_jid(nick);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
470
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
471 if room._occupants[room.jid..'/'..nick] then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
472 -- We only notify for members not currently in the room
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
473 module:log("debug", "Not notifying %s, because he's currently in the room", jid);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
474 else
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
475 -- We only need to notify once, even when there are multiple mentions.
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
476 local user_push_services = push_store:get(jid);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
477 handle_notify_request(event.stanza, jid, user_push_services, true);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
478 return
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
479 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
480 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
481 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
482 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
483
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
484 module:hook("muc-add-history", archive_message_added);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
485
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
486 local function send_ping(event)
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
487 local user = event.user;
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
488 local user_push_services = push_store:get(user);
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
489 local push_services = event.push_services or user_push_services;
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
490 handle_notify_request(nil, user, push_services, true);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
491 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
492 -- can be used by other modules to ping one or more (or all) push endpoints
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
493 module:hook("cloud-notify-ping", send_ping);
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
494
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
495 module:log("info", "Module loaded");
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
496 function module.unload()
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
497 if module.unhook then
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
498 module:unhook("account-disco-info", account_dico_info);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
499 module:unhook("iq-set/host/"..xmlns_push..":enable", push_enable);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
500 module:unhook("iq-set/host/"..xmlns_push..":disable", push_disable);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
501
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
502 module:unhook("muc-add-history", archive_message_added);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
503 module:unhook("cloud-notify-ping", send_ping);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
504
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
505 for push_identifier, _ in pairs(push_errors) do
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
506 local stanza_id = hashes.sha256(push_identifier, true);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
507 module:unhook("iq-error/host/"..stanza_id, handle_push_error);
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
508 module:unhook("iq-result/host/"..stanza_id, handle_push_success);
3883
571249f69577 mod_muc_cloud_notify: Revert last commit
tmolitor <thilo@eightysoft.de>
parents: 3882
diff changeset
509 id2node[stanza_id] = nil;
3319
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
510 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
511 end
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
512
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
513 module:log("info", "Module unloaded");
408f92149774 mod_muc_cloud_notify: New module
JC Brand <jc@opkode.com>
parents:
diff changeset
514 end