Software / code / prosody
Comparison
core/modulemanager.lua @ 592:c6e2c727d0cc
Merge from waqas
| author | Matthew Wild <mwild1@gmail.com> |
|---|---|
| date | Sat, 06 Dec 2008 23:23:08 +0000 |
| parent | 584:eb0cea29c8d7 |
| parent | 591:980ded4c60ef |
| child | 608:3758af511ce8 |
comparison
equal
deleted
inserted
replaced
| 588:e743cb742ca6 | 592:c6e2c727d0cc |
|---|---|
| 44 | 44 |
| 45 local api = {}; -- Module API container | 45 local api = {}; -- Module API container |
| 46 | 46 |
| 47 local modulemap = { ["*"] = {} }; | 47 local modulemap = { ["*"] = {} }; |
| 48 | 48 |
| 49 local m_handler_info = multitable_new(); | 49 local stanza_handlers = multitable_new(); |
| 50 local m_stanza_handlers = multitable_new(); | |
| 51 local handler_info = {}; | 50 local handler_info = {}; |
| 52 local stanza_handlers = {}; | |
| 53 | 51 |
| 54 local modulehelpers = setmetatable({}, { __index = _G }); | 52 local modulehelpers = setmetatable({}, { __index = _G }); |
| 55 | 53 |
| 56 -- Load modules when a host is activated | 54 -- Load modules when a host is activated |
| 57 function load_modules_for_host(host) | 55 function load_modules_for_host(host) |
| 70 return nil, "insufficient-parameters"; | 68 return nil, "insufficient-parameters"; |
| 71 end | 69 end |
| 72 | 70 |
| 73 if not modulemap[host] then | 71 if not modulemap[host] then |
| 74 modulemap[host] = {}; | 72 modulemap[host] = {}; |
| 75 stanza_handlers[host] = {}; | |
| 76 elseif modulemap[host][module_name] then | 73 elseif modulemap[host][module_name] then |
| 77 log("warn", "%s is already loaded for %s, so not loading again", module_name, host); | 74 log("warn", "%s is already loaded for %s, so not loading again", module_name, host); |
| 78 return nil, "module-already-loaded"; | 75 return nil, "module-already-loaded"; |
| 79 elseif modulemap["*"][module_name] then | 76 elseif modulemap["*"][module_name] then |
| 80 return nil, "global-module-already-loaded"; | 77 return nil, "global-module-already-loaded"; |
| 121 end | 118 end |
| 122 end | 119 end |
| 123 | 120 |
| 124 end | 121 end |
| 125 | 122 |
| 126 function _handle_stanza(host, origin, stanza) | |
| 127 local name, xmlns, origin_type = stanza.name, stanza.attr.xmlns, origin.type; | |
| 128 | |
| 129 local handlers = stanza_handlers[host]; | |
| 130 if not handlers then | |
| 131 log("warn", "No handlers for %s", host); | |
| 132 return false; | |
| 133 end | |
| 134 | |
| 135 if name == "iq" and xmlns == "jabber:client" and handlers[origin_type] then | |
| 136 local child = stanza.tags[1]; | |
| 137 if child then | |
| 138 local xmlns = child.attr.xmlns or xmlns; | |
| 139 log("debug", "Stanza of type %s from %s has xmlns: %s", name, origin_type, xmlns); | |
| 140 local handler = handlers[origin_type][name] and handlers[origin_type][name][xmlns]; | |
| 141 if handler then | |
| 142 log("debug", "Passing stanza to mod_%s", handler_info[handler].name); | |
| 143 return handler(origin, stanza) or true; | |
| 144 end | |
| 145 end | |
| 146 elseif handlers[origin_type] then | |
| 147 local handler = handlers[origin_type][name]; | |
| 148 if handler then | |
| 149 handler = handler[xmlns]; | |
| 150 if handler then | |
| 151 log("debug", "Passing stanza to mod_%s", handler_info[handler].name); | |
| 152 return handler(origin, stanza) or true; | |
| 153 end | |
| 154 end | |
| 155 end | |
| 156 log("debug", "Stanza unhandled by any modules, xmlns: %s", stanza.attr.xmlns); | |
| 157 return false; -- we didn't handle it | |
| 158 end | |
| 159 function handle_stanza(host, origin, stanza) | 123 function handle_stanza(host, origin, stanza) |
| 160 local name, xmlns, origin_type = stanza.name, stanza.attr.xmlns, origin.type; | 124 local name, xmlns, origin_type = stanza.name, stanza.attr.xmlns, origin.type; |
| 161 if name == "iq" and xmlns == "jabber:client" then | 125 if name == "iq" and xmlns == "jabber:client" then |
| 162 xmlns = stanza.tags[1].attr.xmlns; | 126 xmlns = stanza.tags[1].attr.xmlns; |
| 163 log("debug", "Stanza of type %s from %s has xmlns: %s", name, origin_type, xmlns); | 127 log("debug", "Stanza of type %s from %s has xmlns: %s", name, origin_type, xmlns); |
| 164 end | 128 end |
| 165 local handlers = m_stanza_handlers:get(host, origin_type, name, xmlns); | 129 local handlers = stanza_handlers:get(host, origin_type, name, xmlns); |
| 166 if handlers then | 130 if handlers then |
| 167 log("debug", "Passing stanza to mod_%s", handler_info[handlers[1]].name); | 131 log("debug", "Passing stanza to mod_%s", handler_info[handlers[1]].name); |
| 168 (handlers[1])(origin, stanza); | 132 (handlers[1])(origin, stanza); |
| 169 return true; | 133 return true; |
| 170 else | 134 else |
| 183 -- Returns the host that the current module is serving | 147 -- Returns the host that the current module is serving |
| 184 function api:get_host() | 148 function api:get_host() |
| 185 return self.host; | 149 return self.host; |
| 186 end | 150 end |
| 187 | 151 |
| 188 | 152 local function _add_handler(module, origin_type, tag, xmlns, handler) |
| 189 local function __add_iq_handler(module, origin_type, xmlns, handler) | 153 local handlers = stanza_handlers:get(module.host, origin_type, tag, xmlns); |
| 190 local handlers = stanza_handlers[module.host]; | 154 local msg = (tag == "iq") and "namespace" or "payload namespace"; |
| 191 handlers[origin_type] = handlers[origin_type] or {}; | 155 if not handlers then |
| 192 handlers[origin_type].iq = handlers[origin_type].iq or {}; | 156 stanza_handlers:add(module.host, origin_type, tag, xmlns, handler); |
| 193 if not handlers[origin_type].iq[xmlns] then | |
| 194 handlers[origin_type].iq[xmlns]= handler; | |
| 195 handler_info[handler] = module; | 157 handler_info[handler] = module; |
| 196 module:log("debug", "I now handle tag 'iq' [%s] with payload namespace '%s'", origin_type, xmlns); | 158 module:log("debug", "I now handle tag '%s' [%s] with %s '%s'", tag, origin_type, msg, xmlns); |
| 197 else | 159 else |
| 198 module:log("warn", "I wanted to handle tag 'iq' [%s] with payload namespace '%s' but mod_%s already handles that", origin_type, xmlns, handler_info[handlers[origin_type].iq[xmlns]].name); | 160 module:log("warn", "I wanted to handle tag '%s' [%s] with %s '%s' but mod_%s already handles that", tag, origin_type, msg, xmlns, handler_info[handlers[1]].module.name); |
| 199 end | |
| 200 end | |
| 201 local function _add_iq_handler(module, origin_type, xmlns, handler) | |
| 202 local handlers = m_stanza_handlers:get(module.host, origin_type, "iq", xmlns); | |
| 203 if not handlers then | |
| 204 m_stanza_handlers:add(module.host, origin_type, "iq", xmlns, handler); | |
| 205 handler_info[handler] = module; | |
| 206 module:log("debug", "I now handle tag 'iq' [%s] with payload namespace '%s'", origin_type, xmlns); | |
| 207 else | |
| 208 module:log("warn", "I wanted to handle tag 'iq' [%s] with payload namespace '%s' but mod_%s already handles that", origin_type, xmlns, handler_info[handlers[1]].name); | |
| 209 end | 161 end |
| 210 end | 162 end |
| 211 | 163 |
| 212 function api:add_iq_handler(origin_type, xmlns, handler) | 164 function api:add_handler(origin_type, tag, xmlns, handler) |
| 213 if not (origin_type and handler and xmlns) then return false; end | 165 if not (origin_type and tag and xmlns and handler) then return false; end |
| 214 if type(origin_type) == "table" then | 166 if type(origin_type) == "table" then |
| 215 for _, origin_type in ipairs(origin_type) do | 167 for _, origin_type in ipairs(origin_type) do |
| 216 _add_iq_handler(self, origin_type, xmlns, handler); | 168 _add_handler(self, origin_type, tag, xmlns, handler); |
| 217 end | 169 end |
| 218 return; | 170 else |
| 171 _add_handler(self, origin_type, tag, xmlns, handler); | |
| 219 end | 172 end |
| 220 _add_iq_handler(self, origin_type, xmlns, handler); | 173 end |
| 174 function api:add_iq_handler(origin_type, xmlns, handler) | |
| 175 self:add_handler(origin_type, "iq", xmlns, handler); | |
| 221 end | 176 end |
| 222 | 177 |
| 223 function api:add_feature(xmlns) | 178 function api:add_feature(xmlns) |
| 224 addDiscoInfoHandler(self.host, function(reply, to, from, node) | 179 addDiscoInfoHandler(self.host, function(reply, to, from, node) |
| 225 if #node == 0 then | 180 if #node == 0 then |
| 229 end); | 184 end); |
| 230 end | 185 end |
| 231 | 186 |
| 232 function api:add_event_hook (...) return eventmanager.add_event_hook(...); end | 187 function api:add_event_hook (...) return eventmanager.add_event_hook(...); end |
| 233 | 188 |
| 234 local function __add_handler(module, origin_type, tag, xmlns, handler) | |
| 235 local handlers = stanza_handlers[module.host]; | |
| 236 handlers[origin_type] = handlers[origin_type] or {}; | |
| 237 if not handlers[origin_type][tag] then | |
| 238 handlers[origin_type][tag] = handlers[origin_type][tag] or {}; | |
| 239 handlers[origin_type][tag][xmlns]= handler; | |
| 240 handler_info[handler] = module; | |
| 241 module:log("debug", "I now handle tag '%s' [%s] with xmlns '%s'", tag, origin_type, xmlns); | |
| 242 elseif handler_info[handlers[origin_type][tag]] then | |
| 243 log("warning", "I wanted to handle tag '%s' [%s] but mod_%s already handles that", tag, origin_type, handler_info[handlers[origin_type][tag]].module.name); | |
| 244 end | |
| 245 end | |
| 246 local function _add_handler(module, origin_type, tag, xmlns, handler) | |
| 247 local handlers = m_stanza_handlers:get(module.host, origin_type, tag, xmlns); | |
| 248 if not handlers then | |
| 249 m_stanza_handlers:add(module.host, origin_type, tag, xmlns, handler); | |
| 250 handler_info[handler] = module; | |
| 251 module:log("debug", "I now handle tag '%s' [%s] with xmlns '%s'", tag, origin_type, xmlns); | |
| 252 else | |
| 253 module:log("warning", "I wanted to handle tag '%s' [%s] but mod_%s already handles that", tag, origin_type, handler_info[handlers[1]].module.name); | |
| 254 end | |
| 255 end | |
| 256 | |
| 257 function api:add_handler(origin_type, tag, xmlns, handler) | |
| 258 if not (origin_type and tag and xmlns and handler) then return false; end | |
| 259 if type(origin_type) == "table" then | |
| 260 for _, origin_type in ipairs(origin_type) do | |
| 261 _add_handler(self, origin_type, tag, xmlns, handler); | |
| 262 end | |
| 263 return; | |
| 264 end | |
| 265 _add_handler(self, origin_type, tag, xmlns, handler); | |
| 266 end | |
| 267 | |
| 268 -------------------------------------------------------------------- | 189 -------------------------------------------------------------------- |
| 269 | 190 |
| 270 return _M; | 191 return _M; |