mirror of https://github.com/BTCPrivate/copay.git
commit
d045fc719e
|
@ -46,6 +46,8 @@ angular.module('copayApp.controllers').controller('HomeController', function($sc
|
||||||
$scope.error = 'Invalid email or password';
|
$scope.error = 'Invalid email or password';
|
||||||
} else if ((err.toString() || '').match('Connection')) {
|
} else if ((err.toString() || '').match('Connection')) {
|
||||||
$scope.error = 'Could not connect to Insight Server';
|
$scope.error = 'Could not connect to Insight Server';
|
||||||
|
} else if ((err.toString() || '').match('Unable')) {
|
||||||
|
$scope.error = 'Unable to read data from the Insight Server';
|
||||||
} else {
|
} else {
|
||||||
$scope.error = 'Unknown error';
|
$scope.error = 'Unknown error';
|
||||||
}
|
}
|
||||||
|
|
|
@ -17,7 +17,7 @@ function PluginManager(config) {
|
||||||
if(config.pluginsPath){
|
if(config.pluginsPath){
|
||||||
pluginClass = require(config.pluginsPath + pluginName);
|
pluginClass = require(config.pluginsPath + pluginName);
|
||||||
} else {
|
} else {
|
||||||
pluginClass = require('../plugins/' + pluginName);
|
pluginClass = require('../js/plugins/' + pluginName);
|
||||||
}
|
}
|
||||||
var pluginObj = new pluginClass(config[pluginName]);
|
var pluginObj = new pluginClass(config[pluginName]);
|
||||||
pluginObj.init();
|
pluginObj.init();
|
||||||
|
|
|
@ -298,32 +298,4 @@ GoogleDrive.prototype._checkHomeDir = function(cb) {
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
GoogleDrive.prototype.allKeys = function(cb) {
|
|
||||||
var self = this;
|
|
||||||
|
|
||||||
this._checkHomeDir(function(homeId) {
|
|
||||||
preconditions.checkState(homeId);
|
|
||||||
|
|
||||||
var request = gapi.client.request({
|
|
||||||
'path': '/drive/v2/files',
|
|
||||||
'method': 'GET',
|
|
||||||
'params': {
|
|
||||||
'q': "'" + homeId + "' in parents and trashed = false",
|
|
||||||
'fields': 'items(id,title)'
|
|
||||||
},
|
|
||||||
});
|
|
||||||
request.execute(function(res) {
|
|
||||||
// console.log('[googleDrive.js.152:res:]', res); //TODO
|
|
||||||
if (res.error)
|
|
||||||
throw new Error(res.error.message);
|
|
||||||
|
|
||||||
var ret = [];
|
|
||||||
for (var ii in res.items) {
|
|
||||||
ret.push(res.items[ii].title);
|
|
||||||
}
|
|
||||||
return cb(ret);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
};
|
|
||||||
|
|
||||||
module.exports = GoogleDrive;
|
module.exports = GoogleDrive;
|
||||||
|
|
|
@ -118,7 +118,7 @@ InsightStorage.prototype._makeGetRequest = function(passphrase, key, callback) {
|
||||||
return callback('PNOTFOUND: Profile not found');
|
return callback('PNOTFOUND: Profile not found');
|
||||||
}
|
}
|
||||||
if (response.statusCode !== 200) {
|
if (response.statusCode !== 200) {
|
||||||
return callback('Connection error');
|
return callback('Unable to read item from insight');
|
||||||
}
|
}
|
||||||
return callback(null, body, InsightStorage.parseResponseHeaders(response.getAllResponseHeaders()));
|
return callback(null, body, InsightStorage.parseResponseHeaders(response.getAllResponseHeaders()));
|
||||||
}
|
}
|
||||||
|
@ -217,7 +217,7 @@ InsightStorage.prototype.removeItem = function(key, callback) {
|
||||||
'Authorization': authHeader
|
'Authorization': authHeader
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
log.debug('erase ' + name);
|
log.debug('Erasing: ' + key);
|
||||||
this.request.get(getParams, function(err, response, body) {
|
this.request.get(getParams, function(err, response, body) {
|
||||||
if (err) {
|
if (err) {
|
||||||
return callback('Connection error');
|
return callback('Connection error');
|
||||||
|
@ -236,14 +236,4 @@ InsightStorage.prototype.clear = function(callback) {
|
||||||
callback();
|
callback();
|
||||||
};
|
};
|
||||||
|
|
||||||
InsightStorage.prototype.allKeys = function(callback) {
|
|
||||||
// TODO: compatibility with localStorage
|
|
||||||
return callback(null);
|
|
||||||
};
|
|
||||||
|
|
||||||
InsightStorage.prototype.getFirst = function(prefix, opts, callback) {
|
|
||||||
// TODO: compatibility with localStorage
|
|
||||||
return callback(null, true, true);
|
|
||||||
};
|
|
||||||
|
|
||||||
module.exports = InsightStorage;
|
module.exports = InsightStorage;
|
||||||
|
|
|
@ -2,82 +2,57 @@
|
||||||
var _ = require('lodash');
|
var _ = require('lodash');
|
||||||
var preconditions = require('preconditions').singleton();
|
var preconditions = require('preconditions').singleton();
|
||||||
|
|
||||||
function LocalStorage() {
|
function LocalStorage(opts) {
|
||||||
this.type = 'DB';
|
this.type = 'DB';
|
||||||
|
opts = opts || {};
|
||||||
|
|
||||||
|
|
||||||
preconditions.checkState(typeof localStorage !== 'undefined',
|
this.ls = opts.ls
|
||||||
'localstorage not available, cannot run plugin');
|
|| ( (typeof localStorage !== 'undefined') ? localStorage : null );
|
||||||
|
|
||||||
|
preconditions.checkState(this.ls,
|
||||||
|
'localstorage not available, cannot run plugin');
|
||||||
};
|
};
|
||||||
|
|
||||||
LocalStorage.prototype.init = function() {
|
LocalStorage.prototype.init = function() {
|
||||||
};
|
};
|
||||||
|
|
||||||
LocalStorage.prototype.setCredentials = function(email, password, opts) {
|
LocalStorage.prototype.setCredentials = function(email, password, opts) {
|
||||||
this.email = email;
|
// NOP
|
||||||
this.password = password;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
LocalStorage.prototype.getItem = function(k,cb) {
|
LocalStorage.prototype.getItem = function(k,cb) {
|
||||||
return cb(null, localStorage.getItem(k));
|
preconditions.checkArgument(_.isFunction(cb));
|
||||||
|
return cb(null, this.ls.getItem(k));
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Same as setItem, but fails if an item already exists
|
* Same as setItem, but fails if an item already exists
|
||||||
*/
|
*/
|
||||||
LocalStorage.prototype.createItem = function(name, value, callback) {
|
LocalStorage.prototype.createItem = function(name, value, callback) {
|
||||||
if (localStorage.getItem(name)) {
|
preconditions.checkArgument(_.isFunction(callback));
|
||||||
|
if (this.ls.getItem(name)) {
|
||||||
return callback('EEXISTS');
|
return callback('EEXISTS');
|
||||||
}
|
}
|
||||||
return this.setItem(name, value, callback);
|
return this.setItem(name, value, callback);
|
||||||
};
|
};
|
||||||
|
|
||||||
LocalStorage.prototype.setItem = function(k,v,cb) {
|
LocalStorage.prototype.setItem = function(k,v,cb) {
|
||||||
localStorage.setItem(k,v);
|
preconditions.checkArgument(_.isFunction(cb));
|
||||||
|
this.ls.setItem(k,v);
|
||||||
return cb();
|
return cb();
|
||||||
};
|
};
|
||||||
|
|
||||||
LocalStorage.prototype.removeItem = function(k,cb) {
|
LocalStorage.prototype.removeItem = function(k,cb) {
|
||||||
localStorage.removeItem(k);
|
preconditions.checkArgument(_.isFunction(cb));
|
||||||
|
this.ls.removeItem(k);
|
||||||
return cb();
|
return cb();
|
||||||
};
|
};
|
||||||
|
|
||||||
LocalStorage.prototype.clear = function(cb) {
|
LocalStorage.prototype.clear = function(cb) {
|
||||||
localStorage.clear();
|
preconditions.checkArgument(_.isFunction(cb));
|
||||||
|
this.ls.clear();
|
||||||
return cb();
|
return cb();
|
||||||
};
|
};
|
||||||
|
|
||||||
LocalStorage.prototype.allKeys = function(cb) {
|
|
||||||
var l = localStorage.length;
|
|
||||||
var ret = [];
|
|
||||||
|
|
||||||
for(var i=0; i<l; i++)
|
|
||||||
ret.push(localStorage.key(i));
|
|
||||||
|
|
||||||
return cb(null, ret);
|
|
||||||
};
|
|
||||||
|
|
||||||
LocalStorage.prototype.getFirst = function(prefix, opts, cb) {
|
|
||||||
opts = opts || {};
|
|
||||||
var that = this;
|
|
||||||
|
|
||||||
this.allKeys(function(err, allKeys) {
|
|
||||||
var keys = _.filter(allKeys, function(k) {
|
|
||||||
if ((k === prefix) || k.indexOf(prefix) === 0) return true;
|
|
||||||
});
|
|
||||||
|
|
||||||
if (keys.length === 0)
|
|
||||||
return cb(new Error('not found'));
|
|
||||||
|
|
||||||
if (opts.onlyKey)
|
|
||||||
return cb(null, null, keys[0]);
|
|
||||||
|
|
||||||
that.getItem(keys[0], function(err, data) {
|
|
||||||
if (err) {
|
|
||||||
return cb(err);
|
|
||||||
}
|
|
||||||
return cb(null, data, keys[0]);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
};
|
|
||||||
|
|
||||||
module.exports = LocalStorage;
|
module.exports = LocalStorage;
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
|
|
||||||
angular.module('copayApp.services')
|
angular.module('copayApp.services')
|
||||||
.factory('localstorageService', function($rootScope) {
|
.factory('localstorageService', function($rootScope) {
|
||||||
var LS = require('../plugins/LocalStorage');
|
var LS = require('../js/plugins/LocalStorage');
|
||||||
var ls = new LS();
|
var ls = new LS();
|
||||||
return ls;
|
return ls;
|
||||||
});
|
});
|
||||||
|
|
|
@ -3,7 +3,7 @@ var _ = require('lodash');
|
||||||
var ls;
|
var ls;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
var LS = require('../plugins/LocalStorage');
|
var LS = require('../js/plugins/LocalStorage');
|
||||||
ls = new LS();
|
ls = new LS();
|
||||||
} catch(e) {};
|
} catch(e) {};
|
||||||
|
|
||||||
|
|
|
@ -46,41 +46,96 @@ describe('insight storage plugin', function() {
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
var setupForRetrieval = function() {
|
var setupForRetrieval = function(code) {
|
||||||
requestMock.get.onFirstCall().callsArgWith(1, null, {
|
requestMock.get.onFirstCall().callsArgWith(1, null, {
|
||||||
statusCode: 200,
|
statusCode: code || 200,
|
||||||
getAllResponseHeaders: sinon.stub().returns(headers),
|
getAllResponseHeaders: sinon.stub().returns(headers),
|
||||||
}, data);
|
}, data);
|
||||||
};
|
};
|
||||||
|
|
||||||
it('should be able to retrieve data in a namespace', function(done) {
|
describe('#getItem', function() {
|
||||||
|
it('should be able to retrieve data in a namespace', function(done) {
|
||||||
|
setupForRetrieval();
|
||||||
|
|
||||||
setupForRetrieval();
|
storage.getItem(namespace, function(err, retrieved) {
|
||||||
|
assert(!err);
|
||||||
|
assert(retrieved === data);
|
||||||
|
var url = requestMock.get.getCall(0).args[0].url;
|
||||||
|
url.should.contain('?key=' + querystring.encode(namespace));
|
||||||
|
return done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
storage.getItem(namespace, function(err, retrieved) {
|
it('should be able to retrieve headers', function(done) {
|
||||||
assert(!err);
|
|
||||||
assert(retrieved === data);
|
setupForRetrieval();
|
||||||
return done();
|
|
||||||
|
storage.getItem(namespace, function(err, retrieved, headers) {
|
||||||
|
assert(!err);
|
||||||
|
headers['X-test'].should.equal('12');
|
||||||
|
headers['X-testb'].should.equal('32');
|
||||||
|
return done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should be able handle 403', function(done) {
|
||||||
|
setupForRetrieval(403);
|
||||||
|
// old profile query
|
||||||
|
requestMock.get.onSecondCall().callsArgWith(1, null, {
|
||||||
|
statusCode: 403,
|
||||||
|
getAllResponseHeaders: sinon.stub().returns(headers),
|
||||||
|
}, data);
|
||||||
|
storage.getItem(namespace, function(err) {
|
||||||
|
err.should.contain('PNOTFOUND');
|
||||||
|
return done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should be able handle other error', function(done) {
|
||||||
|
setupForRetrieval(510);
|
||||||
|
storage.getItem(namespace, function(err) {
|
||||||
|
err.should.contain('Unable');
|
||||||
|
return done();
|
||||||
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should be able to retrieve headers', function(done) {
|
describe('#removeItem', function() {
|
||||||
|
|
||||||
setupForRetrieval();
|
it('should be able to delete Items', function(done) {
|
||||||
|
setupForRetrieval();
|
||||||
|
storage.removeItem(namespace, function(err) {
|
||||||
|
should.not.exist(err);
|
||||||
|
var url = requestMock.get.getCall(0).args[0].url;
|
||||||
|
url.should.contain('?key=' + querystring.encode(namespace));
|
||||||
|
|
||||||
storage.getItem(namespace, function(err, retrieved, headers) {
|
return done();
|
||||||
assert(!err);
|
});
|
||||||
headers['X-test'].should.equal('12');
|
});
|
||||||
headers['X-testb'].should.equal('32');
|
|
||||||
return done();
|
it('should be able handle 406', function(done) {
|
||||||
|
setupForRetrieval(409);
|
||||||
|
storage.removeItem(namespace, function(err) {
|
||||||
|
err.should.contain('BADCREDENTIALS');
|
||||||
|
return done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should be able handle other error', function(done) {
|
||||||
|
setupForRetrieval(510);
|
||||||
|
storage.removeItem(namespace, function(err) {
|
||||||
|
err.should.contain('Unable');
|
||||||
|
return done();
|
||||||
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
var setupForSave = function() {
|
|
||||||
|
var setupForSave = function(code) {
|
||||||
requestMock.post.onFirstCall().callsArgWith(1, null, {
|
requestMock.post.onFirstCall().callsArgWith(1, null, {
|
||||||
statusCode: 200
|
statusCode: code || 200
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -94,6 +149,33 @@ describe('insight storage plugin', function() {
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
|
it('should handle 406 (quota)', function(done) {
|
||||||
|
setupForSave(406);
|
||||||
|
storage.setItem(namespace, data, function(err) {
|
||||||
|
err.should.contain('OVERQUOTA');
|
||||||
|
return done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should handle other error ', function(done) {
|
||||||
|
setupForSave(505);
|
||||||
|
storage.setItem(namespace, data, function(err) {
|
||||||
|
err.should.contain('Unable');
|
||||||
|
return done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should handle 409 (unauthorized)', function(done) {
|
||||||
|
setupForSave(409);
|
||||||
|
|
||||||
|
storage.setItem(namespace, data, function(err) {
|
||||||
|
err.should.contain('BADCREDENTIALS');
|
||||||
|
return done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
it('won\'t make an unnecessary request if old password can\'t work', function(done) {
|
it('won\'t make an unnecessary request if old password can\'t work', function(done) {
|
||||||
storage.setCredentials(email, '!');
|
storage.setCredentials(email, '!');
|
||||||
setupForRetrieval();
|
setupForRetrieval();
|
||||||
|
@ -152,7 +234,7 @@ describe('insight storage plugin', function() {
|
||||||
var url = requestMock.post.firstCall.args[0].url;
|
var url = requestMock.post.firstCall.args[0].url;
|
||||||
var args = querystring.decode(receivedArgs);
|
var args = querystring.decode(receivedArgs);
|
||||||
url.indexOf('change_passphrase').should.not.be.equal(-1);
|
url.indexOf('change_passphrase').should.not.be.equal(-1);
|
||||||
requestMock.post.firstCall.args[0].headers.Authorization.should.be.equal( new Buffer(email + ':' + oldSecret).toString('base64'));
|
requestMock.post.firstCall.args[0].headers.Authorization.should.be.equal(new Buffer(email + ':' + oldSecret).toString('base64'));
|
||||||
args.newPassphrase.should.be.equal(newSecret);
|
args.newPassphrase.should.be.equal(newSecret);
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
|
|
|
@ -0,0 +1,73 @@
|
||||||
|
var LocalStorage = require('../js/plugins/LocalStorage');
|
||||||
|
var assert = require('assert');
|
||||||
|
|
||||||
|
describe('local storage plugin', function() {
|
||||||
|
|
||||||
|
var storage, storageMock, VALUE=123;
|
||||||
|
|
||||||
|
beforeEach(function() {
|
||||||
|
storageMock = {};
|
||||||
|
storageMock.getItem = sinon.stub().returns(VALUE);
|
||||||
|
storageMock.createItem = sinon.stub().returns();
|
||||||
|
storageMock.setItem = sinon.stub().returns();
|
||||||
|
storageMock.removeItem = sinon.stub().returns();
|
||||||
|
storageMock.clear = sinon.stub().returns();
|
||||||
|
storage = new LocalStorage({
|
||||||
|
ls: storageMock
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('#getItem', function(done) {
|
||||||
|
storage.getItem('hola', function(err, value) {
|
||||||
|
assert(!err);
|
||||||
|
storageMock.getItem.getCall(0).args[0].should.equal('hola');
|
||||||
|
value.should.equal(VALUE);
|
||||||
|
return done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('#createItem', function(done) {
|
||||||
|
storageMock.getItem = sinon.stub().returns(null);
|
||||||
|
storage.createItem('hola', 'value', function(err) {
|
||||||
|
assert(!err);
|
||||||
|
return done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('#createItem (Exists)', function(done) {
|
||||||
|
storage.createItem('hola', 'value', function(err) {
|
||||||
|
err.should.contain('EEXISTS');
|
||||||
|
return done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
it('#removeItem', function(done) {
|
||||||
|
storage.removeItem('pepe', function(err) {
|
||||||
|
assert(!err);
|
||||||
|
storageMock.removeItem.getCall(0).args[0].should.equal('pepe');
|
||||||
|
return done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('#setItem', function(done) {
|
||||||
|
storage.setItem('hola', 'chau', function(err) {
|
||||||
|
assert(!err);
|
||||||
|
storageMock.setItem.getCall(0).args[0].should.equal('hola');
|
||||||
|
storageMock.setItem.getCall(0).args[1].should.equal('chau');
|
||||||
|
return done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('#clear', function(done) {
|
||||||
|
storage.clear(function(err) {
|
||||||
|
assert(!err);
|
||||||
|
storageMock.clear.calledOnce.should.equal(true);
|
||||||
|
return done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
});
|
|
@ -11,7 +11,7 @@ describe('log utils', function() {
|
||||||
log.setLevel('info');
|
log.setLevel('info');
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should log fatal', function() {
|
it('should log .warn', function() {
|
||||||
if (console.warn.restore)
|
if (console.warn.restore)
|
||||||
console.warn.restore();
|
console.warn.restore();
|
||||||
|
|
||||||
|
@ -26,6 +26,23 @@ describe('log utils', function() {
|
||||||
console.warn.restore();
|
console.warn.restore();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
|
it('should log .fatal', function() {
|
||||||
|
if (console.log.restore)
|
||||||
|
console.log.restore();
|
||||||
|
|
||||||
|
sinon.stub(console,'log');
|
||||||
|
|
||||||
|
log.setLevel('debug');
|
||||||
|
log.fatal('hola',"que",'tal');
|
||||||
|
|
||||||
|
var arg = console.log.getCall(0).args[0];
|
||||||
|
//arg.should.contain('util.log.js'); /* Firefox does not include the stack track */
|
||||||
|
arg.should.contain('que');
|
||||||
|
console.log.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
it('should not log debug', function() {
|
it('should not log debug', function() {
|
||||||
sinon.stub(console,'log');
|
sinon.stub(console,'log');
|
||||||
log.setLevel('info');
|
log.setLevel('info');
|
||||||
|
@ -38,4 +55,6 @@ describe('log utils', function() {
|
||||||
log.getLevels().debug.should.equal(0);
|
log.getLevels().debug.should.equal(0);
|
||||||
log.getLevels().fatal.should.equal(5);
|
log.getLevels().fatal.should.equal(5);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
|
@ -90,22 +90,22 @@ var createBundle = function(opts) {
|
||||||
|
|
||||||
if (!opts.disablePlugins) {
|
if (!opts.disablePlugins) {
|
||||||
b.require('./js/plugins/GoogleDrive', {
|
b.require('./js/plugins/GoogleDrive', {
|
||||||
expose: '../plugins/GoogleDrive'
|
expose: '../js/plugins/GoogleDrive'
|
||||||
});
|
});
|
||||||
b.require('./js/plugins/InsightStorage', {
|
b.require('./js/plugins/InsightStorage', {
|
||||||
expose: '../plugins/InsightStorage'
|
expose: '../js/plugins/InsightStorage'
|
||||||
});
|
});
|
||||||
b.require('./js/plugins/InsightStorage', {
|
b.require('./js/plugins/InsightStorage', {
|
||||||
expose: '../js/plugins/InsightStorage'
|
expose: '../js/plugins/InsightStorage'
|
||||||
});
|
});
|
||||||
b.require('./js/plugins/LocalStorage', {
|
b.require('./js/plugins/LocalStorage', {
|
||||||
expose: '../plugins/LocalStorage'
|
expose: '../js/plugins/LocalStorage'
|
||||||
});
|
});
|
||||||
b.require('./js/plugins/EncryptedInsightStorage', {
|
b.require('./js/plugins/EncryptedInsightStorage', {
|
||||||
expose: '../plugins/EncryptedInsightStorage'
|
expose: '../js/plugins/EncryptedInsightStorage'
|
||||||
});
|
});
|
||||||
b.require('./js/plugins/EncryptedLocalStorage', {
|
b.require('./js/plugins/EncryptedLocalStorage', {
|
||||||
expose: '../plugins/EncryptedLocalStorage'
|
expose: '../js/plugins/EncryptedLocalStorage'
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue