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
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
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