Permalink
Browse files

first commit

  • Loading branch information...
0 parents commit 0f1ac91eeb71d46cf79b19dff6e2de11c353f3ea @adrai committed May 17, 2012
Showing with 44,909 additions and 0 deletions.
  1. +69 −0 README.markdown
  2. +13 −0 index.js
  3. +161 −0 lib/bases/eventDenormalizerBase.js
  4. +80 −0 lib/bases/eventExtenderBase.js
  5. +88 −0 lib/contextEventDenormalizer.js
  6. +86 −0 lib/eventDispatcher.js
  7. +7 −0 lib/eventEmitter.js
  8. +72 −0 lib/loaders/eventDenormalizerLoader.js
  9. +72 −0 lib/loaders/eventExtenderLoader.js
  10. +37 −0 lib/orderQueue.js
  11. +4 −0 lib/utils.js
  12. +51 −0 lib/utils/object.js
  13. +88 −0 lib/utils/path.js
  14. +19 −0 licence
  15. +9 −0 node_modules/async/.gitmodules
  16. +4 −0 node_modules/async/.npmignore
  17. +19 −0 node_modules/async/LICENSE
  18. +25 −0 node_modules/async/Makefile
  19. +1,022 −0 node_modules/async/README.md
  20. +3 −0 node_modules/async/index.js
  21. +692 −0 node_modules/async/lib/async.js
  22. +42 −0 node_modules/async/package.json
  23. +13 −0 node_modules/eventemitter2/.npmignore
  24. +203 −0 node_modules/eventemitter2/README.md
  25. +1 −0 node_modules/eventemitter2/index.js
  26. +547 −0 node_modules/eventemitter2/lib/eventemitter2.js
  27. +79 −0 node_modules/eventemitter2/package.json
  28. +123 −0 node_modules/eventemitter2/test/common.js
  29. +53 −0 node_modules/eventemitter2/test/perf/benchmark.js
  30. +192 −0 node_modules/eventemitter2/test/simple/addListener.js
  31. +153 −0 node_modules/eventemitter2/test/simple/emit.js
  32. +199 −0 node_modules/eventemitter2/test/simple/removeListener.js
  33. +133 −0 node_modules/eventemitter2/test/simple/setMax.js
  34. +126 −0 node_modules/eventemitter2/test/simple/ttl.js
  35. +307 −0 node_modules/eventemitter2/test/wildcardEvents/addListener.js
  36. +829 −0 node_modules/eventemitter2/test/wildcardEvents/all.js
  37. +216 −0 node_modules/eventemitter2/test/wildcardEvents/customDelimiter.js
  38. +56 −0 node_modules/eventemitter2/test/wildcardEvents/k1.js
  39. +79 −0 node_modules/eventemitter2/test/wildcardEvents/options.js
  40. +284 −0 node_modules/eventemitter2/test/wildcardEvents/removeListener.js
  41. +196 −0 node_modules/eventemitter2/test/wildcardEvents/ttl.js
  42. +3 −0 node_modules/expect.js/.npmignore
  43. +21 −0 node_modules/expect.js/History.md
  44. +242 −0 node_modules/expect.js/README.md
  45. +1,202 −0 node_modules/expect.js/expect.js
  46. +25 −0 node_modules/expect.js/package.json
  47. +13 −0 node_modules/node-queue/.npmignore
  48. +13 −0 node_modules/node-queue/.travis.yml
  49. +161 −0 node_modules/node-queue/README.markdown
  50. +13 −0 node_modules/node-queue/index.js
  51. +104 −0 node_modules/node-queue/lib/databases/inMemory.js
  52. +120 −0 node_modules/node-queue/lib/databases/mongoDb.js
  53. +45 −0 node_modules/node-queue/lib/queue.js
  54. +19 −0 node_modules/node-queue/licence
  55. +56 −0 node_modules/node-queue/package.json
  56. +1 −0 node_modules/node-queue/test/mocha.opts
  57. +322 −0 node_modules/node-queue/test/queueImplementationTest.js
  58. +53 −0 node_modules/node-queue/test/queueTest.js
  59. +2 −0 node_modules/sinon/.npmignore
  60. +24 −0 node_modules/sinon/AUTHORS
  61. +236 −0 node_modules/sinon/Changelog.txt
  62. BIN node_modules/sinon/GPATH
  63. BIN node_modules/sinon/GRTAGS
  64. BIN node_modules/sinon/GSYMS
  65. BIN node_modules/sinon/GTAGS
  66. +27 −0 node_modules/sinon/LICENSE
  67. +10 −0 node_modules/sinon/Makefile
  68. +42 −0 node_modules/sinon/README.md
  69. +92 −0 node_modules/sinon/build
  70. +25 −0 node_modules/sinon/jsTestDriver.conf
  71. +10 −0 node_modules/sinon/jsTestDriverBuild.conf
  72. +54 −0 node_modules/sinon/jsl.conf
  73. +313 −0 node_modules/sinon/lib/sinon.js
  74. +171 −0 node_modules/sinon/lib/sinon/assert.js
  75. +141 −0 node_modules/sinon/lib/sinon/collection.js
  76. +407 −0 node_modules/sinon/lib/sinon/mock.js
  77. +125 −0 node_modules/sinon/lib/sinon/sandbox.js
  78. +488 −0 node_modules/sinon/lib/sinon/spy.js
  79. +277 −0 node_modules/sinon/lib/sinon/stub.js
  80. +67 −0 node_modules/sinon/lib/sinon/test.js
  81. +97 −0 node_modules/sinon/lib/sinon/test_case.js
  82. +74 −0 node_modules/sinon/lib/sinon/util/event.js
  83. +201 −0 node_modules/sinon/lib/sinon/util/fake_server.js
  84. +83 −0 node_modules/sinon/lib/sinon/util/fake_server_with_clock.js
  85. +339 −0 node_modules/sinon/lib/sinon/util/fake_timers.js
  86. +471 −0 node_modules/sinon/lib/sinon/util/fake_xml_http_request.js
  87. +27 −0 node_modules/sinon/lib/sinon/util/timers_ie.js
  88. +19 −0 node_modules/sinon/lib/sinon/util/xhr_ie.js
  89. +115 −0 node_modules/sinon/package.json
  90. +49 −0 node_modules/sinon/step-tests
  91. +595 −0 node_modules/sinon/test/Asserts.js
  92. +27 −0 node_modules/sinon/test/helper.js
  93. +13 −0 node_modules/sinon/test/node/run.js
  94. +1 −0 node_modules/sinon/test/resources/xhr_target.txt
  95. +13,989 −0 node_modules/sinon/test/rhino/env.rhino.1.2.js
  96. +34 −0 node_modules/sinon/test/rhino/run.js
  97. +1,086 −0 node_modules/sinon/test/sinon/assert_test.js
  98. +321 −0 node_modules/sinon/test/sinon/collection_test.js
  99. +955 −0 node_modules/sinon/test/sinon/mock_test.js
  100. +470 −0 node_modules/sinon/test/sinon/sandbox_test.js
  101. +2,401 −0 node_modules/sinon/test/sinon/spy_test.js
  102. +1,011 −0 node_modules/sinon/test/sinon/stub_test.js
  103. +230 −0 node_modules/sinon/test/sinon/test_case_test.js
  104. +513 −0 node_modules/sinon/test/sinon/test_test.js
  105. +125 −0 node_modules/sinon/test/sinon/util/event_test.js
  106. +691 −0 node_modules/sinon/test/sinon/util/fake_server_test.js
  107. +232 −0 node_modules/sinon/test/sinon/util/fake_server_with_clock_test.js
  108. +878 −0 node_modules/sinon/test/sinon/util/fake_timers_test.js
  109. +1,198 −0 node_modules/sinon/test/sinon/util/fake_xml_http_request_test.js
  110. +408 −0 node_modules/sinon/test/sinon_test.js
  111. +79 −0 node_modules/sinon/test/test_case_shim.js
  112. +75 −0 node_modules/sinon/todo.org
  113. +3 −0 node_modules/underscore/.npmignore
  114. +1 −0 node_modules/underscore/CNAME
  115. +22 −0 node_modules/underscore/LICENSE
  116. +19 −0 node_modules/underscore/README.md
  117. BIN node_modules/underscore/favicon.ico
  118. +2,109 −0 node_modules/underscore/index.html
  119. +1 −0 node_modules/underscore/index.js
  120. +38 −0 node_modules/underscore/package.json
  121. BIN node_modules/underscore/raw/underscore.psd
  122. +32 −0 node_modules/underscore/underscore-min.js
  123. +1,059 −0 node_modules/underscore/underscore.js
  124. +13 −0 node_modules/viewmodel/.npmignore
  125. +13 −0 node_modules/viewmodel/.travis.yml
  126. +153 −0 node_modules/viewmodel/README.markdown
  127. +13 −0 node_modules/viewmodel/index.js
  128. +171 −0 node_modules/viewmodel/lib/databases/inMemory.js
  129. +160 −0 node_modules/viewmodel/lib/databases/mongoDb.js
  130. +124 −0 node_modules/viewmodel/lib/repository.js
  131. +19 −0 node_modules/viewmodel/licence
  132. +65 −0 node_modules/viewmodel/package.json
  133. +1 −0 node_modules/viewmodel/test/mocha.opts
  134. +388 −0 node_modules/viewmodel/test/repositoryReadImplementationTest.js
  135. +68 −0 node_modules/viewmodel/test/repositoryTest.js
  136. +792 −0 node_modules/viewmodel/test/repositoryWriteImplementationTest.js
  137. +44 −0 package.json
  138. +436 −0 test/eventDenormalizerBaseTest.js
  139. +298 −0 test/eventDispatcherTest.js
  140. +147 −0 test/eventExtenderBaseTest.js
  141. +496 −0 test/integration/contextEventDenormalizerTest.js
  142. +14 −0 test/integration/eventDenormalizers/dummyDenormalizer.js
  143. +26 −0 test/integration/eventExtenders/dummyExtender.js
  144. +1 −0 test/mocha.opts
