Comparing version 2.5.0 to 2.6.0
@@ -45,3 +45,3 @@ (function() { | ||
// Store a reference to the provide provider. | ||
self.__provide = $provide; | ||
self.__provide = $provide; | ||
// Store a reference to the cache service constructor. | ||
@@ -74,8 +74,9 @@ self.__absyncCache = absyncCache; | ||
* Can also be an object with a "socket" member that provides either of the above. | ||
* @param {Boolean} [debug=false] Enable additional debugging output. | ||
*/ | ||
AbsyncProvider.prototype.configure = function AbsyncProvider$configure( configuration ) { | ||
AbsyncProvider.prototype.configure = function AbsyncProvider$configure( configuration, debug ) { | ||
var self = this; | ||
// If the configuration has a "socket" member, unpack it. | ||
var socket = configuration.socket || configuration; | ||
var socket = configuration.socket || configuration; | ||
// Determine if the socket is an io.Socket. | ||
@@ -102,2 +103,4 @@ var isSocket = io && io.Socket && socket instanceof io.Socket; | ||
} | ||
self.debug = debug || false; | ||
}; | ||
@@ -128,2 +131,5 @@ | ||
// If no debug flag was set, use the value from the core absync provider. | ||
configuration.debug = typeof configuration.debug === "undefined" ? self.debug : configuration.debug; | ||
// Register the service configuration. | ||
@@ -156,2 +162,5 @@ // __absyncCache will return a constructor for a service with the given configuration. | ||
// If no debug flag was set, use the value from the core absync provider. | ||
configuration.debug = typeof configuration.debug === "undefined" ? self.debug : configuration.debug; | ||
// Register the service configuration. | ||
@@ -191,6 +200,7 @@ // __absyncCache will return a constructor for a service with the given configuration. | ||
* @param {io.Socket|Function|Object} configuration The socket.io instance to use. | ||
* @param {Boolean} [debug=false] Enable additional debug output. | ||
*/ | ||
AbsyncService.prototype.configure = function AbsyncService$configure( configuration ) { | ||
AbsyncService.prototype.configure = function AbsyncService$configure( configuration, debug ) { | ||
var _absyncProvider = this.__absyncProvider; | ||
_absyncProvider.configure( configuration ); | ||
_absyncProvider.configure( configuration, debug || false ); | ||
}; | ||
@@ -304,7 +314,8 @@ | ||
* @param {AbsyncService} absync | ||
* @param {Object} absyncNoopLog A log interface that does nothing. | ||
* @returns {CacheService} | ||
* @ngInject | ||
*/ | ||
CacheService.$inject = ["$http", "$injector", "$log", "$q", "$rootScope", "absync"]; | ||
function CacheService( $http, $injector, $log, $q, $rootScope, absync ) { | ||
CacheService.$inject = ["$http", "$injector", "$log", "$q", "$rootScope", "absync", "absyncNoopLog"]; | ||
function CacheService( $http, $injector, $log, $q, $rootScope, absync, absyncNoopLog ) { | ||
var self = this; | ||
@@ -353,3 +364,3 @@ | ||
// Do the same for our logger. | ||
self.logInterface = $log; | ||
self.logInterface = configuration.debug ? $log : absyncNoopLog; | ||
// The scope on which we broadcast all our relevant events. | ||
@@ -1122,5 +1133,6 @@ self.scope = $rootScope; | ||
* Usually, you don't need to provide an alternative here. | ||
* @param {Boolean} [debug=false] Should additional debugging output be enabled? | ||
* @constructor | ||
*/ | ||
function AbsyncServiceConfiguration( model, collectionUri, entityUri, collectionName, entityName, deserialize, serialize, injector ) { | ||
function AbsyncServiceConfiguration( model, collectionUri, entityUri, collectionName, entityName, deserialize, serialize, injector, debug ) { | ||
this.model = model; | ||
@@ -1138,3 +1150,16 @@ this.collectionUri = collectionUri; | ||
this.injector = injector || undefined; | ||
this.debug = debug || false; | ||
} | ||
}());;(function() { | ||
"use strict"; | ||
/* globals angular */ | ||
angular | ||
.module( "absync" ) | ||
.constant( "absyncNoopLog", { | ||
debug : angular.noop, | ||
info : angular.noop, | ||
error : angular.noop | ||
} ); | ||
}()); |
@@ -40,3 +40,3 @@ (function() { | ||
// Store a reference to the provide provider. | ||
self.__provide = $provide; | ||
self.__provide = $provide; | ||
// Store a reference to the cache service constructor. | ||
@@ -69,8 +69,9 @@ self.__absyncCache = absyncCache; | ||
* Can also be an object with a "socket" member that provides either of the above. | ||
* @param {Boolean} [debug=false] Enable additional debugging output. | ||
*/ | ||
AbsyncProvider.prototype.configure = function AbsyncProvider$configure( configuration ) { | ||
AbsyncProvider.prototype.configure = function AbsyncProvider$configure( configuration, debug ) { | ||
var self = this; | ||
// If the configuration has a "socket" member, unpack it. | ||
var socket = configuration.socket || configuration; | ||
var socket = configuration.socket || configuration; | ||
// Determine if the socket is an io.Socket. | ||
@@ -97,2 +98,4 @@ var isSocket = io && io.Socket && socket instanceof io.Socket; | ||
} | ||
self.debug = debug || false; | ||
}; | ||
@@ -123,2 +126,5 @@ | ||
// If no debug flag was set, use the value from the core absync provider. | ||
configuration.debug = typeof configuration.debug === "undefined" ? self.debug : configuration.debug; | ||
// Register the service configuration. | ||
@@ -151,2 +157,5 @@ // __absyncCache will return a constructor for a service with the given configuration. | ||
// If no debug flag was set, use the value from the core absync provider. | ||
configuration.debug = typeof configuration.debug === "undefined" ? self.debug : configuration.debug; | ||
// Register the service configuration. | ||
@@ -186,6 +195,7 @@ // __absyncCache will return a constructor for a service with the given configuration. | ||
* @param {io.Socket|Function|Object} configuration The socket.io instance to use. | ||
* @param {Boolean} [debug=false] Enable additional debug output. | ||
*/ | ||
AbsyncService.prototype.configure = function AbsyncService$configure( configuration ) { | ||
AbsyncService.prototype.configure = function AbsyncService$configure( configuration, debug ) { | ||
var _absyncProvider = this.__absyncProvider; | ||
_absyncProvider.configure( configuration ); | ||
_absyncProvider.configure( configuration, debug || false ); | ||
}; | ||
@@ -192,0 +202,0 @@ |
@@ -38,7 +38,8 @@ (function() { | ||
* @param {AbsyncService} absync | ||
* @param {Object} absyncNoopLog A log interface that does nothing. | ||
* @returns {CacheService} | ||
* @ngInject | ||
*/ | ||
CacheService.$inject = ["$http", "$injector", "$log", "$q", "$rootScope", "absync"]; | ||
function CacheService( $http, $injector, $log, $q, $rootScope, absync ) { | ||
CacheService.$inject = ["$http", "$injector", "$log", "$q", "$rootScope", "absync", "absyncNoopLog"]; | ||
function CacheService( $http, $injector, $log, $q, $rootScope, absync, absyncNoopLog ) { | ||
var self = this; | ||
@@ -87,3 +88,3 @@ | ||
// Do the same for our logger. | ||
self.logInterface = $log; | ||
self.logInterface = configuration.debug ? $log : absyncNoopLog; | ||
// The scope on which we broadcast all our relevant events. | ||
@@ -90,0 +91,0 @@ self.scope = $rootScope; |
@@ -34,5 +34,6 @@ (function() { | ||
* Usually, you don't need to provide an alternative here. | ||
* @param {Boolean} [debug=false] Should additional debugging output be enabled? | ||
* @constructor | ||
*/ | ||
function AbsyncServiceConfiguration( model, collectionUri, entityUri, collectionName, entityName, deserialize, serialize, injector ) { | ||
function AbsyncServiceConfiguration( model, collectionUri, entityUri, collectionName, entityName, deserialize, serialize, injector, debug ) { | ||
this.model = model; | ||
@@ -50,3 +51,5 @@ this.collectionUri = collectionUri; | ||
this.injector = injector || undefined; | ||
this.debug = debug || false; | ||
} | ||
}()); |
@@ -1,2 +0,2 @@ | ||
!function(){"use strict";angular.module("absync",[])}(),function(){"use strict";function e(e,r){return new t(e,r)}function t(e,t){var r=this;r.__provide=e,r.__absyncCache=t,r.__ioSocket=null,r.__registerLater=[],r.__collections={},r.__entities={}}function r(e){this.__absyncProvider=e}e.$inject=["$provide","absyncCache"],angular.module("absync").provider("absync",e),t.prototype.configure=function(e){var t=this,r=e.socket||e,i=io&&io.Socket&&r instanceof io.Socket;if("function"==typeof r)t.__ioSocket=r();else{if(!i)throw new Error("configure() expects input to be a function or a socket.io Socket instance.");t.__ioSocket=r}t.__registerLater.length&&(t.__registerLater.forEach(t.__registerListener.bind(t)),t.__registerLater=[])},t.prototype.__registerListener=function(e){var t=this;t.$get().__handleEntityEvent(e.eventName,e.callback)},t.prototype.collection=function(e,t){var r=this;if(r.__collections[e])throw new Error("A collection with the name '"+e+"' was already requested. Names for collections must be unique.");if(r.__entities[e])throw new Error("An entity with the name '"+e+"' was already requested. Names for collections must be unique and can't be shared with entities.");r.__collections[e]=r.__absyncCache(e,t),r.__provide.service(e,r.__collections[e])},t.prototype.entity=function(e,t){var r=this;if(r.__entities[e])throw new Error("An entity with the name '"+e+"' was already requested. Names for entities must be unique.");if(r.__collections[e])throw new Error("A collection with the name '"+e+"' was already requested. Names for entities must be unique and can't be shared with collections.");r.__entities[e]=r.__absyncCache(e,t),r.__provide.service(e,r.__entities[e])},t.prototype.$get=function(){return new r(this)},r.prototype.configure=function(e){var t=this.__absyncProvider;t.configure(e)},r.prototype.on=function(e,t){var r=this.__absyncProvider,i=this;return r.__ioSocket?i.__handleEntityEvent(e,t):r.__registerLater.length>8192?null:(r.__registerLater.push({eventName:e,callback:t}),null)},r.prototype.__handleEntityEvent=function(e,t){var r=this.__absyncProvider;return r.__ioSocket.on(e,t),function(){r.__ioSocket.removeListener(e,t)}},r.prototype.emit=function(e,t,r){var i=this.__absyncProvider;if(!i.__ioSocket)throw new Error("socket.io is not initialized.");i.__ioSocket.emit(e,t,function(){r&&r.apply(i.__ioSocket,arguments)})}}(),function(){"use strict";function e(e,r){function i(i,n,o,a,c,s){var h=this,l=r.injector||n,y=l.has(r.model);if(!y)throw new Error("Unable to construct the '"+e+"' service, because the referenced model '"+r.model+"' is not available for injection.");var d="string"==typeof r.model?l.get(r.model):r.model,f=d.serialize||r.serialize||t,u=d.deserialize||r.deserialize||t;h.name=e,h.configuration=r,h.entityCache=r.collectionName?[]:{},h.__entityCacheRaw=null,h.enableRequestCache=!0,h.__requestCache={},h.__dataAvailableDeferred=a.defer(),h.__objectsAvailableDeferred=a.defer(),h.dataAvailable=h.__dataAvailableDeferred.promise,h.objectsAvailable=h.__objectsAvailableDeferred.promise,h.httpInterface=i,h.logInterface=o,h.scope=c,h.q=a,h.logPrefix="absync:"+e.toLocaleUpperCase()+" ",h.forceEarlyCacheUpdate=!1,h.throwFailures=!1,h.serializer=f,h.deserializer=u,s.on(r.entityName,h.__onEntityOnWebsocket.bind(h)),r.collectionName&&s.on(r.collectionName,h.__onCollectionOnWebsocket.bind(h)),c.$on(r.entityName,h.__onEntityReceived.bind(h)),r.collectionName&&c.$on(r.collectionName,h.__onCollectionReceived.bind(h)),h.dataAvailable.then(h.__onDataAvailable.bind(h)),h.logInterface.info(h.logPrefix+"service was instantiated.")}function n(e){var t=this;if(e.data[r.entityName]){var i=t.deserializer(e.data[r.entityName]);return t.forceEarlyCacheUpdate&&t.__updateCacheWithEntity(i),i}throw new Error("The response from the server was not in the expected format. It should have a member named '"+r.entityName+"'.")}function o(e){var t=this;if(t.logInterface.error(t.logPrefix+"Unable to store entity on the server.",e),t.logInterface.error(e),t.scope.$emit("absyncError",e),t.throwFailures)throw e}return i.$inject=["$http","$injector","$log","$q","$rootScope","absync"],i.prototype.__onEntityOnWebsocket=function(e){var t=this;t.scope.$broadcast(r.entityName,e[r.entityName])},i.prototype.__onCollectionOnWebsocket=function(e){var t=this;t.scope.$broadcast(r.collectionName,e[r.collectionName])},i.prototype.__onDataAvailable=function(e){function t(e){i.entityCache.push(i.deserializer(e))}var i=this;if(Array.isArray(i.entityCache))e[r.collectionName].forEach(t),i.__objectsAvailableDeferred.resolve(i.entityCache),i.scope.$broadcast("collectionNew",{service:i,cache:i.entityCache});else{var n=i.deserializer(e[r.entityName]);i.__updateCacheWithEntity(n),i.__objectsAvailableDeferred.resolve(i.entityCache)}},i.prototype.__onEntityReceived=function(e,t){var r=this,i=t;1===Object.keys(i).length&&i.hasOwnProperty("id")?(r.logInterface.info(r.logPrefix+"Entity was deleted from the server. Updating cache…"),r.__removeEntityFromCache(i.id)):(r.logInterface.debug(r.logPrefix+"Entity was updated on the server. Updating cache…"),r.__updateCacheWithEntity(r.deserializer(i)))},i.prototype.__onCollectionReceived=function(e,t){function r(e){var t=i.deserializer(e);i.__updateCacheWithEntity(t)}var i=this,n=t;i.entityCache.length=0,n.forEach(r)},i.prototype.ensureLoaded=function(e){function t(e){if(!e.data[r.collectionName])throw new Error("The response from the server was not in the expected format. It should have a member named '"+r.collectionName+"'.");a.__entityCacheRaw=e.data,a.__dataAvailableDeferred.resolve(e.data)}function i(e){if(a.logInterface.error(a.logPrefix+"Unable to retrieve the collection from the server.",e),a.__entityCacheRaw=null,a.scope.$emit("absyncError",e),a.throwFailures)throw e}function n(e){if(!e.data[r.entityName])throw new Error("The response from the server was not in the expected format. It should have a member named '"+r.entityName+"'.");a.__entityCacheRaw=e.data,a.__dataAvailableDeferred.resolve(e.data)}function o(e){if(a.logInterface.error(a.logPrefix+"Unable to retrieve the entity from the server.",e),a.__entityCacheRaw=null,a.scope.$emit("absyncError",e),a.throwFailures)throw e}var a=this;if(e=e===!0,null===a.__entityCacheRaw||e)if(a.__entityCacheRaw=[],r.collectionName&&r.collectionUri)a.logInterface.info(a.logPrefix+"Retrieving '"+r.collectionName+"' collection…"),a.httpInterface.get(r.collectionUri).then(t,i);else{if(!r.entityName||!r.entityUri)return a.q.when([]);a.__entityCacheRaw={},a.httpInterface.get(r.entityUri).then(n,o)}return a.q.all([a.dataAvailable,a.objectsAvailable]).then(function(){return a.entityCache})},i.prototype.read=function(e,t){function i(e){if(!e.data[r.entityName])throw new Error("The response from the server was not in the expected format. It should have a member named '"+r.entityName+"'.");var t=o.deserializer(e.data[r.entityName]);return o.__updateCacheWithEntity(t),t}function n(t){if(o.logInterface.error(o.logPrefix+"Unable to retrieve entity with ID '"+e+"' from the server.",t),o.scope.$emit("absyncError",t),o.throwFailures)throw t}var o=this;if(t=t===!0,o.logInterface.debug(o.logPrefix+"Requesting entity '"+e+"' (forceReload:"+t+")…"),!t)for(var a=0,c=o.entityCache[0];a<o.entityCache.length;++a,c=o.entityCache[a])if(c.id===e)return o.logInterface.debug(o.logPrefix+"Requested entity '"+e+"' is served from cache."),o.q.when(c);return o.logInterface.debug(o.logPrefix+"Requested entity '"+e+"' is fetched from backend."),o.__requestEntity(e).then(i,n)},i.prototype.__requestEntity=function(e){function t(e,t){return delete i.__requestCache[e],t}var i=this;if(i.enableRequestCache&&i.__requestCache&&i.__requestCache[e])return i.logInterface.debug(i.logPrefix+"Entity request '"+e+"' served from request cache."),i.__requestCache[e];var n=r.entityUri+(e?"/"+e:""),o=i.httpInterface.get(n).then(t.bind(i,e));return i.enableRequestCache&&i.__requestCache&&(i.__requestCache[e]=o),o},i.prototype.update=function(e){var t=this,i=t.reduceComplex(e),a=t.serializer(i),c={};return c[r.entityName]=a,"undefined"!=typeof e.id?t.httpInterface.put(r.entityUri+"/"+e.id,c).then(n.bind(t),o.bind(t)):t.httpInterface.post(r.collectionUri,c).then(n.bind(t),o.bind(t))},i.prototype.patch=function(e){var t=this,i=t.reduceComplex(e),a=t.serializer(i),c={};if(c[r.entityName]=a,"undefined"!=typeof e.id)return t.httpInterface.patch(r.entityUri+"/"+e.id,c).then(n.bind(t),o.bind(t));throw new Error("Attempted to patch an entity that was never stored on the server.")},i.prototype.create=i.prototype.update,i.prototype["delete"]=function(e){function t(e){return n.__removeEntityFromCache(o)}function i(e){if(n.logInterface.error(e.data),n.scope.$emit("absyncError",e),n.throwFailures)throw e}var n=this,o=e.id;return n.httpInterface["delete"](r.entityUri+"/"+o).then(t)["catch"](i)},i.prototype.__updateCacheWithEntity=function(e){var t=this;if(t.logInterface.info(t.logPrefix+"Updating entity '"+(e.id||t.name)+"' in cache…",e),!Array.isArray(t.entityCache))return t.scope.$broadcast("beforeEntityUpdated",{service:t,cache:t.entityCache,entity:t.entityCache,updated:e}),"function"==typeof t.entityCache.copyFrom?t.entityCache.copyFrom(e):angular.extend(t.entityCache,e),void t.scope.$broadcast("entityUpdated",{service:t,cache:t.entityCache,entity:t.entityCache});for(var r=!1,i=0,n=t.entityCache[0];i<t.entityCache.length;++i,n=t.entityCache[i])if(n.id==e.id){t.scope.$broadcast("beforeEntityUpdated",{service:t,cache:t.entityCache,entity:t.entityCache[i],updated:e});var o=t.entityCache[i];"function"==typeof o.copyFrom?o.copyFrom(e):angular.extend(o,e),r=!0,t.scope.$broadcast("entityUpdated",{service:t,cache:t.entityCache,entity:t.entityCache[i]});break}r||(t.scope.$broadcast("beforeEntityNew",{service:t,cache:t.entityCache,entity:e}),t.entityCache.push(e),t.scope.$broadcast("entityNew",{service:t,cache:t.entityCache,entity:e}))},i.prototype.__removeEntityFromCache=function(e){for(var t=this,r=0,i=t.entityCache[0];r<t.entityCache.length;++r,i=t.entityCache[r])if(i.id==e){t.scope.$broadcast("beforeEntityRemoved",{service:t,cache:t.entityCache,entity:i}),t.entityCache.splice(r,1),t.scope.$broadcast("entityRemoved",{service:t,cache:t.entityCache,entity:i});break}},i.prototype.lookupTableById=function(){for(var e=this,t=[],r=0;r<e.entityCache.length;++r)t[e.entityCache[r].id]=e.entityCache[r];return t},i.prototype.reduceComplex=function(e,t){var r=this,i=t?[]:{};for(var n in e)e.hasOwnProperty(n)&&(Array.isArray(e[n])?i[n]=r.reduceComplex(e[n],!0):e[n]&&e[n].id?i[n]=e[n].id:i[n]=e[n]);return i},i.prototype.populateComplex=function(e,t,r,i){function n(n,o){function c(r){return e[t][o]=r,e}if("string"!=typeof e[t][o]){if(!i||"object"!=typeof e[t][o]||"string"!=typeof e[t][o].id)return a.q.when(!1);e[t][o]=e[t][o].id}return r.read(e[t][o]).then(c)}function o(r){e[t]=r}var a=this;if(Array.isArray(e[t])){var c=e[t].map(n);return a.q.all(c)}if("string"!=typeof e[t]){if(!i||"object"!=typeof e[t]||"string"!=typeof e[t].id)return a.q.when(!1);e[t]=e[t].id}return r.read(e[t]).then(o)},i}function t(e){return e}angular.module("absync").constant("absyncCache",e)}(),function(){"use strict";function e(){return t}function t(e,t,r,i,n,o,a,c){this.model=e,this.collectionUri=t,this.entityUri=r;var s=e.prototype.constructor.name.toLowerCase();this.collectionName=i||s+"s",this.entityName=n||s,this.deserialize=o||void 0,this.serialize=a||void 0,this.injector=c||void 0}angular.module("absync").service("AbsyncServiceConfiguration",e)}(); | ||
!function(){"use strict";angular.module("absync",[])}(),function(){"use strict";function e(e,n){return new t(e,n)}function t(e,t){var n=this;n.__provide=e,n.__absyncCache=t,n.__ioSocket=null,n.__registerLater=[],n.__collections={},n.__entities={}}function n(e){this.__absyncProvider=e}e.$inject=["$provide","absyncCache"],angular.module("absync").provider("absync",e),t.prototype.configure=function(e,t){var n=this,r=e.socket||e,i=io&&io.Socket&&r instanceof io.Socket;if("function"==typeof r)n.__ioSocket=r();else{if(!i)throw new Error("configure() expects input to be a function or a socket.io Socket instance.");n.__ioSocket=r}n.__registerLater.length&&(n.__registerLater.forEach(n.__registerListener.bind(n)),n.__registerLater=[]),n.debug=t||!1},t.prototype.__registerListener=function(e){var t=this;t.$get().__handleEntityEvent(e.eventName,e.callback)},t.prototype.collection=function(e,t){var n=this;if(n.__collections[e])throw new Error("A collection with the name '"+e+"' was already requested. Names for collections must be unique.");if(n.__entities[e])throw new Error("An entity with the name '"+e+"' was already requested. Names for collections must be unique and can't be shared with entities.");t.debug="undefined"==typeof t.debug?n.debug:t.debug,n.__collections[e]=n.__absyncCache(e,t),n.__provide.service(e,n.__collections[e])},t.prototype.entity=function(e,t){var n=this;if(n.__entities[e])throw new Error("An entity with the name '"+e+"' was already requested. Names for entities must be unique.");if(n.__collections[e])throw new Error("A collection with the name '"+e+"' was already requested. Names for entities must be unique and can't be shared with collections.");t.debug="undefined"==typeof t.debug?n.debug:t.debug,n.__entities[e]=n.__absyncCache(e,t),n.__provide.service(e,n.__entities[e])},t.prototype.$get=function(){return new n(this)},n.prototype.configure=function(e,t){var n=this.__absyncProvider;n.configure(e,t||!1)},n.prototype.on=function(e,t){var n=this.__absyncProvider,r=this;return n.__ioSocket?r.__handleEntityEvent(e,t):n.__registerLater.length>8192?null:(n.__registerLater.push({eventName:e,callback:t}),null)},n.prototype.__handleEntityEvent=function(e,t){var n=this.__absyncProvider;return n.__ioSocket.on(e,t),function(){n.__ioSocket.removeListener(e,t)}},n.prototype.emit=function(e,t,n){var r=this.__absyncProvider;if(!r.__ioSocket)throw new Error("socket.io is not initialized.");r.__ioSocket.emit(e,t,function(){n&&n.apply(r.__ioSocket,arguments)})}}(),function(){"use strict";function e(e,n){function r(r,i,o,a,c,s,l){var h=this,d=n.injector||i,u=d.has(n.model);if(!u)throw new Error("Unable to construct the '"+e+"' service, because the referenced model '"+n.model+"' is not available for injection.");var y="string"==typeof n.model?d.get(n.model):n.model,f=y.serialize||n.serialize||t,_=y.deserialize||n.deserialize||t;h.name=e,h.configuration=n,h.entityCache=n.collectionName?[]:{},h.__entityCacheRaw=null,h.enableRequestCache=!0,h.__requestCache={},h.__dataAvailableDeferred=a.defer(),h.__objectsAvailableDeferred=a.defer(),h.dataAvailable=h.__dataAvailableDeferred.promise,h.objectsAvailable=h.__objectsAvailableDeferred.promise,h.httpInterface=r,h.logInterface=n.debug?o:l,h.scope=c,h.q=a,h.logPrefix="absync:"+e.toLocaleUpperCase()+" ",h.forceEarlyCacheUpdate=!1,h.throwFailures=!1,h.serializer=f,h.deserializer=_,s.on(n.entityName,h.__onEntityOnWebsocket.bind(h)),n.collectionName&&s.on(n.collectionName,h.__onCollectionOnWebsocket.bind(h)),c.$on(n.entityName,h.__onEntityReceived.bind(h)),n.collectionName&&c.$on(n.collectionName,h.__onCollectionReceived.bind(h)),h.dataAvailable.then(h.__onDataAvailable.bind(h)),h.logInterface.info(h.logPrefix+"service was instantiated.")}function i(e){var t=this;if(e.data[n.entityName]){var r=t.deserializer(e.data[n.entityName]);return t.forceEarlyCacheUpdate&&t.__updateCacheWithEntity(r),r}throw new Error("The response from the server was not in the expected format. It should have a member named '"+n.entityName+"'.")}function o(e){var t=this;if(t.logInterface.error(t.logPrefix+"Unable to store entity on the server.",e),t.logInterface.error(e),t.scope.$emit("absyncError",e),t.throwFailures)throw e}return r.$inject=["$http","$injector","$log","$q","$rootScope","absync","absyncNoopLog"],r.prototype.__onEntityOnWebsocket=function(e){var t=this;t.scope.$broadcast(n.entityName,e[n.entityName])},r.prototype.__onCollectionOnWebsocket=function(e){var t=this;t.scope.$broadcast(n.collectionName,e[n.collectionName])},r.prototype.__onDataAvailable=function(e){function t(e){r.entityCache.push(r.deserializer(e))}var r=this;if(Array.isArray(r.entityCache))e[n.collectionName].forEach(t),r.__objectsAvailableDeferred.resolve(r.entityCache),r.scope.$broadcast("collectionNew",{service:r,cache:r.entityCache});else{var i=r.deserializer(e[n.entityName]);r.__updateCacheWithEntity(i),r.__objectsAvailableDeferred.resolve(r.entityCache)}},r.prototype.__onEntityReceived=function(e,t){var n=this,r=t;1===Object.keys(r).length&&r.hasOwnProperty("id")?(n.logInterface.info(n.logPrefix+"Entity was deleted from the server. Updating cache…"),n.__removeEntityFromCache(r.id)):(n.logInterface.debug(n.logPrefix+"Entity was updated on the server. Updating cache…"),n.__updateCacheWithEntity(n.deserializer(r)))},r.prototype.__onCollectionReceived=function(e,t){function n(e){var t=r.deserializer(e);r.__updateCacheWithEntity(t)}var r=this,i=t;r.entityCache.length=0,i.forEach(n)},r.prototype.ensureLoaded=function(e){function t(e){if(!e.data[n.collectionName])throw new Error("The response from the server was not in the expected format. It should have a member named '"+n.collectionName+"'.");a.__entityCacheRaw=e.data,a.__dataAvailableDeferred.resolve(e.data)}function r(e){if(a.logInterface.error(a.logPrefix+"Unable to retrieve the collection from the server.",e),a.__entityCacheRaw=null,a.scope.$emit("absyncError",e),a.throwFailures)throw e}function i(e){if(!e.data[n.entityName])throw new Error("The response from the server was not in the expected format. It should have a member named '"+n.entityName+"'.");a.__entityCacheRaw=e.data,a.__dataAvailableDeferred.resolve(e.data)}function o(e){if(a.logInterface.error(a.logPrefix+"Unable to retrieve the entity from the server.",e),a.__entityCacheRaw=null,a.scope.$emit("absyncError",e),a.throwFailures)throw e}var a=this;if(e=e===!0,null===a.__entityCacheRaw||e)if(a.__entityCacheRaw=[],n.collectionName&&n.collectionUri)a.logInterface.info(a.logPrefix+"Retrieving '"+n.collectionName+"' collection…"),a.httpInterface.get(n.collectionUri).then(t,r);else{if(!n.entityName||!n.entityUri)return a.q.when([]);a.__entityCacheRaw={},a.httpInterface.get(n.entityUri).then(i,o)}return a.q.all([a.dataAvailable,a.objectsAvailable]).then(function(){return a.entityCache})},r.prototype.read=function(e,t){function r(e){if(!e.data[n.entityName])throw new Error("The response from the server was not in the expected format. It should have a member named '"+n.entityName+"'.");var t=o.deserializer(e.data[n.entityName]);return o.__updateCacheWithEntity(t),t}function i(t){if(o.logInterface.error(o.logPrefix+"Unable to retrieve entity with ID '"+e+"' from the server.",t),o.scope.$emit("absyncError",t),o.throwFailures)throw t}var o=this;if(t=t===!0,o.logInterface.debug(o.logPrefix+"Requesting entity '"+e+"' (forceReload:"+t+")…"),!t)for(var a=0,c=o.entityCache[0];a<o.entityCache.length;++a,c=o.entityCache[a])if(c.id===e)return o.logInterface.debug(o.logPrefix+"Requested entity '"+e+"' is served from cache."),o.q.when(c);return o.logInterface.debug(o.logPrefix+"Requested entity '"+e+"' is fetched from backend."),o.__requestEntity(e).then(r,i)},r.prototype.__requestEntity=function(e){function t(e,t){return delete r.__requestCache[e],t}var r=this;if(r.enableRequestCache&&r.__requestCache&&r.__requestCache[e])return r.logInterface.debug(r.logPrefix+"Entity request '"+e+"' served from request cache."),r.__requestCache[e];var i=n.entityUri+(e?"/"+e:""),o=r.httpInterface.get(i).then(t.bind(r,e));return r.enableRequestCache&&r.__requestCache&&(r.__requestCache[e]=o),o},r.prototype.update=function(e){var t=this,r=t.reduceComplex(e),a=t.serializer(r),c={};return c[n.entityName]=a,"undefined"!=typeof e.id?t.httpInterface.put(n.entityUri+"/"+e.id,c).then(i.bind(t),o.bind(t)):t.httpInterface.post(n.collectionUri,c).then(i.bind(t),o.bind(t))},r.prototype.patch=function(e){var t=this,r=t.reduceComplex(e),a=t.serializer(r),c={};if(c[n.entityName]=a,"undefined"!=typeof e.id)return t.httpInterface.patch(n.entityUri+"/"+e.id,c).then(i.bind(t),o.bind(t));throw new Error("Attempted to patch an entity that was never stored on the server.")},r.prototype.create=r.prototype.update,r.prototype["delete"]=function(e){function t(e){return i.__removeEntityFromCache(o)}function r(e){if(i.logInterface.error(e.data),i.scope.$emit("absyncError",e),i.throwFailures)throw e}var i=this,o=e.id;return i.httpInterface["delete"](n.entityUri+"/"+o).then(t)["catch"](r)},r.prototype.__updateCacheWithEntity=function(e){var t=this;if(t.logInterface.info(t.logPrefix+"Updating entity '"+(e.id||t.name)+"' in cache…",e),!Array.isArray(t.entityCache))return t.scope.$broadcast("beforeEntityUpdated",{service:t,cache:t.entityCache,entity:t.entityCache,updated:e}),"function"==typeof t.entityCache.copyFrom?t.entityCache.copyFrom(e):angular.extend(t.entityCache,e),void t.scope.$broadcast("entityUpdated",{service:t,cache:t.entityCache,entity:t.entityCache});for(var n=!1,r=0,i=t.entityCache[0];r<t.entityCache.length;++r,i=t.entityCache[r])if(i.id==e.id){t.scope.$broadcast("beforeEntityUpdated",{service:t,cache:t.entityCache,entity:t.entityCache[r],updated:e});var o=t.entityCache[r];"function"==typeof o.copyFrom?o.copyFrom(e):angular.extend(o,e),n=!0,t.scope.$broadcast("entityUpdated",{service:t,cache:t.entityCache,entity:t.entityCache[r]});break}n||(t.scope.$broadcast("beforeEntityNew",{service:t,cache:t.entityCache,entity:e}),t.entityCache.push(e),t.scope.$broadcast("entityNew",{service:t,cache:t.entityCache,entity:e}))},r.prototype.__removeEntityFromCache=function(e){for(var t=this,n=0,r=t.entityCache[0];n<t.entityCache.length;++n,r=t.entityCache[n])if(r.id==e){t.scope.$broadcast("beforeEntityRemoved",{service:t,cache:t.entityCache,entity:r}),t.entityCache.splice(n,1),t.scope.$broadcast("entityRemoved",{service:t,cache:t.entityCache,entity:r});break}},r.prototype.lookupTableById=function(){for(var e=this,t=[],n=0;n<e.entityCache.length;++n)t[e.entityCache[n].id]=e.entityCache[n];return t},r.prototype.reduceComplex=function(e,t){var n=this,r=t?[]:{};for(var i in e)e.hasOwnProperty(i)&&(Array.isArray(e[i])?r[i]=n.reduceComplex(e[i],!0):e[i]&&e[i].id?r[i]=e[i].id:r[i]=e[i]);return r},r.prototype.populateComplex=function(e,t,n,r){function i(i,o){function c(n){return e[t][o]=n,e}if("string"!=typeof e[t][o]){if(!r||"object"!=typeof e[t][o]||"string"!=typeof e[t][o].id)return a.q.when(!1);e[t][o]=e[t][o].id}return n.read(e[t][o]).then(c)}function o(n){e[t]=n}var a=this;if(Array.isArray(e[t])){var c=e[t].map(i);return a.q.all(c)}if("string"!=typeof e[t]){if(!r||"object"!=typeof e[t]||"string"!=typeof e[t].id)return a.q.when(!1);e[t]=e[t].id}return n.read(e[t]).then(o)},r}function t(e){return e}angular.module("absync").constant("absyncCache",e)}(),function(){"use strict";function e(){return t}function t(e,t,n,r,i,o,a,c,s){this.model=e,this.collectionUri=t,this.entityUri=n;var l=e.prototype.constructor.name.toLowerCase();this.collectionName=r||l+"s",this.entityName=i||l,this.deserialize=o||void 0,this.serialize=a||void 0,this.injector=c||void 0,this.debug=s||!1}angular.module("absync").service("AbsyncServiceConfiguration",e)}(),function(){"use strict";angular.module("absync").constant("absyncNoopLog",{debug:angular.noop,info:angular.noop,error:angular.noop})}(); | ||
//# sourceMappingURL=maps/absync.concat.min.js.map |
{ | ||
"name": "absync", | ||
"version": "2.5.0", | ||
"version": "2.6.0", | ||
"description": "absync", | ||
@@ -5,0 +5,0 @@ "main": "dist/development/absync.concat.js", |
@@ -37,3 +37,3 @@ /* globals angular, io */ | ||
// Store a reference to the provide provider. | ||
self.__provide = $provide; | ||
self.__provide = $provide; | ||
// Store a reference to the cache service constructor. | ||
@@ -66,8 +66,9 @@ self.__absyncCache = absyncCache; | ||
* Can also be an object with a "socket" member that provides either of the above. | ||
* @param {Boolean} [debug=false] Enable additional debugging output. | ||
*/ | ||
AbsyncProvider.prototype.configure = function AbsyncProvider$configure( configuration ) { | ||
AbsyncProvider.prototype.configure = function AbsyncProvider$configure( configuration, debug ) { | ||
var self = this; | ||
// If the configuration has a "socket" member, unpack it. | ||
var socket = configuration.socket || configuration; | ||
var socket = configuration.socket || configuration; | ||
// Determine if the socket is an io.Socket. | ||
@@ -94,2 +95,4 @@ var isSocket = io && io.Socket && socket instanceof io.Socket; | ||
} | ||
self.debug = debug || false; | ||
}; | ||
@@ -120,2 +123,5 @@ | ||
// If no debug flag was set, use the value from the core absync provider. | ||
configuration.debug = typeof configuration.debug === "undefined" ? self.debug : configuration.debug; | ||
// Register the service configuration. | ||
@@ -148,2 +154,5 @@ // __absyncCache will return a constructor for a service with the given configuration. | ||
// If no debug flag was set, use the value from the core absync provider. | ||
configuration.debug = typeof configuration.debug === "undefined" ? self.debug : configuration.debug; | ||
// Register the service configuration. | ||
@@ -183,6 +192,7 @@ // __absyncCache will return a constructor for a service with the given configuration. | ||
* @param {io.Socket|Function|Object} configuration The socket.io instance to use. | ||
* @param {Boolean} [debug=false] Enable additional debug output. | ||
*/ | ||
AbsyncService.prototype.configure = function AbsyncService$configure( configuration ) { | ||
AbsyncService.prototype.configure = function AbsyncService$configure( configuration, debug ) { | ||
var _absyncProvider = this.__absyncProvider; | ||
_absyncProvider.configure( configuration ); | ||
_absyncProvider.configure( configuration, debug || false ); | ||
}; | ||
@@ -189,0 +199,0 @@ |
@@ -36,6 +36,7 @@ /* globals angular */ | ||
* @param {AbsyncService} absync | ||
* @param {Object} absyncNoopLog A log interface that does nothing. | ||
* @returns {CacheService} | ||
* @ngInject | ||
*/ | ||
function CacheService( $http, $injector, $log, $q, $rootScope, absync ) { | ||
function CacheService( $http, $injector, $log, $q, $rootScope, absync, absyncNoopLog ) { | ||
var self = this; | ||
@@ -84,3 +85,3 @@ | ||
// Do the same for our logger. | ||
self.logInterface = $log; | ||
self.logInterface = configuration.debug ? $log : absyncNoopLog; | ||
// The scope on which we broadcast all our relevant events. | ||
@@ -87,0 +88,0 @@ self.scope = $rootScope; |
@@ -32,5 +32,6 @@ /* globals angular */ | ||
* Usually, you don't need to provide an alternative here. | ||
* @param {Boolean} [debug=false] Should additional debugging output be enabled? | ||
* @constructor | ||
*/ | ||
function AbsyncServiceConfiguration( model, collectionUri, entityUri, collectionName, entityName, deserialize, serialize, injector ) { | ||
function AbsyncServiceConfiguration( model, collectionUri, entityUri, collectionName, entityName, deserialize, serialize, injector, debug ) { | ||
this.model = model; | ||
@@ -48,2 +49,4 @@ this.collectionUri = collectionUri; | ||
this.injector = injector || undefined; | ||
this.debug = debug || false; | ||
} |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
860918
40
9355