| 1 | -- Prosody IM |
| 2 | -- Copyright (C) 2008-2010 Matthew Wild |
| 3 | -- Copyright (C) 2008-2010 Waqas Hussain |
| 4 | -- |
| 5 | -- This project is MIT/X11 licensed. Please see the |
| 6 | -- COPYING file in the source package for more information. |
| 7 | -- |
| 8 | |
| 9 | _G.prosody = { full_sessions = {}; bare_sessions = {}; hosts = {}; }; |
| 10 | |
| 11 | function core_process_stanza(core_process_stanza, u) |
| 12 | local stanza = require "util.stanza"; |
| 13 | local s2sout_session = { to_host = "remotehost", from_host = "localhost", type = "s2sout" } |
| 14 | local s2sin_session = { from_host = "remotehost", to_host = "localhost", type = "s2sin", hosts = { ["remotehost"] = { authed = true } } } |
| 15 | local local_host_session = { host = "localhost", type = "local", s2sout = { ["remotehost"] = s2sout_session } } |
| 16 | local local_user_session = { username = "user", host = "localhost", resource = "resource", full_jid = "user@localhost/resource", type = "c2s" } |
| 17 | |
| 18 | _G.prosody.hosts["localhost"] = local_host_session; |
| 19 | _G.prosody.full_sessions["user@localhost/resource"] = local_user_session; |
| 20 | _G.prosody.bare_sessions["user@localhost"] = { sessions = { resource = local_user_session } }; |
| 21 | |
| 22 | -- Test message routing |
| 23 | local function test_message_full_jid() |
| 24 | local env = testlib_new_env(); |
| 25 | local msg = stanza.stanza("message", { to = "user@localhost/resource", type = "chat" }):tag("body"):text("Hello world"); |
| 26 | |
| 27 | local target_routed; |
| 28 | |
| 29 | function env.core_post_stanza(p_origin, p_stanza) |
| 30 | assert_equal(p_origin, local_user_session, "origin of routed stanza is not correct"); |
| 31 | assert_equal(p_stanza, msg, "routed stanza is not correct one: "..p_stanza:pretty_print()); |
| 32 | target_routed = true; |
| 33 | end |
| 34 | |
| 35 | env.hosts = hosts; |
| 36 | env.prosody = { hosts = hosts }; |
| 37 | setfenv(core_process_stanza, env); |
| 38 | assert_equal(core_process_stanza(local_user_session, msg), nil, "core_process_stanza returned incorrect value"); |
| 39 | assert_equal(target_routed, true, "stanza was not routed successfully"); |
| 40 | end |
| 41 | |
| 42 | local function test_message_bare_jid() |
| 43 | local env = testlib_new_env(); |
| 44 | local msg = stanza.stanza("message", { to = "user@localhost", type = "chat" }):tag("body"):text("Hello world"); |
| 45 | |
| 46 | local target_routed; |
| 47 | |
| 48 | function env.core_post_stanza(p_origin, p_stanza) |
| 49 | assert_equal(p_origin, local_user_session, "origin of routed stanza is not correct"); |
| 50 | assert_equal(p_stanza, msg, "routed stanza is not correct one: "..p_stanza:pretty_print()); |
| 51 | target_routed = true; |
| 52 | end |
| 53 | |
| 54 | env.hosts = hosts; |
| 55 | setfenv(core_process_stanza, env); |
| 56 | assert_equal(core_process_stanza(local_user_session, msg), nil, "core_process_stanza returned incorrect value"); |
| 57 | assert_equal(target_routed, true, "stanza was not routed successfully"); |
| 58 | end |
| 59 | |
| 60 | local function test_message_no_to() |
| 61 | local env = testlib_new_env(); |
| 62 | local msg = stanza.stanza("message", { type = "chat" }):tag("body"):text("Hello world"); |
| 63 | |
| 64 | local target_handled; |
| 65 | |
| 66 | function env.core_post_stanza(p_origin, p_stanza) |
| 67 | assert_equal(p_origin, local_user_session, "origin of handled stanza is not correct"); |
| 68 | assert_equal(p_stanza, msg, "handled stanza is not correct one: "..p_stanza:pretty_print()); |
| 69 | target_handled = true; |
| 70 | end |
| 71 | |
| 72 | env.hosts = hosts; |
| 73 | setfenv(core_process_stanza, env); |
| 74 | assert_equal(core_process_stanza(local_user_session, msg), nil, "core_process_stanza returned incorrect value"); |
| 75 | assert_equal(target_handled, true, "stanza was not handled successfully"); |
| 76 | end |
| 77 | |
| 78 | local function test_message_to_remote_bare() |
| 79 | local env = testlib_new_env(); |
| 80 | local msg = stanza.stanza("message", { to = "user@remotehost", type = "chat" }):tag("body"):text("Hello world"); |
| 81 | |
| 82 | local target_routed; |
| 83 | |
| 84 | function env.core_route_stanza(p_origin, p_stanza) |
| 85 | assert_equal(p_origin, local_user_session, "origin of handled stanza is not correct"); |
| 86 | assert_equal(p_stanza, msg, "handled stanza is not correct one: "..p_stanza:pretty_print()); |
| 87 | target_routed = true; |
| 88 | end |
| 89 | |
| 90 | function env.core_post_stanza(...) env.core_route_stanza(...); end |
| 91 | |
| 92 | env.hosts = hosts; |
| 93 | setfenv(core_process_stanza, env); |
| 94 | assert_equal(core_process_stanza(local_user_session, msg), nil, "core_process_stanza returned incorrect value"); |
| 95 | assert_equal(target_routed, true, "stanza was not routed successfully"); |
| 96 | end |
| 97 | |
| 98 | local function test_message_to_remote_server() |
| 99 | local env = testlib_new_env(); |
| 100 | local msg = stanza.stanza("message", { to = "remotehost", type = "chat" }):tag("body"):text("Hello world"); |
| 101 | |
| 102 | local target_routed; |
| 103 | |
| 104 | function env.core_route_stanza(p_origin, p_stanza) |
| 105 | assert_equal(p_origin, local_user_session, "origin of handled stanza is not correct"); |
| 106 | assert_equal(p_stanza, msg, "handled stanza is not correct one: "..p_stanza:pretty_print()); |
| 107 | target_routed = true; |
| 108 | end |
| 109 | |
| 110 | function env.core_post_stanza(...) |
| 111 | env.core_route_stanza(...); |
| 112 | end |
| 113 | |
| 114 | env.hosts = hosts; |
| 115 | setfenv(core_process_stanza, env); |
| 116 | assert_equal(core_process_stanza(local_user_session, msg), nil, "core_process_stanza returned incorrect value"); |
| 117 | assert_equal(target_routed, true, "stanza was not routed successfully"); |
| 118 | end |
| 119 | |
| 120 | --IQ tests |
| 121 | |
| 122 | |
| 123 | local function test_iq_to_remote_server() |
| 124 | local env = testlib_new_env(); |
| 125 | local msg = stanza.stanza("iq", { to = "remotehost", type = "get", id = "id" }):tag("body"):text("Hello world"); |
| 126 | |
| 127 | local target_routed; |
| 128 | |
| 129 | function env.core_route_stanza(p_origin, p_stanza) |
| 130 | assert_equal(p_origin, local_user_session, "origin of handled stanza is not correct"); |
| 131 | assert_equal(p_stanza, msg, "handled stanza is not correct one: "..p_stanza:pretty_print()); |
| 132 | target_routed = true; |
| 133 | end |
| 134 | |
| 135 | function env.core_post_stanza(...) |
| 136 | env.core_route_stanza(...); |
| 137 | end |
| 138 | |
| 139 | env.hosts = hosts; |
| 140 | setfenv(core_process_stanza, env); |
| 141 | assert_equal(core_process_stanza(local_user_session, msg), nil, "core_process_stanza returned incorrect value"); |
| 142 | assert_equal(target_routed, true, "stanza was not routed successfully"); |
| 143 | end |
| 144 | |
| 145 | local function test_iq_error_to_local_user() |
| 146 | local env = testlib_new_env(); |
| 147 | local msg = stanza.stanza("iq", { to = "user@localhost/resource", from = "user@remotehost", type = "error", id = "id" }):tag("error", { type = 'cancel' }):tag("item-not-found", { xmlns='urn:ietf:params:xml:ns:xmpp-stanzas' }); |
| 148 | |
| 149 | local target_routed; |
| 150 | |
| 151 | function env.core_route_stanza(p_origin, p_stanza) |
| 152 | assert_equal(p_origin, s2sin_session, "origin of handled stanza is not correct"); |
| 153 | assert_equal(p_stanza, msg, "handled stanza is not correct one: "..p_stanza:pretty_print()); |
| 154 | target_routed = true; |
| 155 | end |
| 156 | |
| 157 | function env.core_post_stanza(...) |
| 158 | env.core_route_stanza(...); |
| 159 | end |
| 160 | |
| 161 | env.hosts = hosts; |
| 162 | setfenv(core_process_stanza, env); |
| 163 | assert_equal(core_process_stanza(s2sin_session, msg), nil, "core_process_stanza returned incorrect value"); |
| 164 | assert_equal(target_routed, true, "stanza was not routed successfully"); |
| 165 | end |
| 166 | |
| 167 | local function test_iq_to_local_bare() |
| 168 | local env = testlib_new_env(); |
| 169 | local msg = stanza.stanza("iq", { to = "user@localhost", from = "user@localhost", type = "get", id = "id" }):tag("ping", { xmlns = "urn:xmpp:ping:0" }); |
| 170 | |
| 171 | local target_handled; |
| 172 | |
| 173 | function env.core_post_stanza(p_origin, p_stanza) |
| 174 | assert_equal(p_origin, local_user_session, "origin of handled stanza is not correct"); |
| 175 | assert_equal(p_stanza, msg, "handled stanza is not correct one: "..p_stanza:pretty_print()); |
| 176 | target_handled = true; |
| 177 | end |
| 178 | |
| 179 | env.hosts = hosts; |
| 180 | setfenv(core_process_stanza, env); |
| 181 | assert_equal(core_process_stanza(local_user_session, msg), nil, "core_process_stanza returned incorrect value"); |
| 182 | assert_equal(target_handled, true, "stanza was not handled successfully"); |
| 183 | end |
| 184 | |
| 185 | runtest(test_message_full_jid, "Messages with full JID destinations get routed"); |
| 186 | runtest(test_message_bare_jid, "Messages with bare JID destinations get routed"); |
| 187 | runtest(test_message_no_to, "Messages with no destination are handled by the server"); |
| 188 | runtest(test_message_to_remote_bare, "Messages to a remote user are routed by the server"); |
| 189 | runtest(test_message_to_remote_server, "Messages to a remote server's JID are routed"); |
| 190 | |
| 191 | runtest(test_iq_to_remote_server, "iq to a remote server's JID are routed"); |
| 192 | runtest(test_iq_to_local_bare, "iq from a local user to a local user's bare JID are handled"); |
| 193 | runtest(test_iq_error_to_local_user, "iq type=error to a local user's JID are routed"); |
| 194 | end |
| 195 | |
| 196 | function core_route_stanza(core_route_stanza) |
| 197 | local stanza = require "util.stanza"; |
| 198 | local s2sout_session = { to_host = "remotehost", from_host = "localhost", type = "s2sout" } |
| 199 | local s2sin_session = { from_host = "remotehost", to_host = "localhost", type = "s2sin", hosts = { ["remotehost"] = { authed = true } } } |
| 200 | local local_host_session = { host = "localhost", type = "local", s2sout = { ["remotehost"] = s2sout_session }, sessions = {} } |
| 201 | local local_user_session = { username = "user", host = "localhost", resource = "resource", full_jid = "user@localhost/resource", type = "c2s" } |
| 202 | local hosts = { |
| 203 | ["localhost"] = local_host_session; |
| 204 | } |
| 205 | |
| 206 | local function test_iq_result_to_offline_user() |
| 207 | local env = testlib_new_env(); |
| 208 | local msg = stanza.stanza("iq", { to = "user@localhost/foo", from = "user@localhost", type = "result" }):tag("ping", { xmlns = "urn:xmpp:ping:0" }); |
| 209 | local msg2 = stanza.stanza("iq", { to = "user@localhost/foo", from = "user@localhost", type = "error" }):tag("ping", { xmlns = "urn:xmpp:ping:0" }); |
| 210 | --package.loaded["core.usermanager"] = { user_exists = function (user, host) print("RAR!") return true or user == "user" and host == "localhost" and true; end }; |
| 211 | local target_handled, target_replied; |
| 212 | |
| 213 | function env.core_post_stanza(p_origin, p_stanza) |
| 214 | target_handled = true; |
| 215 | end |
| 216 | |
| 217 | function local_user_session.send(data) |
| 218 | --print("Replying with: ", tostring(data)); |
| 219 | --print(debug.traceback()) |
| 220 | target_replied = true; |
| 221 | end |
| 222 | |
| 223 | env.hosts = hosts; |
| 224 | setfenv(core_route_stanza, env); |
| 225 | assert_equal(core_route_stanza(local_user_session, msg), nil, "core_route_stanza returned incorrect value"); |
| 226 | assert_equal(target_handled, nil, "stanza was handled and not dropped"); |
| 227 | assert_equal(target_replied, nil, "stanza was replied to and not dropped"); |
| 228 | package.loaded["core.usermanager"] = nil; |
| 229 | end |
| 230 | |
| 231 | --runtest(test_iq_result_to_offline_user, "iq type=result|error to an offline user are not replied to"); |
| 232 | end |