@@ -0,0 +1,69 @@
+# Introduction
+
+[![Build Status](https://secure.travis-ci.org/adrai/node-cqrs-eventdenormalizer.png)](http://travis-ci.org/adrai/node-cqrs-eventdenormalizer)
+
+Node-cqrs-eventdenormalizer is a node.js module that implements the cqrs pattern.
+It can be very useful as eventdenormalizer component if you work with (d)ddd, cqrs, domain, host, etc.
+
+# Installation
+
+ $ npm install node-cqrs-eventdenormalizer
+
+# Usage
+
+## Initialization
+
+ var contextEventDenormalizer = require('node-cqrs-eventdenormalizer').contextEventDenormalizer;
+
+ contextEventDenormalizer.on('event', function(evt) {
+ // send to clients
+ });
+ contextEventDenormalizer.initialize({
+ denormalizersPath: __dirname + '/eventDenormalizers',
+ extendersPath: __dirname + '/eventExtenders'
+ }, function(err) {
+
+ });
+
+ contextEventDenormalizer.denormalize({ id: 'msgId', event: 'dummyChanged', payload: { id: '23445' } }, function(err) {
+
+ });
+
+## Define eventdenormalizers...
+
+ var base = require('node-cqrs-eventdenormalizer').eventDenormalizerBase;
+
+ module.exports = base.extend({
+
+ events: ['dummied', {'dummyCreated': 'create'}, {'dummyChanged': 'update'}, {'dummyDeleted': 'delete'}],
+ collectionName: 'dummies',
+
+ dummied: function(evt, aux, callback) {
+ callback(null);
+ }
+
+ });
+
+See [tests](https://github.com/adrai/node-cqrs-eventdenormalizer/tree/master/test) for detailed information...
+
+# License
+
+Copyright (c) 2012 Adriano Raiano
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+THE SOFTWARE.
@@ -0,0 +1,13 @@
+var index;
+
+if (typeof module.exports !== 'undefined') {
+ index = module.exports;
+} else {
+ index = root.index = {};
+}
+
+index.VERSION = '0.0.1';
+
+index.contextEventDenormalizer = require('./lib/contextEventDenormalizer');
+index.eventDenormalizerBase = require('./lib/bases/eventDenormalizerBase');
+index.eventExtenderBase = require('./lib/bases/eventExtenderBase');
@@ -0,0 +1,161 @@
+var _ = require('underscore')
+ , eventEmitter = require('../eventEmitter')
+ , Queue = require('../orderQueue');
+
+var EventDenormalizer = {};
+EventDenormalizer.prototype = {
+
+ configure: function(fn) {
+ fn.call(this);
+ return this;
+ },
+
+ use: function(module) {
+ if (!module) return;
+
+ if (module.commit) {
+ this.repository = module;
+ }
+ },
+
+ create: function(evt, aux, callback) {
+ return this.defaultAction(evt, aux, 'create', callback);
+ },
+
+ update: function(evt, aux, callback) {
+ return this.defaultAction(evt, aux, 'update', callback);
+ },
+
+ 'delete': function(evt, aux, callback) {
+ return this.defaultAction(evt, aux, 'delete', callback);
+ },
+
+ defaultAction: function(evt, aux, action, callback) {
+
+ var self = this;
+ aux.repository.get(evt.payload.id, function(err, vm) {
+ // If the view model has just been created (i.e. it has not been
+ // saved yet), and it shall be deleted, simply discard it and
+ // return.
+ if((vm.actionOnCommit === 'create') && (action === 'delete')) {
+ return callback(null);
+ }
+
+ if(!aux.defaultQueuingStrategy(evt, vm, callback)) {
+ return;
+ }
+
+ // set the next expected revision
+ aux.defaultRevisionUpdateStrategy(vm, evt);
+
+ if(action !== 'delete') {
+ _.extend(vm, evt.payload);
+ } else {
+ vm.destroy();
+ }
+
+ aux.repository.commit(vm, function(err) {
+ callback(err); // done this event
+
+ // dequeue
+ aux.defaultDequeuingStrategy(vm);
+ });
+ });
+
+ },
+
+ _getAux: function() {
+ var self = this;
+
+ this._aux = this._aux || {
+ repository: self.repository,
+
+ queueEvent: function(id, evt) {
+ self.queue.push(id, evt);
+ },
+ getQueuedEvents: function(id) {
+ return self.queue.get(id);
+ },
+ removeQueuedEvent: function(id, evt) {
+ self.queue.remove(id, evt);
+ },
+
+ defaultQueuingStrategy: function(evt, vm, callback) {
+ if(evt.head.revision < vm._revision) {
+ callback(null);
+ return false;
+ }
+ if(evt.head.revision > vm._revision) {
+ this.queueEvent(vm.id, evt);
+ return false;
+ }
+ return true;
+ },
+ defaultDequeuingStrategy: function(vm) {
+ var pendingEvents = this.getQueuedEvents(vm.id);
+ if(!pendingEvents) return;
+
+ var nextEvent = _.find(pendingEvents, function(item) {
+ return item.head.revision === vm._revision;
+ });
+ if(!nextEvent) return;
+
+ this.removeQueuedEvent(vm.id, nextEvent); // dequeue event
+ self.handle(nextEvent); // handle event
+ },
+ defaultRevisionUpdateStrategy: function(vm, evt) {
+ vm._revision = evt.head.revision + 1;
+ }
+ };
+
+ return this._aux;
+ },
+
+ handle: function(evt) {
+
+ // Map events to function names:
+ // - For the event handler matching the current event, its name is returned
+ // - For all other event handlers, undefined is returned
+ var fnNames = _.map(this.events, function(item) {
+ if (_.isString(item) && item === evt.event) {
+ return item;
+ } else if (item[evt.event]) {
+ return item[evt.event];
+ }
+ }
+ );
+
+ // Reduce function names to function name:
+ // - Replace all undefineds by an empty string
+ // - Keep all non-undefined values
+ //
+ // NOTE: This will fail if multiple event handlers match the current event,
+ // but this is not allowed anyway, so it can only happen on error.
+ var fnName = _.reduce(fnNames, function(memo, item) {
+ return memo + (item || '');
+ }, '');
+
+ if(this[fnName]) {
+ // Call the event handler found by map-reduce.
+ this[fnName](evt, this._getAux(), function(err) {
+ eventEmitter.emit('denormalized:' + evt.event, evt);
+ });
+ } else {
+ throw(new Error('missing handle function'));
+ }
+
+ }
+
+};
+
+module.exports = {
+
+ extend: function(obj) {
+ var newObj = _.extend(_.clone(EventDenormalizer.prototype), obj);
+
+ newObj.queue = new Queue();
+
+ return newObj;
+ }
+
+};
@@ -0,0 +1,80 @@
+var _ = require('underscore')
+ , eventEmitter = require('../eventEmitter');
+
+var EventExtender = {};
+EventExtender.prototype = {
+
+ configure: function(fn) {
+ fn.call(this);
+ return this;
+ },
+
+ use: function(module) {
+ if (!module) return;
+
+ if (module.commit) {
+ this.repository = module;
+ }
+ },
+
+ _getAux: function() {
+ var self = this;
+
+ this._aux = this._aux || {
+ repository: self.repository
+ };
+
+ return this._aux;
+ },
+
+ handle: function(evt) {
+
+ // Map events to function names:
+ // - For the event handler matching the current event, its name is returned
+ // - For all other event handlers, undefined is returned
+ var fnNames = _.map(this.events, function(item) {
+ if (_.isString(item) && item === evt.event) {
+ return item;
+ } else if (item[evt.event]) {
+ return item[evt.event];
+ }
+ }
+ );
+
+ // Reduce function names to function name:
+ // - Replace all undefineds by an empty string
+ // - Keep all non-undefined values
+ //
+ // NOTE: This will fail if multiple event handlers match the current event,
+ // but this is not allowed anyway, so it can only happen on error.
+ var fnName = _.reduce(fnNames, function(memo, item) {
+ return memo + (item || '');
+ }, '');
+
+ if(this[fnName]) {
+ // Call the event handler found by map-reduce.
+ this[fnName](evt, this._getAux(), function(err, extEvt) {
+ extEvt = extEvt || evt;
+ eventEmitter.emit('extended:' + extEvt.event, extEvt);
+ });
+ } else if(this.defaultAction) {
+ // Call the event handler found by map-reduce.
+ this.defaultAction(evt, this._getAux(), function(err, extEvt) {
+ extEvt = extEvt || evt;
+ eventEmitter.emit('extended:' + extEvt.event, extEvt);
+ });
+ } else {
+ eventEmitter.emit('extended:' + evt.event, evt);
+ }
+
+ }
+
+};
+
+module.exports = {
+
+ extend: function(obj) {
+ return _.extend(_.clone(EventExtender.prototype), obj);
+ }
+
+};
Oops, something went wrong.

0 comments on commit 0f1ac91

Please sign in to comment.