Mercurial > prosody-modules
annotate mod_offline_email/mod_offline_email.lua @ 737:e4ea03b060ed
mod_archive: switch from/to
The XEP-0136 is not very explicit about the meening of <from> and <to>
elements, but the examples are clear: <from> means it comes from the user in
the 'with' attribute of the collection.
That is the opposite of what is currently implemented in that module.
So for better compatibility with complient clients, this switch the 'from' and
'to' fields
author | Olivier Goffart <ogoffart@woboq.com> |
---|---|
date | Wed, 04 Jul 2012 14:08:43 +0200 |
parents | 010452cfaf53 |
children | f1a0a0754b87 |
rev | line source |
---|---|
0
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
1 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
2 local full_sessions = full_sessions; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
3 local bare_sessions = bare_sessions; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
4 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
5 local st = require "util.stanza"; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
6 local jid_bare = require "util.jid".bare; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
7 local jid_split = require "util.jid".split; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
8 local user_exists = require "core.usermanager".user_exists; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
9 local urlencode = require "net.http".urlencode; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
10 local add_task = require "util.timer".add_task; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
11 local os_time = os.time; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
12 local t_concat = table.concat; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
13 local smtp = require "socket.smtp"; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
14 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
15 local smtp_server = module:get_option("smtp_server"); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
16 local smtp_user = module:get_option("smtp_username"); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
17 local smtp_pass = module:get_option("smtp_password"); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
18 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
19 local smtp_address = module:get_option("smtp_from") or ((smtp_user or "xmpp").."@"..(smtp_server or module.host)); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
20 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
21 local queue_offline_emails = module:get_option("queue_offline_emails"); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
22 if queue_offline_emails == true then queue_offline_emails = 300; end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
23 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
24 local send_message_as_email; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
25 local message_body_from_stanza; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
26 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
27 function process_to_bare(bare, origin, stanza) |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
28 local user = bare_sessions[bare]; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
29 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
30 local t = stanza.attr.type; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
31 if t == nil or t == "chat" or t == "normal" then -- chat or normal message |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
32 if not (user and user.top_resources) then -- No resources online? |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
33 if user_exists(jid_split(bare)) then |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
34 local text = message_body_from_stanza(stanza); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
35 if text then |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
36 send_message_as_email(bare, jid_bare(stanza.attr.from), text); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
37 else |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
38 module:log("error", "Unable to extract message body from offline message to put into an email"); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
39 end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
40 end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
41 end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
42 end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
43 return; -- Leave for further processing |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
44 end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
45 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
46 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
47 module:hook("message/full", function(data) |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
48 -- message to full JID recieved |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
49 local origin, stanza = data.origin, data.stanza; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
50 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
51 local session = full_sessions[stanza.attr.to]; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
52 if not session then -- resource not online |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
53 return process_to_bare(jid_bare(stanza.attr.to), origin, stanza); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
54 end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
55 end, 20); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
56 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
57 module:hook("message/bare", function(data) |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
58 -- message to bare JID recieved |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
59 local origin, stanza = data.origin, data.stanza; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
60 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
61 return process_to_bare(stanza.attr.to or (origin.username..'@'..origin.host), origin, stanza); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
62 end, 20); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
63 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
64 function send_message_as_email(address, from_address, message_text, subject) |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
65 module:log("info", "Forwarding offline message to %s via email", address); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
66 local rcpt = "<"..address..">"; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
67 local from_user, from_domain = jid_split(from_address); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
68 local from = "<"..urlencode(from_user).."@"..from_domain..">"; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
69 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
70 local mesgt = { |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
71 headers = { |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
72 to = address; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
73 subject = subject or ("Offline message from "..jid_bare(from_address)); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
74 }; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
75 body = message_text; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
76 }; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
77 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
78 local ok, err = smtp.send{ from = from, rcpt = rcpt, source = smtp.message(mesgt), |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
79 server = smtp_server, user = smtp_user, password = smtp_pass }; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
80 if not ok then |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
81 module:log("error", "Failed to deliver to %s: %s", tostring(address), tostring(err)); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
82 return false; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
83 end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
84 return true; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
85 end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
86 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
87 if queue_offline_emails then |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
88 local queues = {}; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
89 local real_send_message_as_email = send_message_as_email; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
90 function send_message_as_email(address, from_address, message_text) |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
91 local pair_key = address.."\0"..from_address; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
92 local queue = queues[pair_key]; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
93 if not queue then |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
94 queue = { from = from_address, to = address, messages = {} }; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
95 queues[pair_key] = queue; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
96 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
97 add_task(queue_offline_emails+5, function () |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
98 module:log("info", "Checking on %s", from_address); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
99 local current_time = os_time(); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
100 local diff = current_time - queue.last_message_time; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
101 if diff > queue_offline_emails then |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
102 module:log("info", "Enough silence, sending..."); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
103 real_send_message_as_email(address, from_address, t_concat(queue.messages, "\n"), "You have "..#queue.messages.." offline message"..(#queue.messages == 1 and "" or "s").." from "..from_address) |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
104 else |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
105 module:log("info", "Next check in %d", queue_offline_emails - diff + 5); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
106 return queue_offline_emails - diff + 5; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
107 end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
108 end); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
109 end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
110 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
111 queue.last_message_time = os_time(); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
112 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
113 local messages = queue.messages; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
114 messages[#messages+1] = message_text; |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
115 end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
116 end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
117 |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
118 function message_body_from_stanza(stanza) |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
119 local message_text = stanza:child_with_name("body"); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
120 if message_text then |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
121 return message_text:get_text(); |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
122 end |
010452cfaf53
mod_offline_email: Initial commit
Matthew Wild <mwild1@gmail.com>
parents:
diff
changeset
|
123 end |