Mercurial > psgxs
annotate psgxs.js @ 8:efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
author | Emmanuel Gil Peyrot <linkmauve@linkmauve.fr> |
---|---|
date | Thu, 26 Aug 2010 23:50:04 +0200 |
parents | 781ac4f1e304 |
children | a6429f48e403 |
rev | line source |
---|---|
0 | 1 #!/usr/bin/env node |
2 | |
3 /* | |
4 * Copyright (C) 2010 Emmanuel Gil Peyrot <linkmauve@linkmauve.fr> | |
5 * | |
6 * This file is part of PSĜS, a PubSub server written in JavaScript. | |
7 * | |
8 * PSĜS is free software: you can redistribute it and/or modify | |
9 * it under the terms of the GNU Affero General Public License as | |
10 * published by the Free Software Foundation, either version 3 of the | |
11 * License. | |
12 * | |
13 * PSĜS is distributed in the hope that it will be useful, | |
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
16 * GNU Affero General Public License for more details. | |
17 * | |
18 * You should have received a copy of the GNU Affero General Public License | |
19 * along with PSĜS. If not, see <http://www.gnu.org/licenses/>. | |
20 */ | |
21 | |
22 var sys = require('sys'); | |
23 var xmpp = require('xmpp'); | |
24 var sha1 = require('sha1'); | |
25 require('./iso8601'); | |
26 var storage = require('./storage'); | |
27 var errors = require('./errors'); | |
28 var utils = require('./util'); | |
29 var toBareJID = utils.toBareJID; | |
30 var config = require('./configuration'); | |
31 var forms = require('./forms'); | |
32 var conn = new xmpp.Connection(); | |
33 | |
34 var service_configuration = config.service_configuration; | |
35 var componentJID = config.jid; | |
36 var componentPassword = config.password; | |
37 | |
38 conn.log = function (_, m) { sys.puts(m); }; | |
39 | |
40 function _(m, c) { | |
41 if (c) | |
42 sys.print('\033[1;'+c+'m'); | |
43 sys.print(sys.inspect(m, false, null)); | |
44 if (c) | |
45 sys.print('\033[0m'); | |
46 sys.puts(''); | |
47 }; | |
48 | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
49 if (typeof xmpp.StanzaBuilder.cnode != 'function' || typeof xmpp.StanzaBuilder.prototype.cnode != 'function') { |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
50 xmpp.StanzaBuilder.prototype.cnode = function (stanza) |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
51 { |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
52 var parent = this; |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
53 parent.tags.push(stanza); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
54 parent.children.push(stanza); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
55 return this; |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
56 }; |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
57 } |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
58 |
0 | 59 function onIq(stanza) { |
60 var type = stanza.getAttribute('type'); | |
61 var from = stanza.getAttribute('to'); | |
62 var to = stanza.getAttribute('from'); | |
63 var id = stanza.getAttribute('id'); | |
64 | |
65 var response; | |
66 if (id) | |
67 response = xmpp.iq({to: to, from: from, type: 'result', id: id}); | |
68 else | |
69 response = xmpp.iq({to: to, from: from, type: 'result'}); | |
70 | |
71 if (type == 'get') { | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
72 |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
73 // XEP-0092 |
0 | 74 if (stanza.getChild('query', 'jabber:iq:version')) { |
75 var query = xmpp.stanza('query', {xmlns: 'jabber:iq:version'}) | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
76 .s('name').t('PSĜS') |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
77 .s('version').t(config.version) |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
78 .s('os').t(config.os); |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
79 response.cnode(query); |
0 | 80 |
81 // SECTION 5.1 | |
82 } else if (stanza.getChild('query', 'http://jabber.org/protocol/disco#info')) { | |
83 var query = stanza.getChild('query', 'http://jabber.org/protocol/disco#info'); | |
84 var nodeID = query.getAttribute('node'); | |
85 | |
86 // SECTION 5.3 | |
87 if (nodeID && nodeID != '') { | |
88 if (!storage.existsNode(nodeID)) | |
89 return makeError(response, errors.node_does_not_exist.n); | |
90 | |
91 var conf = storage.getConfiguration(nodeID); | |
92 if (typeof conf == 'number') | |
93 return makeError(response, conf); | |
94 | |
95 var type = 'leaf' | |
96 if (conf['pubsub#node_type']) | |
97 type = conf['pubsub#node_type']; | |
98 | |
6 | 99 var q = xmpp.stanza('query', {xmlns: 'http://jabber.org/protocol/disco#info', node: nodeID}) |
0 | 100 q.s('identity', {category: 'pubsub', type: type}); |
101 q.s('feature', {'var': 'http://jabber.org/protocol/pubsub'}); | |
102 | |
103 // SECTION 5.4 | |
104 if (config.enabled('meta-data')) { | |
4
4c93e76fa371
Ensure that the creator of a node is the default owner; don’t crash
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
3
diff
changeset
|
105 var x = forms.build('result', 'node_metadata', storage.getMetadata(nodeID), true); |
0 | 106 if (x) |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
107 q.cnode(x); |
0 | 108 } |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
109 response.cnode(q); |
0 | 110 |
111 // SECTION 5.1 | |
112 } else { | |
113 var q = xmpp.stanza('query', {xmlns: 'http://jabber.org/protocol/disco#info'}) | |
114 .s('identity', {category: 'pubsub', type: 'service', name: 'PubSub JavaScript Server'}) | |
115 .s('feature', {'var': 'http://jabber.org/protocol/disco#info'}) | |
116 .s('feature', {'var': 'http://jabber.org/protocol/disco#items'}) | |
117 .s('feature', {'var': 'http://jabber.org/protocol/pubsub'}) | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
118 .s('feature', {'var': 'jabber:iq:version'}) |
0 | 119 // .s('feature', {'var': 'http://jabber.org/protocol/commands'}) |
120 for (var i in config.activated) | |
121 if (typeof i == 'string') | |
122 q.s('feature', {'var': 'http://jabber.org/protocol/pubsub#' + config.activated[i]}); | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
123 response.cnode(q); |
0 | 124 } |
125 | |
126 // SECTION 5.2 | |
127 } else if (stanza.getChild('query', 'http://jabber.org/protocol/disco#items')) { | |
128 var query = stanza.getChild('query', 'http://jabber.org/protocol/disco#items'); | |
129 var q; | |
130 var children; | |
131 var nodeID = query.getAttribute('node'); | |
132 if (nodeID && nodeID != '') { | |
133 if (!storage.existsNode(nodeID)) | |
134 return makeError(response, errors.node_does_not_exist.n); | |
135 | |
136 q = xmpp.stanza('query', {xmlns: 'http://jabber.org/protocol/disco#items', node: nodeID}); | |
137 | |
138 children = storage.getChildren(nodeID); | |
139 if (typeof children == 'number') | |
140 return makeError(response, children); | |
141 } else { | |
142 q = xmpp.stanza('query', {xmlns: 'http://jabber.org/protocol/disco#items'}); | |
143 | |
144 children = storage.getChildren(); | |
145 if (typeof children == 'number') | |
146 return makeError(response, children); | |
147 } | |
148 | |
149 for (var i in children) { | |
150 var attr = {jid: componentJID}; | |
151 if (children[i] == 'node') { | |
152 if (config.enabled('meta-data')) { | |
153 var metadata = storage.getMetadata(i); | |
154 if (metadata['pubsub#title']) | |
155 attr.name = metadata['pubsub#title']; | |
156 } | |
157 attr.node = i; | |
158 | |
159 // SECTION 5.5 | |
160 } else | |
161 attr.name = i; | |
162 | |
163 q.s('item', attr); | |
164 } | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
165 response.cnode(q); |
0 | 166 } else if (stanza.getChild('pubsub', 'http://jabber.org/protocol/pubsub')) { |
167 var pubsub = stanza.getChild('pubsub', 'http://jabber.org/protocol/pubsub'); | |
168 | |
169 // SECTION 5.6 | |
170 if (pubsub.getChild('subscriptions')) { | |
171 if (!config.enabled('retrieve-subscriptions')) | |
172 return makeError(response, errors.subscriptions_retrieval_not_supported.n); | |
173 | |
174 var subscriptions = pubsub.getChild('subscriptions'); | |
175 var subs; | |
176 | |
177 var nodeID = subscriptions.getAttribute('node'); | |
178 if (nodeID && nodeID != '') { | |
179 if (!storage.existsNode(nodeID)) | |
180 return makeError(response, errors.node_does_not_exist.n); | |
181 subs = storage.getSubscription(toBareJID(to), node); | |
182 } else | |
183 subs = storage.getSubscription(toBareJID(to)); | |
184 | |
185 var s = xmpp.stanza('subscriptions'); | |
186 for (i in subs) | |
187 s.s('subscription', {node: i, jid: to, subscription: subs[i].type, subid: subs[i].subid}); | |
188 | |
189 var p = xmpp.stanza('pubsub', {xmlns: 'http://jabber.org/protocol/pubsub'}); | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
190 p.cnode(s); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
191 response.cnode(p); |
0 | 192 |
193 // SECTION 5.7 | |
194 } else if (pubsub.getChild('affiliations')) { | |
195 if (!config.enabled('retrieve-affiliations')) | |
196 return makeError(response, errors.affiliations_retrieval_not_supported.n); | |
197 | |
198 var affiliations = pubsub.getChild('affiliations'); | |
199 var nodeID = affiliations.getAttribute('node'); | |
200 var affils; | |
201 if (nodeID && nodeID != '') { | |
202 if (!storage.existsNode(nodeID)) | |
203 return makeError(response, errors.node_does_not_exist.n); | |
6 | 204 affils = {}; |
205 affils[nodeID] = storage.getAffiliation(toBareJID(to), nodeID); | |
0 | 206 } else |
207 affils = storage.getAffiliationsFromJID(toBareJID(to)); | |
6 | 208 |
0 | 209 var s = xmpp.stanza('affiliations'); |
210 for (i in affils) | |
211 s.s('affiliation', {node: i, affiliation: affils[i]}); | |
6 | 212 |
0 | 213 var p = xmpp.stanza('pubsub', {xmlns: 'http://jabber.org/protocol/pubsub'}); |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
214 p.cnode(s); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
215 response.cnode(p); |
0 | 216 |
217 // SECTION 6.3.2 | |
218 } else if (pubsub.getChild('options')) { | |
219 if (!config.enabled('subscription-options')) | |
220 return makeError(response, errors.sub.configure.subscription_options_not_supported.n); | |
221 | |
222 var options = pubsub.getChild('options'); | |
223 | |
224 var nodeID = options.getAttribute('node'); | |
225 if (!nodeID || nodeID == '') | |
226 return makeError(response, errors.nodeid_required.n); | |
227 if (!storage.existsNode(nodeID)) | |
228 return makeError(response, errors.node_does_not_exist.n); | |
229 | |
230 var jid = options.getAttribute('jid'); | |
231 if (!jid) | |
232 return makeError(response, errors.sub.configure.subscriber_jid_required.n); | |
233 if (toBareJID(jid) != toBareJID(to)) | |
234 return makeError(response, errors.sub.configure.insufficient_privileges.n); | |
235 | |
236 var subs = storage.getSubscription(jid, nodeID); | |
237 if (subs == {}) | |
238 return makeError(response, errors.sub.configure.no_such_subscriber.n); | |
239 | |
240 var s = xmpp.stanza('options', {node: nodeID, jid: jid}); | |
241 var p = xmpp.stanza('pubsub', {xmlns: 'http://jabber.org/protocol/pubsub'}); | |
242 var form = forms.build('form', 'subscribe_options', subs.options, true); | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
243 s.cnode(form); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
244 p.cnode(s); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
245 response.cnode(p); |
0 | 246 |
247 // SECTION 6.4 | |
248 } else if (pubsub.getChild('default')) { | |
249 if (!config.enabled('retrieve-default-sub')) | |
250 return makeError(response, errors.sub.default_options.default_subscription_configuration_retrieval_not_supported.n); | |
251 | |
252 var def = pubsub.getChild('default'); | |
253 | |
254 var nodeID = def.getAttribute('node'); | |
255 if (nodeID && !storage.existsNode(nodeID)) | |
256 return makeError(response, errors.node_does_not_exist.n); | |
257 | |
258 var p = xmpp.stanza('pubsub', {xmlns: 'http://jabber.org/protocol/pubsub'}); | |
259 var s; | |
260 if (nodeID) | |
261 s = xmpp.stanza('default', {node: nodeID}); | |
262 else | |
263 s = xmpp.stanza('default'); | |
264 | |
265 var form = forms.build('form', 'subscribe_options', 'default', false); | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
266 s.cnode(form); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
267 p.cnode(s); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
268 response.cnode(p); |
0 | 269 |
270 // SECTION 6.5 | |
271 } else if (pubsub.getChild('items')) { | |
272 if (!config.enabled('retrieve-items')) | |
273 return makeError(response, errors.sub.default_options.node_configuration_not_supported.n); | |
274 | |
275 var items = pubsub.getChild('items'); | |
276 | |
277 var nodeID = items.getAttribute('node'); | |
278 if (!nodeID || nodeID == '') | |
279 return makeError(response, errors.nodeid_required.n); | |
280 if (!storage.existsNode(nodeID)) | |
281 return makeError(response, errors.node_does_not_exist.n); | |
282 | |
6 | 283 var configuration = storage.getConfiguration(nodeID); |
284 if (configuration['pubsub#access_model'] == 'whitelist') { | |
285 var affil = storage.getAffiliation(toBareJID(to), nodeID); | |
286 if (affil != 'super-owner' && affil != 'owner' && affil != 'publisher' && affil != 'member') | |
287 return makeError(response, errors.pub.publish.insufficient_privileges.n); | |
288 } | |
0 | 289 |
290 var item = []; | |
291 for (var i=0; i<items.children.length; i++) { | |
292 var j = items.children[i]; | |
293 if (j.name == 'item' && j.attr['id'] && j.attr['id'] != '') | |
294 item.push(j.attr['id']); | |
295 } | |
296 | |
297 var max_items = items.getAttribute('max_items'); | |
298 if (max_items) | |
299 max_items = Number (max_items); | |
300 | |
301 if (item.length) { | |
302 var s = xmpp.stanza('items', {node: nodeID}); | |
303 | |
304 for (var i=0; i<item.length; i++) { | |
305 var j = storage.getItem(nodeID, item[i]); | |
306 if (typeof j == 'number') | |
307 return makeError(response, j); | |
308 | |
309 var k = xmpp.stanza('item', {id: item[i]}) | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
310 k.cnode(j); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
311 s.cnode(k); |
0 | 312 } |
313 } else { | |
314 var s = xmpp.stanza('items', {node: nodeID}); | |
315 | |
316 var j; | |
317 if (max_items) | |
318 j = storage.getLastItem(nodeID, max_items); | |
319 else | |
320 j = storage.getItems(nodeID); | |
321 if (typeof j == 'number') | |
322 return makeError(response, j); | |
323 | |
324 var k = 0; | |
325 for (var i in j) { | |
326 var contentItem = xmpp.stanza('item', {id: i}).t(j[i].content); | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
327 s.cnode(contentItem); |
0 | 328 } |
329 } | |
330 var p = xmpp.stanza('pubsub', {xmlns: 'http://jabber.org/protocol/pubsub'}); | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
331 p.cnode(s); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
332 response.cnode(p); |
0 | 333 } else |
334 return makeError(response, errors.feature_not_implemented.n); | |
335 } else if (stanza.getChild('pubsub', 'http://jabber.org/protocol/pubsub#owner')) { | |
336 var pubsub = stanza.getChild('pubsub', 'http://jabber.org/protocol/pubsub#owner'); | |
337 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
338 // SECTION 8.2 |
0 | 339 if (pubsub.getChild('configure')) { |
340 if (!config.enabled('config-node')) | |
341 return makeError(response, errors.owner.configure.node_configuration_not_supported.n); | |
342 | |
343 var nodeID = pubsub.getChild('configure').getAttribute('node'); | |
344 if (!nodeID || nodeID == '') | |
345 return makeError(response, errors.nodeid_required.n); | |
346 if (!storage.existsNode(nodeID)) | |
347 return makeError(response, errors.node_does_not_exist.n); | |
348 | |
349 var affil = storage.getAffiliation(toBareJID(to), nodeID); | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
350 if (affil != 'super-owner' && affil != 'owner' && affil != 'publish-only') |
0 | 351 return makeError(response, errors.pub.publish.insufficient_privileges.n); |
352 | |
353 var p = xmpp.stanza('pubsub', {xmlns: 'http://jabber.org/protocol/pubsub#owner'}); | |
354 var s = xmpp.stanza('configure', {node: nodeID}); | |
355 var form = forms.build('form', 'node_config', 'default', true); | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
356 s.cnode(form); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
357 p.cnode(s); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
358 response.cnode(p); |
0 | 359 |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
360 // SECTION 8.3 |
0 | 361 } else if (pubsub.getChild('default')) { |
362 if (!config.enabled('config-node')) | |
363 return makeError(response, errors.owner.default_options.node_configuration_not_supported.n); | |
364 | |
365 var p = xmpp.stanza('pubsub', {xmlns: 'http://jabber.org/protocol/pubsub#owner'}); | |
366 var s = xmpp.stanza('default'); | |
367 var form = forms.build('node_config', service_configuration.node_config, null, true); | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
368 s.cnode(form); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
369 p.cnode(s); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
370 response.cnode(p); |
0 | 371 |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
372 // SECTION 8.8 |
0 | 373 } else if (pubsub.getChild('subscriptions')) { |
374 if (!config.enabled('manage-subscriptions')) | |
375 return makeError(response, errors.owner.manage_subscriptions.not_supported.n); | |
376 | |
377 var subscriptions = pubsub.getChild('subscriptions'); | |
378 | |
379 var nodeID = subscriptions.getAttribute('node'); | |
380 if (!nodeID || nodeID == '') | |
381 return makeError(response, errors.nodeid_required.n); | |
382 if (!storage.existsNode(nodeID)) | |
383 return makeError(response, errors.node_does_not_exist.n); | |
384 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
385 var affil = storage.getAffiliation(toBareJID(to), nodeID); |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
386 if (affil != 'super-owner' && affil != 'owner') |
0 | 387 return makeError(response, errors.forbidden.n); |
388 | |
389 var p = xmpp.stanza('pubsub', {xmlns: 'http://jabber.org/protocol/pubsub#owner'}); | |
390 var s = xmpp.stanza('subscriptions', {node: nodeID}); | |
391 | |
392 var subs = storage.getSubscriptionsFromNodeID(nodeID) | |
393 for (var jid in subs) | |
394 s.s('subscription', {jid: jid, subscription: subs[jid].type, subid: subs[jid].subid}) | |
395 | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
396 p.cnode(s); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
397 response.cnode(p); |
0 | 398 |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
399 // SECTION 8.9 |
0 | 400 } else if (pubsub.getChild('affiliations')) { |
401 if (!config.enabled('modify-affiliations')) | |
402 return makeError(response, errors.owner.manage_affiliations.not_supported.n); | |
403 | |
404 var affiliations = pubsub.getChild('affiliations'); | |
405 | |
406 var nodeID = affiliations.getAttribute('node'); | |
407 if (!nodeID || nodeID == '') | |
408 return makeError(response, errors.nodeid_required.n); | |
409 if (!storage.existsNode(nodeID)) | |
410 return makeError(response, errors.node_does_not_exist.n); | |
411 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
412 var affils = storage.getAffiliationsFromNodeID(nodeID); |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
413 var affil = affils[toBareJID(to)]; |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
414 if (affil != 'super-owner' && affil != 'owner') |
0 | 415 return makeError(response, errors.owner.manage_affiliations.retrieve_list.entity_is_not_an_owner.n); |
416 | |
417 var p = xmpp.stanza('pubsub', {xmlns: 'http://jabber.org/protocol/pubsub#owner'}); | |
418 var s = xmpp.stanza('affiliations', {node: nodeID}); | |
419 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
420 for (var jid in affils) |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
421 s.s('affiliation', {jid: jid, affiliation: affils[jid]}) |
0 | 422 |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
423 p.cnode(s); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
424 response.cnode(p); |
0 | 425 } else |
426 return makeError(response, errors.feature_not_implemented.n); | |
427 } else | |
428 return makeError(response, errors.feature_not_implemented.n); | |
429 } else if (type == 'set') { | |
430 if (stanza.getChild('pubsub', 'http://jabber.org/protocol/pubsub')) { | |
431 var pubsub = stanza.getChild('pubsub', 'http://jabber.org/protocol/pubsub'); | |
432 | |
433 // SECTION 6.1 | |
434 if (pubsub.getChild('subscribe')) { | |
435 if (!config.enabled('subscribe')) | |
436 return makeError(response, errors.sub.subscribe.not_supported.n); | |
437 | |
438 var subscribe = pubsub.getChild('subscribe'); | |
439 | |
440 var nodeID = subscribe.getAttribute('node'); | |
441 if (!nodeID || nodeID == '') | |
442 return makeError(response, errors.nodeid_required.n); | |
443 if (!storage.existsNode(nodeID)) | |
444 return makeError(response, errors.node_does_not_exist.n); | |
445 | |
446 var configuration = storage.getConfiguration(nodeID); | |
447 if (!configuration['pubsub#subscribe']) | |
448 return makeError(response, errors.sub.subscribe.not_supported.n); | |
449 | |
450 var affil = storage.getAffiliation(toBareJID(to), nodeID); | |
451 if (affil == 'publish-only' || affil == 'outcast') | |
452 return makeError(response, errors.pub.publish.insufficient_privileges.n); | |
453 | |
454 var jid = subscribe.getAttribute('jid'); | |
455 if (!jid || toBareJID(jid) != toBareJID(to)) | |
456 return makeError(response, errors.sub.subscribe.jids_do_not_match.n); | |
457 | |
458 // SECTION 6.3.7 | |
459 var options = pubsub.getChild('options'); | |
460 if (options && config.enabled('subscription-options')) { | |
461 if (options.getAttribute('node') || options.getAttribute('jid')) | |
462 return makeError(response, errors.bad_request.n); | |
463 | |
464 var x = options.getChild('x', 'jabber:x:data'); | |
465 if (!x || x.getAttribute('type') != 'submit') | |
466 return makeError(response, errors.bad_request.n); | |
467 | |
468 var form = forms.parse(x, true); | |
469 if (typeof form == 'number') | |
470 return makeError(response, form); | |
471 | |
472 var conf = form; | |
473 } | |
474 | |
475 var subID; | |
476 if (configuration['pubsub#access_model'] == 'open') { | |
477 subID = storage.subscribe(nodeID, jid, 'subscribe', conf); | |
478 if (typeof subID == 'number') | |
479 return makeError(response, subID); | |
480 } else if (configuration['pubsub#access_model'] == 'authorize') { | |
481 subID = storage.subscribe(nodeID, jid, 'pending', conf); | |
482 if (typeof subID == 'number') | |
483 return makeError(response, subID); | |
484 } else if (configuration['pubsub#access_model'] == 'whitelist') { | |
485 var affil = storage.getAffiliation(jid, nodeID); | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
486 if (affil != 'super-owner' && affil != 'owner' && affil != 'publisher' && affil != 'member') |
0 | 487 return makeError(response, errors.sub.subscribe.not_on_whitelist.n); |
488 | |
489 subID = storage.subscribe(nodeID, jid, conf); | |
490 if (typeof subID == 'number') | |
491 return makeError(response, subID); | |
492 } | |
493 | |
494 response.c('pubsub', {xmlns: 'http://jabber.org/protocol/pubsub'}) | |
495 .c('subscription', {node: nodeID, jid: jid, subid: subID.subid, subscription: subID.type}); | |
496 | |
497 if (conf) | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
498 response.cnode(options); |
0 | 499 |
500 if (config.enabled('get-pending')) { | |
501 var affiliates = storage.getAffiliationsFromNodeID(nodeID); | |
502 var form = forms.build('form', 'subscribe_authorization', {allow: false, node: nodeID, subscriber_jid: jid}, true); //168 | |
503 for (var i in affiliates) { | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
504 if (affiliates[i] == 'super-owner' || affiliates[i] == 'owner') { |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
505 var message = xmpp.message({to: i}).cnode(form); |
0 | 506 conn.send(message); |
507 } | |
508 } | |
509 } | |
510 | |
511 if (config.enabled('last-published')) { | |
512 var last = storage.getLastItem(nodeID); | |
513 if (typeof last != 'number') { | |
514 var item = storage.getItem(nodeID, last); | |
515 if (typeof item != 'number') { | |
516 var attr = {}; | |
517 attr[last] = {content: item}; | |
518 sendNotifs(jid, 'items', nodeID, attr); | |
519 } | |
520 } | |
521 } | |
522 | |
523 // SECTION 6.2 | |
524 } else if (pubsub.getChild('unsubscribe')) { | |
525 if (!config.enabled('subscribe')) | |
526 return makeError(response, errors.sub.subscribe.not_supported.n); | |
527 | |
528 var unsubscribe = pubsub.getChild('unsubscribe'); | |
529 var nodeID = unsubscribe.getAttribute('node'); | |
530 if (!nodeID || nodeID == '') | |
531 return makeError(response, errors.nodeid_required.n); | |
532 if (!storage.existsNode(nodeID)) | |
533 return makeError(response, errors.node_does_not_exist.n); | |
534 | |
535 var jid = unsubscribe.getAttribute('jid'); | |
536 if (!jid || toBareJID(jid) != toBareJID(to)) | |
537 return makeError(response, errors.sub.unsubscribe.insufficient_privileges.n); | |
538 | |
539 var subID = storage.subscribe(nodeID, jid, 'none'); | |
540 if (typeof subID == 'number') | |
541 return makeError(response, subID); | |
542 | |
543 // SECTIONS 6.3.5 | |
544 } else if (pubsub.getChild('options')) { | |
545 if (!config.enabled('subscription-options')) | |
546 return makeError(response, errors.sub.subscribe.not_supported.n); | |
547 | |
548 var options = pubsub.getChild('options'); | |
549 | |
550 var nodeID = unsubscribe.getAttribute('node'); | |
551 if (!nodeID || nodeID == '') | |
552 return makeError(response, errors.nodeid_required.n); | |
553 if (!storage.existsNode(nodeID)) | |
554 return makeError(response, errors.node_does_not_exist.n); | |
555 | |
556 var jid = unsubscribe.getAttribute('jid'); | |
557 if (!jid || toBareJID(jid) != toBareJID(to)) | |
558 return makeError(response, errors.sub.unsubscribe.insufficient_privileges.n); | |
559 | |
560 var x = options.getChild('x', 'jabber:x:data'); | |
561 if (!x || x.getAttribute(type) != 'submit') | |
562 return makeError(response, errors.bad_request); | |
563 | |
564 var form = forms.parse(x, true); | |
565 if (typeof form == 'number') | |
566 return makeError(response, form); | |
567 | |
568 var set = storage.configureSubscription(nodeID, jid, form); | |
569 if (typeof form == 'number') | |
570 return makeError(response, form); | |
571 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
572 // SECTION 7.1 |
0 | 573 } else if (pubsub.getChild('publish')) { |
574 if (!config.enabled('publish')) | |
575 return makeError(response, errors.pub.publish.item_publication_not_supported.n); | |
576 | |
577 var publish = pubsub.getChild('publish'); | |
578 var nodeID = publish.getAttribute('node'); | |
579 if (!nodeID || nodeID == '') | |
580 return makeError(response, errors.nodeid_required.n); | |
581 | |
6 | 582 var autocreate = false; |
583 if (!storage.existsNode(nodeID)) { | |
584 if (config.enabled('auto-create')) | |
585 autocreate = true; | |
586 else | |
587 return makeError(response, errors.node_does_not_exist.n); | |
588 } | |
589 | |
0 | 590 var affil = storage.getAffiliation(toBareJID(to), nodeID); |
6 | 591 if (typeof affil == 'number' && affil != errors.node_does_not_exist.n) |
0 | 592 return makeError(response, affil); |
6 | 593 if (!autocreate && affil != 'super-owner' && affil != 'owner' && affil != 'publisher' && affil != 'publish-only') |
0 | 594 return makeError(response, errors.forbidden.n); |
595 | |
596 var item = publish.getChild('item'); | |
597 var itemID = item.getAttribute('id'); | |
598 if (!config.enabled('item-ids') && itemID) | |
599 return makeError(response, errors.itemid_required.n); | |
600 itemID = itemID? itemID: utils.makeRandomId(); | |
601 | |
602 if (item.tags.length != 1) | |
603 return makeError(response, errors.pub.publish.bad_payload.n); | |
604 | |
605 var conf = storage.getConfiguration(nodeID); | |
606 var publishOptions = pubsub.getChild('publish-options'); | |
607 if (publishOptions && config.enabled('publish-options')) { | |
608 var x = publishOptions.getChild('x', 'jabber:x:data'); | |
609 if (!x || x.getAttribute('type') != 'submit') | |
610 return makeError(response, errors.bad_request.n); | |
611 | |
612 var form = forms.parse(x, true); | |
613 if (form.access_model != conf['pubsub#access_model'] && !autocreate) | |
614 return makeError(response, errors.pub.configuration.precondition.n); | |
615 } | |
616 | |
617 if (!config.enabled('persistent-items')) { | |
618 var notifs = storage.purgeNode(nodeID); | |
619 if (typeof notifs == 'number') | |
620 return makeError(response, r); | |
621 } | |
622 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
623 if (autocreate) { |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
624 if (!form) |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
625 form = {}; |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
626 form['pubsub#creator'] = toBareJID(to); |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
627 |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
628 var r = storage.createNode(nodeID, form); |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
629 if (typeof r == 'number') |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
630 return makeError(response, r); |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
631 } |
0 | 632 |
633 var content = item.getChild(); | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
634 |
0 | 635 subscribers = storage.setItem(nodeID, itemID, content); |
636 if (typeof subscribers == 'number') | |
637 return makeError(response, subscribers); | |
638 | |
639 var attrs = {}; | |
640 if (content) | |
641 attrs[itemID] = {content: content}; | |
642 else | |
643 attrs[itemID] = {}; | |
644 sendNotifs(subscribers, 'items', nodeID, attrs); | |
645 | |
646 response.c('pubsub', {xmlns: 'http://jabber.org/protocol/pubsub'}) | |
647 .c('publish', {node: nodeID}) | |
648 .c('item', {id: itemID}); | |
649 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
650 // SECTION 7.2 |
0 | 651 } else if (pubsub.getChild('retract')) { |
652 if (!config.enabled('retract-items')) | |
653 return makeError(response, errors.pub.retract.item_deletion_not_supported.n); | |
654 | |
655 var retract = pubsub.getChild('retract'); | |
656 | |
657 var nodeID = retract.getAttribute('node'); | |
658 if (!nodeID || nodeID == '') | |
659 return makeError(response, errors.nodeid_required.n); | |
660 if (!storage.existsNode(nodeID)) | |
661 return makeError(response, errors.node_does_not_exist.n); | |
662 | |
663 var item = retract.getChild('item'); | |
664 if (!item) | |
665 return makeError(response, errors.pub.retract.item_or_itemid_required.n); | |
666 | |
667 var itemID = item.getAttribute('id') | |
668 if (!itemID || itemID == '') | |
669 return makeError(response, errors.pub.retract.item_or_itemid_required.n); | |
670 | |
6 | 671 var affil = storage.getAffiliation(toBareJID(to), nodeID); |
672 if (affil != 'super-owner' && affil != 'owner' && affil != 'publish-only') | |
673 return makeError(response, errors.forbidden.n); | |
674 | |
0 | 675 var subscribers = storage.deleteItem(nodeID, itemID); |
676 if (typeof subscribers == 'number') | |
677 return makeError(response, subscribers); | |
678 | |
679 var attrs = {}; | |
680 attrs[itemID] = {}; | |
681 sendNotifs(subscribers, 'items', nodeID, attrs, 'retract') | |
682 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
683 // SECTION 8.1 |
0 | 684 } else if (pubsub.getChild('create')) { |
685 if (!config.enabled('create-nodes')) | |
686 return makeError(response, errors.owner.create.node_creation_not_supported.n); | |
687 | |
688 var instant = false; | |
689 | |
690 var nodeID = pubsub.getChild('create').getAttribute('node'); | |
691 if (!nodeID || nodeID == '') { | |
4
4c93e76fa371
Ensure that the creator of a node is the default owner; don’t crash
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
3
diff
changeset
|
692 if (!config.enabled('instant-nodes')) |
0 | 693 return makeError(response, errors.owner.create.instant_nodes_not_supported.n); |
694 nodeID = utils.makeRandomId(); | |
695 instant = true; | |
696 } | |
697 if (storage.existsNode(nodeID)) | |
698 return makeError(response, errors.nodeid_already_exists.n); | |
699 | |
2
d3ae2f8b685d
Make create node working.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
1
diff
changeset
|
700 var bare = toBareJID(to); |
d3ae2f8b685d
Make create node working.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
1
diff
changeset
|
701 var right = false; |
7
781ac4f1e304
Allow others JIDs than super-owners to create nodes.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
6
diff
changeset
|
702 |
781ac4f1e304
Allow others JIDs than super-owners to create nodes.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
6
diff
changeset
|
703 // Check for super-owner |
2
d3ae2f8b685d
Make create node working.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
1
diff
changeset
|
704 for (var i in config.owner) |
d3ae2f8b685d
Make create node working.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
1
diff
changeset
|
705 if (config.owner[i] == bare) |
d3ae2f8b685d
Make create node working.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
1
diff
changeset
|
706 right = true; |
d3ae2f8b685d
Make create node working.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
1
diff
changeset
|
707 |
7
781ac4f1e304
Allow others JIDs than super-owners to create nodes.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
6
diff
changeset
|
708 // Check for authorized user |
781ac4f1e304
Allow others JIDs than super-owners to create nodes.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
6
diff
changeset
|
709 for (var i in config.allowCreateNode) |
781ac4f1e304
Allow others JIDs than super-owners to create nodes.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
6
diff
changeset
|
710 if (config.allowCreateNode[i].exec(bare)) |
781ac4f1e304
Allow others JIDs than super-owners to create nodes.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
6
diff
changeset
|
711 right = true; |
781ac4f1e304
Allow others JIDs than super-owners to create nodes.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
6
diff
changeset
|
712 |
2
d3ae2f8b685d
Make create node working.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
1
diff
changeset
|
713 if (!right) |
0 | 714 return makeError(response, errors.forbidden.n); |
715 | |
716 var configure = pubsub.getChild('configure'); | |
717 if (configure && config.enabled('create-and-configure')) { | |
718 if (!config.enabled('config-node')) | |
719 return makeError(response, errors.owner.configure.node_configuration_not_supported.n); | |
720 | |
721 if (configure.getAttribute('node')) | |
722 return makeError(response, errors.bad_request.n); | |
723 | |
724 var x = configure.getChild('x', 'jabber:x:data'); | |
725 if (!x || x.getAttribute('type') != 'submit') | |
726 return makeError(response, errors.bad_request.n); | |
727 | |
728 var form = forms.parse(x, true); | |
729 if (typeof form == 'number') | |
730 return makeError(response, form); | |
731 | |
732 var conf = form; | |
733 } | |
734 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
735 if (!conf) |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
736 conf = {}; |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
737 conf['pubsub#creator'] = toBareJID(to); |
0 | 738 var r = storage.createNode(nodeID, conf); |
739 if (typeof r == 'number') | |
740 return makeError(response, r); | |
741 | |
742 if (instant) | |
743 response.c('pubsub', {xmlns: 'http://jabber.org/protocol/pubsub'}) | |
744 .c('create', {node: nodeID}); | |
745 } else | |
746 return makeError(response, errors.feature_not_implemented.n); | |
747 } else if (stanza.getChild('pubsub', 'http://jabber.org/protocol/pubsub#owner')) { | |
748 var pubsub = stanza.getChild('pubsub', 'http://jabber.org/protocol/pubsub#owner'); | |
749 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
750 // SECTION 8.2.4 |
0 | 751 if (pubsub.getChild('configure')) { |
752 if (!config.enabled('config-node')) | |
753 return makeError(response, errors.owner.configure.node_configuration_not_supported.n); | |
754 | |
755 var nodeID = configure.getAttribute('node'); | |
756 if (!nodeID) | |
757 return makeError(response, errors.nodeid_required.n); | |
758 if (!storage.existsNode(nodeID)) | |
759 return makeError(response, errors.node_does_not_exist.n); | |
760 | |
761 var affil = storage.getAffiliation(toBareJID(to), nodeID); | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
762 if (affil != 'super-owner' && affil != 'owner' && affil != 'publish-only') |
0 | 763 return makeError(response, errors.forbidden.n); |
764 | |
765 var x = configure.getChild('x', 'jabber:x:data'); | |
766 if (!x || x.getAttribute(type) != 'submit') | |
767 return makeError(response, errors.bad_request.n); | |
768 | |
769 var form = forms.parse(x, true); | |
770 if (typeof form == 'number') | |
771 return makeError(response, form); | |
772 | |
773 var conf = form; | |
774 | |
775 var set = storage.configure(nodeID, conf); | |
776 if (typeof set == 'number') | |
777 return makeError(response, set); | |
778 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
779 // SECTION 8.4 |
0 | 780 } else if (pubsub.getChild('delete')) { |
781 if (!config.enabled('delete-nodes')) | |
782 return makeError(response, errors.feature_not_implemented.n); //XXX | |
783 | |
784 var del = pubsub.getChild('delete'); | |
785 | |
786 var nodeID = del.getAttribute('node'); | |
787 if (!nodeID) | |
788 return makeError(response, errors.nodeid_required.n); | |
789 if (!storage.existsNode(nodeID)) | |
790 return makeError(response, errors.node_does_not_exist.n); | |
791 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
792 var affil = storage.getAffiliation(toBareJID(to), nodeID); |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
793 if (affil != 'super-owner' && affil != 'owner') |
0 | 794 return makeError(response, errors.forbidden.n); |
795 | |
796 var notifs = storage.deleteNode(nodeID); | |
797 if (typeof notifs == 'number') | |
798 return makeError(response, r); | |
799 | |
800 sendNotifs(notifs, 'delete', nodeID); | |
801 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
802 // SECTION 8.5 |
0 | 803 } else if (pubsub.getChild('purge')) { |
804 if (!config.enabled('purge-nodes')) | |
805 return makeError(response, errors.owner.purge.node_purging_not_supported.n); //XXX | |
806 | |
807 var purge = pubsub.getChild('purge'); | |
808 | |
809 var nodeID = purge.getAttribute('node'); | |
810 if (!nodeID) | |
811 return makeError(response, errors.nodeid_required.n); | |
812 if (!storage.existsNode(nodeID)) | |
813 return makeError(response, errors.node_does_not_exist.n); | |
814 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
815 var affil = storage.getAffiliation(toBareJID(to), nodeID); |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
816 if (affil != 'super-owner' && affil != 'owner') |
0 | 817 return makeError(response, errors.forbidden.n); |
818 | |
819 if (!config.enabled('persistent-items')) //FIXME: autre condition, supporté par le node | |
820 return makeError(response, errors.owner.purge.node_does_not_persist_items.n); | |
821 | |
822 var notifs = storage.purgeNode(nodeID); | |
823 if (typeof notifs == 'number') | |
824 return makeError(response, r); | |
825 | |
826 sendNotifs(notifs, 'purge', nodeID); | |
827 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
828 // SECTION 8.8.2 |
0 | 829 } else if (pubsub.getChild('subscriptions')) { |
830 if (!config.enabled('manage-subscriptions')) | |
831 return makeError(response, errors.owner.manage_subscriptions.not_supported.n); //XXX | |
832 | |
833 var subscriptions = pubsub.getChild('subscriptions'); | |
834 | |
835 var nodeID = subscriptions.getAttribute('node'); | |
836 if (!nodeID) | |
837 return makeError(response, errors.nodeid_required.n); | |
838 if (!storage.existsNode(nodeID)) | |
839 return makeError(response, errors.node_does_not_exist.n); | |
840 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
841 var affil = storage.getAffiliation(toBareJID(to), nodeID); |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
842 if (affil != 'super-owner' && affil != 'owner') |
0 | 843 return makeError(response, errors.forbidden.n); |
844 | |
845 var e = false; | |
846 for (i in subscriptions.tags) { | |
847 var jid = subscriptions.tags[i].getAttribute('jid'); | |
848 var subscription = subscriptions.tags[i].getAttribute('subscription'); | |
849 | |
850 var set = storage.subscribe(nodeID, jid, subscription); | |
851 if (typeof set == 'number') | |
852 e = true; | |
853 else { | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
854 // SECTION 8.8.4 |
0 | 855 sendNotifs(jid, 'subscription', nodeID, {jid: jid, subscription: subscription}); |
856 subscriptions.tags.splice(i, 1); | |
857 } | |
858 } | |
859 | |
860 if (e) | |
861 return makeError(response, errors.owner.manage_subscriptions.modify.multiple_simultaneous_modifications.n, pubsub); | |
862 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
863 // SECTION 8.9.2 |
0 | 864 } else if (pubsub.getChild('affiliations')) { |
865 if (!config.enabled('modify-affiliations')) | |
866 return makeError(response, errors.owner.manage_affiliations.not_supported.n); //XXX | |
867 | |
868 var affiliations = pubsub.getChild('affiliations'); | |
869 | |
870 var nodeID = affiliations.getAttribute('node'); | |
871 if (!nodeID) | |
872 return makeError(response, errors.nodeid_required.n); | |
873 if (!storage.existsNode(nodeID)) | |
874 return makeError(response, errors.node_does_not_exist.n); | |
875 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
876 var affil = storage.getAffiliation(toBareJID(to), nodeID); |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
877 if (affil != 'super-owner' && affil != 'owner') |
0 | 878 return makeError(response, errors.forbidden.n); |
879 | |
880 var e = false; | |
881 for (i in affiliations.children) { | |
882 var jid = affiliations.children[i].getAttribute('jid'); | |
883 var affiliation = affiliations.children[i].getAttribute('affiliation'); | |
884 | |
885 var set = storage.setAffiliation(nodeID, jid, affiliation); | |
886 if (typeof set == 'number') | |
887 e = true; | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
888 else { |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
889 // SECTION 8.9.4 |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
890 sendNotifs(jid, 'affiliations', nodeID, {jid: jid, affiliation: affiliation}); |
0 | 891 affiliations.children.splice(i, 1); |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
892 } |
0 | 893 } |
894 | |
895 if (e) | |
896 return makeError(response, errors.owner.manage_affiliations.modify.multiple_simultaneous_modifications.n, pubsub); | |
897 } else | |
898 return makeError(response, errors.feature_not_implemented.n); | |
899 } else | |
900 return makeError(response, errors.feature_not_implemented.n); | |
901 } else | |
902 return makeError(response, errors.feature_not_implemented.n); | |
903 conn.send(response); | |
904 } | |
905 | |
906 function onMessage(stanza) { | |
907 var from = stanza.getAttribute('to'); | |
908 var to = stanza.getAttribute('from'); | |
909 var id = stanza.getAttribute('id'); | |
910 | |
911 var response; | |
912 if (id) | |
913 response = xmpp.message({to: to, from: from, id: id}); | |
914 else | |
915 response = xmpp.message({to: to, from: from}); | |
916 | |
917 var x = stanza.getChild('x', 'jabber:x:data'); | |
918 if (x) { | |
919 var form = forms.parse(x); | |
920 if (form.type == 'submit' && form.fields.FORM_TYPE.value == 'subscribe_authorization') { | |
921 if (form.fields.subid && form.fields.subid.value) | |
922 var subID = form.fields.subid.value; | |
923 if (form.fields.node && form.fields.node.value) | |
924 var nodeID = form.fields.node.value; | |
925 if (form.fields.subscriber_jid && form.fields.subscriber_jid.value) | |
926 var jid = form.fields.subscriber_jid.value; | |
927 if (form.fields.allow && form.fields.allow.value) | |
928 var allow = form.fields.allow.value; | |
929 | |
930 var type = allow? 'subscribed': 'none'; | |
931 var set = storage.subscribe(nodeID, jid, type) | |
932 //if (set.subid != subID) //TODO: support the multi-subscribe feature | |
933 sendNotifs(jid, 'subscription', nodeID, {jid: jid, subscription: type}); | |
934 } else | |
935 return makeError(response, errors.feature_not_implemented.n); | |
936 } else | |
937 return makeError(response, errors.feature_not_implemented.n); | |
938 conn.send(response) | |
939 } | |
940 | |
941 function onPresence(stanza) { | |
942 var from = stanza.getAttribute('to'); | |
943 var to = stanza.getAttribute('from'); | |
944 var id = stanza.getAttribute('id'); | |
945 | |
946 var response; | |
947 if (id) | |
948 response = xmpp.presence({to: to, from: from, id: id}); | |
949 else | |
950 response = xmpp.presence({to: to, from: from}); | |
951 | |
952 makeError(response, errors.feature_not_implemented.n); | |
953 } | |
954 | |
955 function makeError(response, errorNumber, payload) { | |
956 response.attr.type = 'error'; | |
957 if (payload) | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
958 response.cnode(payload); |
0 | 959 |
960 var e = errors.reverse[errorNumber]; | |
961 var error = xmpp.stanza('error', {type: e.type}); | |
962 | |
963 error.s(e.error, {xmlns: 'urn:ietf:params:xml:ns:xmpp-stanzas'}) | |
964 | |
965 if (e.reason) { | |
966 if (e.feature) | |
967 error.s(e.reason, {xmlns: 'http://jabber.org/protocol/pubsub#errors', feature: e.feature}); | |
968 else | |
969 error.s(e.reason, {xmlns: 'http://jabber.org/protocol/pubsub#errors'}); | |
970 } | |
971 | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
972 response.cnode(error); |
0 | 973 conn.send(response); |
974 } | |
975 | |
976 function sendNotifs(notifs, type, nodeID, a1, a2) { | |
977 var ev = xmpp.stanza('event', {xmlns: 'http://jabber.org/protocol/pubsub#event'}); | |
978 | |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
979 if (type == 'affiliations') { |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
980 ev.attr.xmlns = 'http://jabber.org/protocol/pubsub'; |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
981 |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
982 var args = {}; |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
983 for (i in a1) { |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
984 var attr = a1[i]; |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
985 if (i == 'affiliation') |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
986 args.affiliation = attr; |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
987 else if (i == 'jid') |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
988 args.jid = attr; |
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
989 } |
3
80e607c0b39e
Make affiliation notifications working.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
2
diff
changeset
|
990 var affiliations = xmpp.stanza('affiliations', {node: nodeID}) |
4
4c93e76fa371
Ensure that the creator of a node is the default owner; don’t crash
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
3
diff
changeset
|
991 .c('affiliation', args); |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
992 ev.cnode(affiliations); |
1
c2954a9e5665
Add a super-owner that has power over all nodes; add support for
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
0
diff
changeset
|
993 } else if (type == 'collection') { |
0 | 994 var collection = xmpp.stanza('collection', {node: nodeID}); |
995 if (a1 == 'associate') | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
996 collection.cnode('associate', {node: nodeID}); |
0 | 997 else |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
998 collection.cnode('disassociate', {node: nodeID}); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
999 ev.cnode(collection); |
0 | 1000 } else if (type == 'configuration') { |
1001 if (!config.enabled('config-node')) { | |
1002 _('Error #4', 41) | |
1003 return; | |
1004 } | |
1005 | |
1006 var configuration = xmpp.stanza('configuration', {node: nodeID}); | |
1007 if (a1) { | |
1008 var x = forms.build('node_config', service_configuration.node_config, storage.getConfiguration(nodeID)); | |
1009 if (x) | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
1010 configuration.cnode(x); //TODO: voir exemple 150 |
0 | 1011 } |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
1012 ev.cnode(configuration); |
0 | 1013 } else if (type == 'delete') { |
1014 var del = xmpp.stanza('delete', {node: nodeID}); | |
1015 if (a1) | |
1016 del.c('redirect', {uri: a1}); | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
1017 ev.cnode(del); |
0 | 1018 } else if (type == 'items') { |
1019 var items = xmpp.stanza(type, {node: nodeID}); | |
1020 if (a2 == 'retract') | |
1021 for (var i in a1) | |
1022 items.s('retract', {id: i}); | |
1023 else { | |
1024 for (var i in a1) { | |
1025 var item = a1[i]; | |
1026 var args = {}; | |
1027 if (i != '') | |
1028 args.id = i; | |
1029 if (item.node) | |
1030 args.node = item.node; | |
1031 if (item.publisher) | |
1032 args.publisher = item.publisher; | |
1033 var it = xmpp.stanza('item', args); | |
1034 if (item.content) | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
1035 it.cnode(item.content); |
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
1036 items.cnode(it); |
0 | 1037 } |
1038 } | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
1039 ev.cnode(items); |
0 | 1040 } else if (type == 'purge') { |
1041 ev.c('purge', {node: nodeID}); | |
1042 } else if (type == 'subscription') { | |
1043 if (!config.enabled('subscription-notifications')) | |
1044 return; | |
1045 | |
1046 var args = {node: nodeID}; | |
1047 for (i in a1) { | |
1048 var attr = a1[i]; | |
1049 if (i == 'subscription') { | |
1050 if (attr == 'none' || attr == 'pending' || attr == 'subscribed' || attr == 'unconfigured') | |
1051 args[i] = attr; | |
1052 else { | |
1053 _('Error #3', 41) | |
1054 return; | |
1055 } | |
1056 } else if (i == 'jid' || i == 'subid') | |
1057 args[i] = attr; | |
1058 else if (i == 'expiry') | |
1059 args[i] = attr.toString(); | |
1060 } | |
1061 if (!args.jid || args.jid == '') { | |
1062 _('Error #2', 41) | |
1063 return; | |
1064 } | |
1065 var sub = xmpp.stanza('subscription', args); | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
1066 ev.cnode(sub); |
0 | 1067 } else { |
1068 _('Error #1', 41) | |
1069 return; | |
1070 } | |
1071 | |
1072 var subs; | |
1073 if (typeof notifs == 'string') { | |
1074 subs = {}; | |
1075 subs[notifs] = storage.getSubscription(notifs, nodeID); | |
1076 } else | |
1077 subs = notifs; | |
1078 | |
1079 for (var i in subs) { | |
1080 var sub = subs[i]; | |
1081 | |
1082 if (sub.options) { | |
1083 if (typeof sub.options['pubsub#deliver'] != 'undefined' && !sub.options['pubsub#deliver']) | |
1084 continue; | |
1085 | |
1086 if (typeof sub.options['pubsub#digest'] != 'undefined' && sub.options['pubsub#digest']) { | |
1087 if (!sub.digest) | |
1088 sub.digest = []; | |
1089 sub.digest.push(ev) | |
1090 | |
1091 if (sub.digestTimeout) | |
1092 continue; | |
1093 | |
1094 var freq; | |
1095 if (typeof sub.options['pubsub#digest_frequency'] == 'undefined') | |
1096 freq = 0; | |
1097 else | |
1098 freq = parseInt(sub.options['pubsub#digest_frequency']); | |
1099 | |
1100 if (freq == 0) | |
1101 freq = 24*60*60*1000; | |
1102 | |
1103 setTimeout(sendDigest, freq, notifs[i], nodeID); | |
1104 sub.digestTimeout = true; | |
1105 continue; | |
1106 } | |
1107 } | |
1108 | |
1109 var message = xmpp.message({to: i, from: componentJID, id: conn.getUniqueId()}); | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
1110 message.cnode(ev); |
0 | 1111 conn.send(message); |
1112 } | |
1113 } | |
1114 | |
1115 function sendDigest(jid, nodeID) { | |
1116 var sub = storage.getSubscription(jid, nodeID); | |
1117 if (sub.digestTimeout) | |
1118 sub.digestTimeout = false; | |
1119 | |
1120 var message = xmpp.message({to: jid, from: componentJID, id: conn.getUniqueId()}); | |
1121 for (var i in sub.digest) | |
8
efe8dbd34780
Rename cx method to cnode and define it if xmpp.js didn’t.
Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
parents:
7
diff
changeset
|
1122 message.cnode(sub.digest[i]); |
0 | 1123 conn.send(message); |
1124 } | |
1125 | |
1126 conn.connect(componentJID, componentPassword, function (status, condition) { | |
1127 if (status == xmpp.Status.CONNECTED) { | |
1128 conn.addHandler(onMessage, null, 'message', null, null, null); | |
1129 conn.addHandler(onIq, null, 'iq', null, null, null); | |
1130 conn.addHandler(onPresence, null, 'presence', null, null, null); | |
1131 | |
1132 if (process.argv.length >= 3) | |
1133 storage.load(process.argv[2]); | |
1134 else | |
1135 storage.load(); | |
1136 | |
1137 var stdin = process.openStdin(); | |
1138 stdin.setEncoding('utf8'); | |
1139 stdin.addListener('data', storage.debug); | |
1140 } else | |
1141 conn.log(xmpp.LogLevel.DEBUG, 'New connection status: ' + status + (condition? (' ('+condition+')'): '')); | |
1142 }); |