angular-promise-cache
Advanced tools
Comparing version 0.0.12 to 0.1.0
@@ -24,5 +24,11 @@ /** | ||
*/ | ||
(function(window, angular, undefined) { | ||
(function (root, factory) { | ||
if(typeof define === 'function' && define.amd) { | ||
define([root, 'angular'], factory); | ||
} else if(typeof module === 'object' && module.exports) { | ||
module.exports = factory(root, require('angular')); | ||
} else { | ||
root['angular-promise-cache'] = factory(root, root['angular']); | ||
} | ||
}(typeof window !== "undefined" ? window : this, function(window, angular) { | ||
'use strict'; | ||
@@ -37,8 +43,5 @@ | ||
dateReferences = {}, | ||
ls = window.localStorage || { | ||
setItem: function() { }, | ||
removeItem: function() { }, | ||
getItem: function() { } | ||
}, | ||
hasOwnProperty = Object.prototype.hasOwnProperty, | ||
toString = Object.prototype.toString, | ||
lsInaccessible = false, | ||
store = function(key, complexValue) { | ||
@@ -56,3 +59,3 @@ ls.setItem(key, JSON.stringify(complexValue)); | ||
catch (e) { | ||
console.warn('Unable to parse json response from local storage', str); | ||
!lsInaccessible && console.warn('Unable to parse json response from local storage', str); | ||
} | ||
@@ -92,2 +95,16 @@ return str; | ||
// This can be null/undefined or throw access exceptions | ||
var ls = null; | ||
try { | ||
ls = window.localStorage; | ||
} catch (e) { | ||
// Do nothing - probably access denied | ||
lsInaccessible = true; | ||
} | ||
ls = ls || { | ||
setItem: function() { }, | ||
removeItem: function() { }, | ||
getItem: function() { } | ||
}; | ||
var promiseCacheFunction = function(opts) { | ||
@@ -213,16 +230,37 @@ // TODO: BETTER ERROR HANDLING | ||
promiseCacheFunction.remove = function(key, keepInLS) { | ||
if (!memos[key]) return; | ||
var opts = memos[key].opts; | ||
dateReferences[key] = new Date().getTime(); | ||
if (!keepInLS && isLsEnabled(opts)) { | ||
remove(getLsKey(opts, key)); | ||
// v0.0.13 | ||
var keys = []; | ||
if (typeof key === 'object') { | ||
var toStr = toString.call(key); | ||
switch (toString.call(key)) { | ||
case '[object RegExp]': | ||
keys = Object.keys(memos).filter(function(_key) { | ||
return key.test(_key); | ||
}); | ||
break; | ||
case '[object Array]': | ||
keys = key.slice(0); | ||
break; | ||
default: | ||
throw 'Unsupported parameter to .remove(). Acceptable paramters are: string, array, regexp'; | ||
} | ||
} | ||
delete memos[key]; | ||
$rootScope.$broadcast('angular-promise-cache.removed', key); | ||
else { | ||
keys.push(key); | ||
} | ||
keys.forEach(function(key) { | ||
if (!memos[key]) return; | ||
var opts = memos[key].opts; | ||
dateReferences[key] = new Date().getTime(); | ||
if (!keepInLS && isLsEnabled(opts)) { | ||
remove(getLsKey(opts, key)); | ||
} | ||
delete memos[key]; | ||
$rootScope.$broadcast('angular-promise-cache.removed', key); | ||
}); | ||
}; | ||
promiseCacheFunction.removeAll = function(keepInLS) { | ||
Object.keys(memos).forEach(function(key) { | ||
promiseCacheFunction.remove(key, keepInLS); | ||
}); | ||
promiseCacheFunction.remove(Object.keys(memos), keepInLS); | ||
}; | ||
@@ -233,2 +271,2 @@ | ||
})(window, window.angular); | ||
})); |
@@ -24,2 +24,2 @@ /** | ||
*/ | ||
!function(e,r){"use strict";r.module("angular-promise-cache",[]).factory("promiseCache",["$q","$rootScope",function(t,n){var o={},a=5e3,c="$",i=/\s+/g,s={},u=e.localStorage||{setItem:function(){},removeItem:function(){},getItem:function(){}},l=Object.prototype.hasOwnProperty,p=function(e,r){u.setItem(e,JSON.stringify(r))},f=function(e){u.removeItem(e)},m=function(e){var r=u.getItem(e);try{r=JSON.parse(r)}catch(t){console.warn("Unable to parse json response from local storage",r)}return r},g=function(e,r){return parseInt(e.split(c)[1])||s[r]},h=function(e){return c+e+c},v=function(e){return e.key||e.promise.toString().replace(i,"")},y=function(e){return!!e.localStorageEnabled},d=function(e,r){return e.localStorageKey||r},b=function(e,r){var t=+new Date+"",n=function(){var o=n.cache,a=r?r.apply(this,arguments):t+arguments[0];return l.call(o,a)?o[a]:o[a]=e.apply(this,arguments)};return n.cache={},n},w=function(e){var c,i,u,w,I=e.promise,S=parseInt(e.ttl)||a,$=!!e.bustCache,O=e.expireOnFailure,j=e.args,x=(new Date).getTime(),E=v(e),D=y(e),k=d(e,E),C=m(k);return s[E]=s[E]||x,D&&(C&&"object"==typeof C&&l.call(C,"resolver")&&l.call(C,"response")?(c=g(C.resolver,E),u=c+S-x,o[E]=b(I,function(){return h(c)}),i=o[E].cache||{},w=t.defer(),w.resolve(C.response),i[h(c)]=w.promise,o[E].cache=i):C={}),l.call(o,E)?(o[E].opts=e,o[E].cache=function(){var e,r,t,a={},i=o[E].cache,u=!!o[E].forceExpiration;for(e in i)r=g(e,E),t=$||u||S>0&&x>r+S,t?(n.$broadcast("angular-promise-cache.expired",e,E),s[E]=x,D&&(c=s[E],f(k))):(n.$broadcast("angular-promise-cache.active",e,r+S,E),a[e]=i[e]);return o[E].forceExpiration=!1,a}()):(o[E]=b(I,function(){return h(s[E])}),o[E].opts=e,n.$broadcast("angular-promise-cache.new",h(s[E]),E)),o[E].apply(this,j||[]).then(function(e){return D&&(C.response=arguments[0],C.resolver=h(c||s[E]),p(k,C)),e},function(e){return r.isFunction(O)&&O.apply(this,arguments)&&(o[E].forceExpiration=!0),t.reject(e)})};return w.remove=function(e,r){if(o[e]){var t=o[e].opts;s[e]=(new Date).getTime(),!r&&y(t)&&f(d(t,e)),delete o[e],n.$broadcast("angular-promise-cache.removed",e)}},w.removeAll=function(e){Object.keys(o).forEach(function(r){w.remove(r,e)})},w}])}(window,window.angular); | ||
!function(e,r){"function"==typeof define&&define.amd?define([e,"angular"],r):"object"==typeof module&&module.exports?module.exports=r(e,require("angular")):e["angular-promise-cache"]=r(e,e.angular)}("undefined"!=typeof window?window:this,function(e,r){"use strict";r.module("angular-promise-cache",[]).factory("promiseCache",["$q","$rootScope",function(t,n){var o={},a=5e3,c="$",i=/\s+/g,s={},u=Object.prototype.hasOwnProperty,l=Object.prototype.toString,p=!1,f=function(e,r){j.setItem(e,JSON.stringify(r))},m=function(e){j.removeItem(e)},g=function(e){var r=j.getItem(e);try{r=JSON.parse(r)}catch(t){!p&&console.warn("Unable to parse json response from local storage",r)}return r},h=function(e,r){return parseInt(e.split(c)[1])||s[r]},d=function(e){return c+e+c},y=function(e){return e.key||e.promise.toString().replace(i,"")},v=function(e){return!!e.localStorageEnabled},b=function(e,r){return e.localStorageKey||r},w=function(e,r){var t=+new Date+"",n=function(){var o=n.cache,a=r?r.apply(this,arguments):t+arguments[0];return u.call(o,a)?o[a]:o[a]=e.apply(this,arguments)};return n.cache={},n},j=null;try{j=e.localStorage}catch(x){p=!0}j=j||{setItem:function(){},removeItem:function(){},getItem:function(){}};var I=function(e){var c,i,l,p,j=e.promise,x=parseInt(e.ttl)||a,I=!!e.bustCache,O=e.expireOnFailure,S=e.args,$=(new Date).getTime(),E=y(e),k=v(e),A=b(e,E),D=g(A);return s[E]=s[E]||$,k&&(D&&"object"==typeof D&&u.call(D,"resolver")&&u.call(D,"response")?(c=h(D.resolver,E),l=c+x-$,o[E]=w(j,function(){return d(c)}),i=o[E].cache||{},p=t.defer(),p.resolve(D.response),i[d(c)]=p.promise,o[E].cache=i):D={}),u.call(o,E)?(o[E].opts=e,o[E].cache=function(){var e,r,t,a={},i=o[E].cache,u=!!o[E].forceExpiration;for(e in i)r=h(e,E),t=I||u||x>0&&$>r+x,t?(n.$broadcast("angular-promise-cache.expired",e,E),s[E]=$,k&&(c=s[E],m(A))):(n.$broadcast("angular-promise-cache.active",e,r+x,E),a[e]=i[e]);return o[E].forceExpiration=!1,a}()):(o[E]=w(j,function(){return d(s[E])}),o[E].opts=e,n.$broadcast("angular-promise-cache.new",d(s[E]),E)),o[E].apply(this,S||[]).then(function(e){return k&&(D.response=arguments[0],D.resolver=d(c||s[E]),f(A,D)),e},function(e){return r.isFunction(O)&&O.apply(this,arguments)&&(o[E].forceExpiration=!0),t.reject(e)})};return I.remove=function(e,r){var t=[];if("object"==typeof e){l.call(e);switch(l.call(e)){case"[object RegExp]":t=Object.keys(o).filter(function(r){return e.test(r)});break;case"[object Array]":t=e.slice(0);break;default:throw"Unsupported parameter to .remove(). Acceptable paramters are: string, array, regexp"}}else t.push(e);t.forEach(function(e){if(o[e]){var t=o[e].opts;s[e]=(new Date).getTime(),!r&&v(t)&&m(b(t,e)),delete o[e],n.$broadcast("angular-promise-cache.removed",e)}})},I.removeAll=function(e){I.remove(Object.keys(o),e)},I}])}); |
@@ -398,26 +398,2 @@ 'use strict'; | ||
// v0.0.7 | ||
it('should support remove', function() { | ||
var calls = 0; | ||
function getPromise() { | ||
var deferred = q.defer(); | ||
deferred.resolve(++calls); | ||
return deferred.promise; | ||
} | ||
var one = { key: 'test', promise: getPromise, localStorageEnabled: true }; | ||
apc(one).then(function(idx) { expect(idx).toBe(1); }); | ||
scope.$apply(); | ||
apc.remove('test'); | ||
scope.$apply(); | ||
apc(one).then(function(idx) { expect(idx).toBe(2); }); | ||
expect(window.localStorage.getItem(one.key)).toBeNull(); | ||
scope.$apply(); | ||
apc.remove('test', true); | ||
apc(one).then(function(idx) { expect(idx).toBe(3); }); | ||
expect(window.localStorage.getItem(one.key)).not.toBeNull(); | ||
}); | ||
// v0.0.10 | ||
@@ -445,2 +421,108 @@ it('should support removeAll', function() { | ||
}); | ||
// v0.0.13 | ||
describe('remove()', function() { | ||
it('should support a string', function() { | ||
var calls = 0; | ||
function getPromise() { | ||
var deferred = q.defer(); | ||
deferred.resolve(++calls); | ||
return deferred.promise; | ||
} | ||
var one = { key: 'test', promise: getPromise, localStorageEnabled: true }; | ||
apc(one).then(function(idx) { expect(idx).toBe(1); }); | ||
scope.$apply(); | ||
apc.remove('test'); | ||
scope.$apply(); | ||
apc(one).then(function(idx) { expect(idx).toBe(2); }); | ||
expect(window.localStorage.getItem(one.key)).toBeNull(); | ||
scope.$apply(); | ||
apc.remove('test', true); | ||
apc(one).then(function(idx) { expect(idx).toBe(3); }); | ||
expect(window.localStorage.getItem(one.key)).not.toBeNull(); | ||
// Clear for the next tests | ||
apc.remove('test'); | ||
}); | ||
it('should support an array', function() { | ||
var calls = 0; | ||
function getPromise() { | ||
var deferred = q.defer(); | ||
deferred.resolve(++calls); | ||
return deferred.promise; | ||
} | ||
var one = { key: 'test', promise: getPromise, localStorageEnabled: true }; | ||
var two = { key: 'test2', promise: getPromise, localStorageEnabled: true }; | ||
apc(one).then(function(idx) { expect(idx).toBe(1); }); | ||
apc(two).then(function(idx) { expect(idx).toBe(2); }); | ||
scope.$apply(); | ||
apc.remove(['test', 'test2']); | ||
scope.$apply(); | ||
apc(one).then(function(idx) { expect(idx).toBe(3); }); | ||
apc(two).then(function(idx) { expect(idx).toBe(4); }); | ||
expect(window.localStorage.getItem(one.key)).toBeNull(); | ||
scope.$apply(); | ||
apc.remove(['test', 'test2'], true); | ||
apc(one).then(function(idx) { expect(idx).toBe(5); }); | ||
apc(two).then(function(idx) { expect(idx).toBe(6); }); | ||
expect(window.localStorage.getItem(one.key)).not.toBeNull(); | ||
// Clear for the next tests | ||
apc.remove(['test', 'test2']); | ||
}); | ||
it('should support a regular expression', function() { | ||
var calls = 0; | ||
function getPromise() { | ||
var deferred = q.defer(); | ||
deferred.resolve(++calls); | ||
return deferred.promise; | ||
} | ||
var one = { key: 'test5', promise: getPromise, localStorageEnabled: true }; | ||
apc(one).then(function(idx) { expect(idx).toBe(1); }); | ||
scope.$apply(); | ||
apc.remove(/test([0-9]{1})/); | ||
scope.$apply(); | ||
apc(one).then(function(idx) { expect(idx).toBe(2); }); | ||
expect(window.localStorage.getItem(one.key)).toBeNull(); | ||
scope.$apply(); | ||
apc.remove(/test([0-9]{1})/, true); | ||
apc(one).then(function(idx) { expect(idx).toBe(3); }); | ||
expect(window.localStorage.getItem(one.key)).not.toBeNull(); | ||
// Clear for the next tests | ||
apc.remove(/test([0-9]{1})/); | ||
}); | ||
it('should support throw an error for supported parameter types', function() { | ||
function getPromise() { | ||
var deferred = q.defer(); | ||
deferred.resolve(); | ||
return deferred.promise; | ||
} | ||
function remove() { | ||
apc.remove({ foo: 'bar' }); | ||
} | ||
var one = { key: 'test', promise: getPromise, localStorageEnabled: true }; | ||
apc(one); | ||
scope.$apply(); | ||
expect(remove).toThrow(); | ||
}); | ||
}); | ||
}); |
{ | ||
"name": "angular-promise-cache", | ||
"version": "0.0.12", | ||
"version": "0.1.0", | ||
"main": "angular-promise-cache.js", | ||
@@ -5,0 +5,0 @@ "devDependencies": { |
@@ -5,2 +5,3 @@ var gulp = require('gulp'); | ||
var karma = require('gulp-karma'); | ||
var Server = require('karma').Server; | ||
@@ -14,10 +15,7 @@ gulp.task('build', function() { | ||
gulp.task('test', function() { | ||
return gulp.src([ | ||
'bower_components/angular/angular.min.js', | ||
'bower_components/angular-mocks/angular-mocks.js', | ||
'angular-promise-cache.js', | ||
'angular-promise-cache.test.js' | ||
]) | ||
.pipe(karma({configFile:'karma.conf.js',action:'run'})); | ||
gulp.task('test', function(done) { | ||
new Server({ | ||
configFile: __dirname + '/karma.conf.js', | ||
singleRun: true | ||
}, done).start(); | ||
}); | ||
@@ -24,0 +22,0 @@ |
@@ -16,3 +16,8 @@ // Karma configuration | ||
// list of files / patterns to load in the browser | ||
files: [], | ||
files: [ | ||
'bower_components/angular/angular.min.js', | ||
'bower_components/angular-mocks/angular-mocks.js', | ||
'angular-promise-cache.js', | ||
'angular-promise-cache.test.js' | ||
], | ||
@@ -19,0 +24,0 @@ |
{ | ||
"name": "angular-promise-cache", | ||
"version": "0.0.12", | ||
"version": "0.1.0", | ||
"description": "AngularJS service that provides a generic way to cache promises and ensure all cached promises are resolved correctly.", | ||
@@ -27,10 +27,12 @@ "main": "angular-promise-cache.js", | ||
"devDependencies": { | ||
"gulp": "~3.8.7", | ||
"gulp-bump": "^0.1.13", | ||
"gulp-karma": "0.0.4", | ||
"gulp-rename": "~1.2.0", | ||
"gulp-uglify": "~0.3.1", | ||
"karma-jasmine": "~0.1.5", | ||
"karma-phantomjs-launcher": "~0.1.4" | ||
"gulp": "^3.9.0", | ||
"gulp-bump": "^1.0.0", | ||
"gulp-karma": "0.0.5", | ||
"gulp-rename": "^1.2.2", | ||
"gulp-uglify": "^1.4.2", | ||
"karma": "^0.13.15", | ||
"karma-jasmine": "~0.1.0", | ||
"karma-phantomjs-launcher": "^0.2.1", | ||
"phantomjs": "^1.9.18" | ||
} | ||
} |
@@ -165,2 +165,4 @@ angular-promise-cache | ||
Added in v0.0.13, the remove method supports both an array of keys or a regular expression | ||
Added in v0.0.10, removeAll iterates over all cached promises and calls .remove() | ||
@@ -216,2 +218,4 @@ | ||
--------- | ||
- v0.1.0 - Adding modularity support (for AMD, CommonJS) and fixing issue with local storage access issues, #14 | ||
- v0.0.13 - Fixing issue #11 | ||
- v0.0.12 - Fixing issue #9 | ||
@@ -218,0 +222,0 @@ - v0.0.11 - Fixing issue #8 |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
Minified code
QualityThis package contains minified code. This may be harmless in some cases where minified code is included in packaged libraries, however packages on npm should not minify code.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
55584
931
229
1
9
3