summaryrefslogtreecommitdiff
path: root/frontend/gamma/js/Clipperz/Async.js
Unidiff
Diffstat (limited to 'frontend/gamma/js/Clipperz/Async.js') (more/less context) (ignore whitespace changes)
-rw-r--r--frontend/gamma/js/Clipperz/Async.js707
1 files changed, 707 insertions, 0 deletions
diff --git a/frontend/gamma/js/Clipperz/Async.js b/frontend/gamma/js/Clipperz/Async.js
new file mode 100644
index 0000000..e80c3a2
--- a/dev/null
+++ b/frontend/gamma/js/Clipperz/Async.js
@@ -0,0 +1,707 @@
1/*
2
3Copyright 2008-2011 Clipperz Srl
4
5This file is part of Clipperz's Javascript Crypto Library.
6Javascript Crypto Library provides web developers with an extensive
7and efficient set of cryptographic functions. The library aims to
8obtain maximum execution speed while preserving modularity and
9reusability.
10For further information about its features and functionalities please
11refer to http://www.clipperz.com
12
13* Javascript Crypto Library is free software: you can redistribute
14 it and/or modify it under the terms of the GNU Affero General Public
15 License as published by the Free Software Foundation, either version
16 3 of the License, or (at your option) any later version.
17
18* Javascript Crypto Library is distributed in the hope that it will
19 be useful, but WITHOUT ANY WARRANTY; without even the implied
20 warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
21 See the GNU Affero General Public License for more details.
22
23* You should have received a copy of the GNU Affero General Public
24 License along with Javascript Crypto Library. If not, see
25 <http://www.gnu.org/licenses/>.
26
27*/
28
29//Clipperz.Async = MochiKit.Async;
30
31
32if (typeof(Clipperz) == 'undefined') { Clipperz = {}; }
33if (typeof(Clipperz.Async) == 'undefined') { Clipperz.Async = {}; }
34
35Clipperz.Async.VERSION = "0.1";
36Clipperz.Async.NAME = "Clipperz.Async";
37
38Clipperz.Async.Deferred = function(aName, args) {
39 args = args || {};
40
41 Clipperz.Async.Deferred.superclass.constructor.call(this, args.canceller);
42
43 this._args = args;
44 this._name = aName || "Anonymous deferred";
45 this._count = 0;
46 this._shouldTrace = ((CLIPPERZ_DEFERRED_TRACING_ENABLED === true) || (args.trace === true));
47 this._vars = null;
48
49 return this;
50}
51
52//=============================================================================
53
54Clipperz.Base.extend(Clipperz.Async.Deferred, MochiKit.Async.Deferred, {
55
56 'name': function () {
57 return this._name;
58 },
59
60 'args': function () {
61 return this._args;
62 },
63
64 //-----------------------------------------------------------------------------
65
66 'callback': function (aValue) {
67 if (this._shouldTrace) {
68 Clipperz.log("CALLBACK " + this._name, aValue);
69 }
70
71 if (this.chained == false) {
72 var message;
73
74 message = "ERROR [" + this._name + "]";
75 this.addErrback(function(aResult) {
76 if (! (aResult instanceof MochiKit.Async.CancelledError)) {
77 Clipperz.log(message, aResult);
78 }
79 return aResult;
80 });
81
82 if (this._shouldTrace) {
83 var resultMessage;
84
85 resultMessage = "RESULT " + this._name + " <==";
86 // this.addCallback(function(aResult) {
87 Clipperz.Async.Deferred.superclass.addCallback.call(this, function(aResult) {
88 Clipperz.log(resultMessage, aResult);
89
90 return aResult;
91 });
92 }
93 }
94
95 if (CLIPPERZ_DEFERRED_CALL_LOGGING_ENABLED === true) {
96 Clipperz.log("callback " + this._name, this);
97 }
98
99 return Clipperz.Async.Deferred.superclass.callback.apply(this, arguments);
100 },
101
102 //-----------------------------------------------------------------------------
103
104 'addCallback': function () {
105 var message;
106
107 if (this._shouldTrace) {
108 this._count ++;
109 message = "[" + this._count + "] " + this._name + " ";
110 // this.addBoth(function(aResult) {Clipperz.log(message + "-->", aResult); return aResult;});
111 this.addCallbacks(
112 function(aResult) {Clipperz.log("-OK- " + message + "-->"/*, aResult*/); return aResult;},
113 function(aResult) {Clipperz.log("FAIL " + message + "-->"/*, aResult*/); return aResult;}
114 );
115 }
116
117 Clipperz.Async.Deferred.superclass.addCallback.apply(this, arguments);
118
119 if (this._shouldTrace) {
120 // this.addBoth(function(aResult) {Clipperz.log(message + "<--", aResult); return aResult;});
121 this.addCallbacks(
122 function(aResult) {Clipperz.log("-OK- " + message + "<--", aResult); return aResult;},
123 function(aResult) {Clipperz.log("FAIL " + message + "<--", aResult); return aResult;}
124 );
125 }
126 },
127
128 //=============================================================================
129
130 'addCallbackPass': function() {
131 var passFunction;
132
133 passFunction = MochiKit.Base.partial.apply(null, arguments);
134
135 this.addCallback(function() {
136 var result;
137
138 result = arguments[arguments.length -1];
139 passFunction();
140
141 return result;
142 });
143 },
144
145 //-----------------------------------------------------------------------------
146
147 'addErrbackPass': function() {
148 var passFunction;
149
150 passFunction = MochiKit.Base.partial.apply(null, arguments);
151
152 this.addErrback(function() {
153 var result;
154
155 result = arguments[arguments.length -1];
156 passFunction();
157
158 return result;
159 });
160 },
161
162 //-----------------------------------------------------------------------------
163
164 'addBothPass': function() {
165 var passFunction;
166
167 passFunction = MochiKit.Base.partial.apply(null, arguments);
168
169 this.addBoth(function() {
170 var result;
171
172 result = arguments[arguments.length -1];
173 passFunction();
174
175 return result;
176 });
177 },
178
179 //-----------------------------------------------------------------------------
180
181 'addIf': function (aThenBlock, anElseBlock) {
182 this.addCallback(MochiKit.Base.bind(function (aValue) {
183 var deferredResult;
184
185 if (!MochiKit.Base.isUndefinedOrNull(aValue) && aValue) {
186 deferredResult = Clipperz.Async.callbacks(this._name + " <then>", aThenBlock, null, aValue);
187 } else {
188 deferredResult = Clipperz.Async.callbacks(this._name + " <else>", anElseBlock, null, aValue);
189 }
190
191 return deferredResult;
192 }))
193 },
194
195 //-----------------------------------------------------------------------------
196
197 'addMethod': function () {
198 this.addCallback(MochiKit.Base.method.apply(this, arguments));
199 },
200
201 //-----------------------------------------------------------------------------
202
203 'addMethodcaller': function () {
204 this.addCallback(MochiKit.Base.methodcaller.apply(this, arguments));
205 },
206
207 //=============================================================================
208
209 'addLog': function (aLog) {
210 if (CLIPPERZ_DEFERRED_LOGGING_ENABLED) {
211 this.addBothPass(function(res) {Clipperz.log(aLog + " ", res);});
212 // this.addBothPass(function(res) {console.log(aLog + " ", res);});
213 }
214 },
215
216 //=============================================================================
217
218 'acquireLock': function (aLock) {
219 // this.addCallback(function (aResult) {
220 // return Clipperz.Async.callbacks("Clipperz.Async.acquireLock", [
221 // MochiKit.Base.method(aLock, 'acquire'),
222 // MochiKit.Base.partial(MochiKit.Async.succeed, aResult)
223 // ], {trace:false});
224 // });
225
226 this.addCallback(MochiKit.Base.method(aLock, 'acquire'));
227 },
228
229 'releaseLock': function (aLock) {
230 // this.addCallback(function (aResult) {
231 // return Clipperz.Async.callbacks("Clipperz.Async.release <ok>", [
232 // MochiKit.Base.method(aLock, 'release'),
233 // MochiKit.Base.partial(MochiKit.Async.succeed, aResult)
234 // ], {trace:false});
235 // });
236 // this.addErrback(function (aResult) {
237///console.log("releaseLock.addErrback:", aResult);
238 // return Clipperz.Async.callbacks("Clipperz.Async.release <fail>", [
239 // MochiKit.Base.method(aLock, 'release'),
240 // MochiKit.Base.partial(MochiKit.Async.fail, aResult)
241 // ], {trace:false});
242 // });
243
244 // this.addBothPass(MochiKit.Base.method(aLock, 'release'));
245 this.addCallbackPass(MochiKit.Base.method(aLock, 'release'));
246 this.addErrback(function (anError) {
247 aLock.release();
248
249 return anError;
250 });
251 },
252
253 //=============================================================================
254
255 'collectResults': function (someRequests) {
256 this.addCallback(Clipperz.Async.collectResults(this._name + " <collect results>", someRequests, this._args));
257 },
258
259 'addCallbackList': function (aRequestList) {
260 this.addCallback(Clipperz.Async.callbacks, this._name + " <callback list>", aRequestList, this._args);
261 },
262
263 //=============================================================================
264
265 'vars': function () {
266 if (this._vars == null) {
267 this._vars = {}
268 }
269
270 return this._vars;
271 },
272
273 'setValue': function (aKey) {
274 this.addCallback(MochiKit.Base.bind(function (aValue) {
275 this.vars()[aKey] = aValue;
276 return aValue;
277 }, this));
278 },
279
280 'getValue': function (aKey) {
281 this.addCallback(MochiKit.Base.bind(function () {
282 return this.vars()[aKey];
283 }, this));
284 },
285
286 //=============================================================================
287
288 __syntaxFix__: "syntax fix"
289});
290
291//#############################################################################
292
293Clipperz.Async.DeferredSynchronizer = function(aName, someMethods) {
294 this._name = aName || "Anonymous deferred Synchronizer";
295 this._methods = someMethods;
296
297 this._numberOfMethodsDone= 0;
298 this._methodResults = [];
299
300 this._result = new Clipperz.Async.Deferred("Clipperz.Async.DeferredSynchronizer # " + this.name(), {trace:false});
301 this._result.addMethod(this, 'methodResults');
302 this._result.addCallback(function(someResults) {
303 varcancels;
304 var errors;
305 var result;
306
307 cancels = MochiKit.Base.filter(function(aResult) { return (aResult instanceof MochiKit.Async.CancelledError)}, someResults);
308
309 if (cancels.length == 0) {
310 errors = MochiKit.Base.filter(function(aResult) { return (aResult instanceof Error)}, someResults);
311
312 if (errors.length == 0) {
313 // result = MochiKit.Async.succeed(someResults);
314 result = someResults;
315 } else {
316 result = MochiKit.Async.fail(someResults);
317 }
318 } else {
319 result = MochiKit.Async.fail(cancels[0]);
320 }
321
322 return result;
323 }/*, this._methodResults */);
324
325 return this;
326}
327
328MochiKit.Base.update(Clipperz.Async.DeferredSynchronizer.prototype, {
329
330 //-----------------------------------------------------------------------------
331
332 'name': function() {
333 return this._name;
334 },
335
336 //-----------------------------------------------------------------------------
337
338 'methods': function() {
339 return this._methods;
340 },
341
342 'methodResults': function() {
343 return this._methodResults;
344 },
345
346 //-----------------------------------------------------------------------------
347
348 'result': function() {
349 return this._result;
350 },
351
352 //-----------------------------------------------------------------------------
353
354 'numberOfMethodsDone':function() {
355 return this._numberOfMethodsDone;
356 },
357
358 'incrementNumberOfMethodsDone': function() {
359 this._numberOfMethodsDone ++;
360 },
361
362 //-----------------------------------------------------------------------------
363
364 'run': function(args, aValue) {
365 var deferredResults;
366 var i, c;
367
368 deferredResults = [];
369 args = args || {};
370
371 c = this.methods().length;
372 for (i=0; i<c; i++) {
373 var deferredResult;
374 varmethodCalls;
375 var ii, cc;
376
377//console.log("TYPEOF", typeof(this.methods()[i]));
378 if (typeof(this.methods()[i]) == 'function') {
379 methodCalls = [ this.methods()[i] ];
380 } else {
381 methodCalls = this.methods()[i];
382 }
383
384 cc = methodCalls.length;
385 deferredResult = new Clipperz.Async.Deferred("Clipperz.Async.DeferredSynchronizer.run => " + this.name() + "[" + i + "]", args);
386 for (ii=0; ii<cc; ii++) {
387 deferredResult.addCallback(methodCalls[ii]);
388 }
389 deferredResult.addBoth(MochiKit.Base.method(this, 'handleMethodCallDone', i));
390
391 deferredResults.push(deferredResult);
392 }
393
394 for (i=0; i<c; i++) {
395 deferredResults[i].callback(aValue);
396 }
397
398 return this.result();
399 },
400
401 //-----------------------------------------------------------------------------
402
403 'handleMethodCallDone': function(anIndexValue, aResult) {
404 this.incrementNumberOfMethodsDone();
405 this.methodResults()[anIndexValue] = aResult;
406
407 if (this.numberOfMethodsDone() < this.methods().length) {
408 //nothing to do here other than possibly log something
409 } else if (this.numberOfMethodsDone() == this.methods().length) {
410 this.result().callback();
411 } else if (this.numberOfMethodsDone() > this.methods().length) {
412 //WTF!!! :(
413 }
414
415 },
416
417 //-----------------------------------------------------------------------------
418
419 __syntaxFix__: "syntax fix"
420});
421
422//#############################################################################
423
424MochiKit.Base.update(Clipperz.Async, {
425
426 'callbacks': function (aName, someFunctions, someArguments, aCallbackValue) {
427 var deferredResult;
428 var i, c;
429
430 deferredResult = new Clipperz.Async.Deferred(aName, someArguments);
431 c = someFunctions.length;
432 for (i=0; i<c; i++) {
433 deferredResult.addCallback(someFunctions[i]);
434 }
435 deferredResult.callback(aCallbackValue);
436
437 return deferredResult;
438 },
439
440 //-------------------------------------------------------------------------
441
442 'forkAndJoin': function (aName, someMethods, args) {
443 return MochiKit.Base.partial(function (aName, someMethods, args, aValue) {
444 var synchronizer;
445 varresult;
446
447 args = args || {};
448 synchronizer = new Clipperz.Async.DeferredSynchronizer(aName, someMethods);
449 result = synchronizer.run(args, aValue);
450
451 return result;
452 }, aName, someMethods, args);
453 },
454
455 //-------------------------------------------------------------------------
456
457 'collectResults': function(aName, someRequests, args) {
458 return MochiKit.Base.partial(function(aName, someRequests, args, aValue) {
459 var deferredResult;
460 var requestKeys;
461 var methods;
462
463 requestKeys = MochiKit.Base.keys(someRequests);
464 methods = MochiKit.Base.values(someRequests);
465
466 deferredResult = new Clipperz.Async.Deferred(aName, args);
467 deferredResult.addCallback(Clipperz.Async.forkAndJoin(aName + " [inner forkAndJoin]", methods, args));
468 deferredResult.addBoth(function(someResults) {
469 var returnFunction;
470 var results;
471 var i,c;
472 var result;
473
474 if (someResults instanceof MochiKit.Async.CancelledError) {
475 returnFunction = MochiKit.Async.fail;
476 result = someResults;
477 } else {
478 if (someResults instanceof Error) {
479 returnFunction = MochiKit.Async.fail;
480 results = someResults['message'];
481 } else {
482 returnFunction = MochiKit.Async.succeed;
483 results = someResults;
484 }
485
486 result = {};
487
488 c = requestKeys.length;
489 for (i=0; i<c; i++) {
490 result[requestKeys[i]] = results[i];
491 }
492 }
493
494 return returnFunction.call(null, result);
495 });
496 deferredResult.callback(aValue);
497
498 return deferredResult;
499 }, aName, someRequests, args);
500 },
501
502 //-------------------------------------------------------------------------
503
504 'collectAll': function (someDeferredObjects) {
505 var deferredResult;
506
507 deferredResult = new MochiKit.Async.DeferredList(someDeferredObjects, false, false, false);
508 deferredResult.addCallback(function (aResultList) {
509 return MochiKit.Base.map(function (aResult) {
510 if (aResult[0]) {
511 return aResult[1];
512 } else {
513 throw aResult[1];
514 }
515 }, aResultList);
516 });
517
518 return deferredResult;
519 },
520
521 //-------------------------------------------------------------------------
522
523 'setItem': function (anObject, aKey, aValue) {
524 anObject[aKey] = aValue;
525
526 return anObject;
527 },
528
529 'setItemOnObject': function (aKey, aValue, anObject) {
530 anObject[aKey] = aValue;
531
532 return anObject;
533 },
534
535 'setDeferredItemOnObject': function (aKey, aDeferredFunction, anObject) {
536 return Clipperz.Async.callbacks("Clipperz.Async.setDeferredItemOnObject", [
537 aDeferredFunction,
538 MochiKit.Base.partial(Clipperz.Async.setItem, anObject, aKey)
539 ], {trace:false}, anObject);
540 },
541
542 //-------------------------------------------------------------------------
543
544 'deferredIf': function (aName, aThenBlock, anElseBlock) {
545 return function (aValue) {
546 var deferredResult;
547
548 if (!MochiKit.Base.isUndefinedOrNull(aValue) && aValue) {
549 deferredResult = Clipperz.Async.callbacks(aName + " <then>", aThenBlock, null, aValue);
550 } else {
551 deferredResult = Clipperz.Async.callbacks(aName + " <else>", anElseBlock, null, aValue);
552 }
553
554 return deferredResult;
555 }
556 },
557
558 //-------------------------------------------------------------------------
559
560 'log': function(aMessage, aResult) {
561 if (CLIPPERZ_DEFERRED_LOGGING_ENABLED) {
562 Clipperz.log(aMessage + " ", aResult);
563 }
564
565 return aResult;
566 },
567
568 //=========================================================================
569
570 'deferredCompare': function (aComparator, aDeferred, bDeferred) {
571 var deferredResult;
572
573 deferredResult = new Clipperz.Async.Deferred("Clipperz.Async.deferredCompare", {trace:false});
574 deferredResult.addCallback(Clipperz.Async.collectAll, [aDeferred, bDeferred]);
575 deferredResult.addCallback(function (someResults) {
576 var result;
577
578 if (aComparator(someResults[0], someResults[1]) > 0) {
579 result = MochiKit.Async.succeed();
580 } else {
581 result = MochiKit.Async.fail();
582 };
583
584 return result;
585 });
586 deferredResult.callback();
587
588 return deferredResult;
589 },
590
591 //-------------------------------------------------------------------------
592
593 'insertIntoSortedArray': function (anObject, aDeferredComparator, aSortedResult) {
594 var deferredResult;
595 var i, c;
596
597 if (aSortedResult.length == 0) {
598 deferredResult = MochiKit.Async.succeed([anObject]);
599 } else {
600 deferredResult = new Clipperz.Async.Deferred("Clipperz.Async.insertIntoSortedArray", {trace:false});
601 c = aSortedResult.length + 1;
602 for (i=0; i<c; i++) {
603 deferredResult.addCallback(function (aDeferredComparator, aObject, bObject, aContext) {
604 var innerDeferredResult;
605
606 innerDeferredResult = new Clipperz.Async.Deferred("Clipperz.Async.insertIntoSortedArray <inner compare>", {trace:false});
607 innerDeferredResult.addCallback(aDeferredComparator, aObject, bObject);
608 innerDeferredResult.addErrback(MochiKit.Async.fail, aContext);
609 innerDeferredResult.callback();
610
611 return innerDeferredResult;
612 }, aDeferredComparator, anObject, aSortedResult[i], i);
613 }
614 deferredResult.addMethod(aSortedResult, 'push', anObject);
615 deferredResult.addErrback(function (anError) {
616 aSortedResult.splice(anError.message, 0, anObject);
617 })
618 deferredResult.addBoth(MochiKit.Async.succeed, aSortedResult);
619 deferredResult.callback();
620 }
621
622 return deferredResult;
623 },
624
625 //-------------------------------------------------------------------------
626
627 'deferredSort': function (aDeferredComparator, someObjects) {
628 var deferredResult;
629 var i, c;
630
631 deferredResult = new Clipperz.Async.Deferred("Clipperz.Async.deferredSort", {trace:false});
632 c = someObjects.length;
633 for (i=0; i<c; i++) {
634 deferredResult.addCallback(Clipperz.Async.insertIntoSortedArray, someObjects[i], aDeferredComparator);
635 if ((i % 50) == 0) {
636 //console.log("######### sort wait ##########");
637 deferredResult.addCallback(MochiKit.Async.wait, 0.5);
638 }
639 }
640 deferredResult.callback([]);
641
642 return deferredResult;
643 },
644
645 //=========================================================================
646
647 'deferredFilter': function (aFunction, someObjects) {
648 vardeferredResult;
649 vari, c;
650
651 deferredResult = new Clipperz.Async.Deferred("Clipperz.Async.deferredFilter", {trace:false});
652 c = someObjects.length;
653 for (i=0; i<c; i++) {
654 deferredResult.addCallback(function (aFunction, anObject, anIndex, aResult) {
655 var innerDeferredResult;
656
657 innerDeferredResult = new Clipperz.Async.Deferred("Clipperz.Async.deferredFilter <inner - " + anIndex + ">", {trace:false});
658 innerDeferredResult.addCallback(aFunction, anObject);
659 innerDeferredResult.addCallback(function (aFilterResult) {
660 if (aFilterResult) {
661 aResult.push(anObject);
662 };
663 });
664 innerDeferredResult.addBoth(MochiKit.Async.succeed, aResult);
665 innerDeferredResult.callback();
666
667 return innerDeferredResult;
668 }, aFunction, someObjects[i], i);
669 }
670 deferredResult.callback([]);
671
672 return deferredResult;
673 },
674
675 'forEach': function (aFunction) {
676 return MochiKit.Base.partial(function (aFunction, anIterable) {
677 MochiKit.Iter.forEach(anIterable, aFunction);
678 }, aFunction);
679 },
680
681 //=========================================================================
682
683 'or': function (someValues) {
684 return Clipperz.Async.callbacks("Clipperz.Async.or", [
685 MochiKit.Base.values,
686 MochiKit.Base.flattenArguments,
687//function (aValue) { console.log("Record.hasAnyCleanTextData - flatten", aValue); return aValue; },
688 function(someInnerValues) {
689 return MochiKit.Iter.some(someInnerValues, MochiKit.Base.operator.identity);
690 }
691 ], {trace:false}, someValues);
692 },
693
694 //=========================================================================
695
696 'clearResult': function () {},
697
698 //=========================================================================
699 __syntaxFix__: "syntax fix"
700});
701
702
703//#############################################################################
704
705CLIPPERZ_DEFERRED_LOGGING_ENABLED = true;
706CLIPPERZ_DEFERRED_TRACING_ENABLED = false;
707CLIPPERZ_DEFERRED_CALL_LOGGING_ENABLED = false;