mirror of
https://github.com/moparisthebest/mail
synced 2024-11-25 18:32:20 -05:00
WIP add unit tests
This commit is contained in:
parent
c36cd069e0
commit
9bfda73969
2
.gitignore
vendored
2
.gitignore
vendored
@ -8,3 +8,5 @@ dist/
|
|||||||
release/
|
release/
|
||||||
test/integration/src/
|
test/integration/src/
|
||||||
.elasticbeanstalk/
|
.elasticbeanstalk/
|
||||||
|
test/unit/index.js
|
||||||
|
test/unit/index.js.map
|
||||||
|
17
.jshintrc
17
.jshintrc
@ -18,19 +18,18 @@
|
|||||||
"unused": true,
|
"unused": true,
|
||||||
|
|
||||||
"predef": [
|
"predef": [
|
||||||
|
"self",
|
||||||
"console",
|
"console",
|
||||||
"Notification",
|
"process",
|
||||||
"importScripts",
|
|
||||||
"process",
|
|
||||||
"Event",
|
|
||||||
"chrome",
|
"chrome",
|
||||||
"define",
|
"Notification",
|
||||||
"self",
|
"Event",
|
||||||
|
"sinon",
|
||||||
|
"mocha",
|
||||||
|
"chai",
|
||||||
|
"expect",
|
||||||
"describe",
|
"describe",
|
||||||
"it",
|
"it",
|
||||||
"chai",
|
|
||||||
"sinon",
|
|
||||||
"mocha",
|
|
||||||
"before",
|
"before",
|
||||||
"beforeEach",
|
"beforeEach",
|
||||||
"after",
|
"after",
|
||||||
|
51
Gruntfile.js
51
Gruntfile.js
@ -1,6 +1,8 @@
|
|||||||
module.exports = function(grunt) {
|
module.exports = function(grunt) {
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
|
require('time-grunt')(grunt);
|
||||||
|
|
||||||
var version = grunt.option('release'),
|
var version = grunt.option('release'),
|
||||||
zipName = (version) ? version : 'DEV';
|
zipName = (version) ? version : 'DEV';
|
||||||
|
|
||||||
@ -24,7 +26,7 @@ module.exports = function(grunt) {
|
|||||||
},
|
},
|
||||||
|
|
||||||
jshint: {
|
jshint: {
|
||||||
all: ['Gruntfile.js', 'src/*.js', 'src/js/**/*.js', 'test/unit/*.js', 'test/integration/*.js'],
|
all: ['Gruntfile.js', 'src/*.js', 'src/js/**/*.js', 'test/unit/*-test.js', 'test/integration/*.js'],
|
||||||
options: {
|
options: {
|
||||||
jshintrc: '.jshintrc'
|
jshintrc: '.jshintrc'
|
||||||
}
|
}
|
||||||
@ -109,16 +111,22 @@ module.exports = function(grunt) {
|
|||||||
'dist/js/app.min.js': ['src/js/app.js']
|
'dist/js/app.min.js': ['src/js/app.js']
|
||||||
},
|
},
|
||||||
options: {
|
options: {
|
||||||
external: ['node-forge', 'net', 'tls'] // common.js apis not required at build time
|
external: []
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
/* TODO:
|
unitTest: {
|
||||||
tls-worker: {},
|
files: {
|
||||||
mailreader-worker: {},
|
'test/unit/index.js': ['test/unit/*-test.js']
|
||||||
pbkdf2-worker: {},
|
},
|
||||||
unitTest: {},
|
options: {
|
||||||
unitTest: {},
|
external: []
|
||||||
integrationTest: {}
|
}
|
||||||
|
},
|
||||||
|
/*
|
||||||
|
TODO:
|
||||||
|
mailreader-worker: {},
|
||||||
|
pbkdf2-worker: {},
|
||||||
|
integrationTest: {}
|
||||||
*/
|
*/
|
||||||
},
|
},
|
||||||
|
|
||||||
@ -126,6 +134,7 @@ module.exports = function(grunt) {
|
|||||||
all: {
|
all: {
|
||||||
files: {
|
files: {
|
||||||
'dist/js/app.min.js': [
|
'dist/js/app.min.js': [
|
||||||
|
'src/lib/openpgp/openpgp.js',
|
||||||
'src/lib/underscore/underscore-min.js',
|
'src/lib/underscore/underscore-min.js',
|
||||||
'node_modules/jquery/dist/jquery.min.js',
|
'node_modules/jquery/dist/jquery.min.js',
|
||||||
'src/lib/angular/angular.min.js',
|
'src/lib/angular/angular.min.js',
|
||||||
@ -142,6 +151,28 @@ module.exports = function(grunt) {
|
|||||||
]
|
]
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
unitTest: {
|
||||||
|
files: {
|
||||||
|
'test/unit/index.js': [
|
||||||
|
'src/lib/underscore/underscore-min.js',
|
||||||
|
'node_modules/jquery/dist/jquery.min.js',
|
||||||
|
'src/lib/openpgp/openpgp.js',
|
||||||
|
'src/lib/angular/angular.min.js',
|
||||||
|
'node_modules/angular-mocks/angular-mocks.js',
|
||||||
|
'src/lib/angular/angular-route.min.js',
|
||||||
|
'src/lib/angular/angular-animate.min.js',
|
||||||
|
'src/lib/ngtagsinput/ng-tags-input.min.js',
|
||||||
|
'src/lib/fastclick/fastclick.js',
|
||||||
|
'node_modules/ng-infinite-scroll/build/ng-infinite-scroll.min.js',
|
||||||
|
'src/lib/lawnchair/lawnchair-git.js',
|
||||||
|
'src/lib/lawnchair/lawnchair-adapter-webkit-sqlite-git.js',
|
||||||
|
'src/lib/lawnchair/lawnchair-adapter-indexed-db-git.js',
|
||||||
|
'node_modules/dompurify/purify.js',
|
||||||
|
'test/lib/angular-mocks.js',
|
||||||
|
'test/unit/index.js'
|
||||||
|
]
|
||||||
|
}
|
||||||
|
},
|
||||||
options: {
|
options: {
|
||||||
banner: '/*! Copyright © <%= grunt.template.today("yyyy") %>, Whiteout Networks GmbH.*/\n'
|
banner: '/*! Copyright © <%= grunt.template.today("yyyy") %>, Whiteout Networks GmbH.*/\n'
|
||||||
}
|
}
|
||||||
@ -152,7 +183,7 @@ module.exports = function(grunt) {
|
|||||||
expand: true,
|
expand: true,
|
||||||
flatten: true,
|
flatten: true,
|
||||||
cwd: 'node_modules/',
|
cwd: 'node_modules/',
|
||||||
src: ['requirejs/require.js', 'mocha/mocha.css', 'mocha/mocha.js', 'chai/chai.js', 'sinon/pkg/sinon.js', 'angularjs/src/ngMock/angular-mocks.js', 'browsercrow/src/*.js', 'browsersmtp/src/*.js'],
|
src: ['mocha/mocha.css', 'mocha/mocha.js', 'chai/chai.js', 'sinon/pkg/sinon.js', 'browsercrow/src/*.js', 'browsersmtp/src/*.js'],
|
||||||
dest: 'test/lib/'
|
dest: 'test/lib/'
|
||||||
},
|
},
|
||||||
font: {
|
font: {
|
||||||
|
138
package.json
138
package.json
@ -1,70 +1,72 @@
|
|||||||
{
|
{
|
||||||
"name": "whiteout-mail",
|
"name": "whiteout-mail",
|
||||||
"version": "0.0.1",
|
"version": "0.0.1",
|
||||||
"description": "Mail App with integrated OpenPGP encryption.",
|
"description": "Mail App with integrated OpenPGP encryption.",
|
||||||
"author": "Whiteout Networks",
|
"author": "Whiteout Networks",
|
||||||
"homepage": "https://whiteout.io",
|
"homepage": "https://whiteout.io",
|
||||||
"repository": {
|
"repository": {
|
||||||
"type": "git",
|
"type": "git",
|
||||||
"url": "https://github.com/whiteout-io/mail-html5.git"
|
"url": "https://github.com/whiteout-io/mail-html5.git"
|
||||||
},
|
},
|
||||||
"keywords": [
|
"keywords": [
|
||||||
"email",
|
"email",
|
||||||
"mail",
|
"mail",
|
||||||
"client",
|
"client",
|
||||||
"app",
|
"app",
|
||||||
"openpgp",
|
"openpgp",
|
||||||
"pgp",
|
"pgp",
|
||||||
"gpg",
|
"gpg",
|
||||||
"imap",
|
"imap",
|
||||||
"smtp"
|
"smtp"
|
||||||
],
|
],
|
||||||
"engines": {
|
"engines": {
|
||||||
"node": ">=0.10"
|
"node": ">=0.10"
|
||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"test": "grunt && grunt test",
|
"test": "grunt && grunt test",
|
||||||
"start": "node server.js"
|
"start": "node server.js"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"axe-logger": "~0.0.2",
|
"axe-logger": "~0.0.2",
|
||||||
"compression": "^1.0.11",
|
"compression": "^1.0.11",
|
||||||
"config": "^1.0.2",
|
"config": "^1.0.2",
|
||||||
"crypto-lib": "~0.2.1",
|
"crypto-lib": "~0.2.1",
|
||||||
"dompurify": "~0.4.2",
|
"dompurify": "~0.4.2",
|
||||||
"express": "^4.8.3",
|
"express": "^4.8.3",
|
||||||
"imap-client": "~0.4.3",
|
"imap-client": "~0.4.3",
|
||||||
"jquery": "~2.1.1",
|
"jquery": "~2.1.1",
|
||||||
"mailreader": "~0.3.5",
|
"mailreader": "~0.3.5",
|
||||||
"morgan": "^1.2.3",
|
"morgan": "^1.2.3",
|
||||||
"ng-infinite-scroll": "~1.1.2",
|
"ng-infinite-scroll": "~1.1.2",
|
||||||
"npmlog": "^0.1.1",
|
"npmlog": "^0.1.1",
|
||||||
"pgpbuilder": "~0.4.0",
|
"pgpbuilder": "~0.4.0",
|
||||||
"pgpmailer": "~0.4.0",
|
"pgpmailer": "~0.4.0",
|
||||||
"socket.io": "^1.0.6",
|
"socket.io": "^1.0.6",
|
||||||
"tcp-socket": "^0.3.9",
|
"tcp-socket": "^0.3.9",
|
||||||
"wo-smtpclient": "^0.3.8"
|
"wo-smtpclient": "^0.3.8"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"angularjs": "https://github.com/whiteout-io/angular.js/tarball/npm-version",
|
"angular-mocks": "^1.2.25",
|
||||||
"browsercrow": "https://github.com/whiteout-io/browsercrow/tarball/master",
|
"angularjs": "https://github.com/whiteout-io/angular.js/tarball/npm-version",
|
||||||
"browsersmtp": "https://github.com/whiteout-io/browsersmtp/tarball/master",
|
"browsercrow": "https://github.com/whiteout-io/browsercrow/tarball/master",
|
||||||
"chai": "~1.7.2",
|
"browsersmtp": "https://github.com/whiteout-io/browsersmtp/tarball/master",
|
||||||
"grunt": "~0.4.1",
|
"chai": "~1.7.2",
|
||||||
"grunt-autoprefixer": "~0.7.2",
|
"grunt": "~0.4.1",
|
||||||
"grunt-browserify": "^3.0.1",
|
"grunt-autoprefixer": "~0.7.2",
|
||||||
"grunt-contrib-clean": "~0.5.0",
|
"grunt-browserify": "^3.0.1",
|
||||||
"grunt-contrib-compress": "~0.5.2",
|
"grunt-contrib-clean": "~0.5.0",
|
||||||
"grunt-contrib-connect": "~0.5.0",
|
"grunt-contrib-compress": "~0.5.2",
|
||||||
"grunt-contrib-copy": "~0.4.1",
|
"grunt-contrib-connect": "~0.5.0",
|
||||||
"grunt-contrib-jshint": "~0.6.4",
|
"grunt-contrib-copy": "~0.4.1",
|
||||||
"grunt-contrib-sass": "~0.7.3",
|
"grunt-contrib-jshint": "~0.6.4",
|
||||||
"grunt-contrib-uglify": "^0.6.0",
|
"grunt-contrib-sass": "~0.7.3",
|
||||||
"grunt-contrib-watch": "~0.5.3",
|
"grunt-contrib-uglify": "^0.6.0",
|
||||||
"grunt-csso": "~0.6.1",
|
"grunt-contrib-watch": "~0.5.3",
|
||||||
"grunt-manifest": "^0.4.0",
|
"grunt-csso": "~0.6.1",
|
||||||
"grunt-mocha": "~0.4.1",
|
"grunt-manifest": "^0.4.0",
|
||||||
"mocha": "~1.13.0",
|
"grunt-mocha": "~0.4.1",
|
||||||
"sinon": "~1.7.3"
|
"mocha": "~1.13.0",
|
||||||
}
|
"sinon": "~1.7.3",
|
||||||
|
"time-grunt": "^1.0.0"
|
||||||
|
}
|
||||||
}
|
}
|
@ -1,101 +1,97 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
AccountCtrl = require('../../src/js/controller/account'),
|
||||||
mocks = require('angularMocks'),
|
PGP = require('../../src/js/crypto/pgp'),
|
||||||
AccountCtrl = require('js/controller/account'),
|
dl = require('../../src/js/util/download'),
|
||||||
PGP = require('js/crypto/pgp'),
|
appController = require('../../src/js/app-controller'),
|
||||||
dl = require('js/util/download'),
|
KeychainDAO = require('../../src/js/dao/keychain-dao');
|
||||||
appController = require('js/app-controller'),
|
|
||||||
KeychainDAO = require('js/dao/keychain-dao');
|
|
||||||
|
|
||||||
describe('Account Controller unit test', function() {
|
describe('Account Controller unit test', function() {
|
||||||
var scope, accountCtrl,
|
var scope, accountCtrl,
|
||||||
dummyFingerprint, expectedFingerprint,
|
dummyFingerprint, expectedFingerprint,
|
||||||
dummyKeyId, expectedKeyId,
|
dummyKeyId, expectedKeyId,
|
||||||
emailAddress, keySize, pgpMock, keychainMock;
|
emailAddress, keySize, pgpMock, keychainMock;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
appController._pgp = pgpMock = sinon.createStubInstance(PGP);
|
appController._pgp = pgpMock = sinon.createStubInstance(PGP);
|
||||||
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
||||||
|
|
||||||
dummyFingerprint = '3A2D39B4E1404190B8B949DE7D7E99036E712926';
|
dummyFingerprint = '3A2D39B4E1404190B8B949DE7D7E99036E712926';
|
||||||
expectedFingerprint = '3A2D 39B4 E140 4190 B8B9 49DE 7D7E 9903 6E71 2926';
|
expectedFingerprint = '3A2D 39B4 E140 4190 B8B9 49DE 7D7E 9903 6E71 2926';
|
||||||
dummyKeyId = '9FEB47936E712926';
|
dummyKeyId = '9FEB47936E712926';
|
||||||
expectedKeyId = '6E712926';
|
expectedKeyId = '6E712926';
|
||||||
pgpMock.getFingerprint.returns(dummyFingerprint);
|
pgpMock.getFingerprint.returns(dummyFingerprint);
|
||||||
pgpMock.getKeyId.returns(dummyKeyId);
|
pgpMock.getKeyId.returns(dummyKeyId);
|
||||||
emailAddress = 'fred@foo.com';
|
emailAddress = 'fred@foo.com';
|
||||||
keySize = 1234;
|
keySize = 1234;
|
||||||
appController._emailDao = {
|
appController._emailDao = {
|
||||||
_account: {
|
_account: {
|
||||||
emailAddress: emailAddress,
|
emailAddress: emailAddress,
|
||||||
asymKeySize: keySize
|
asymKeySize: keySize
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
pgpMock.getKeyParams.returns({
|
pgpMock.getKeyParams.returns({
|
||||||
_id: dummyKeyId,
|
_id: dummyKeyId,
|
||||||
fingerprint: dummyFingerprint,
|
fingerprint: dummyFingerprint,
|
||||||
userId: emailAddress,
|
userId: emailAddress,
|
||||||
bitSize: keySize
|
bitSize: keySize
|
||||||
});
|
|
||||||
|
|
||||||
angular.module('accounttest', []);
|
|
||||||
mocks.module('accounttest');
|
|
||||||
mocks.inject(function($rootScope, $controller) {
|
|
||||||
scope = $rootScope.$new();
|
|
||||||
scope.state = {};
|
|
||||||
accountCtrl = $controller(AccountCtrl, {
|
|
||||||
$scope: scope
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {});
|
angular.module('accounttest', []);
|
||||||
|
mocks.module('accounttest');
|
||||||
describe('scope variables', function() {
|
mocks.inject(function($rootScope, $controller) {
|
||||||
it('should be set correctly', function() {
|
scope = $rootScope.$new();
|
||||||
expect(scope.eMail).to.equal(emailAddress);
|
scope.state = {};
|
||||||
expect(scope.keyId).to.equal(expectedKeyId);
|
accountCtrl = $controller(AccountCtrl, {
|
||||||
expect(scope.fingerprint).to.equal(expectedFingerprint);
|
$scope: scope
|
||||||
expect(scope.keysize).to.equal(keySize);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
describe('export to key file', function() {
|
|
||||||
it('should work', function() {
|
|
||||||
var createDownloadMock = sinon.stub(dl, 'createDownload');
|
|
||||||
keychainMock.getUserKeyPair.withArgs(emailAddress).yields(null, {
|
|
||||||
publicKey: {
|
|
||||||
_id: dummyKeyId,
|
|
||||||
publicKey: 'a'
|
|
||||||
},
|
|
||||||
privateKey: {
|
|
||||||
encryptedKey: 'b'
|
|
||||||
}
|
|
||||||
});
|
|
||||||
createDownloadMock.withArgs(sinon.match(function(arg) {
|
|
||||||
return arg.content === 'a\r\nb' && arg.filename === 'whiteout_mail_' + emailAddress + '_' + expectedKeyId + '.asc' && arg.contentType === 'text/plain';
|
|
||||||
})).returns();
|
|
||||||
|
|
||||||
scope.exportKeyFile();
|
|
||||||
|
|
||||||
expect(scope.state.lightbox).to.equal(undefined);
|
|
||||||
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
|
||||||
expect(dl.createDownload.calledOnce).to.be.true;
|
|
||||||
dl.createDownload.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not work when key export failed', function(done) {
|
|
||||||
keychainMock.getUserKeyPair.yields(new Error('Boom!'));
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err.message).to.equal('Boom!');
|
|
||||||
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.exportKeyFile();
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
afterEach(function() {});
|
||||||
|
|
||||||
|
describe('scope variables', function() {
|
||||||
|
it('should be set correctly', function() {
|
||||||
|
expect(scope.eMail).to.equal(emailAddress);
|
||||||
|
expect(scope.keyId).to.equal(expectedKeyId);
|
||||||
|
expect(scope.fingerprint).to.equal(expectedFingerprint);
|
||||||
|
expect(scope.keysize).to.equal(keySize);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
describe('export to key file', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
var createDownloadMock = sinon.stub(dl, 'createDownload');
|
||||||
|
keychainMock.getUserKeyPair.withArgs(emailAddress).yields(null, {
|
||||||
|
publicKey: {
|
||||||
|
_id: dummyKeyId,
|
||||||
|
publicKey: 'a'
|
||||||
|
},
|
||||||
|
privateKey: {
|
||||||
|
encryptedKey: 'b'
|
||||||
|
}
|
||||||
|
});
|
||||||
|
createDownloadMock.withArgs(sinon.match(function(arg) {
|
||||||
|
return arg.content === 'a\r\nb' && arg.filename === 'whiteout_mail_' + emailAddress + '_' + expectedKeyId + '.asc' && arg.contentType === 'text/plain';
|
||||||
|
})).returns();
|
||||||
|
|
||||||
|
scope.exportKeyFile();
|
||||||
|
|
||||||
|
expect(scope.state.lightbox).to.equal(undefined);
|
||||||
|
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
||||||
|
expect(dl.createDownload.calledOnce).to.be.true;
|
||||||
|
dl.createDownload.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not work when key export failed', function(done) {
|
||||||
|
keychainMock.getUserKeyPair.yields(new Error('Boom!'));
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err.message).to.equal('Boom!');
|
||||||
|
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.exportKeyFile();
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
@ -1,216 +1,212 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
AddAccountCtrl = require('../../src/js/controller/add-account'),
|
||||||
mocks = require('angularMocks'),
|
Auth = require('../../src/js/bo/auth'),
|
||||||
AddAccountCtrl = require('js/controller/add-account'),
|
AdminDao = require('../../src/js/dao/admin-dao'),
|
||||||
Auth = require('js/bo/auth'),
|
appController = require('../../src/js/app-controller');
|
||||||
AdminDao = require('js/dao/admin-dao'),
|
|
||||||
appController = require('js/app-controller');
|
|
||||||
|
|
||||||
describe('Add Account Controller unit test', function() {
|
describe('Add Account Controller unit test', function() {
|
||||||
var scope, location, ctrl, authStub, origAuth, adminStub;
|
var scope, location, ctrl, authStub, origAuth, adminStub;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
// remember original module to restore later, then replace it
|
// remember original module to restore later, then replace it
|
||||||
origAuth = appController._auth;
|
origAuth = appController._auth;
|
||||||
appController._auth = authStub = sinon.createStubInstance(Auth);
|
appController._auth = authStub = sinon.createStubInstance(Auth);
|
||||||
appController._adminDao = adminStub = sinon.createStubInstance(AdminDao);
|
appController._adminDao = adminStub = sinon.createStubInstance(AdminDao);
|
||||||
|
|
||||||
angular.module('addaccounttest', []);
|
angular.module('addaccounttest', []);
|
||||||
mocks.module('addaccounttest');
|
mocks.module('addaccounttest');
|
||||||
mocks.inject(function($controller, $rootScope, $location) {
|
mocks.inject(function($controller, $rootScope, $location) {
|
||||||
location = $location;
|
location = $location;
|
||||||
scope = $rootScope.$new();
|
scope = $rootScope.$new();
|
||||||
scope.state = {};
|
scope.state = {};
|
||||||
scope.form = {};
|
scope.form = {};
|
||||||
scope.formValidate = {};
|
scope.formValidate = {};
|
||||||
|
|
||||||
sinon.stub(location, 'path').returns(location);
|
sinon.stub(location, 'path').returns(location);
|
||||||
sinon.stub(location, 'search').returns(location);
|
sinon.stub(location, 'search').returns(location);
|
||||||
sinon.stub(scope, '$apply', function() {});
|
sinon.stub(scope, '$apply', function() {});
|
||||||
|
|
||||||
ctrl = $controller(AddAccountCtrl, {
|
ctrl = $controller(AddAccountCtrl, {
|
||||||
$location: location,
|
$location: location,
|
||||||
$scope: scope,
|
$scope: scope,
|
||||||
$routeParams: {}
|
$routeParams: {}
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
|
||||||
// restore the app controller module
|
|
||||||
appController._auth = origAuth;
|
|
||||||
|
|
||||||
location.path.restore();
|
|
||||||
location.search.restore();
|
|
||||||
if (scope.$apply.restore) {
|
|
||||||
scope.$apply.restore();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('createWhiteoutAccount', function() {
|
|
||||||
it('should return early for invalid form', function() {
|
|
||||||
scope.form.$invalid = true;
|
|
||||||
scope.createWhiteoutAccount();
|
|
||||||
expect(adminStub.createUser.called).to.be.false;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail to error creating user', function(done) {
|
|
||||||
scope.form.$invalid = false;
|
|
||||||
scope.betaCode = 'asfd';
|
|
||||||
scope.phone = '12345';
|
|
||||||
adminStub.createUser.yieldsAsync(new Error('asdf'));
|
|
||||||
|
|
||||||
scope.$apply = function() {
|
|
||||||
expect(scope.busy).to.be.false;
|
|
||||||
expect(scope.errMsg).to.equal('asdf');
|
|
||||||
expect(adminStub.createUser.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.createWhiteoutAccount();
|
|
||||||
expect(scope.busy).to.be.true;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
scope.form.$invalid = false;
|
|
||||||
scope.betaCode = 'asfd';
|
|
||||||
scope.phone = '12345';
|
|
||||||
adminStub.createUser.yieldsAsync();
|
|
||||||
|
|
||||||
scope.$apply = function() {
|
|
||||||
expect(scope.busy).to.be.false;
|
|
||||||
expect(scope.errMsg).to.be.undefined;
|
|
||||||
expect(scope.step).to.equal(3);
|
|
||||||
expect(adminStub.createUser.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.createWhiteoutAccount();
|
|
||||||
expect(scope.busy).to.be.true;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('validateUser', function() {
|
|
||||||
it('should return early for invalid form', function() {
|
|
||||||
scope.formValidate.$invalid = true;
|
|
||||||
scope.validateUser();
|
|
||||||
expect(adminStub.validateUser.called).to.be.false;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail to error creating user', function(done) {
|
|
||||||
scope.formValidate.$invalid = false;
|
|
||||||
scope.token = 'asfd';
|
|
||||||
adminStub.validateUser.yieldsAsync(new Error('asdf'));
|
|
||||||
|
|
||||||
scope.$apply = function() {
|
|
||||||
expect(scope.busyValidate).to.be.false;
|
|
||||||
expect(scope.errMsgValidate).to.equal('asdf');
|
|
||||||
expect(adminStub.validateUser.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.validateUser();
|
|
||||||
expect(scope.busyValidate).to.be.true;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
scope.formValidate.$invalid = false;
|
|
||||||
scope.token = 'asfd';
|
|
||||||
adminStub.validateUser.yieldsAsync();
|
|
||||||
|
|
||||||
scope.login = function() {
|
|
||||||
expect(scope.busyValidate).to.be.true;
|
|
||||||
expect(scope.errMsgValidate).to.be.undefined;
|
|
||||||
expect(adminStub.validateUser.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.validateUser();
|
|
||||||
expect(scope.busyValidate).to.be.true;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('login', function() {
|
|
||||||
it('should work', function() {
|
|
||||||
scope.form.$invalid = false;
|
|
||||||
authStub.setCredentials.returns();
|
|
||||||
|
|
||||||
scope.login();
|
|
||||||
expect(authStub.setCredentials.calledOnce).to.be.true;
|
|
||||||
expect(location.path.calledWith('/login')).to.be.true;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('connectToGoogle', function() {
|
|
||||||
it('should forward to login', function() {
|
|
||||||
authStub._oauth = {
|
|
||||||
isSupported: function() {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
authStub.getOAuthToken.yields();
|
|
||||||
|
|
||||||
scope.connectToGoogle();
|
|
||||||
|
|
||||||
expect(location.path.calledWith('/login-set-credentials')).to.be.true;
|
|
||||||
expect(location.search.calledWith({
|
|
||||||
provider: 'gmail'
|
|
||||||
})).to.be.true;
|
|
||||||
expect(authStub.getOAuthToken.calledOnce).to.be.true;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not use oauth for gmail', function() {
|
|
||||||
authStub._oauth = {
|
|
||||||
isSupported: function() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.connectToGoogle();
|
|
||||||
|
|
||||||
expect(location.path.calledWith('/login-set-credentials')).to.be.true;
|
|
||||||
expect(location.search.calledWith({
|
|
||||||
provider: 'gmail'
|
|
||||||
})).to.be.true;
|
|
||||||
expect(authStub.getOAuthToken.called).to.be.false;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not forward to login when oauth fails', function(done) {
|
|
||||||
authStub._oauth = {
|
|
||||||
isSupported: function() {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
authStub.getOAuthToken.yields(new Error());
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(location.path.called).to.be.false;
|
|
||||||
expect(location.search.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.connectToGoogle();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('connectTo', function() {
|
|
||||||
it('should forward to login', function() {
|
|
||||||
var provider = 'wmail';
|
|
||||||
scope.connectTo(provider);
|
|
||||||
|
|
||||||
expect(location.path.calledWith('/login-set-credentials')).to.be.true;
|
|
||||||
expect(location.search.calledWith({
|
|
||||||
provider: provider
|
|
||||||
})).to.be.true;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
// restore the app controller module
|
||||||
|
appController._auth = origAuth;
|
||||||
|
|
||||||
|
location.path.restore();
|
||||||
|
location.search.restore();
|
||||||
|
if (scope.$apply.restore) {
|
||||||
|
scope.$apply.restore();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('createWhiteoutAccount', function() {
|
||||||
|
it('should return early for invalid form', function() {
|
||||||
|
scope.form.$invalid = true;
|
||||||
|
scope.createWhiteoutAccount();
|
||||||
|
expect(adminStub.createUser.called).to.be.false;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail to error creating user', function(done) {
|
||||||
|
scope.form.$invalid = false;
|
||||||
|
scope.betaCode = 'asfd';
|
||||||
|
scope.phone = '12345';
|
||||||
|
adminStub.createUser.yieldsAsync(new Error('asdf'));
|
||||||
|
|
||||||
|
scope.$apply = function() {
|
||||||
|
expect(scope.busy).to.be.false;
|
||||||
|
expect(scope.errMsg).to.equal('asdf');
|
||||||
|
expect(adminStub.createUser.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.createWhiteoutAccount();
|
||||||
|
expect(scope.busy).to.be.true;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
scope.form.$invalid = false;
|
||||||
|
scope.betaCode = 'asfd';
|
||||||
|
scope.phone = '12345';
|
||||||
|
adminStub.createUser.yieldsAsync();
|
||||||
|
|
||||||
|
scope.$apply = function() {
|
||||||
|
expect(scope.busy).to.be.false;
|
||||||
|
expect(scope.errMsg).to.be.undefined;
|
||||||
|
expect(scope.step).to.equal(3);
|
||||||
|
expect(adminStub.createUser.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.createWhiteoutAccount();
|
||||||
|
expect(scope.busy).to.be.true;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('validateUser', function() {
|
||||||
|
it('should return early for invalid form', function() {
|
||||||
|
scope.formValidate.$invalid = true;
|
||||||
|
scope.validateUser();
|
||||||
|
expect(adminStub.validateUser.called).to.be.false;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail to error creating user', function(done) {
|
||||||
|
scope.formValidate.$invalid = false;
|
||||||
|
scope.token = 'asfd';
|
||||||
|
adminStub.validateUser.yieldsAsync(new Error('asdf'));
|
||||||
|
|
||||||
|
scope.$apply = function() {
|
||||||
|
expect(scope.busyValidate).to.be.false;
|
||||||
|
expect(scope.errMsgValidate).to.equal('asdf');
|
||||||
|
expect(adminStub.validateUser.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.validateUser();
|
||||||
|
expect(scope.busyValidate).to.be.true;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
scope.formValidate.$invalid = false;
|
||||||
|
scope.token = 'asfd';
|
||||||
|
adminStub.validateUser.yieldsAsync();
|
||||||
|
|
||||||
|
scope.login = function() {
|
||||||
|
expect(scope.busyValidate).to.be.true;
|
||||||
|
expect(scope.errMsgValidate).to.be.undefined;
|
||||||
|
expect(adminStub.validateUser.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.validateUser();
|
||||||
|
expect(scope.busyValidate).to.be.true;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('login', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
scope.form.$invalid = false;
|
||||||
|
authStub.setCredentials.returns();
|
||||||
|
|
||||||
|
scope.login();
|
||||||
|
expect(authStub.setCredentials.calledOnce).to.be.true;
|
||||||
|
expect(location.path.calledWith('/login')).to.be.true;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('connectToGoogle', function() {
|
||||||
|
it('should forward to login', function() {
|
||||||
|
authStub._oauth = {
|
||||||
|
isSupported: function() {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
authStub.getOAuthToken.yields();
|
||||||
|
|
||||||
|
scope.connectToGoogle();
|
||||||
|
|
||||||
|
expect(location.path.calledWith('/login-set-credentials')).to.be.true;
|
||||||
|
expect(location.search.calledWith({
|
||||||
|
provider: 'gmail'
|
||||||
|
})).to.be.true;
|
||||||
|
expect(authStub.getOAuthToken.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not use oauth for gmail', function() {
|
||||||
|
authStub._oauth = {
|
||||||
|
isSupported: function() {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.connectToGoogle();
|
||||||
|
|
||||||
|
expect(location.path.calledWith('/login-set-credentials')).to.be.true;
|
||||||
|
expect(location.search.calledWith({
|
||||||
|
provider: 'gmail'
|
||||||
|
})).to.be.true;
|
||||||
|
expect(authStub.getOAuthToken.called).to.be.false;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not forward to login when oauth fails', function(done) {
|
||||||
|
authStub._oauth = {
|
||||||
|
isSupported: function() {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
authStub.getOAuthToken.yields(new Error());
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(location.path.called).to.be.false;
|
||||||
|
expect(location.search.called).to.be.false;
|
||||||
|
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.connectToGoogle();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('connectTo', function() {
|
||||||
|
it('should forward to login', function() {
|
||||||
|
var provider = 'wmail';
|
||||||
|
scope.connectTo(provider);
|
||||||
|
|
||||||
|
expect(location.path.calledWith('/login-set-credentials')).to.be.true;
|
||||||
|
expect(location.search.calledWith({
|
||||||
|
provider: provider
|
||||||
|
})).to.be.true;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
});
|
});
|
@ -1,146 +1,142 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var RestDAO = require('js/dao/rest-dao'),
|
var RestDAO = require('../../src/js/dao/rest-dao'),
|
||||||
AdminDAO = require('js/dao/admin-dao'),
|
AdminDAO = require('../../src/js/dao/admin-dao');
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
describe('Admin DAO unit tests', function() {
|
describe('Admin DAO unit tests', function() {
|
||||||
|
|
||||||
var adminDao, restDaoStub,
|
var adminDao, restDaoStub,
|
||||||
emailAddress = 'test@example.com',
|
emailAddress = 'test@example.com',
|
||||||
password = 'secret';
|
password = 'secret';
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
restDaoStub = sinon.createStubInstance(RestDAO);
|
restDaoStub = sinon.createStubInstance(RestDAO);
|
||||||
adminDao = new AdminDAO(restDaoStub);
|
adminDao = new AdminDAO(restDaoStub);
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {});
|
afterEach(function() {});
|
||||||
|
|
||||||
describe('createUser', function() {
|
describe('createUser', function() {
|
||||||
it('should fail due to incomplete args', function(done) {
|
it('should fail due to incomplete args', function(done) {
|
||||||
var opt = {
|
var opt = {
|
||||||
emailAddress: emailAddress
|
emailAddress: emailAddress
|
||||||
};
|
};
|
||||||
|
|
||||||
adminDao.createUser(opt, function(err) {
|
adminDao.createUser(opt, function(err) {
|
||||||
expect(err).to.exist;
|
expect(err).to.exist;
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail if user already exists', function(done) {
|
|
||||||
var opt = {
|
|
||||||
emailAddress: emailAddress,
|
|
||||||
password: password,
|
|
||||||
phone: '12345'
|
|
||||||
};
|
|
||||||
|
|
||||||
restDaoStub.post.withArgs(opt, '/user').yields({
|
|
||||||
code: 409
|
|
||||||
});
|
|
||||||
|
|
||||||
adminDao.createUser(opt, function(err) {
|
|
||||||
expect(err.message).to.contain('already taken');
|
|
||||||
expect(restDaoStub.post.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail due to unknown error', function(done) {
|
|
||||||
var opt = {
|
|
||||||
emailAddress: emailAddress,
|
|
||||||
password: password,
|
|
||||||
phone: '12345'
|
|
||||||
};
|
|
||||||
|
|
||||||
restDaoStub.post.withArgs(opt, '/user').yields(new Error());
|
|
||||||
|
|
||||||
adminDao.createUser(opt, function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(restDaoStub.post.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
var opt = {
|
|
||||||
emailAddress: emailAddress,
|
|
||||||
password: password,
|
|
||||||
phone: '12345'
|
|
||||||
};
|
|
||||||
|
|
||||||
restDaoStub.post.withArgs(opt, '/user').yields();
|
|
||||||
|
|
||||||
adminDao.createUser(opt, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(restDaoStub.post.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('validateUser', function() {
|
it('should fail if user already exists', function(done) {
|
||||||
it('should fail due to incomplete args', function(done) {
|
var opt = {
|
||||||
var opt = {
|
emailAddress: emailAddress,
|
||||||
emailAddress: emailAddress
|
password: password,
|
||||||
};
|
phone: '12345'
|
||||||
|
};
|
||||||
|
|
||||||
adminDao.validateUser(opt, function(err) {
|
restDaoStub.post.withArgs(opt, '/user').yields({
|
||||||
expect(err).to.exist;
|
code: 409
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should fail due to error in rest api', function(done) {
|
adminDao.createUser(opt, function(err) {
|
||||||
var opt = {
|
expect(err.message).to.contain('already taken');
|
||||||
emailAddress: emailAddress,
|
expect(restDaoStub.post.calledOnce).to.be.true;
|
||||||
token: 'H45Z6D'
|
done();
|
||||||
};
|
|
||||||
|
|
||||||
restDaoStub.post.withArgs(opt, '/user/validate').yields(new Error());
|
|
||||||
|
|
||||||
adminDao.validateUser(opt, function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(restDaoStub.post.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work with no error object', function(done) {
|
|
||||||
var opt = {
|
|
||||||
emailAddress: emailAddress,
|
|
||||||
token: 'H45Z6D'
|
|
||||||
};
|
|
||||||
|
|
||||||
restDaoStub.post.withArgs(opt, '/user/validate').yields();
|
|
||||||
|
|
||||||
adminDao.validateUser(opt, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(restDaoStub.post.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work with 202', function(done) {
|
|
||||||
var opt = {
|
|
||||||
emailAddress: emailAddress,
|
|
||||||
token: 'H45Z6D'
|
|
||||||
};
|
|
||||||
|
|
||||||
restDaoStub.post.withArgs(opt, '/user/validate').yields({
|
|
||||||
code: 202
|
|
||||||
});
|
|
||||||
|
|
||||||
adminDao.validateUser(opt, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(restDaoStub.post.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should fail due to unknown error', function(done) {
|
||||||
|
var opt = {
|
||||||
|
emailAddress: emailAddress,
|
||||||
|
password: password,
|
||||||
|
phone: '12345'
|
||||||
|
};
|
||||||
|
|
||||||
|
restDaoStub.post.withArgs(opt, '/user').yields(new Error());
|
||||||
|
|
||||||
|
adminDao.createUser(opt, function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(restDaoStub.post.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
var opt = {
|
||||||
|
emailAddress: emailAddress,
|
||||||
|
password: password,
|
||||||
|
phone: '12345'
|
||||||
|
};
|
||||||
|
|
||||||
|
restDaoStub.post.withArgs(opt, '/user').yields();
|
||||||
|
|
||||||
|
adminDao.createUser(opt, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(restDaoStub.post.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('validateUser', function() {
|
||||||
|
it('should fail due to incomplete args', function(done) {
|
||||||
|
var opt = {
|
||||||
|
emailAddress: emailAddress
|
||||||
|
};
|
||||||
|
|
||||||
|
adminDao.validateUser(opt, function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail due to error in rest api', function(done) {
|
||||||
|
var opt = {
|
||||||
|
emailAddress: emailAddress,
|
||||||
|
token: 'H45Z6D'
|
||||||
|
};
|
||||||
|
|
||||||
|
restDaoStub.post.withArgs(opt, '/user/validate').yields(new Error());
|
||||||
|
|
||||||
|
adminDao.validateUser(opt, function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(restDaoStub.post.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work with no error object', function(done) {
|
||||||
|
var opt = {
|
||||||
|
emailAddress: emailAddress,
|
||||||
|
token: 'H45Z6D'
|
||||||
|
};
|
||||||
|
|
||||||
|
restDaoStub.post.withArgs(opt, '/user/validate').yields();
|
||||||
|
|
||||||
|
adminDao.validateUser(opt, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(restDaoStub.post.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work with 202', function(done) {
|
||||||
|
var opt = {
|
||||||
|
emailAddress: emailAddress,
|
||||||
|
token: 'H45Z6D'
|
||||||
|
};
|
||||||
|
|
||||||
|
restDaoStub.post.withArgs(opt, '/user/validate').yields({
|
||||||
|
code: 202
|
||||||
|
});
|
||||||
|
|
||||||
|
adminDao.validateUser(opt, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(restDaoStub.post.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
});
|
});
|
@ -1,212 +1,209 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var controller = require('js/app-controller'),
|
var controller = require('../../src/js/app-controller'),
|
||||||
EmailDAO = require('js/dao/email-dao'),
|
EmailDAO = require('../../src/js/dao/email-dao'),
|
||||||
OutboxBO = require('js/bo/outbox'),
|
OutboxBO = require('../../src/js/bo/outbox'),
|
||||||
DeviceStorageDAO = require('js/dao/devicestorage-dao'),
|
DeviceStorageDAO = require('../../src/js/dao/devicestorage-dao'),
|
||||||
UpdateHandler = require('js/util/update/update-handler'),
|
UpdateHandler = require('../../src/js/util/update/update-handler'),
|
||||||
Auth = require('js/bo/auth'),
|
Auth = require('../../src/js/bo/auth');
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
describe('App Controller unit tests', function() {
|
describe('App Controller unit tests', function() {
|
||||||
var emailDaoStub, outboxStub, updateHandlerStub, appConfigStoreStub, devicestorageStub, isOnlineStub, authStub;
|
var emailDaoStub, outboxStub, updateHandlerStub, appConfigStoreStub, devicestorageStub, isOnlineStub, authStub;
|
||||||
|
|
||||||
|
beforeEach(function() {
|
||||||
|
controller._emailDao = emailDaoStub = sinon.createStubInstance(EmailDAO);
|
||||||
|
controller._outboxBo = outboxStub = sinon.createStubInstance(OutboxBO);
|
||||||
|
controller._appConfigStore = appConfigStoreStub = sinon.createStubInstance(DeviceStorageDAO);
|
||||||
|
controller._userStorage = devicestorageStub = sinon.createStubInstance(DeviceStorageDAO);
|
||||||
|
controller._updateHandler = updateHandlerStub = sinon.createStubInstance(UpdateHandler);
|
||||||
|
controller._auth = authStub = sinon.createStubInstance(Auth);
|
||||||
|
|
||||||
|
isOnlineStub = sinon.stub(controller, 'isOnline');
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
isOnlineStub.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('buildModules', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
controller.buildModules({
|
||||||
|
onError: function() {}
|
||||||
|
});
|
||||||
|
expect(controller._appConfigStore).to.exist;
|
||||||
|
expect(controller._auth).to.exist;
|
||||||
|
expect(controller._userStorage).to.exist;
|
||||||
|
expect(controller._invitationDao).to.exist;
|
||||||
|
expect(controller._keychain).to.exist;
|
||||||
|
expect(controller._pgp).to.exist;
|
||||||
|
expect(controller._pgpbuilder).to.exist;
|
||||||
|
expect(controller._emailDao).to.exist;
|
||||||
|
expect(controller._outboxBo).to.exist;
|
||||||
|
expect(controller._updateHandler).to.exist;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('start', function() {
|
||||||
|
it('should not explode', function(done) {
|
||||||
|
controller.start({
|
||||||
|
onError: function() {}
|
||||||
|
}, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('onDisconnect', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
controller.onDisconnect();
|
||||||
|
|
||||||
|
expect(emailDaoStub.onDisconnect.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('logout', function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
authStub.logout.yields();
|
||||||
|
emailDaoStub.onDisconnect.yields(new Error());
|
||||||
|
|
||||||
|
controller.onError = function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(authStub.logout.calledOnce).to.be.true;
|
||||||
|
expect(emailDaoStub.onDisconnect.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
controller.logout();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('onConnect', function() {
|
||||||
|
beforeEach(function() {
|
||||||
|
controller._emailDao._account = {};
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not connect if offline', function(done) {
|
||||||
|
isOnlineStub.returns(false);
|
||||||
|
|
||||||
|
controller.onConnect(function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not connect if account is not initialized', function(done) {
|
||||||
|
controller._emailDao._account = null;
|
||||||
|
|
||||||
|
controller.onConnect(function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail due to error in auth.getCredentials', function(done) {
|
||||||
|
isOnlineStub.returns(true);
|
||||||
|
authStub.getCredentials.yields(new Error());
|
||||||
|
|
||||||
|
controller.onConnect(function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(authStub.getCredentials.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
isOnlineStub.returns(true);
|
||||||
|
authStub.getCredentials.yields(null, {
|
||||||
|
emailAddress: 'asdf@example.com',
|
||||||
|
oauthToken: 'token',
|
||||||
|
sslCert: 'cert',
|
||||||
|
imap: {},
|
||||||
|
smtp: {}
|
||||||
|
});
|
||||||
|
emailDaoStub.onConnect.yields();
|
||||||
|
|
||||||
|
controller.onConnect(function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(authStub.getCredentials.calledOnce).to.be.true;
|
||||||
|
expect(emailDaoStub.onConnect.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('init', function() {
|
||||||
|
var onConnectStub, emailAddress;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
controller._emailDao = emailDaoStub = sinon.createStubInstance(EmailDAO);
|
emailAddress = 'alice@bob.com';
|
||||||
controller._outboxBo = outboxStub = sinon.createStubInstance(OutboxBO);
|
|
||||||
controller._appConfigStore = appConfigStoreStub = sinon.createStubInstance(DeviceStorageDAO);
|
|
||||||
controller._userStorage = devicestorageStub = sinon.createStubInstance(DeviceStorageDAO);
|
|
||||||
controller._updateHandler = updateHandlerStub = sinon.createStubInstance(UpdateHandler);
|
|
||||||
controller._auth = authStub = sinon.createStubInstance(Auth);
|
|
||||||
|
|
||||||
isOnlineStub = sinon.stub(controller, 'isOnline');
|
// onConnect
|
||||||
|
onConnectStub = sinon.stub(controller, 'onConnect');
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
afterEach(function() {
|
||||||
isOnlineStub.restore();
|
onConnectStub.restore();
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('buildModules', function() {
|
it('should fail due to error in storage initialization', function(done) {
|
||||||
it('should work', function() {
|
devicestorageStub.init.withArgs(undefined).yields({});
|
||||||
controller.buildModules({
|
|
||||||
onError: function() {}
|
controller.init({}, function(err, keypair) {
|
||||||
});
|
expect(err).to.exist;
|
||||||
expect(controller._appConfigStore).to.exist;
|
expect(keypair).to.not.exist;
|
||||||
expect(controller._auth).to.exist;
|
expect(devicestorageStub.init.calledOnce).to.be.true;
|
||||||
expect(controller._userStorage).to.exist;
|
expect(updateHandlerStub.update.calledOnce).to.be.false;
|
||||||
expect(controller._invitationDao).to.exist;
|
done();
|
||||||
expect(controller._keychain).to.exist;
|
|
||||||
expect(controller._pgp).to.exist;
|
|
||||||
expect(controller._pgpbuilder).to.exist;
|
|
||||||
expect(controller._emailDao).to.exist;
|
|
||||||
expect(controller._outboxBo).to.exist;
|
|
||||||
expect(controller._updateHandler).to.exist;
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('start', function() {
|
it('should fail due to error in update handler', function(done) {
|
||||||
it('should not explode', function(done) {
|
devicestorageStub.init.yields();
|
||||||
controller.start({
|
updateHandlerStub.update.yields({});
|
||||||
onError: function() {}
|
|
||||||
}, function(err) {
|
controller.init({
|
||||||
expect(err).to.not.exist;
|
emailAddress: emailAddress
|
||||||
done();
|
}, function(err, keypair) {
|
||||||
});
|
expect(err).to.exist;
|
||||||
|
expect(keypair).to.not.exist;
|
||||||
|
expect(updateHandlerStub.update.calledOnce).to.be.true;
|
||||||
|
expect(devicestorageStub.init.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('onDisconnect', function() {
|
it('should fail due to error in emailDao.init', function(done) {
|
||||||
it('should work', function() {
|
devicestorageStub.init.yields();
|
||||||
controller.onDisconnect();
|
updateHandlerStub.update.yields();
|
||||||
|
emailDaoStub.init.yields({});
|
||||||
|
|
||||||
expect(emailDaoStub.onDisconnect.calledOnce).to.be.true;
|
controller.init({
|
||||||
|
emailAddress: emailAddress
|
||||||
|
}, function(err, keypair) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(keypair).to.not.exist;
|
||||||
|
expect(updateHandlerStub.update.calledOnce).to.be.true;
|
||||||
|
expect(emailDaoStub.init.calledOnce).to.be.true;
|
||||||
|
expect(devicestorageStub.init.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('logout', function() {
|
it('should work and return a keypair', function(done) {
|
||||||
it('should work', function(done) {
|
devicestorageStub.init.withArgs(emailAddress).yields();
|
||||||
authStub.logout.yields();
|
emailDaoStub.init.yields(null, {});
|
||||||
emailDaoStub.onDisconnect.yields(new Error());
|
updateHandlerStub.update.yields();
|
||||||
|
|
||||||
controller.onError = function(err) {
|
controller.init({
|
||||||
expect(err).to.exist;
|
emailAddress: emailAddress
|
||||||
expect(authStub.logout.calledOnce).to.be.true;
|
}, function(err, keypair) {
|
||||||
expect(emailDaoStub.onDisconnect.calledOnce).to.be.true;
|
expect(err).to.not.exist;
|
||||||
done();
|
expect(keypair).to.exist;
|
||||||
};
|
expect(updateHandlerStub.update.calledOnce).to.be.true;
|
||||||
|
expect(emailDaoStub.init.calledOnce).to.be.true;
|
||||||
controller.logout();
|
expect(devicestorageStub.init.calledOnce).to.be.true;
|
||||||
});
|
done();
|
||||||
});
|
|
||||||
|
|
||||||
describe('onConnect', function() {
|
|
||||||
beforeEach(function() {
|
|
||||||
controller._emailDao._account = {};
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not connect if offline', function(done) {
|
|
||||||
isOnlineStub.returns(false);
|
|
||||||
|
|
||||||
controller.onConnect(function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not connect if account is not initialized', function(done) {
|
|
||||||
controller._emailDao._account = null;
|
|
||||||
|
|
||||||
controller.onConnect(function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail due to error in auth.getCredentials', function(done) {
|
|
||||||
isOnlineStub.returns(true);
|
|
||||||
authStub.getCredentials.yields(new Error());
|
|
||||||
|
|
||||||
controller.onConnect(function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(authStub.getCredentials.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
isOnlineStub.returns(true);
|
|
||||||
authStub.getCredentials.yields(null, {
|
|
||||||
emailAddress: 'asdf@example.com',
|
|
||||||
oauthToken: 'token',
|
|
||||||
sslCert: 'cert',
|
|
||||||
imap: {},
|
|
||||||
smtp: {}
|
|
||||||
});
|
|
||||||
emailDaoStub.onConnect.yields();
|
|
||||||
|
|
||||||
controller.onConnect(function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(authStub.getCredentials.calledOnce).to.be.true;
|
|
||||||
expect(emailDaoStub.onConnect.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('init', function() {
|
|
||||||
var onConnectStub, emailAddress;
|
|
||||||
|
|
||||||
beforeEach(function() {
|
|
||||||
emailAddress = 'alice@bob.com';
|
|
||||||
|
|
||||||
// onConnect
|
|
||||||
onConnectStub = sinon.stub(controller, 'onConnect');
|
|
||||||
});
|
|
||||||
|
|
||||||
afterEach(function() {
|
|
||||||
onConnectStub.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail due to error in storage initialization', function(done) {
|
|
||||||
devicestorageStub.init.withArgs(undefined).yields({});
|
|
||||||
|
|
||||||
controller.init({}, function(err, keypair) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(keypair).to.not.exist;
|
|
||||||
expect(devicestorageStub.init.calledOnce).to.be.true;
|
|
||||||
expect(updateHandlerStub.update.calledOnce).to.be.false;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail due to error in update handler', function(done) {
|
|
||||||
devicestorageStub.init.yields();
|
|
||||||
updateHandlerStub.update.yields({});
|
|
||||||
|
|
||||||
controller.init({
|
|
||||||
emailAddress: emailAddress
|
|
||||||
}, function(err, keypair) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(keypair).to.not.exist;
|
|
||||||
expect(updateHandlerStub.update.calledOnce).to.be.true;
|
|
||||||
expect(devicestorageStub.init.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail due to error in emailDao.init', function(done) {
|
|
||||||
devicestorageStub.init.yields();
|
|
||||||
updateHandlerStub.update.yields();
|
|
||||||
emailDaoStub.init.yields({});
|
|
||||||
|
|
||||||
controller.init({
|
|
||||||
emailAddress: emailAddress
|
|
||||||
}, function(err, keypair) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(keypair).to.not.exist;
|
|
||||||
expect(updateHandlerStub.update.calledOnce).to.be.true;
|
|
||||||
expect(emailDaoStub.init.calledOnce).to.be.true;
|
|
||||||
expect(devicestorageStub.init.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work and return a keypair', function(done) {
|
|
||||||
devicestorageStub.init.withArgs(emailAddress).yields();
|
|
||||||
emailDaoStub.init.yields(null, {});
|
|
||||||
updateHandlerStub.update.yields();
|
|
||||||
|
|
||||||
controller.init({
|
|
||||||
emailAddress: emailAddress
|
|
||||||
}, function(err, keypair) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(keypair).to.exist;
|
|
||||||
expect(updateHandlerStub.update.calledOnce).to.be.true;
|
|
||||||
expect(emailDaoStub.init.calledOnce).to.be.true;
|
|
||||||
expect(devicestorageStub.init.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -1,377 +1,374 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var Auth = require('js/bo/auth'),
|
var Auth = require('../../src/js/bo/auth'),
|
||||||
OAuth = require('js/util/oauth'),
|
OAuth = require('../../src/js/util/oauth'),
|
||||||
PGP = require('js/crypto/pgp'),
|
PGP = require('../../src/js/crypto/pgp'),
|
||||||
DeviceStorageDAO = require('js/dao/devicestorage-dao'),
|
DeviceStorageDAO = require('../../src/js/dao/devicestorage-dao');
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
describe('Auth unit tests', function() {
|
describe('Auth unit tests', function() {
|
||||||
// Constancts
|
// Constancts
|
||||||
var EMAIL_ADDR_DB_KEY = 'emailaddress';
|
var EMAIL_ADDR_DB_KEY = 'emailaddress';
|
||||||
var USERNAME_DB_KEY = 'username';
|
var USERNAME_DB_KEY = 'username';
|
||||||
var REALNAME_DB_KEY = 'realname';
|
var REALNAME_DB_KEY = 'realname';
|
||||||
var PASSWD_DB_KEY = 'password';
|
var PASSWD_DB_KEY = 'password';
|
||||||
var PROVIDER_DB_KEY = 'provider';
|
var PROVIDER_DB_KEY = 'provider';
|
||||||
var IMAP_DB_KEY = 'imap';
|
var IMAP_DB_KEY = 'imap';
|
||||||
var SMTP_DB_KEY = 'smtp';
|
var SMTP_DB_KEY = 'smtp';
|
||||||
// SUT
|
// SUT
|
||||||
var auth;
|
var auth;
|
||||||
|
|
||||||
// Dependencies
|
// Dependencies
|
||||||
var storageStub, oauthStub, pgpStub;
|
var storageStub, oauthStub, pgpStub;
|
||||||
|
|
||||||
// test data
|
// test data
|
||||||
var emailAddress = 'bla@blubb.com';
|
var emailAddress = 'bla@blubb.com';
|
||||||
var password = 'passwordpasswordpassword';
|
var password = 'passwordpasswordpassword';
|
||||||
var encryptedPassword = 'pgppasswordpgppassword';
|
var encryptedPassword = 'pgppasswordpgppassword';
|
||||||
var oauthToken = 'tokentokentokentoken';
|
var oauthToken = 'tokentokentokentoken';
|
||||||
var provider = 'gmail';
|
var provider = 'gmail';
|
||||||
var realname = 'Bla Blubb';
|
var realname = 'Bla Blubb';
|
||||||
var username = 'bla';
|
var username = 'bla';
|
||||||
var imap = {
|
var imap = {
|
||||||
host: 'mail.blablubb.com',
|
host: 'mail.blablubb.com',
|
||||||
port: 123,
|
port: 123,
|
||||||
secure: true,
|
secure: true,
|
||||||
ca: 'PEMPEMPEMPEMPEMPEMPEMPEMPEMPEM'
|
ca: 'PEMPEMPEMPEMPEMPEMPEMPEMPEMPEM'
|
||||||
};
|
};
|
||||||
var smtp = {
|
var smtp = {
|
||||||
host: 'mail.blablubb.com',
|
host: 'mail.blablubb.com',
|
||||||
port: 456,
|
port: 456,
|
||||||
secure: true,
|
secure: true,
|
||||||
ca: 'PEMPEMPEMPEMPEMPEMPEMPEMPEMPEM'
|
ca: 'PEMPEMPEMPEMPEMPEMPEMPEMPEMPEM'
|
||||||
};
|
};
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
storageStub = sinon.createStubInstance(DeviceStorageDAO);
|
storageStub = sinon.createStubInstance(DeviceStorageDAO);
|
||||||
oauthStub = sinon.createStubInstance(OAuth);
|
oauthStub = sinon.createStubInstance(OAuth);
|
||||||
pgpStub = sinon.createStubInstance(PGP);
|
pgpStub = sinon.createStubInstance(PGP);
|
||||||
auth = new Auth(storageStub, oauthStub, pgpStub);
|
auth = new Auth(storageStub, oauthStub, pgpStub);
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('#getCredentials', function() {
|
||||||
|
it('should load credentials and retrieve credentials from cfg', function(done) {
|
||||||
|
storageStub.listItems.withArgs(EMAIL_ADDR_DB_KEY, 0, null).yieldsAsync(null, [emailAddress]);
|
||||||
|
storageStub.listItems.withArgs(PASSWD_DB_KEY, 0, null).yieldsAsync(null, [encryptedPassword]);
|
||||||
|
storageStub.listItems.withArgs(PROVIDER_DB_KEY, 0, null).yieldsAsync(null, [provider]);
|
||||||
|
storageStub.listItems.withArgs(USERNAME_DB_KEY, 0, null).yieldsAsync(null, [username]);
|
||||||
|
storageStub.listItems.withArgs(REALNAME_DB_KEY, 0, null).yieldsAsync(null, [realname]);
|
||||||
|
storageStub.listItems.withArgs(IMAP_DB_KEY, 0, null).yieldsAsync(null, [imap]);
|
||||||
|
storageStub.listItems.withArgs(SMTP_DB_KEY, 0, null).yieldsAsync(null, [smtp]);
|
||||||
|
pgpStub.decrypt.withArgs(encryptedPassword, undefined).yields(null, password);
|
||||||
|
|
||||||
|
auth.getCredentials(function(err, cred) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
|
||||||
|
expect(auth.provider).to.equal(provider);
|
||||||
|
expect(auth.emailAddress).to.equal(emailAddress);
|
||||||
|
expect(auth.password).to.equal(password);
|
||||||
|
|
||||||
|
expect(cred.imap.host).to.equal(imap.host);
|
||||||
|
expect(cred.imap.port).to.equal(imap.port);
|
||||||
|
expect(cred.imap.secure).to.equal(imap.secure);
|
||||||
|
expect(cred.imap.ca).to.equal(imap.ca);
|
||||||
|
expect(cred.imap.auth.user).to.equal(username);
|
||||||
|
expect(cred.imap.auth.pass).to.equal(password);
|
||||||
|
|
||||||
|
expect(cred.smtp.host).to.equal(smtp.host);
|
||||||
|
expect(cred.smtp.port).to.equal(smtp.port);
|
||||||
|
expect(cred.smtp.secure).to.equal(smtp.secure);
|
||||||
|
expect(cred.smtp.ca).to.equal(smtp.ca);
|
||||||
|
expect(cred.smtp.auth.user).to.equal(username);
|
||||||
|
expect(cred.smtp.auth.pass).to.equal(password);
|
||||||
|
|
||||||
|
expect(storageStub.listItems.callCount).to.equal(7);
|
||||||
|
expect(pgpStub.decrypt.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('#setCredentials', function() {
|
||||||
|
it('should set the credentials', function() {
|
||||||
|
auth.setCredentials({
|
||||||
|
provider: 'albhsvadlbvsdalbsadflb',
|
||||||
|
emailAddress: emailAddress,
|
||||||
|
username: username,
|
||||||
|
realname: realname,
|
||||||
|
password: password,
|
||||||
|
imap: imap,
|
||||||
|
smtp: smtp
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(auth.provider).to.equal('albhsvadlbvsdalbsadflb');
|
||||||
|
expect(auth.emailAddress).to.equal(emailAddress);
|
||||||
|
expect(auth.username).to.equal(username);
|
||||||
|
expect(auth.realname).to.equal(realname);
|
||||||
|
expect(auth.password).to.equal(password);
|
||||||
|
expect(auth.smtp).to.equal(smtp);
|
||||||
|
expect(auth.imap).to.equal(imap);
|
||||||
|
expect(auth.credentialsDirty).to.be.true;
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('#getCredentials', function() {
|
});
|
||||||
it('should load credentials and retrieve credentials from cfg', function(done) {
|
|
||||||
storageStub.listItems.withArgs(EMAIL_ADDR_DB_KEY, 0, null).yieldsAsync(null, [emailAddress]);
|
|
||||||
storageStub.listItems.withArgs(PASSWD_DB_KEY, 0, null).yieldsAsync(null, [encryptedPassword]);
|
|
||||||
storageStub.listItems.withArgs(PROVIDER_DB_KEY, 0, null).yieldsAsync(null, [provider]);
|
|
||||||
storageStub.listItems.withArgs(USERNAME_DB_KEY, 0, null).yieldsAsync(null, [username]);
|
|
||||||
storageStub.listItems.withArgs(REALNAME_DB_KEY, 0, null).yieldsAsync(null, [realname]);
|
|
||||||
storageStub.listItems.withArgs(IMAP_DB_KEY, 0, null).yieldsAsync(null, [imap]);
|
|
||||||
storageStub.listItems.withArgs(SMTP_DB_KEY, 0, null).yieldsAsync(null, [smtp]);
|
|
||||||
pgpStub.decrypt.withArgs(encryptedPassword, undefined).yields(null, password);
|
|
||||||
|
|
||||||
auth.getCredentials(function(err, cred) {
|
describe('#storeCredentials', function() {
|
||||||
expect(err).to.not.exist;
|
it('should persist ALL the things!', function(done) {
|
||||||
|
auth.credentialsDirty = true;
|
||||||
|
auth.emailAddress = emailAddress;
|
||||||
|
auth.username = username;
|
||||||
|
auth.realname = realname;
|
||||||
|
auth.password = password;
|
||||||
|
auth.smtp = smtp;
|
||||||
|
auth.imap = imap;
|
||||||
|
auth.provider = provider;
|
||||||
|
|
||||||
expect(auth.provider).to.equal(provider);
|
storageStub.storeList.withArgs([encryptedPassword], PASSWD_DB_KEY).yieldsAsync();
|
||||||
expect(auth.emailAddress).to.equal(emailAddress);
|
storageStub.storeList.withArgs([emailAddress], EMAIL_ADDR_DB_KEY).yieldsAsync();
|
||||||
expect(auth.password).to.equal(password);
|
storageStub.storeList.withArgs([provider], PROVIDER_DB_KEY).yieldsAsync();
|
||||||
|
storageStub.storeList.withArgs([username], USERNAME_DB_KEY).yieldsAsync();
|
||||||
|
storageStub.storeList.withArgs([realname], REALNAME_DB_KEY).yieldsAsync();
|
||||||
|
storageStub.storeList.withArgs([imap], IMAP_DB_KEY).yieldsAsync();
|
||||||
|
storageStub.storeList.withArgs([smtp], SMTP_DB_KEY).yieldsAsync();
|
||||||
|
pgpStub.encrypt.withArgs(password).yields(null, encryptedPassword);
|
||||||
|
|
||||||
expect(cred.imap.host).to.equal(imap.host);
|
auth.storeCredentials(function(err) {
|
||||||
expect(cred.imap.port).to.equal(imap.port);
|
expect(err).to.not.exist;
|
||||||
expect(cred.imap.secure).to.equal(imap.secure);
|
|
||||||
expect(cred.imap.ca).to.equal(imap.ca);
|
|
||||||
expect(cred.imap.auth.user).to.equal(username);
|
|
||||||
expect(cred.imap.auth.pass).to.equal(password);
|
|
||||||
|
|
||||||
expect(cred.smtp.host).to.equal(smtp.host);
|
expect(storageStub.storeList.callCount).to.equal(7);
|
||||||
expect(cred.smtp.port).to.equal(smtp.port);
|
expect(pgpStub.encrypt.calledOnce).to.be.true;
|
||||||
expect(cred.smtp.secure).to.equal(smtp.secure);
|
|
||||||
expect(cred.smtp.ca).to.equal(smtp.ca);
|
|
||||||
expect(cred.smtp.auth.user).to.equal(username);
|
|
||||||
expect(cred.smtp.auth.pass).to.equal(password);
|
|
||||||
|
|
||||||
expect(storageStub.listItems.callCount).to.equal(7);
|
done();
|
||||||
expect(pgpStub.decrypt.calledOnce).to.be.true;
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
done();
|
describe('#getOAuthToken', function() {
|
||||||
});
|
it('should refresh token with known email address', function(done) {
|
||||||
|
auth.emailAddress = emailAddress;
|
||||||
|
auth.oauthToken = 'oldToken';
|
||||||
|
|
||||||
|
oauthStub.refreshToken.withArgs({
|
||||||
|
emailAddress: emailAddress,
|
||||||
|
oldToken: 'oldToken'
|
||||||
|
}).yieldsAsync(null, oauthToken);
|
||||||
|
|
||||||
|
auth.getOAuthToken(function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(auth.emailAddress).to.equal(emailAddress);
|
||||||
|
expect(auth.oauthToken).to.equal(oauthToken);
|
||||||
|
|
||||||
|
expect(oauthStub.refreshToken.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('#setCredentials', function() {
|
it('should fetch token with known email address', function(done) {
|
||||||
it('should set the credentials', function() {
|
auth.emailAddress = emailAddress;
|
||||||
auth.setCredentials({
|
oauthStub.getOAuthToken.withArgs(emailAddress).yieldsAsync(null, oauthToken);
|
||||||
provider: 'albhsvadlbvsdalbsadflb',
|
|
||||||
emailAddress: emailAddress,
|
|
||||||
username: username,
|
|
||||||
realname: realname,
|
|
||||||
password: password,
|
|
||||||
imap: imap,
|
|
||||||
smtp: smtp
|
|
||||||
});
|
|
||||||
|
|
||||||
expect(auth.provider).to.equal('albhsvadlbvsdalbsadflb');
|
auth.getOAuthToken(function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
expect(auth.emailAddress).to.equal(emailAddress);
|
expect(auth.emailAddress).to.equal(emailAddress);
|
||||||
|
expect(auth.oauthToken).to.equal(oauthToken);
|
||||||
|
|
||||||
|
expect(oauthStub.getOAuthToken.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fetch token with unknown email address', function(done) {
|
||||||
|
oauthStub.getOAuthToken.withArgs(undefined).yieldsAsync(null, oauthToken);
|
||||||
|
oauthStub.queryEmailAddress.withArgs(oauthToken).yieldsAsync(null, emailAddress);
|
||||||
|
|
||||||
|
auth.getOAuthToken(function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(auth.emailAddress).to.equal(emailAddress);
|
||||||
|
expect(auth.oauthToken).to.equal(oauthToken);
|
||||||
|
|
||||||
|
expect(oauthStub.getOAuthToken.calledOnce).to.be.true;
|
||||||
|
expect(oauthStub.queryEmailAddress.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail when email address fetch fails', function(done) {
|
||||||
|
oauthStub.getOAuthToken.yieldsAsync(null, oauthToken);
|
||||||
|
oauthStub.queryEmailAddress.yieldsAsync(new Error());
|
||||||
|
|
||||||
|
auth.getOAuthToken(function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(auth.emailAddress).to.not.exist;
|
||||||
|
expect(auth.oauthToken).to.not.exist;
|
||||||
|
|
||||||
|
expect(oauthStub.getOAuthToken.calledOnce).to.be.true;
|
||||||
|
expect(oauthStub.queryEmailAddress.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail when oauth fetch fails', function(done) {
|
||||||
|
oauthStub.getOAuthToken.yieldsAsync(new Error());
|
||||||
|
|
||||||
|
auth.getOAuthToken(function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(auth.emailAddress).to.not.exist;
|
||||||
|
expect(auth.oauthToken).to.not.exist;
|
||||||
|
|
||||||
|
expect(oauthStub.getOAuthToken.calledOnce).to.be.true;
|
||||||
|
expect(oauthStub.queryEmailAddress.called).to.be.false;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('#_loadCredentials', function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
storageStub.listItems.withArgs(EMAIL_ADDR_DB_KEY, 0, null).yieldsAsync(null, [emailAddress]);
|
||||||
|
storageStub.listItems.withArgs(PASSWD_DB_KEY, 0, null).yieldsAsync(null, [encryptedPassword]);
|
||||||
|
storageStub.listItems.withArgs(PROVIDER_DB_KEY, 0, null).yieldsAsync(null, [provider]);
|
||||||
|
storageStub.listItems.withArgs(USERNAME_DB_KEY, 0, null).yieldsAsync(null, [username]);
|
||||||
|
storageStub.listItems.withArgs(REALNAME_DB_KEY, 0, null).yieldsAsync(null, [realname]);
|
||||||
|
storageStub.listItems.withArgs(IMAP_DB_KEY, 0, null).yieldsAsync(null, [imap]);
|
||||||
|
storageStub.listItems.withArgs(SMTP_DB_KEY, 0, null).yieldsAsync(null, [smtp]);
|
||||||
|
|
||||||
|
auth._loadCredentials(function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(auth.emailAddress).to.equal(emailAddress);
|
||||||
|
expect(auth.password).to.equal(encryptedPassword);
|
||||||
|
expect(auth.provider).to.equal(provider);
|
||||||
|
expect(auth.imap).to.equal(imap);
|
||||||
|
expect(auth.smtp).to.equal(smtp);
|
||||||
expect(auth.username).to.equal(username);
|
expect(auth.username).to.equal(username);
|
||||||
expect(auth.realname).to.equal(realname);
|
expect(auth.realname).to.equal(realname);
|
||||||
expect(auth.password).to.equal(password);
|
|
||||||
expect(auth.smtp).to.equal(smtp);
|
|
||||||
expect(auth.imap).to.equal(imap);
|
|
||||||
expect(auth.credentialsDirty).to.be.true;
|
|
||||||
});
|
|
||||||
|
|
||||||
});
|
expect(auth.passwordNeedsDecryption).to.be.true;
|
||||||
|
|
||||||
describe('#storeCredentials', function() {
|
expect(storageStub.listItems.callCount).to.equal(7);
|
||||||
it('should persist ALL the things!', function(done) {
|
|
||||||
auth.credentialsDirty = true;
|
|
||||||
auth.emailAddress = emailAddress;
|
|
||||||
auth.username = username;
|
|
||||||
auth.realname = realname;
|
|
||||||
auth.password = password;
|
|
||||||
auth.smtp = smtp;
|
|
||||||
auth.imap = imap;
|
|
||||||
auth.provider = provider;
|
|
||||||
|
|
||||||
storageStub.storeList.withArgs([encryptedPassword], PASSWD_DB_KEY).yieldsAsync();
|
done();
|
||||||
storageStub.storeList.withArgs([emailAddress], EMAIL_ADDR_DB_KEY).yieldsAsync();
|
|
||||||
storageStub.storeList.withArgs([provider], PROVIDER_DB_KEY).yieldsAsync();
|
|
||||||
storageStub.storeList.withArgs([username], USERNAME_DB_KEY).yieldsAsync();
|
|
||||||
storageStub.storeList.withArgs([realname], REALNAME_DB_KEY).yieldsAsync();
|
|
||||||
storageStub.storeList.withArgs([imap], IMAP_DB_KEY).yieldsAsync();
|
|
||||||
storageStub.storeList.withArgs([smtp], SMTP_DB_KEY).yieldsAsync();
|
|
||||||
pgpStub.encrypt.withArgs(password).yields(null, encryptedPassword);
|
|
||||||
|
|
||||||
auth.storeCredentials(function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
|
|
||||||
expect(storageStub.storeList.callCount).to.equal(7);
|
|
||||||
expect(pgpStub.encrypt.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('#getOAuthToken', function() {
|
it('should fail', function(done) {
|
||||||
it('should refresh token with known email address', function(done) {
|
storageStub.listItems.yieldsAsync(new Error());
|
||||||
auth.emailAddress = emailAddress;
|
|
||||||
auth.oauthToken = 'oldToken';
|
|
||||||
|
|
||||||
oauthStub.refreshToken.withArgs({
|
auth._loadCredentials(function(err) {
|
||||||
emailAddress: emailAddress,
|
expect(err).to.exist;
|
||||||
oldToken: 'oldToken'
|
expect(auth.emailAddress).to.not.exist;
|
||||||
}).yieldsAsync(null, oauthToken);
|
expect(auth.password).to.not.exist;
|
||||||
|
expect(auth.provider).to.not.exist;
|
||||||
|
expect(auth.imap).to.not.exist;
|
||||||
|
expect(auth.smtp).to.not.exist;
|
||||||
|
expect(auth.username).to.not.exist;
|
||||||
|
expect(auth.realname).to.not.exist;
|
||||||
|
|
||||||
auth.getOAuthToken(function(err) {
|
expect(storageStub.listItems.calledOnce).to.be.true;
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(auth.emailAddress).to.equal(emailAddress);
|
|
||||||
expect(auth.oauthToken).to.equal(oauthToken);
|
|
||||||
|
|
||||||
expect(oauthStub.refreshToken.calledOnce).to.be.true;
|
done();
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fetch token with known email address', function(done) {
|
|
||||||
auth.emailAddress = emailAddress;
|
|
||||||
oauthStub.getOAuthToken.withArgs(emailAddress).yieldsAsync(null, oauthToken);
|
|
||||||
|
|
||||||
auth.getOAuthToken(function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(auth.emailAddress).to.equal(emailAddress);
|
|
||||||
expect(auth.oauthToken).to.equal(oauthToken);
|
|
||||||
|
|
||||||
expect(oauthStub.getOAuthToken.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fetch token with unknown email address', function(done) {
|
|
||||||
oauthStub.getOAuthToken.withArgs(undefined).yieldsAsync(null, oauthToken);
|
|
||||||
oauthStub.queryEmailAddress.withArgs(oauthToken).yieldsAsync(null, emailAddress);
|
|
||||||
|
|
||||||
auth.getOAuthToken(function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(auth.emailAddress).to.equal(emailAddress);
|
|
||||||
expect(auth.oauthToken).to.equal(oauthToken);
|
|
||||||
|
|
||||||
expect(oauthStub.getOAuthToken.calledOnce).to.be.true;
|
|
||||||
expect(oauthStub.queryEmailAddress.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail when email address fetch fails', function(done) {
|
|
||||||
oauthStub.getOAuthToken.yieldsAsync(null, oauthToken);
|
|
||||||
oauthStub.queryEmailAddress.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
auth.getOAuthToken(function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(auth.emailAddress).to.not.exist;
|
|
||||||
expect(auth.oauthToken).to.not.exist;
|
|
||||||
|
|
||||||
expect(oauthStub.getOAuthToken.calledOnce).to.be.true;
|
|
||||||
expect(oauthStub.queryEmailAddress.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail when oauth fetch fails', function(done) {
|
|
||||||
oauthStub.getOAuthToken.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
auth.getOAuthToken(function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(auth.emailAddress).to.not.exist;
|
|
||||||
expect(auth.oauthToken).to.not.exist;
|
|
||||||
|
|
||||||
expect(oauthStub.getOAuthToken.calledOnce).to.be.true;
|
|
||||||
expect(oauthStub.queryEmailAddress.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe('#_loadCredentials', function() {
|
describe('#handleCertificateUpdate', function() {
|
||||||
it('should work', function(done) {
|
var storeCredentialsStub;
|
||||||
storageStub.listItems.withArgs(EMAIL_ADDR_DB_KEY, 0, null).yieldsAsync(null, [emailAddress]);
|
var dummyCert = 'cert';
|
||||||
storageStub.listItems.withArgs(PASSWD_DB_KEY, 0, null).yieldsAsync(null, [encryptedPassword]);
|
|
||||||
storageStub.listItems.withArgs(PROVIDER_DB_KEY, 0, null).yieldsAsync(null, [provider]);
|
|
||||||
storageStub.listItems.withArgs(USERNAME_DB_KEY, 0, null).yieldsAsync(null, [username]);
|
|
||||||
storageStub.listItems.withArgs(REALNAME_DB_KEY, 0, null).yieldsAsync(null, [realname]);
|
|
||||||
storageStub.listItems.withArgs(IMAP_DB_KEY, 0, null).yieldsAsync(null, [imap]);
|
|
||||||
storageStub.listItems.withArgs(SMTP_DB_KEY, 0, null).yieldsAsync(null, [smtp]);
|
|
||||||
|
|
||||||
auth._loadCredentials(function(err) {
|
function onConnectDummy() {}
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(auth.emailAddress).to.equal(emailAddress);
|
|
||||||
expect(auth.password).to.equal(encryptedPassword);
|
|
||||||
expect(auth.provider).to.equal(provider);
|
|
||||||
expect(auth.imap).to.equal(imap);
|
|
||||||
expect(auth.smtp).to.equal(smtp);
|
|
||||||
expect(auth.username).to.equal(username);
|
|
||||||
expect(auth.realname).to.equal(realname);
|
|
||||||
|
|
||||||
expect(auth.passwordNeedsDecryption).to.be.true;
|
beforeEach(function() {
|
||||||
|
storeCredentialsStub = sinon.stub(auth, 'storeCredentials');
|
||||||
expect(storageStub.listItems.callCount).to.equal(7);
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail', function(done) {
|
|
||||||
storageStub.listItems.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
auth._loadCredentials(function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(auth.emailAddress).to.not.exist;
|
|
||||||
expect(auth.password).to.not.exist;
|
|
||||||
expect(auth.provider).to.not.exist;
|
|
||||||
expect(auth.imap).to.not.exist;
|
|
||||||
expect(auth.smtp).to.not.exist;
|
|
||||||
expect(auth.username).to.not.exist;
|
|
||||||
expect(auth.realname).to.not.exist;
|
|
||||||
|
|
||||||
expect(storageStub.listItems.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('#handleCertificateUpdate', function() {
|
it('should work for Trust on first use', function(done) {
|
||||||
var storeCredentialsStub;
|
auth.imap = {};
|
||||||
var dummyCert = 'cert';
|
storeCredentialsStub.yields();
|
||||||
|
|
||||||
function onConnectDummy() {}
|
function callback(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(storeCredentialsStub.callCount).to.equal(1);
|
||||||
|
done();
|
||||||
|
}
|
||||||
|
auth.handleCertificateUpdate('imap', onConnectDummy, callback, dummyCert);
|
||||||
|
});
|
||||||
|
|
||||||
beforeEach(function() {
|
it('should work for stored cert', function() {
|
||||||
storeCredentialsStub = sinon.stub(auth, 'storeCredentials');
|
auth.imap = {
|
||||||
});
|
ca: dummyCert
|
||||||
|
};
|
||||||
|
storeCredentialsStub.yields();
|
||||||
|
|
||||||
it('should work for Trust on first use', function(done) {
|
auth.handleCertificateUpdate('imap', onConnectDummy, onConnectDummy, dummyCert);
|
||||||
auth.imap = {};
|
expect(storeCredentialsStub.callCount).to.equal(0);
|
||||||
storeCredentialsStub.yields();
|
});
|
||||||
|
|
||||||
function callback(err) {
|
it('should work for pinned cert', function(done) {
|
||||||
expect(err).to.not.exist;
|
auth.imap = {
|
||||||
expect(storeCredentialsStub.callCount).to.equal(1);
|
ca: 'other',
|
||||||
done();
|
pinned: true
|
||||||
}
|
};
|
||||||
auth.handleCertificateUpdate('imap', onConnectDummy, callback, dummyCert);
|
storeCredentialsStub.yields();
|
||||||
});
|
|
||||||
|
|
||||||
it('should work for stored cert', function() {
|
function callback(err) {
|
||||||
auth.imap = {
|
expect(err).to.exist;
|
||||||
ca: dummyCert
|
expect(err.message).to.exist;
|
||||||
};
|
|
||||||
storeCredentialsStub.yields();
|
|
||||||
|
|
||||||
auth.handleCertificateUpdate('imap', onConnectDummy, onConnectDummy, dummyCert);
|
|
||||||
expect(storeCredentialsStub.callCount).to.equal(0);
|
expect(storeCredentialsStub.callCount).to.equal(0);
|
||||||
});
|
done();
|
||||||
|
}
|
||||||
|
auth.handleCertificateUpdate('imap', onConnectDummy, callback, dummyCert);
|
||||||
|
});
|
||||||
|
|
||||||
it('should work for pinned cert', function(done) {
|
it('should work for updated cert', function(done) {
|
||||||
auth.imap = {
|
auth.imap = {
|
||||||
ca: 'other',
|
ca: 'other'
|
||||||
pinned: true
|
};
|
||||||
};
|
storeCredentialsStub.yields();
|
||||||
storeCredentialsStub.yields();
|
|
||||||
|
|
||||||
function callback(err) {
|
function callback(err) {
|
||||||
|
if (err && err.callback) {
|
||||||
expect(err).to.exist;
|
expect(err).to.exist;
|
||||||
expect(err.message).to.exist;
|
expect(err.message).to.exist;
|
||||||
expect(storeCredentialsStub.callCount).to.equal(0);
|
expect(storeCredentialsStub.callCount).to.equal(0);
|
||||||
|
err.callback(true);
|
||||||
|
} else {
|
||||||
|
expect(storeCredentialsStub.callCount).to.equal(1);
|
||||||
done();
|
done();
|
||||||
}
|
}
|
||||||
auth.handleCertificateUpdate('imap', onConnectDummy, callback, dummyCert);
|
}
|
||||||
});
|
|
||||||
|
|
||||||
it('should work for updated cert', function(done) {
|
function onConnect(callback) {
|
||||||
auth.imap = {
|
callback();
|
||||||
ca: 'other'
|
}
|
||||||
};
|
|
||||||
storeCredentialsStub.yields();
|
|
||||||
|
|
||||||
function callback(err) {
|
auth.handleCertificateUpdate('imap', onConnect, callback, dummyCert);
|
||||||
if (err && err.callback) {
|
});
|
||||||
expect(err).to.exist;
|
});
|
||||||
expect(err.message).to.exist;
|
|
||||||
expect(storeCredentialsStub.callCount).to.equal(0);
|
|
||||||
err.callback(true);
|
|
||||||
} else {
|
|
||||||
expect(storeCredentialsStub.callCount).to.equal(1);
|
|
||||||
done();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
function onConnect(callback) {
|
describe('#logout', function() {
|
||||||
callback();
|
it('should fail to to error in calling db clear', function(done) {
|
||||||
}
|
storageStub.clear.yields(new Error());
|
||||||
|
|
||||||
auth.handleCertificateUpdate('imap', onConnect, callback, dummyCert);
|
auth.logout(function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('#logout', function() {
|
it('should work', function(done) {
|
||||||
it('should fail to to error in calling db clear', function(done) {
|
storageStub.clear.yields();
|
||||||
storageStub.clear.yields(new Error());
|
|
||||||
|
|
||||||
auth.logout(function(err) {
|
auth.logout(function(err) {
|
||||||
expect(err).to.exist;
|
expect(err).to.not.exist;
|
||||||
done();
|
expect(auth.password).to.be.undefined;
|
||||||
});
|
expect(auth.initialized).to.be.undefined;
|
||||||
});
|
expect(auth.credentialsDirty).to.be.undefined;
|
||||||
|
expect(auth.passwordNeedsDecryption).to.be.undefined;
|
||||||
it('should work', function(done) {
|
done();
|
||||||
storageStub.clear.yields();
|
|
||||||
|
|
||||||
auth.logout(function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(auth.password).to.be.undefined;
|
|
||||||
expect(auth.initialized).to.be.undefined;
|
|
||||||
expect(auth.credentialsDirty).to.be.undefined;
|
|
||||||
expect(auth.passwordNeedsDecryption).to.be.undefined;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -1,67 +1,64 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var btnHandler = require('js/util/backbutton-handler'),
|
var btnHandler = require('../../src/js/util/backbutton-handler');
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
describe('Backbutton Handler', function() {
|
describe('Backbutton Handler', function() {
|
||||||
chai.Assertion.includeStack = true;
|
chai.Assertion.includeStack = true;
|
||||||
|
|
||||||
var scope, event;
|
var scope, event;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
scope = {
|
scope = {
|
||||||
state: {},
|
state: {},
|
||||||
$apply: function() {}
|
$apply: function() {}
|
||||||
};
|
};
|
||||||
|
|
||||||
event = new CustomEvent('backbutton');
|
event = new CustomEvent('backbutton');
|
||||||
|
|
||||||
// this is a precondition for the test. throw an exception
|
// this is a precondition for the test. throw an exception
|
||||||
// if this would produce side effects
|
// if this would produce side effects
|
||||||
expect(navigator.app).to.not.exist;
|
expect(navigator.app).to.not.exist;
|
||||||
navigator.app = {};
|
navigator.app = {};
|
||||||
|
|
||||||
btnHandler.attachHandler(scope);
|
btnHandler.attachHandler(scope);
|
||||||
btnHandler.start();
|
btnHandler.start();
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
afterEach(function() {
|
||||||
btnHandler.stop();
|
btnHandler.stop();
|
||||||
delete navigator.app;
|
delete navigator.app;
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should close lightbox', function() {
|
it('should close lightbox', function() {
|
||||||
scope.state.lightbox = 'asd';
|
scope.state.lightbox = 'asd';
|
||||||
document.dispatchEvent(event);
|
document.dispatchEvent(event);
|
||||||
expect(scope.state.lightbox).to.be.undefined;
|
expect(scope.state.lightbox).to.be.undefined;
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should close reader', function() {
|
it('should close reader', function() {
|
||||||
scope.state.read = {
|
scope.state.read = {
|
||||||
open: true,
|
open: true,
|
||||||
toggle: function(state) {
|
toggle: function(state) {
|
||||||
scope.state.read.open = state;
|
scope.state.read.open = state;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
document.dispatchEvent(event);
|
document.dispatchEvent(event);
|
||||||
expect(scope.state.read.open).to.be.false;
|
expect(scope.state.read.open).to.be.false;
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should close navigation', function() {
|
it('should close navigation', function() {
|
||||||
scope.state.nav = {
|
scope.state.nav = {
|
||||||
open: true,
|
open: true,
|
||||||
toggle: function(state) {
|
toggle: function(state) {
|
||||||
scope.state.nav.open = state;
|
scope.state.nav.open = state;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
document.dispatchEvent(event);
|
document.dispatchEvent(event);
|
||||||
expect(scope.state.nav.open).to.be.false;
|
expect(scope.state.nav.open).to.be.false;
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should close app', function(done) {
|
it('should close app', function(done) {
|
||||||
navigator.app.exitApp = done;
|
navigator.app.exitApp = done;
|
||||||
document.dispatchEvent(event);
|
document.dispatchEvent(event);
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
@ -1,413 +1,410 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var ConnectionDoctor = require('js/util/connection-doctor'),
|
var TCPSocket = require('tcp-socket'),
|
||||||
TCPSocket = require('tcp-socket'),
|
ImapClient = require('imap-client'),
|
||||||
ImapClient = require('imap-client'),
|
SmtpClient = require('wo-smtpclient'),
|
||||||
SmtpClient = require('smtpclient'),
|
ConnectionDoctor = require('../../src/js/util/connection-doctor'),
|
||||||
cfg = require('js/app-config').config,
|
cfg = require('../../src/js/app-config').config;
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
describe('Connection Doctor', function() {
|
describe('Connection Doctor', function() {
|
||||||
var doctor;
|
var doctor;
|
||||||
var socketStub, imapStub, smtpStub, credentials;
|
var socketStub, imapStub, smtpStub, credentials;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
//
|
//
|
||||||
// Stubs
|
// Stubs
|
||||||
//
|
//
|
||||||
|
|
||||||
// there is no socket shim for for this use case, use dummy object
|
// there is no socket shim for for this use case, use dummy object
|
||||||
socketStub = {
|
socketStub = {
|
||||||
close: function() {
|
close: function() {
|
||||||
this.onclose();
|
this.onclose();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
imapStub = sinon.createStubInstance(ImapClient);
|
||||||
|
smtpStub = sinon.createStubInstance(SmtpClient);
|
||||||
|
|
||||||
|
//
|
||||||
|
// Fixture
|
||||||
|
//
|
||||||
|
credentials = {
|
||||||
|
imap: {
|
||||||
|
host: 'asd',
|
||||||
|
port: 1234,
|
||||||
|
secure: true,
|
||||||
|
ca: 'cert'
|
||||||
|
},
|
||||||
|
smtp: {
|
||||||
|
host: 'qwe',
|
||||||
|
port: 5678,
|
||||||
|
secure: false,
|
||||||
|
ca: 'cert'
|
||||||
|
},
|
||||||
|
username: 'username',
|
||||||
|
password: 'password'
|
||||||
|
};
|
||||||
|
|
||||||
|
sinon.stub(TCPSocket, 'open').returns(socketStub); // convenience constructors suck
|
||||||
|
|
||||||
|
//
|
||||||
|
// Setup SUT
|
||||||
|
//
|
||||||
|
doctor = new ConnectionDoctor();
|
||||||
|
doctor.configure(credentials);
|
||||||
|
doctor._imap = imapStub;
|
||||||
|
doctor._smtp = smtpStub;
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
TCPSocket.open.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('#_checkOnline', function() {
|
||||||
|
it('should check if browser is online', function(done) {
|
||||||
|
doctor._checkOnline(function(error) {
|
||||||
|
if (navigator.onLine) {
|
||||||
|
expect(error).to.not.exist;
|
||||||
|
} else {
|
||||||
|
expect(error).to.exist;
|
||||||
|
expect(error.code).to.equal(ConnectionDoctor.OFFLINE);
|
||||||
}
|
}
|
||||||
};
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
imapStub = sinon.createStubInstance(ImapClient);
|
describe('#_checkReachable', function() {
|
||||||
smtpStub = sinon.createStubInstance(SmtpClient);
|
it('should be able to reach the host w/o cert', function(done) {
|
||||||
|
credentials.imap.ca = undefined;
|
||||||
|
|
||||||
//
|
doctor._checkReachable(credentials.imap, function(error) {
|
||||||
// Fixture
|
expect(error).to.not.exist;
|
||||||
//
|
expect(TCPSocket.open.calledOnce).to.be.true;
|
||||||
credentials = {
|
expect(TCPSocket.open.calledWith(credentials.imap.host, credentials.imap.port, {
|
||||||
imap: {
|
binaryType: 'arraybuffer',
|
||||||
host: 'asd',
|
useSecureTransport: credentials.imap.secure,
|
||||||
port: 1234,
|
ca: credentials.imap.ca
|
||||||
secure: true,
|
})).to.be.true;
|
||||||
ca: 'cert'
|
|
||||||
},
|
|
||||||
smtp: {
|
|
||||||
host: 'qwe',
|
|
||||||
port: 5678,
|
|
||||||
secure: false,
|
|
||||||
ca: 'cert'
|
|
||||||
},
|
|
||||||
username: 'username',
|
|
||||||
password: 'password'
|
|
||||||
};
|
|
||||||
|
|
||||||
sinon.stub(TCPSocket, 'open').returns(socketStub); // convenience constructors suck
|
done();
|
||||||
|
});
|
||||||
|
|
||||||
//
|
socketStub.oncert();
|
||||||
// Setup SUT
|
socketStub.onopen();
|
||||||
//
|
|
||||||
doctor = new ConnectionDoctor();
|
|
||||||
doctor.configure(credentials);
|
|
||||||
doctor._imap = imapStub;
|
|
||||||
doctor._smtp = smtpStub;
|
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
it('should catch Mozilla TCPSocket exception', function(done) {
|
||||||
TCPSocket.open.restore();
|
// Mozilla forbids extensions to the TCPSocket object
|
||||||
|
Object.defineProperty(socketStub, 'oncert', {
|
||||||
|
set: function() {
|
||||||
|
throw 'Mozilla specific behavior';
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
doctor._checkReachable(credentials.imap, function(error) {
|
||||||
|
expect(error).to.not.exist;
|
||||||
|
expect(TCPSocket.open.calledOnce).to.be.true;
|
||||||
|
expect(TCPSocket.open.calledWith(credentials.imap.host, credentials.imap.port, {
|
||||||
|
binaryType: 'arraybuffer',
|
||||||
|
useSecureTransport: credentials.imap.secure,
|
||||||
|
ca: credentials.imap.ca
|
||||||
|
})).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
|
||||||
|
socketStub.onopen();
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('#_checkOnline', function() {
|
it('should fail w/ wrong cert', function(done) {
|
||||||
it('should check if browser is online', function(done) {
|
doctor._checkReachable(credentials.imap, function(error) {
|
||||||
doctor._checkOnline(function(error) {
|
expect(error).to.exist;
|
||||||
if (navigator.onLine) {
|
expect(error.code).to.equal(ConnectionDoctor.TLS_WRONG_CERT);
|
||||||
expect(error).to.not.exist;
|
expect(TCPSocket.open.calledOnce).to.be.true;
|
||||||
} else {
|
expect(TCPSocket.open.calledWith(credentials.imap.host, credentials.imap.port, {
|
||||||
expect(error).to.exist;
|
binaryType: 'arraybuffer',
|
||||||
expect(error.code).to.equal(ConnectionDoctor.OFFLINE);
|
useSecureTransport: credentials.imap.secure,
|
||||||
}
|
ca: credentials.imap.ca
|
||||||
done();
|
})).to.be.true;
|
||||||
});
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
|
||||||
|
socketStub.oncert();
|
||||||
|
socketStub.onerror();
|
||||||
|
socketStub.onclose();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail w/ host unreachable', function(done) {
|
||||||
|
doctor._checkReachable(credentials.imap, function(error) {
|
||||||
|
expect(error).to.exist;
|
||||||
|
expect(error.code).to.equal(ConnectionDoctor.HOST_UNREACHABLE);
|
||||||
|
expect(TCPSocket.open.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
|
||||||
|
socketStub.onerror({
|
||||||
|
data: new Error()
|
||||||
|
});
|
||||||
|
socketStub.onclose();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail w/ timeout', function(done) {
|
||||||
|
var origTimeout = cfg.connDocTimeout; // remember timeout from the config to reset it on done
|
||||||
|
cfg.connDocTimeout = 20; // set to 20ms for the test
|
||||||
|
|
||||||
|
doctor._checkReachable(credentials.imap, function(error) {
|
||||||
|
expect(error).to.exist;
|
||||||
|
expect(error.code).to.equal(ConnectionDoctor.HOST_TIMEOUT);
|
||||||
|
expect(TCPSocket.open.calledOnce).to.be.true;
|
||||||
|
cfg.connDocTimeout = origTimeout;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('#_checkImap', function() {
|
||||||
|
it('should perform IMAP login, list folders, logout', function(done) {
|
||||||
|
imapStub.login.yieldsAsync();
|
||||||
|
imapStub.listWellKnownFolders.yieldsAsync(null, {
|
||||||
|
Inbox: [{}]
|
||||||
|
});
|
||||||
|
imapStub.logout.yieldsAsync();
|
||||||
|
|
||||||
|
doctor._checkImap(function(error) {
|
||||||
|
expect(error).to.not.exist;
|
||||||
|
expect(imapStub.login.calledOnce).to.be.true;
|
||||||
|
expect(imapStub.listWellKnownFolders.calledOnce).to.be.true;
|
||||||
|
expect(imapStub.logout.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('#_checkReachable', function() {
|
it('should fail w/ generic error on logout', function(done) {
|
||||||
it('should be able to reach the host w/o cert', function(done) {
|
imapStub.login.yieldsAsync();
|
||||||
credentials.imap.ca = undefined;
|
imapStub.listWellKnownFolders.yieldsAsync(null, {
|
||||||
|
Inbox: [{}]
|
||||||
doctor._checkReachable(credentials.imap, function(error) {
|
|
||||||
expect(error).to.not.exist;
|
|
||||||
expect(TCPSocket.open.calledOnce).to.be.true;
|
|
||||||
expect(TCPSocket.open.calledWith(credentials.imap.host, credentials.imap.port, {
|
|
||||||
binaryType: 'arraybuffer',
|
|
||||||
useSecureTransport: credentials.imap.secure,
|
|
||||||
ca: credentials.imap.ca
|
|
||||||
})).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
|
|
||||||
socketStub.oncert();
|
|
||||||
socketStub.onopen();
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should catch Mozilla TCPSocket exception', function(done) {
|
doctor._checkImap(function(error) {
|
||||||
// Mozilla forbids extensions to the TCPSocket object
|
expect(error).to.exist;
|
||||||
Object.defineProperty(socketStub, 'oncert', {
|
expect(error.code).to.equal(ConnectionDoctor.GENERIC_ERROR);
|
||||||
set: function() {
|
expect(error.underlyingError).to.exist;
|
||||||
throw 'Mozilla specific behavior';
|
expect(imapStub.login.calledOnce).to.be.true;
|
||||||
}
|
expect(imapStub.listWellKnownFolders.calledOnce).to.be.true;
|
||||||
});
|
expect(imapStub.logout.calledOnce).to.be.true;
|
||||||
|
|
||||||
doctor._checkReachable(credentials.imap, function(error) {
|
done();
|
||||||
expect(error).to.not.exist;
|
|
||||||
expect(TCPSocket.open.calledOnce).to.be.true;
|
|
||||||
expect(TCPSocket.open.calledWith(credentials.imap.host, credentials.imap.port, {
|
|
||||||
binaryType: 'arraybuffer',
|
|
||||||
useSecureTransport: credentials.imap.secure,
|
|
||||||
ca: credentials.imap.ca
|
|
||||||
})).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
|
|
||||||
socketStub.onopen();
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should fail w/ wrong cert', function(done) {
|
setTimeout(function() {
|
||||||
doctor._checkReachable(credentials.imap, function(error) {
|
// this error is thrown while we're waiting for the logout
|
||||||
expect(error).to.exist;
|
imapStub.onError(new Error());
|
||||||
expect(error.code).to.equal(ConnectionDoctor.TLS_WRONG_CERT);
|
}, 50);
|
||||||
expect(TCPSocket.open.calledOnce).to.be.true;
|
});
|
||||||
expect(TCPSocket.open.calledWith(credentials.imap.host, credentials.imap.port, {
|
|
||||||
binaryType: 'arraybuffer',
|
|
||||||
useSecureTransport: credentials.imap.secure,
|
|
||||||
ca: credentials.imap.ca
|
|
||||||
})).to.be.true;
|
|
||||||
|
|
||||||
done();
|
it('should fail w/ generic error on inbox missing', function(done) {
|
||||||
});
|
imapStub.login.yieldsAsync();
|
||||||
|
imapStub.listWellKnownFolders.yieldsAsync(null, {
|
||||||
socketStub.oncert();
|
Inbox: []
|
||||||
socketStub.onerror();
|
|
||||||
socketStub.onclose();
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should fail w/ host unreachable', function(done) {
|
doctor._checkImap(function(error) {
|
||||||
doctor._checkReachable(credentials.imap, function(error) {
|
expect(error).to.exist;
|
||||||
expect(error).to.exist;
|
expect(error.code).to.equal(ConnectionDoctor.NO_INBOX);
|
||||||
expect(error.code).to.equal(ConnectionDoctor.HOST_UNREACHABLE);
|
expect(imapStub.login.calledOnce).to.be.true;
|
||||||
expect(TCPSocket.open.calledOnce).to.be.true;
|
expect(imapStub.listWellKnownFolders.calledOnce).to.be.true;
|
||||||
|
expect(imapStub.logout.called).to.be.false;
|
||||||
|
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
|
|
||||||
socketStub.onerror({
|
|
||||||
data: new Error()
|
|
||||||
});
|
|
||||||
socketStub.onclose();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail w/ timeout', function(done) {
|
|
||||||
var origTimeout = cfg.connDocTimeout; // remember timeout from the config to reset it on done
|
|
||||||
cfg.connDocTimeout = 20; // set to 20ms for the test
|
|
||||||
|
|
||||||
doctor._checkReachable(credentials.imap, function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(error.code).to.equal(ConnectionDoctor.HOST_TIMEOUT);
|
|
||||||
expect(TCPSocket.open.calledOnce).to.be.true;
|
|
||||||
cfg.connDocTimeout = origTimeout;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('#_checkImap', function() {
|
it('should fail w/ generic error on listing folders fails', function(done) {
|
||||||
it('should perform IMAP login, list folders, logout', function(done) {
|
imapStub.login.yieldsAsync();
|
||||||
imapStub.login.yieldsAsync();
|
imapStub.listWellKnownFolders.yieldsAsync(new Error());
|
||||||
imapStub.listWellKnownFolders.yieldsAsync(null, {
|
|
||||||
Inbox: [{}]
|
|
||||||
});
|
|
||||||
imapStub.logout.yieldsAsync();
|
|
||||||
|
|
||||||
doctor._checkImap(function(error) {
|
doctor._checkImap(function(error) {
|
||||||
expect(error).to.not.exist;
|
expect(error).to.exist;
|
||||||
expect(imapStub.login.calledOnce).to.be.true;
|
expect(error.code).to.equal(ConnectionDoctor.GENERIC_ERROR);
|
||||||
expect(imapStub.listWellKnownFolders.calledOnce).to.be.true;
|
expect(error.underlyingError).to.exist;
|
||||||
expect(imapStub.logout.calledOnce).to.be.true;
|
expect(imapStub.login.calledOnce).to.be.true;
|
||||||
|
expect(imapStub.listWellKnownFolders.calledOnce).to.be.true;
|
||||||
|
expect(imapStub.logout.called).to.be.false;
|
||||||
|
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail w/ generic error on logout', function(done) {
|
|
||||||
imapStub.login.yieldsAsync();
|
|
||||||
imapStub.listWellKnownFolders.yieldsAsync(null, {
|
|
||||||
Inbox: [{}]
|
|
||||||
});
|
|
||||||
|
|
||||||
doctor._checkImap(function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(error.code).to.equal(ConnectionDoctor.GENERIC_ERROR);
|
|
||||||
expect(error.underlyingError).to.exist;
|
|
||||||
expect(imapStub.login.calledOnce).to.be.true;
|
|
||||||
expect(imapStub.listWellKnownFolders.calledOnce).to.be.true;
|
|
||||||
expect(imapStub.logout.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
|
|
||||||
setTimeout(function() {
|
|
||||||
// this error is thrown while we're waiting for the logout
|
|
||||||
imapStub.onError(new Error());
|
|
||||||
}, 50);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail w/ generic error on inbox missing', function(done) {
|
|
||||||
imapStub.login.yieldsAsync();
|
|
||||||
imapStub.listWellKnownFolders.yieldsAsync(null, {
|
|
||||||
Inbox: []
|
|
||||||
});
|
|
||||||
|
|
||||||
doctor._checkImap(function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(error.code).to.equal(ConnectionDoctor.NO_INBOX);
|
|
||||||
expect(imapStub.login.calledOnce).to.be.true;
|
|
||||||
expect(imapStub.listWellKnownFolders.calledOnce).to.be.true;
|
|
||||||
expect(imapStub.logout.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail w/ generic error on listing folders fails', function(done) {
|
|
||||||
imapStub.login.yieldsAsync();
|
|
||||||
imapStub.listWellKnownFolders.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
doctor._checkImap(function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(error.code).to.equal(ConnectionDoctor.GENERIC_ERROR);
|
|
||||||
expect(error.underlyingError).to.exist;
|
|
||||||
expect(imapStub.login.calledOnce).to.be.true;
|
|
||||||
expect(imapStub.listWellKnownFolders.calledOnce).to.be.true;
|
|
||||||
expect(imapStub.logout.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail w/ auth rejected', function(done) {
|
|
||||||
doctor._checkImap(function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(error.code).to.equal(ConnectionDoctor.AUTH_REJECTED);
|
|
||||||
expect(error.underlyingError).to.exist;
|
|
||||||
expect(imapStub.login.calledOnce).to.be.true;
|
|
||||||
expect(imapStub.listWellKnownFolders.called).to.be.false;
|
|
||||||
expect(imapStub.logout.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
|
|
||||||
setTimeout(function() {
|
|
||||||
// this error is thrown while we're waiting for the login
|
|
||||||
imapStub.onError(new Error());
|
|
||||||
}, 50);
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('#_checkSmtp', function() {
|
it('should fail w/ auth rejected', function(done) {
|
||||||
it('should perform SMTP login, logout', function(done) {
|
doctor._checkImap(function(error) {
|
||||||
doctor._checkSmtp(function(error) {
|
expect(error).to.exist;
|
||||||
expect(error).to.not.exist;
|
expect(error.code).to.equal(ConnectionDoctor.AUTH_REJECTED);
|
||||||
expect(smtpStub.connect.calledOnce).to.be.true;
|
expect(error.underlyingError).to.exist;
|
||||||
expect(smtpStub.quit.calledOnce).to.be.true;
|
expect(imapStub.login.calledOnce).to.be.true;
|
||||||
|
expect(imapStub.listWellKnownFolders.called).to.be.false;
|
||||||
|
expect(imapStub.logout.called).to.be.false;
|
||||||
|
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
|
|
||||||
smtpStub.onidle();
|
|
||||||
smtpStub.onclose();
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should fail w/ auth rejected', function(done) {
|
setTimeout(function() {
|
||||||
doctor._checkSmtp(function(error) {
|
// this error is thrown while we're waiting for the login
|
||||||
expect(error).to.exist;
|
imapStub.onError(new Error());
|
||||||
expect(error.code).to.equal(ConnectionDoctor.AUTH_REJECTED);
|
}, 50);
|
||||||
expect(error.underlyingError).to.exist;
|
});
|
||||||
expect(smtpStub.connect.calledOnce).to.be.true;
|
});
|
||||||
expect(smtpStub.quit.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
describe('#_checkSmtp', function() {
|
||||||
});
|
it('should perform SMTP login, logout', function(done) {
|
||||||
|
doctor._checkSmtp(function(error) {
|
||||||
|
expect(error).to.not.exist;
|
||||||
|
expect(smtpStub.connect.calledOnce).to.be.true;
|
||||||
|
expect(smtpStub.quit.calledOnce).to.be.true;
|
||||||
|
|
||||||
smtpStub.onerror(new Error());
|
done();
|
||||||
|
});
|
||||||
|
|
||||||
|
smtpStub.onidle();
|
||||||
|
smtpStub.onclose();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail w/ auth rejected', function(done) {
|
||||||
|
doctor._checkSmtp(function(error) {
|
||||||
|
expect(error).to.exist;
|
||||||
|
expect(error.code).to.equal(ConnectionDoctor.AUTH_REJECTED);
|
||||||
|
expect(error.underlyingError).to.exist;
|
||||||
|
expect(smtpStub.connect.calledOnce).to.be.true;
|
||||||
|
expect(smtpStub.quit.called).to.be.false;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
|
||||||
|
smtpStub.onerror(new Error());
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('#check', function() {
|
||||||
|
beforeEach(function() {
|
||||||
|
sinon.stub(doctor, '_checkOnline');
|
||||||
|
sinon.stub(doctor, '_checkReachable');
|
||||||
|
sinon.stub(doctor, '_checkImap');
|
||||||
|
sinon.stub(doctor, '_checkSmtp');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should perform all tests', function(done) {
|
||||||
|
doctor._checkOnline.yieldsAsync();
|
||||||
|
doctor._checkReachable.withArgs(credentials.imap).yieldsAsync();
|
||||||
|
doctor._checkReachable.withArgs(credentials.smtp).yieldsAsync();
|
||||||
|
doctor._checkImap.yieldsAsync();
|
||||||
|
doctor._checkSmtp.yieldsAsync();
|
||||||
|
|
||||||
|
doctor.check(function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(doctor._checkOnline.calledOnce).to.be.true;
|
||||||
|
expect(doctor._checkReachable.calledTwice).to.be.true;
|
||||||
|
expect(doctor._checkImap.calledOnce).to.be.true;
|
||||||
|
expect(doctor._checkSmtp.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('#check', function() {
|
it('should fail for smtp', function(done) {
|
||||||
beforeEach(function() {
|
doctor._checkOnline.yieldsAsync();
|
||||||
sinon.stub(doctor, '_checkOnline');
|
doctor._checkReachable.withArgs(credentials.imap).yieldsAsync();
|
||||||
sinon.stub(doctor, '_checkReachable');
|
doctor._checkReachable.withArgs(credentials.smtp).yieldsAsync();
|
||||||
sinon.stub(doctor, '_checkImap');
|
doctor._checkImap.yieldsAsync();
|
||||||
sinon.stub(doctor, '_checkSmtp');
|
doctor._checkSmtp.yieldsAsync(new Error());
|
||||||
|
|
||||||
|
doctor.check(function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(doctor._checkOnline.calledOnce).to.be.true;
|
||||||
|
expect(doctor._checkReachable.calledTwice).to.be.true;
|
||||||
|
expect(doctor._checkImap.calledOnce).to.be.true;
|
||||||
|
expect(doctor._checkSmtp.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should perform all tests', function(done) {
|
it('should fail for imap', function(done) {
|
||||||
doctor._checkOnline.yieldsAsync();
|
doctor._checkOnline.yieldsAsync();
|
||||||
doctor._checkReachable.withArgs(credentials.imap).yieldsAsync();
|
doctor._checkReachable.withArgs(credentials.imap).yieldsAsync();
|
||||||
doctor._checkReachable.withArgs(credentials.smtp).yieldsAsync();
|
doctor._checkReachable.withArgs(credentials.smtp).yieldsAsync();
|
||||||
doctor._checkImap.yieldsAsync();
|
doctor._checkImap.yieldsAsync(new Error());
|
||||||
doctor._checkSmtp.yieldsAsync();
|
|
||||||
|
|
||||||
doctor.check(function(err) {
|
doctor.check(function(err) {
|
||||||
expect(err).to.not.exist;
|
expect(err).to.exist;
|
||||||
expect(doctor._checkOnline.calledOnce).to.be.true;
|
expect(doctor._checkOnline.calledOnce).to.be.true;
|
||||||
expect(doctor._checkReachable.calledTwice).to.be.true;
|
expect(doctor._checkReachable.calledTwice).to.be.true;
|
||||||
expect(doctor._checkImap.calledOnce).to.be.true;
|
expect(doctor._checkImap.calledOnce).to.be.true;
|
||||||
expect(doctor._checkSmtp.calledOnce).to.be.true;
|
expect(doctor._checkSmtp.called).to.be.false;
|
||||||
|
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should fail for smtp', function(done) {
|
it('should fail for smtp reachability', function(done) {
|
||||||
doctor._checkOnline.yieldsAsync();
|
doctor._checkOnline.yieldsAsync();
|
||||||
doctor._checkReachable.withArgs(credentials.imap).yieldsAsync();
|
doctor._checkReachable.withArgs(credentials.imap).yieldsAsync();
|
||||||
doctor._checkReachable.withArgs(credentials.smtp).yieldsAsync();
|
doctor._checkReachable.withArgs(credentials.smtp).yieldsAsync(new Error());
|
||||||
doctor._checkImap.yieldsAsync();
|
|
||||||
doctor._checkSmtp.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
doctor.check(function(err) {
|
doctor.check(function(err) {
|
||||||
expect(err).to.exist;
|
expect(err).to.exist;
|
||||||
expect(doctor._checkOnline.calledOnce).to.be.true;
|
expect(doctor._checkOnline.calledOnce).to.be.true;
|
||||||
expect(doctor._checkReachable.calledTwice).to.be.true;
|
expect(doctor._checkReachable.calledTwice).to.be.true;
|
||||||
expect(doctor._checkImap.calledOnce).to.be.true;
|
expect(doctor._checkImap.called).to.be.false;
|
||||||
expect(doctor._checkSmtp.calledOnce).to.be.true;
|
expect(doctor._checkSmtp.called).to.be.false;
|
||||||
|
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should fail for imap', function(done) {
|
it('should fail for imap reachability', function(done) {
|
||||||
doctor._checkOnline.yieldsAsync();
|
doctor._checkOnline.yieldsAsync();
|
||||||
doctor._checkReachable.withArgs(credentials.imap).yieldsAsync();
|
doctor._checkReachable.withArgs(credentials.imap).yieldsAsync(new Error());
|
||||||
doctor._checkReachable.withArgs(credentials.smtp).yieldsAsync();
|
|
||||||
doctor._checkImap.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
doctor.check(function(err) {
|
doctor.check(function(err) {
|
||||||
expect(err).to.exist;
|
expect(err).to.exist;
|
||||||
expect(doctor._checkOnline.calledOnce).to.be.true;
|
expect(doctor._checkOnline.calledOnce).to.be.true;
|
||||||
expect(doctor._checkReachable.calledTwice).to.be.true;
|
expect(doctor._checkReachable.calledOnce).to.be.true;
|
||||||
expect(doctor._checkImap.calledOnce).to.be.true;
|
expect(doctor._checkImap.called).to.be.false;
|
||||||
expect(doctor._checkSmtp.called).to.be.false;
|
expect(doctor._checkSmtp.called).to.be.false;
|
||||||
|
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should fail for smtp reachability', function(done) {
|
it('should fail for offline', function(done) {
|
||||||
doctor._checkOnline.yieldsAsync();
|
doctor._checkOnline.yieldsAsync(new Error());
|
||||||
doctor._checkReachable.withArgs(credentials.imap).yieldsAsync();
|
|
||||||
doctor._checkReachable.withArgs(credentials.smtp).yieldsAsync(new Error());
|
|
||||||
|
|
||||||
doctor.check(function(err) {
|
doctor.check(function(err) {
|
||||||
expect(err).to.exist;
|
expect(err).to.exist;
|
||||||
expect(doctor._checkOnline.calledOnce).to.be.true;
|
expect(doctor._checkOnline.calledOnce).to.be.true;
|
||||||
expect(doctor._checkReachable.calledTwice).to.be.true;
|
expect(doctor._checkReachable.called).to.be.false;
|
||||||
expect(doctor._checkImap.called).to.be.false;
|
expect(doctor._checkImap.called).to.be.false;
|
||||||
expect(doctor._checkSmtp.called).to.be.false;
|
expect(doctor._checkSmtp.called).to.be.false;
|
||||||
|
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should fail for imap reachability', function(done) {
|
it('should fail w/o config', function(done) {
|
||||||
doctor._checkOnline.yieldsAsync();
|
doctor.credentials = doctor._imap = doctor._smtp = undefined;
|
||||||
doctor._checkReachable.withArgs(credentials.imap).yieldsAsync(new Error());
|
|
||||||
|
|
||||||
doctor.check(function(err) {
|
doctor.check(function(err) {
|
||||||
expect(err).to.exist;
|
expect(err).to.exist;
|
||||||
expect(doctor._checkOnline.calledOnce).to.be.true;
|
expect(doctor._checkOnline.called).to.be.false;
|
||||||
expect(doctor._checkReachable.calledOnce).to.be.true;
|
expect(doctor._checkReachable.called).to.be.false;
|
||||||
expect(doctor._checkImap.called).to.be.false;
|
expect(doctor._checkImap.called).to.be.false;
|
||||||
expect(doctor._checkSmtp.called).to.be.false;
|
expect(doctor._checkSmtp.called).to.be.false;
|
||||||
|
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail for offline', function(done) {
|
|
||||||
doctor._checkOnline.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
doctor.check(function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(doctor._checkOnline.calledOnce).to.be.true;
|
|
||||||
expect(doctor._checkReachable.called).to.be.false;
|
|
||||||
expect(doctor._checkImap.called).to.be.false;
|
|
||||||
expect(doctor._checkSmtp.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail w/o config', function(done) {
|
|
||||||
doctor.credentials = doctor._imap = doctor._smtp = undefined;
|
|
||||||
|
|
||||||
doctor.check(function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(doctor._checkOnline.called).to.be.false;
|
|
||||||
expect(doctor._checkReachable.called).to.be.false;
|
|
||||||
expect(doctor._checkImap.called).to.be.false;
|
|
||||||
expect(doctor._checkSmtp.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -1,190 +1,186 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
ContactsCtrl = require('../../src/js/controller/contacts'),
|
||||||
mocks = require('angularMocks'),
|
appController = require('../../src/js/app-controller'),
|
||||||
ContactsCtrl = require('js/controller/contacts'),
|
KeychainDAO = require('../../src/js/dao/keychain-dao'),
|
||||||
appController = require('js/app-controller'),
|
PGP = require('../../src/js/crypto/pgp');
|
||||||
KeychainDAO = require('js/dao/keychain-dao'),
|
|
||||||
PGP = require('js/crypto/pgp');
|
|
||||||
|
|
||||||
describe('Contacts Controller unit test', function() {
|
describe('Contacts Controller unit test', function() {
|
||||||
var scope, contactsCtrl,
|
var scope, contactsCtrl,
|
||||||
origKeychain, keychainMock,
|
origKeychain, keychainMock,
|
||||||
origPgp, pgpMock;
|
origPgp, pgpMock;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
origPgp = appController._pgp;
|
origPgp = appController._pgp;
|
||||||
appController._pgp = pgpMock = sinon.createStubInstance(PGP);
|
appController._pgp = pgpMock = sinon.createStubInstance(PGP);
|
||||||
origKeychain = appController._keychain;
|
origKeychain = appController._keychain;
|
||||||
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
||||||
|
|
||||||
angular.module('contactstest', []);
|
angular.module('contactstest', []);
|
||||||
mocks.module('contactstest');
|
mocks.module('contactstest');
|
||||||
mocks.inject(function($rootScope, $controller) {
|
mocks.inject(function($rootScope, $controller) {
|
||||||
scope = $rootScope.$new();
|
scope = $rootScope.$new();
|
||||||
scope.state = {};
|
scope.state = {};
|
||||||
contactsCtrl = $controller(ContactsCtrl, {
|
contactsCtrl = $controller(ContactsCtrl, {
|
||||||
$scope: scope
|
$scope: scope
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
afterEach(function() {
|
|
||||||
// restore the module
|
|
||||||
appController._pgp = origPgp;
|
|
||||||
appController._keychain = origKeychain;
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('scope variables', function() {
|
|
||||||
it('should be set correctly', function() {
|
|
||||||
expect(scope.fingerprint).to.equal('XXXX XXXX XXXX XXXX XXXX XXXX XXXX XXXX XXXX XXXX');
|
|
||||||
expect(scope.state.contacts.toggle).to.exist;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('listKeys', function() {
|
|
||||||
it('should fail due to error in keychain.listLocalPublicKeys', function(done) {
|
|
||||||
keychainMock.listLocalPublicKeys.yields(42);
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.equal(42);
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.listKeys();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
keychainMock.listLocalPublicKeys.yields(null, [{
|
|
||||||
_id: '12345'
|
|
||||||
}]);
|
|
||||||
pgpMock.getKeyParams.returns({
|
|
||||||
fingerprint: 'asdf'
|
|
||||||
});
|
|
||||||
|
|
||||||
scope.$apply = function() {
|
|
||||||
expect(scope.keys.length).to.equal(1);
|
|
||||||
expect(scope.keys[0]._id).to.equal('12345');
|
|
||||||
expect(scope.keys[0].fingerprint).to.equal('asdf');
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
expect(scope.keys).to.not.exist;
|
|
||||||
scope.listKeys();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('getFingerprint', function() {
|
|
||||||
it('should work', function() {
|
|
||||||
var key = {
|
|
||||||
fingerprint: 'YYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYY'
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.getFingerprint(key);
|
|
||||||
|
|
||||||
expect(scope.fingerprint).to.equal('YYYY YYYY YYYY YYYY YYYY ... YYYY YYYY YYYY YYYY YYYY');
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('importKey', function() {
|
|
||||||
it('should work', function(done) {
|
|
||||||
var keyArmored = '-----BEGIN PGP PUBLIC KEY BLOCK-----';
|
|
||||||
|
|
||||||
pgpMock.getKeyParams.returns({
|
|
||||||
_id: '12345',
|
|
||||||
userId: 'max@example.com',
|
|
||||||
userIds: []
|
|
||||||
});
|
|
||||||
|
|
||||||
keychainMock.saveLocalPublicKey.withArgs({
|
|
||||||
_id: '12345',
|
|
||||||
userId: 'max@example.com',
|
|
||||||
userIds: [],
|
|
||||||
publicKey: '-----BEGIN PGP PUBLIC KEY BLOCK-----',
|
|
||||||
imported: true
|
|
||||||
}).yields();
|
|
||||||
|
|
||||||
scope.listKeys = function() {
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.importKey(keyArmored);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail due to invalid armored key', function(done) {
|
|
||||||
var keyArmored = '-----BEGIN PGP PRIVATE KEY BLOCK-----';
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.importKey(keyArmored);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail due to error in pgp.getKeyParams', function(done) {
|
|
||||||
var keyArmored = '-----BEGIN PGP PUBLIC KEY BLOCK-----';
|
|
||||||
|
|
||||||
pgpMock.getKeyParams.throws(new Error('WAT'));
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.importKey(keyArmored);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail due to error in keychain.saveLocalPublicKey', function(done) {
|
|
||||||
var keyArmored = '-----BEGIN PGP PUBLIC KEY BLOCK-----';
|
|
||||||
|
|
||||||
pgpMock.getKeyParams.returns({
|
|
||||||
_id: '12345',
|
|
||||||
userId: 'max@example.com'
|
|
||||||
});
|
|
||||||
|
|
||||||
keychainMock.saveLocalPublicKey.yields(42);
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.equal(42);
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.importKey(keyArmored);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('removeKey', function() {
|
|
||||||
it('should work', function(done) {
|
|
||||||
var key = {
|
|
||||||
_id: '12345'
|
|
||||||
};
|
|
||||||
|
|
||||||
keychainMock.removeLocalPublicKey.withArgs('12345').yields();
|
|
||||||
|
|
||||||
scope.listKeys = function() {
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.removeKey(key);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail due to error in keychain.removeLocalPublicKey', function(done) {
|
|
||||||
var key = {
|
|
||||||
_id: '12345'
|
|
||||||
};
|
|
||||||
|
|
||||||
keychainMock.removeLocalPublicKey.withArgs('12345').yields(42);
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.equal(42);
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.removeKey(key);
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
// restore the module
|
||||||
|
appController._pgp = origPgp;
|
||||||
|
appController._keychain = origKeychain;
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('scope variables', function() {
|
||||||
|
it('should be set correctly', function() {
|
||||||
|
expect(scope.fingerprint).to.equal('XXXX XXXX XXXX XXXX XXXX XXXX XXXX XXXX XXXX XXXX');
|
||||||
|
expect(scope.state.contacts.toggle).to.exist;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('listKeys', function() {
|
||||||
|
it('should fail due to error in keychain.listLocalPublicKeys', function(done) {
|
||||||
|
keychainMock.listLocalPublicKeys.yields(42);
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.equal(42);
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.listKeys();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
keychainMock.listLocalPublicKeys.yields(null, [{
|
||||||
|
_id: '12345'
|
||||||
|
}]);
|
||||||
|
pgpMock.getKeyParams.returns({
|
||||||
|
fingerprint: 'asdf'
|
||||||
|
});
|
||||||
|
|
||||||
|
scope.$apply = function() {
|
||||||
|
expect(scope.keys.length).to.equal(1);
|
||||||
|
expect(scope.keys[0]._id).to.equal('12345');
|
||||||
|
expect(scope.keys[0].fingerprint).to.equal('asdf');
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
expect(scope.keys).to.not.exist;
|
||||||
|
scope.listKeys();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('getFingerprint', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
var key = {
|
||||||
|
fingerprint: 'YYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYYY'
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.getFingerprint(key);
|
||||||
|
|
||||||
|
expect(scope.fingerprint).to.equal('YYYY YYYY YYYY YYYY YYYY ... YYYY YYYY YYYY YYYY YYYY');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('importKey', function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
var keyArmored = '-----BEGIN PGP PUBLIC KEY BLOCK-----';
|
||||||
|
|
||||||
|
pgpMock.getKeyParams.returns({
|
||||||
|
_id: '12345',
|
||||||
|
userId: 'max@example.com',
|
||||||
|
userIds: []
|
||||||
|
});
|
||||||
|
|
||||||
|
keychainMock.saveLocalPublicKey.withArgs({
|
||||||
|
_id: '12345',
|
||||||
|
userId: 'max@example.com',
|
||||||
|
userIds: [],
|
||||||
|
publicKey: '-----BEGIN PGP PUBLIC KEY BLOCK-----',
|
||||||
|
imported: true
|
||||||
|
}).yields();
|
||||||
|
|
||||||
|
scope.listKeys = function() {
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.importKey(keyArmored);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail due to invalid armored key', function(done) {
|
||||||
|
var keyArmored = '-----BEGIN PGP PRIVATE KEY BLOCK-----';
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.importKey(keyArmored);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail due to error in pgp.getKeyParams', function(done) {
|
||||||
|
var keyArmored = '-----BEGIN PGP PUBLIC KEY BLOCK-----';
|
||||||
|
|
||||||
|
pgpMock.getKeyParams.throws(new Error('WAT'));
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.importKey(keyArmored);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail due to error in keychain.saveLocalPublicKey', function(done) {
|
||||||
|
var keyArmored = '-----BEGIN PGP PUBLIC KEY BLOCK-----';
|
||||||
|
|
||||||
|
pgpMock.getKeyParams.returns({
|
||||||
|
_id: '12345',
|
||||||
|
userId: 'max@example.com'
|
||||||
|
});
|
||||||
|
|
||||||
|
keychainMock.saveLocalPublicKey.yields(42);
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.equal(42);
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.importKey(keyArmored);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('removeKey', function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
var key = {
|
||||||
|
_id: '12345'
|
||||||
|
};
|
||||||
|
|
||||||
|
keychainMock.removeLocalPublicKey.withArgs('12345').yields();
|
||||||
|
|
||||||
|
scope.listKeys = function() {
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.removeKey(key);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail due to error in keychain.removeLocalPublicKey', function(done) {
|
||||||
|
var key = {
|
||||||
|
_id: '12345'
|
||||||
|
};
|
||||||
|
|
||||||
|
keychainMock.removeLocalPublicKey.withArgs('12345').yields(42);
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.equal(42);
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.removeKey(key);
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
@ -1,58 +1,55 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var Crypto = require('js/crypto/crypto'),
|
var Crypto = require('../../src/js/crypto/crypto'),
|
||||||
util = require('js/crypto/util'),
|
config = require('../../src/js/app-config').config,
|
||||||
config = require('js/app-config').config,
|
util = require('crypto-lib').util;
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
describe('Crypto unit tests', function() {
|
describe('Crypto unit tests', function() {
|
||||||
this.timeout(20000);
|
this.timeout(20000);
|
||||||
|
|
||||||
var crypto,
|
var crypto,
|
||||||
password = 'password',
|
password = 'password',
|
||||||
keySize = config.symKeySize,
|
keySize = config.symKeySize,
|
||||||
ivSize = config.symIvSize;
|
ivSize = config.symIvSize;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
crypto = new Crypto();
|
crypto = new Crypto();
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {});
|
afterEach(function() {});
|
||||||
|
|
||||||
describe('AES encrypt/decrypt', function() {
|
describe('AES encrypt/decrypt', function() {
|
||||||
it('should work', function(done) {
|
it('should work', function(done) {
|
||||||
var plaintext = 'Hello, World!';
|
var plaintext = 'Hello, World!';
|
||||||
var key = util.random(keySize);
|
var key = util.random(keySize);
|
||||||
var iv = util.random(ivSize);
|
var iv = util.random(ivSize);
|
||||||
|
|
||||||
crypto.encrypt(plaintext, key, iv, function(err, ciphertext) {
|
crypto.encrypt(plaintext, key, iv, function(err, ciphertext) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(ciphertext).to.exist;
|
||||||
|
|
||||||
|
crypto.decrypt(ciphertext, key, iv, function(err, decrypted) {
|
||||||
expect(err).to.not.exist;
|
expect(err).to.not.exist;
|
||||||
expect(ciphertext).to.exist;
|
expect(decrypted).to.equal(plaintext);
|
||||||
|
|
||||||
crypto.decrypt(ciphertext, key, iv, function(err, decrypted) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(decrypted).to.equal(plaintext);
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe("PBKDF2 (Async/Worker)", function() {
|
|
||||||
it('should work', function(done) {
|
|
||||||
var salt = util.random(keySize);
|
|
||||||
|
|
||||||
crypto.deriveKey(password, salt, keySize, function(err, key) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(util.base642Str(key).length * 8).to.equal(keySize);
|
|
||||||
|
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe("PBKDF2 (Async/Worker)", function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
var salt = util.random(keySize);
|
||||||
|
|
||||||
|
crypto.deriveKey(password, salt, keySize, function(err, key) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(util.base642Str(key).length * 8).to.equal(keySize);
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
});
|
});
|
@ -1,105 +1,101 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var LawnchairDAO = require('js/dao/lawnchair-dao'),
|
var LawnchairDAO = require('../../src/js/dao/lawnchair-dao'),
|
||||||
DeviceStorageDAO = require('js/dao/devicestorage-dao'),
|
DeviceStorageDAO = require('../../src/js/dao/devicestorage-dao');
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
var testUser = 'test@example.com';
|
var testUser = 'test@example.com';
|
||||||
|
|
||||||
describe('Device Storage DAO unit tests', function() {
|
describe('Device Storage DAO unit tests', function() {
|
||||||
|
|
||||||
var storageDao, lawnchairDaoStub;
|
var storageDao, lawnchairDaoStub;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
lawnchairDaoStub = sinon.createStubInstance(LawnchairDAO);
|
lawnchairDaoStub = sinon.createStubInstance(LawnchairDAO);
|
||||||
storageDao = new DeviceStorageDAO(lawnchairDaoStub);
|
storageDao = new DeviceStorageDAO(lawnchairDaoStub);
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {});
|
||||||
|
|
||||||
|
describe('init', function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
lawnchairDaoStub.init.yields();
|
||||||
|
|
||||||
|
storageDao.init(testUser, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(lawnchairDaoStub.init.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
afterEach(function() {});
|
describe('store list', function() {
|
||||||
|
it('should fail', function(done) {
|
||||||
|
var list = [{}];
|
||||||
|
|
||||||
describe('init', function() {
|
storageDao.storeList(list, '', function(err) {
|
||||||
it('should work', function(done) {
|
expect(err).to.exist;
|
||||||
lawnchairDaoStub.init.yields();
|
done();
|
||||||
|
|
||||||
storageDao.init(testUser, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(lawnchairDaoStub.init.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('store list', function() {
|
it('should work with empty list', function(done) {
|
||||||
it('should fail', function(done) {
|
var list = [];
|
||||||
var list = [{}];
|
|
||||||
|
|
||||||
storageDao.storeList(list, '', function(err) {
|
storageDao.storeList(list, 'email', function(err) {
|
||||||
expect(err).to.exist;
|
expect(err).to.not.exist;
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work with empty list', function(done) {
|
|
||||||
var list = [];
|
|
||||||
|
|
||||||
storageDao.storeList(list, 'email', function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
lawnchairDaoStub.batch.yields();
|
|
||||||
|
|
||||||
var list = [{
|
|
||||||
foo: 'bar'
|
|
||||||
}];
|
|
||||||
|
|
||||||
storageDao.storeList(list, 'email', function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(lawnchairDaoStub.batch.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('remove list', function() {
|
it('should work', function(done) {
|
||||||
it('should work', function(done) {
|
lawnchairDaoStub.batch.yields();
|
||||||
lawnchairDaoStub.removeList.yields();
|
|
||||||
|
|
||||||
storageDao.removeList('email', function(err) {
|
var list = [{
|
||||||
expect(err).to.not.exist;
|
foo: 'bar'
|
||||||
expect(lawnchairDaoStub.removeList.calledOnce).to.be.true;
|
}];
|
||||||
done();
|
|
||||||
});
|
storageDao.storeList(list, 'email', function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(lawnchairDaoStub.batch.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe('list items', function() {
|
describe('remove list', function() {
|
||||||
it('should work', function(done) {
|
it('should work', function(done) {
|
||||||
lawnchairDaoStub.list.yields();
|
lawnchairDaoStub.removeList.yields();
|
||||||
|
|
||||||
storageDao.listItems('email', 0, null, function(err) {
|
storageDao.removeList('email', function(err) {
|
||||||
expect(err).to.not.exist;
|
expect(err).to.not.exist;
|
||||||
expect(lawnchairDaoStub.list.calledOnce).to.be.true;
|
expect(lawnchairDaoStub.removeList.calledOnce).to.be.true;
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe('clear', function() {
|
describe('list items', function() {
|
||||||
it('should work', function(done) {
|
it('should work', function(done) {
|
||||||
lawnchairDaoStub.clear.yields();
|
lawnchairDaoStub.list.yields();
|
||||||
|
|
||||||
storageDao.clear(function(err) {
|
storageDao.listItems('email', 0, null, function(err) {
|
||||||
expect(err).to.not.exist;
|
expect(err).to.not.exist;
|
||||||
expect(lawnchairDaoStub.clear.calledOnce).to.be.true;
|
expect(lawnchairDaoStub.list.calledOnce).to.be.true;
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('clear', function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
lawnchairDaoStub.clear.yields();
|
||||||
|
|
||||||
|
storageDao.clear(function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(lawnchairDaoStub.clear.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
});
|
});
|
@ -1,50 +1,46 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
DialogCtrl = require('../../src/js/controller/dialog');
|
||||||
mocks = require('angularMocks'),
|
|
||||||
DialogCtrl = require('js/controller/dialog');
|
|
||||||
|
|
||||||
describe('Dialog Controller unit test', function() {
|
describe('Dialog Controller unit test', function() {
|
||||||
var scope, dialogCtrl;
|
var scope, dialogCtrl;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
angular.module('dialogtest', []);
|
angular.module('dialogtest', []);
|
||||||
mocks.module('dialogtest');
|
mocks.module('dialogtest');
|
||||||
mocks.inject(function($rootScope, $controller) {
|
mocks.inject(function($rootScope, $controller) {
|
||||||
scope = $rootScope.$new();
|
scope = $rootScope.$new();
|
||||||
scope.state = {
|
scope.state = {
|
||||||
dialog: {}
|
dialog: {}
|
||||||
};
|
};
|
||||||
dialogCtrl = $controller(DialogCtrl, {
|
dialogCtrl = $controller(DialogCtrl, {
|
||||||
$scope: scope
|
$scope: scope
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
afterEach(function() {});
|
|
||||||
|
|
||||||
describe('confirm', function() {
|
|
||||||
it('should work', function(done) {
|
|
||||||
scope.state.dialog.callback = function(confirmed) {
|
|
||||||
expect(confirmed).to.be.true;
|
|
||||||
expect(scope.state.dialog.open).to.be.false;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
scope.confirm(true);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('cancel', function() {
|
|
||||||
it('should work', function(done) {
|
|
||||||
scope.state.dialog.callback = function(confirmed) {
|
|
||||||
expect(confirmed).to.be.false;
|
|
||||||
expect(scope.state.dialog.open).to.be.false;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
scope.confirm(false);
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
afterEach(function() {});
|
||||||
|
|
||||||
|
describe('confirm', function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
scope.state.dialog.callback = function(confirmed) {
|
||||||
|
expect(confirmed).to.be.true;
|
||||||
|
expect(scope.state.dialog.open).to.be.false;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
scope.confirm(true);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('cancel', function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
scope.state.dialog.callback = function(confirmed) {
|
||||||
|
expect(confirmed).to.be.false;
|
||||||
|
expect(scope.state.dialog.open).to.be.false;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
scope.confirm(false);
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
File diff suppressed because it is too large
Load Diff
@ -9,11 +9,70 @@
|
|||||||
<body>
|
<body>
|
||||||
<div id="mocha"></div>
|
<div id="mocha"></div>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
//
|
||||||
|
// Polyfills
|
||||||
|
//
|
||||||
|
|
||||||
|
(function() {
|
||||||
|
'use strict';
|
||||||
|
// Mozilla bind polyfill because phantomjs is stupid
|
||||||
|
if (!Function.prototype.bind) {
|
||||||
|
Function.prototype.bind = function(oThis) {
|
||||||
|
if (typeof this !== "function") {
|
||||||
|
// closest thing possible to the ECMAScript 5 internal IsCallable function
|
||||||
|
throw new TypeError("Function.prototype.bind - what is trying to be bound is not callable");
|
||||||
|
}
|
||||||
|
|
||||||
|
var aArgs = Array.prototype.slice.call(arguments, 1),
|
||||||
|
fToBind = this,
|
||||||
|
FNOP = function() {},
|
||||||
|
fBound = function() {
|
||||||
|
return fToBind.apply(this instanceof FNOP && oThis ? this : oThis, aArgs.concat(Array.prototype.slice.call(arguments)));
|
||||||
|
};
|
||||||
|
|
||||||
|
FNOP.prototype = this.prototype;
|
||||||
|
fBound.prototype = new FNOP();
|
||||||
|
|
||||||
|
return fBound;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
// a warm round of applause for phantomjs for missing events
|
||||||
|
(function() {
|
||||||
|
function CustomEvent(event, params) {
|
||||||
|
params = params || {
|
||||||
|
bubbles: false,
|
||||||
|
cancelable: false,
|
||||||
|
detail: undefined
|
||||||
|
};
|
||||||
|
var evt = document.createEvent('CustomEvent');
|
||||||
|
evt.initCustomEvent(event, params.bubbles, params.cancelable, params.detail);
|
||||||
|
return evt;
|
||||||
|
}
|
||||||
|
|
||||||
|
CustomEvent.prototype = window.Event.prototype;
|
||||||
|
|
||||||
|
window.CustomEvent = CustomEvent;
|
||||||
|
})();
|
||||||
|
})();
|
||||||
|
</script>
|
||||||
|
|
||||||
<script src="../lib/chai.js"></script>
|
<script src="../lib/chai.js"></script>
|
||||||
<script src="../lib/sinon.js"></script>
|
|
||||||
<script src="../lib/mocha.js"></script>
|
<script src="../lib/mocha.js"></script>
|
||||||
|
<script src="../lib/sinon.js"></script>
|
||||||
|
|
||||||
<script data-main="main.js" src="../../src/lib/require.js"></script>
|
<script>
|
||||||
|
window.expect = chai.expect;
|
||||||
|
mocha.setup('bdd');
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<script src="index.js"></script>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
mocha.checkLeaks();
|
||||||
|
mocha.globals([]);
|
||||||
|
mocha.run();
|
||||||
|
</script>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
@ -1,108 +1,105 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var RestDAO = require('js/dao/rest-dao'),
|
var RestDAO = require('../../src/js/dao/rest-dao'),
|
||||||
InvitationDAO = require('js/dao/invitation-dao'),
|
InvitationDAO = require('../../src/js/dao/invitation-dao');
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
describe('Invitation DAO unit tests', function() {
|
describe('Invitation DAO unit tests', function() {
|
||||||
var restDaoStub, invitationDao,
|
var restDaoStub, invitationDao,
|
||||||
alice = 'zuhause@aol.com',
|
alice = 'zuhause@aol.com',
|
||||||
bob = 'manfred.mustermann@musterdomain.com',
|
bob = 'manfred.mustermann@musterdomain.com',
|
||||||
expectedUri = '/invitation/recipient/' + alice + '/sender/' + bob;
|
expectedUri = '/invitation/recipient/' + alice + '/sender/' + bob;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
restDaoStub = sinon.createStubInstance(RestDAO);
|
restDaoStub = sinon.createStubInstance(RestDAO);
|
||||||
invitationDao = new InvitationDAO(restDaoStub);
|
invitationDao = new InvitationDAO(restDaoStub);
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('initialization', function() {
|
||||||
|
it('should wire up correctly', function() {
|
||||||
|
expect(invitationDao._restDao).to.equal(restDaoStub);
|
||||||
|
expect(invitationDao.invite).to.exist;
|
||||||
|
expect(InvitationDAO.INVITE_MISSING).to.equal(1);
|
||||||
|
expect(InvitationDAO.INVITE_PENDING).to.equal(2);
|
||||||
|
expect(InvitationDAO.INVITE_SUCCESS).to.equal(4);
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe('initialization', function() {
|
describe('invite', function() {
|
||||||
it('should wire up correctly', function() {
|
it('should invite the recipient', function(done) {
|
||||||
expect(invitationDao._restDao).to.equal(restDaoStub);
|
restDaoStub.put.yieldsAsync(null, undefined, 201);
|
||||||
expect(invitationDao.invite).to.exist;
|
|
||||||
expect(InvitationDAO.INVITE_MISSING).to.equal(1);
|
invitationDao.invite({
|
||||||
expect(InvitationDAO.INVITE_PENDING).to.equal(2);
|
recipient: alice,
|
||||||
expect(InvitationDAO.INVITE_SUCCESS).to.equal(4);
|
sender: bob
|
||||||
|
}, function(err, status) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(status).to.equal(InvitationDAO.INVITE_SUCCESS);
|
||||||
|
expect(restDaoStub.put.calledWith({}, expectedUri)).to.be.true;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('invite', function() {
|
it('should point out already invited recipient', function(done) {
|
||||||
it('should invite the recipient', function(done) {
|
restDaoStub.put.yieldsAsync(null, undefined, 304);
|
||||||
restDaoStub.put.yieldsAsync(null, undefined, 201);
|
|
||||||
|
|
||||||
invitationDao.invite({
|
invitationDao.invite({
|
||||||
recipient: alice,
|
recipient: alice,
|
||||||
sender: bob
|
sender: bob
|
||||||
}, function(err, status) {
|
}, function(err, status) {
|
||||||
expect(err).to.not.exist;
|
expect(err).to.not.exist;
|
||||||
expect(status).to.equal(InvitationDAO.INVITE_SUCCESS);
|
expect(status).to.equal(InvitationDAO.INVITE_PENDING);
|
||||||
expect(restDaoStub.put.calledWith({}, expectedUri)).to.be.true;
|
done();
|
||||||
done();
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should not work for http error', function(done) {
|
||||||
|
restDaoStub.put.yieldsAsync({
|
||||||
|
errMsg: 'jawollja.'
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should point out already invited recipient', function(done) {
|
invitationDao.invite({
|
||||||
restDaoStub.put.yieldsAsync(null, undefined, 304);
|
recipient: alice,
|
||||||
|
sender: bob
|
||||||
invitationDao.invite({
|
}, function(err, status) {
|
||||||
recipient: alice,
|
expect(err).to.exist;
|
||||||
sender: bob
|
expect(status).to.not.exist;
|
||||||
}, function(err, status) {
|
done();
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(status).to.equal(InvitationDAO.INVITE_PENDING);
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should not work for http error', function(done) {
|
it('should not work for unexpected response', function(done) {
|
||||||
restDaoStub.put.yieldsAsync({
|
restDaoStub.put.yieldsAsync(null, undefined, 1337);
|
||||||
errMsg: 'jawollja.'
|
|
||||||
});
|
|
||||||
|
|
||||||
invitationDao.invite({
|
invitationDao.invite({
|
||||||
recipient: alice,
|
recipient: alice,
|
||||||
sender: bob
|
sender: bob
|
||||||
}, function(err, status) {
|
}, function(err, status) {
|
||||||
expect(err).to.exist;
|
expect(err).to.exist;
|
||||||
expect(status).to.not.exist;
|
expect(status).to.not.exist;
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should not work for unexpected response', function(done) {
|
it('should report erroneous usage', function() {
|
||||||
restDaoStub.put.yieldsAsync(null, undefined, 1337);
|
invitationDao.invite({
|
||||||
|
sender: bob
|
||||||
|
}, expectError);
|
||||||
|
|
||||||
invitationDao.invite({
|
invitationDao.invite({
|
||||||
recipient: alice,
|
recipient: alice,
|
||||||
sender: bob
|
}, expectError);
|
||||||
}, function(err, status) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(status).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should report erroneous usage', function() {
|
invitationDao.invite({
|
||||||
invitationDao.invite({
|
recipient: 123,
|
||||||
sender: bob
|
sender: 123
|
||||||
}, expectError);
|
}, expectError);
|
||||||
|
|
||||||
invitationDao.invite({
|
invitationDao.invite('asd', expectError);
|
||||||
recipient: alice,
|
|
||||||
}, expectError);
|
|
||||||
|
|
||||||
invitationDao.invite({
|
function expectError(err, status) {
|
||||||
recipient: 123,
|
expect(err).to.exist;
|
||||||
sender: 123
|
expect(status).to.not.exist;
|
||||||
}, expectError);
|
}
|
||||||
|
|
||||||
invitationDao.invite('asd', expectError);
|
|
||||||
|
|
||||||
function expectError(err, status) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(status).to.not.exist;
|
|
||||||
}
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
File diff suppressed because it is too large
Load Diff
@ -1,152 +1,148 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var LawnchairDAO = require('js/dao/lawnchair-dao'),
|
var LawnchairDAO = require('../../src/js/dao/lawnchair-dao');
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
|
|
||||||
var dbName = 'lawnchair@test.com';
|
var dbName = 'lawnchair@test.com';
|
||||||
|
|
||||||
var key = 'type_1';
|
var key = 'type_1';
|
||||||
var data = {
|
var data = {
|
||||||
name: 'testName1',
|
name: 'testName1',
|
||||||
type: 'testType1'
|
type: 'testType1'
|
||||||
};
|
};
|
||||||
|
|
||||||
var key2 = 'type_2';
|
var key2 = 'type_2';
|
||||||
var data2 = {
|
var data2 = {
|
||||||
name: 'testName2',
|
name: 'testName2',
|
||||||
type: 'testType2'
|
type: 'testType2'
|
||||||
};
|
};
|
||||||
|
|
||||||
describe('Lawnchair DAO unit tests', function() {
|
describe('Lawnchair DAO unit tests', function() {
|
||||||
var lawnchairDao;
|
var lawnchairDao;
|
||||||
|
|
||||||
beforeEach(function(done) {
|
beforeEach(function(done) {
|
||||||
lawnchairDao = new LawnchairDAO();
|
lawnchairDao = new LawnchairDAO();
|
||||||
lawnchairDao.init(dbName, function(err) {
|
lawnchairDao.init(dbName, function(err) {
|
||||||
expect(err).to.not.exist;
|
expect(err).to.not.exist;
|
||||||
expect(lawnchairDao._db).to.exist;
|
expect(lawnchairDao._db).to.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function(done) {
|
||||||
|
lawnchairDao.clear(function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('read', function() {
|
||||||
|
it('should fail', function(done) {
|
||||||
|
lawnchairDao.read(undefined, function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('list', function() {
|
||||||
|
it('should fail', function(done) {
|
||||||
|
lawnchairDao.list(undefined, 0, null, function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('remove list', function() {
|
||||||
|
it('should fail', function(done) {
|
||||||
|
lawnchairDao.removeList(undefined, function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('persist/read/remove', function() {
|
||||||
|
it('should fail', function(done) {
|
||||||
|
lawnchairDao.persist(undefined, data, function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
it('should fail', function(done) {
|
||||||
|
lawnchairDao.persist('1234', undefined, function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function(done) {
|
it('should work', function(done) {
|
||||||
lawnchairDao.clear(function(err) {
|
lawnchairDao.persist(key, data, function(err) {
|
||||||
expect(err).to.not.exist;
|
expect(err).to.not.exist;
|
||||||
|
lawnchairDao.read(key, onRead);
|
||||||
|
});
|
||||||
|
|
||||||
|
function onRead(err, fetched) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(fetched).to.deep.equal(data);
|
||||||
|
lawnchairDao.remove(key, onRemove);
|
||||||
|
}
|
||||||
|
|
||||||
|
function onRemove(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
lawnchairDao.read(key, onReadAgain);
|
||||||
|
}
|
||||||
|
|
||||||
|
function onReadAgain(err, fetched) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(fetched).to.not.exist;
|
||||||
|
done();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('batch/list/removeList', function() {
|
||||||
|
it('should fails', function(done) {
|
||||||
|
lawnchairDao.batch({}, function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('read', function() {
|
it('should work', function(done) {
|
||||||
it('should fail', function(done) {
|
var list = [{
|
||||||
lawnchairDao.read(undefined, function(err) {
|
key: key,
|
||||||
expect(err).to.exist;
|
object: data
|
||||||
done();
|
}, {
|
||||||
});
|
key: key2,
|
||||||
|
object: data2
|
||||||
|
}];
|
||||||
|
|
||||||
|
lawnchairDao.batch(list, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
lawnchairDao.list('type', 0, null, onList);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
function onList(err, fetched) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(fetched.length).to.equal(2);
|
||||||
|
expect(fetched[0]).to.deep.equal(list[0].object);
|
||||||
|
lawnchairDao.removeList('type', onRemoveList);
|
||||||
|
}
|
||||||
|
|
||||||
|
function onRemoveList(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
lawnchairDao.list('type', 0, null, onListAgain);
|
||||||
|
}
|
||||||
|
|
||||||
|
function onListAgain(err, fetched) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(fetched).to.exist;
|
||||||
|
expect(fetched.length).to.equal(0);
|
||||||
|
done();
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('list', function() {
|
|
||||||
it('should fail', function(done) {
|
|
||||||
lawnchairDao.list(undefined, 0, null, function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('remove list', function() {
|
|
||||||
it('should fail', function(done) {
|
|
||||||
lawnchairDao.removeList(undefined, function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('persist/read/remove', function() {
|
|
||||||
it('should fail', function(done) {
|
|
||||||
lawnchairDao.persist(undefined, data, function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should fail', function(done) {
|
|
||||||
lawnchairDao.persist('1234', undefined, function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
lawnchairDao.persist(key, data, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
lawnchairDao.read(key, onRead);
|
|
||||||
});
|
|
||||||
|
|
||||||
function onRead(err, fetched) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(fetched).to.deep.equal(data);
|
|
||||||
lawnchairDao.remove(key, onRemove);
|
|
||||||
}
|
|
||||||
|
|
||||||
function onRemove(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
lawnchairDao.read(key, onReadAgain);
|
|
||||||
}
|
|
||||||
|
|
||||||
function onReadAgain(err, fetched) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(fetched).to.not.exist;
|
|
||||||
done();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('batch/list/removeList', function() {
|
|
||||||
it('should fails', function(done) {
|
|
||||||
lawnchairDao.batch({}, function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
var list = [{
|
|
||||||
key: key,
|
|
||||||
object: data
|
|
||||||
}, {
|
|
||||||
key: key2,
|
|
||||||
object: data2
|
|
||||||
}];
|
|
||||||
|
|
||||||
lawnchairDao.batch(list, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
lawnchairDao.list('type', 0, null, onList);
|
|
||||||
});
|
|
||||||
|
|
||||||
function onList(err, fetched) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(fetched.length).to.equal(2);
|
|
||||||
expect(fetched[0]).to.deep.equal(list[0].object);
|
|
||||||
lawnchairDao.removeList('type', onRemoveList);
|
|
||||||
}
|
|
||||||
|
|
||||||
function onRemoveList(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
lawnchairDao.list('type', 0, null, onListAgain);
|
|
||||||
}
|
|
||||||
|
|
||||||
function onListAgain(err, fetched) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(fetched).to.exist;
|
|
||||||
expect(fetched.length).to.equal(0);
|
|
||||||
done();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
});
|
});
|
@ -1,236 +1,232 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
LoginCtrl = require('../../src/js/controller/login'),
|
||||||
mocks = require('angularMocks'),
|
EmailDAO = require('../../src/js/dao/email-dao'),
|
||||||
LoginCtrl = require('js/controller/login'),
|
Auth = require('../../src/js/bo/auth'),
|
||||||
EmailDAO = require('js/dao/email-dao'),
|
appController = require('../../src/js/app-controller'),
|
||||||
Auth = require('js/bo/auth'),
|
KeychainDAO = require('../../src/js/dao/keychain-dao');
|
||||||
appController = require('js/app-controller'),
|
|
||||||
KeychainDAO = require('js/dao/keychain-dao');
|
|
||||||
|
|
||||||
describe('Login Controller unit test', function() {
|
describe('Login Controller unit test', function() {
|
||||||
var scope, location, ctrl,
|
var scope, location, ctrl,
|
||||||
origEmailDao, emailDaoMock,
|
origEmailDao, emailDaoMock,
|
||||||
origKeychain, keychainMock,
|
origKeychain, keychainMock,
|
||||||
origAuth, authStub,
|
origAuth, authStub,
|
||||||
emailAddress = 'fred@foo.com',
|
emailAddress = 'fred@foo.com',
|
||||||
startAppStub,
|
startAppStub,
|
||||||
checkForUpdateStub,
|
checkForUpdateStub,
|
||||||
initStub;
|
initStub;
|
||||||
|
|
||||||
describe('initialization', function() {
|
describe('initialization', function() {
|
||||||
var hasChrome, hasIdentity;
|
var hasChrome, hasIdentity;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
hasChrome = !!window.chrome;
|
hasChrome = !!window.chrome;
|
||||||
hasIdentity = !!window.chrome.identity;
|
hasIdentity = !!window.chrome.identity;
|
||||||
window.chrome = window.chrome || {};
|
window.chrome = window.chrome || {};
|
||||||
window.chrome.identity = window.chrome.identity || {};
|
window.chrome.identity = window.chrome.identity || {};
|
||||||
|
|
||||||
// remember original module to restore later, then replace it
|
// remember original module to restore later, then replace it
|
||||||
origEmailDao = appController._emailDao;
|
origEmailDao = appController._emailDao;
|
||||||
origKeychain = appController._keychain;
|
origKeychain = appController._keychain;
|
||||||
origAuth = appController._auth;
|
origAuth = appController._auth;
|
||||||
appController._emailDao = emailDaoMock = sinon.createStubInstance(EmailDAO);
|
appController._emailDao = emailDaoMock = sinon.createStubInstance(EmailDAO);
|
||||||
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
||||||
appController._auth = authStub = sinon.createStubInstance(Auth);
|
appController._auth = authStub = sinon.createStubInstance(Auth);
|
||||||
|
|
||||||
startAppStub = sinon.stub(appController, 'start');
|
startAppStub = sinon.stub(appController, 'start');
|
||||||
checkForUpdateStub = sinon.stub(appController, 'checkForUpdate');
|
checkForUpdateStub = sinon.stub(appController, 'checkForUpdate');
|
||||||
initStub = sinon.stub(appController, 'init');
|
initStub = sinon.stub(appController, 'init');
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
// restore the browser
|
||||||
|
if (!hasIdentity) {
|
||||||
|
delete window.chrome.identity;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!hasChrome) {
|
||||||
|
delete window.chrome;
|
||||||
|
}
|
||||||
|
|
||||||
|
// restore the app controller module
|
||||||
|
appController._emailDao = origEmailDao;
|
||||||
|
appController._keychain = origKeychain;
|
||||||
|
appController._auth = origAuth;
|
||||||
|
appController.start.restore && appController.start.restore();
|
||||||
|
appController.checkForUpdate.restore && appController.checkForUpdate.restore();
|
||||||
|
appController.init.restore && appController.init.restore();
|
||||||
|
location.path.restore && location.path.restore();
|
||||||
|
|
||||||
|
startAppStub.restore();
|
||||||
|
checkForUpdateStub.restore();
|
||||||
|
initStub.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should forward directly to desktop for empty passphrase', function(done) {
|
||||||
|
var testKeys = {
|
||||||
|
privateKey: 'a',
|
||||||
|
publicKey: 'b'
|
||||||
|
};
|
||||||
|
|
||||||
|
startAppStub.yields();
|
||||||
|
authStub.getEmailAddress.yields(null, {
|
||||||
|
emailAddress: emailAddress,
|
||||||
|
realname: 'asd'
|
||||||
});
|
});
|
||||||
|
initStub.yields(null, testKeys);
|
||||||
|
|
||||||
afterEach(function() {
|
emailDaoMock.unlock.withArgs({
|
||||||
// restore the browser
|
keypair: testKeys,
|
||||||
if (!hasIdentity) {
|
passphrase: undefined
|
||||||
delete window.chrome.identity;
|
}).yields();
|
||||||
}
|
|
||||||
|
|
||||||
if (!hasChrome) {
|
angular.module('logintest', []);
|
||||||
delete window.chrome;
|
mocks.module('logintest');
|
||||||
}
|
mocks.inject(function($controller, $rootScope, $location) {
|
||||||
|
location = $location;
|
||||||
// restore the app controller module
|
sinon.stub(location, 'path', function(path) {
|
||||||
appController._emailDao = origEmailDao;
|
expect(path).to.equal('/desktop');
|
||||||
appController._keychain = origKeychain;
|
expect(startAppStub.calledOnce).to.be.true;
|
||||||
appController._auth = origAuth;
|
expect(checkForUpdateStub.calledOnce).to.be.true;
|
||||||
appController.start.restore && appController.start.restore();
|
expect(authStub.getEmailAddress.calledOnce).to.be.true;
|
||||||
appController.checkForUpdate.restore && appController.checkForUpdate.restore();
|
done();
|
||||||
appController.init.restore && appController.init.restore();
|
|
||||||
location.path.restore && location.path.restore();
|
|
||||||
|
|
||||||
startAppStub.restore();
|
|
||||||
checkForUpdateStub.restore();
|
|
||||||
initStub.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should forward directly to desktop for empty passphrase', function(done) {
|
|
||||||
var testKeys = {
|
|
||||||
privateKey: 'a',
|
|
||||||
publicKey: 'b'
|
|
||||||
};
|
|
||||||
|
|
||||||
startAppStub.yields();
|
|
||||||
authStub.getEmailAddress.yields(null, {
|
|
||||||
emailAddress: emailAddress,
|
|
||||||
realname: 'asd'
|
|
||||||
});
|
});
|
||||||
initStub.yields(null, testKeys);
|
scope = $rootScope.$new();
|
||||||
|
scope.state = {};
|
||||||
emailDaoMock.unlock.withArgs({
|
ctrl = $controller(LoginCtrl, {
|
||||||
keypair: testKeys,
|
$location: location,
|
||||||
passphrase: undefined
|
$scope: scope
|
||||||
}).yields();
|
|
||||||
|
|
||||||
angular.module('logintest', []);
|
|
||||||
mocks.module('logintest');
|
|
||||||
mocks.inject(function($controller, $rootScope, $location) {
|
|
||||||
location = $location;
|
|
||||||
sinon.stub(location, 'path', function(path) {
|
|
||||||
expect(path).to.equal('/desktop');
|
|
||||||
expect(startAppStub.calledOnce).to.be.true;
|
|
||||||
expect(checkForUpdateStub.calledOnce).to.be.true;
|
|
||||||
expect(authStub.getEmailAddress.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
scope = $rootScope.$new();
|
|
||||||
scope.state = {};
|
|
||||||
ctrl = $controller(LoginCtrl, {
|
|
||||||
$location: location,
|
|
||||||
$scope: scope
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should forward to existing user login', function(done) {
|
it('should forward to existing user login', function(done) {
|
||||||
var testKeys = {
|
var testKeys = {
|
||||||
privateKey: 'a',
|
privateKey: 'a',
|
||||||
publicKey: 'b'
|
publicKey: 'b'
|
||||||
};
|
};
|
||||||
|
|
||||||
startAppStub.yields();
|
startAppStub.yields();
|
||||||
authStub.getEmailAddress.yields(null, {
|
authStub.getEmailAddress.yields(null, {
|
||||||
emailAddress: emailAddress,
|
emailAddress: emailAddress,
|
||||||
realname: 'asd'
|
realname: 'asd'
|
||||||
|
});
|
||||||
|
initStub.yields(null, testKeys);
|
||||||
|
|
||||||
|
emailDaoMock.unlock.withArgs({
|
||||||
|
keypair: testKeys,
|
||||||
|
passphrase: undefined
|
||||||
|
}).yields({});
|
||||||
|
|
||||||
|
angular.module('logintest', []);
|
||||||
|
mocks.module('logintest');
|
||||||
|
mocks.inject(function($controller, $rootScope, $location) {
|
||||||
|
location = $location;
|
||||||
|
sinon.stub(location, 'path', function(path) {
|
||||||
|
expect(path).to.equal('/login-existing');
|
||||||
|
expect(startAppStub.calledOnce).to.be.true;
|
||||||
|
expect(checkForUpdateStub.calledOnce).to.be.true;
|
||||||
|
expect(authStub.getEmailAddress.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
initStub.yields(null, testKeys);
|
scope = $rootScope.$new();
|
||||||
|
scope.state = {};
|
||||||
emailDaoMock.unlock.withArgs({
|
ctrl = $controller(LoginCtrl, {
|
||||||
keypair: testKeys,
|
$location: location,
|
||||||
passphrase: undefined
|
$scope: scope
|
||||||
}).yields({});
|
|
||||||
|
|
||||||
angular.module('logintest', []);
|
|
||||||
mocks.module('logintest');
|
|
||||||
mocks.inject(function($controller, $rootScope, $location) {
|
|
||||||
location = $location;
|
|
||||||
sinon.stub(location, 'path', function(path) {
|
|
||||||
expect(path).to.equal('/login-existing');
|
|
||||||
expect(startAppStub.calledOnce).to.be.true;
|
|
||||||
expect(checkForUpdateStub.calledOnce).to.be.true;
|
|
||||||
expect(authStub.getEmailAddress.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
scope = $rootScope.$new();
|
|
||||||
scope.state = {};
|
|
||||||
ctrl = $controller(LoginCtrl, {
|
|
||||||
$location: location,
|
|
||||||
$scope: scope
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should forward to privatekey download login', function(done) {
|
it('should forward to privatekey download login', function(done) {
|
||||||
startAppStub.yields();
|
startAppStub.yields();
|
||||||
authStub.getEmailAddress.yields(null, {
|
authStub.getEmailAddress.yields(null, {
|
||||||
emailAddress: emailAddress,
|
emailAddress: emailAddress,
|
||||||
realname: 'asd'
|
realname: 'asd'
|
||||||
});
|
});
|
||||||
initStub.yields(null, {
|
initStub.yields(null, {
|
||||||
publicKey: 'b'
|
publicKey: 'b'
|
||||||
});
|
});
|
||||||
keychainMock.requestPrivateKeyDownload.yields(null, {});
|
keychainMock.requestPrivateKeyDownload.yields(null, {});
|
||||||
|
|
||||||
angular.module('logintest', []);
|
angular.module('logintest', []);
|
||||||
mocks.module('logintest');
|
mocks.module('logintest');
|
||||||
mocks.inject(function($controller, $rootScope, $location) {
|
mocks.inject(function($controller, $rootScope, $location) {
|
||||||
location = $location;
|
location = $location;
|
||||||
sinon.stub(location, 'path', function(path) {
|
sinon.stub(location, 'path', function(path) {
|
||||||
expect(path).to.equal('/login-privatekey-download');
|
expect(path).to.equal('/login-privatekey-download');
|
||||||
expect(startAppStub.calledOnce).to.be.true;
|
expect(startAppStub.calledOnce).to.be.true;
|
||||||
expect(checkForUpdateStub.calledOnce).to.be.true;
|
expect(checkForUpdateStub.calledOnce).to.be.true;
|
||||||
expect(authStub.getEmailAddress.calledOnce).to.be.true;
|
expect(authStub.getEmailAddress.calledOnce).to.be.true;
|
||||||
expect(keychainMock.requestPrivateKeyDownload.calledOnce).to.be.true;
|
expect(keychainMock.requestPrivateKeyDownload.calledOnce).to.be.true;
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
scope = $rootScope.$new();
|
scope = $rootScope.$new();
|
||||||
scope.state = {};
|
scope.state = {};
|
||||||
ctrl = $controller(LoginCtrl, {
|
ctrl = $controller(LoginCtrl, {
|
||||||
$location: location,
|
$location: location,
|
||||||
$scope: scope
|
$scope: scope
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should forward to new device login', function(done) {
|
it('should forward to new device login', function(done) {
|
||||||
startAppStub.yields();
|
startAppStub.yields();
|
||||||
authStub.getEmailAddress.yields(null, {
|
authStub.getEmailAddress.yields(null, {
|
||||||
emailAddress: emailAddress,
|
emailAddress: emailAddress,
|
||||||
realname: 'asd'
|
realname: 'asd'
|
||||||
});
|
});
|
||||||
initStub.yields(null, {
|
initStub.yields(null, {
|
||||||
publicKey: 'b'
|
publicKey: 'b'
|
||||||
});
|
});
|
||||||
keychainMock.requestPrivateKeyDownload.yields();
|
keychainMock.requestPrivateKeyDownload.yields();
|
||||||
|
|
||||||
angular.module('logintest', []);
|
angular.module('logintest', []);
|
||||||
mocks.module('logintest');
|
mocks.module('logintest');
|
||||||
mocks.inject(function($controller, $rootScope, $location) {
|
mocks.inject(function($controller, $rootScope, $location) {
|
||||||
location = $location;
|
location = $location;
|
||||||
sinon.stub(location, 'path', function(path) {
|
sinon.stub(location, 'path', function(path) {
|
||||||
expect(path).to.equal('/login-new-device');
|
expect(path).to.equal('/login-new-device');
|
||||||
expect(startAppStub.calledOnce).to.be.true;
|
expect(startAppStub.calledOnce).to.be.true;
|
||||||
expect(checkForUpdateStub.calledOnce).to.be.true;
|
expect(checkForUpdateStub.calledOnce).to.be.true;
|
||||||
expect(authStub.getEmailAddress.calledOnce).to.be.true;
|
expect(authStub.getEmailAddress.calledOnce).to.be.true;
|
||||||
expect(keychainMock.requestPrivateKeyDownload.calledOnce).to.be.true;
|
expect(keychainMock.requestPrivateKeyDownload.calledOnce).to.be.true;
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
scope = $rootScope.$new();
|
scope = $rootScope.$new();
|
||||||
scope.state = {};
|
scope.state = {};
|
||||||
ctrl = $controller(LoginCtrl, {
|
ctrl = $controller(LoginCtrl, {
|
||||||
$location: location,
|
$location: location,
|
||||||
$scope: scope
|
$scope: scope
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should forward to initial login', function(done) {
|
it('should forward to initial login', function(done) {
|
||||||
startAppStub.yields();
|
startAppStub.yields();
|
||||||
authStub.getEmailAddress.yields(null, {
|
authStub.getEmailAddress.yields(null, {
|
||||||
emailAddress: emailAddress,
|
emailAddress: emailAddress,
|
||||||
realname: 'asd'
|
realname: 'asd'
|
||||||
|
});
|
||||||
|
initStub.yields();
|
||||||
|
|
||||||
|
angular.module('logintest', []);
|
||||||
|
mocks.module('logintest');
|
||||||
|
mocks.inject(function($controller, $rootScope, $location) {
|
||||||
|
location = $location;
|
||||||
|
sinon.stub(location, 'path', function(path) {
|
||||||
|
expect(path).to.equal('/login-initial');
|
||||||
|
expect(startAppStub.calledOnce).to.be.true;
|
||||||
|
expect(checkForUpdateStub.calledOnce).to.be.true;
|
||||||
|
expect(authStub.getEmailAddress.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
initStub.yields();
|
scope = $rootScope.$new();
|
||||||
|
scope.state = {};
|
||||||
angular.module('logintest', []);
|
ctrl = $controller(LoginCtrl, {
|
||||||
mocks.module('logintest');
|
$location: location,
|
||||||
mocks.inject(function($controller, $rootScope, $location) {
|
$scope: scope
|
||||||
location = $location;
|
|
||||||
sinon.stub(location, 'path', function(path) {
|
|
||||||
expect(path).to.equal('/login-initial');
|
|
||||||
expect(startAppStub.calledOnce).to.be.true;
|
|
||||||
expect(checkForUpdateStub.calledOnce).to.be.true;
|
|
||||||
expect(authStub.getEmailAddress.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
scope = $rootScope.$new();
|
|
||||||
scope.state = {};
|
|
||||||
ctrl = $controller(LoginCtrl, {
|
|
||||||
$location: location,
|
|
||||||
$scope: scope
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -1,116 +1,112 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var Auth = require('../../src/js/bo/auth'),
|
||||||
angular = require('angular'),
|
mocks = angular.mocks,
|
||||||
Auth = require('js/bo/auth'),
|
LoginExistingCtrl = require('../../src/js/controller/login-existing'),
|
||||||
mocks = require('angularMocks'),
|
EmailDAO = require('../../src/js/dao/email-dao'),
|
||||||
LoginExistingCtrl = require('js/controller/login-existing'),
|
KeychainDAO = require('../../src/js/dao/keychain-dao'),
|
||||||
EmailDAO = require('js/dao/email-dao'),
|
appController = require('../../src/js/app-controller');
|
||||||
KeychainDAO = require('js/dao/keychain-dao'),
|
|
||||||
appController = require('js/app-controller');
|
|
||||||
|
|
||||||
describe('Login (existing user) Controller unit test', function() {
|
describe('Login (existing user) Controller unit test', function() {
|
||||||
var scope, location, ctrl, origEmailDao, emailDaoMock,
|
var scope, location, ctrl, origEmailDao, emailDaoMock,
|
||||||
origAuth, authMock,
|
origAuth, authMock,
|
||||||
emailAddress = 'fred@foo.com',
|
emailAddress = 'fred@foo.com',
|
||||||
passphrase = 'asd',
|
passphrase = 'asd',
|
||||||
keychainMock;
|
keychainMock;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
// remember original module to restore later
|
// remember original module to restore later
|
||||||
origEmailDao = appController._emailDao;
|
origEmailDao = appController._emailDao;
|
||||||
origAuth = appController._auth;
|
origAuth = appController._auth;
|
||||||
|
|
||||||
appController._emailDao = emailDaoMock = sinon.createStubInstance(EmailDAO);
|
appController._emailDao = emailDaoMock = sinon.createStubInstance(EmailDAO);
|
||||||
appController._auth = authMock = sinon.createStubInstance(Auth);
|
appController._auth = authMock = sinon.createStubInstance(Auth);
|
||||||
|
|
||||||
keychainMock = sinon.createStubInstance(KeychainDAO);
|
keychainMock = sinon.createStubInstance(KeychainDAO);
|
||||||
emailDaoMock._keychain = keychainMock;
|
emailDaoMock._keychain = keychainMock;
|
||||||
|
|
||||||
emailDaoMock._account = {
|
emailDaoMock._account = {
|
||||||
emailAddress: emailAddress,
|
emailAddress: emailAddress,
|
||||||
};
|
};
|
||||||
|
|
||||||
angular.module('loginexistingtest', []);
|
angular.module('loginexistingtest', []);
|
||||||
mocks.module('loginexistingtest');
|
mocks.module('loginexistingtest');
|
||||||
mocks.inject(function($rootScope, $controller, $location) {
|
mocks.inject(function($rootScope, $controller, $location) {
|
||||||
location = $location;
|
location = $location;
|
||||||
scope = $rootScope.$new();
|
scope = $rootScope.$new();
|
||||||
scope.state = {};
|
scope.state = {};
|
||||||
ctrl = $controller(LoginExistingCtrl, {
|
ctrl = $controller(LoginExistingCtrl, {
|
||||||
$scope: scope,
|
$scope: scope,
|
||||||
$routeParams: {}
|
$routeParams: {}
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
afterEach(function() {
|
||||||
// restore the module
|
// restore the module
|
||||||
appController._emailDao = origEmailDao;
|
appController._emailDao = origEmailDao;
|
||||||
appController._auth = origAuth;
|
appController._auth = origAuth;
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('initial state', function() {
|
||||||
|
it('should be well defined', function() {
|
||||||
|
expect(scope.buttonEnabled).to.be.true;
|
||||||
|
expect(scope.incorrect).to.be.false;
|
||||||
|
expect(scope.change).to.exist;
|
||||||
|
expect(scope.confirmPassphrase).to.exist;
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe('initial state', function() {
|
describe('functionality', function() {
|
||||||
it('should be well defined', function() {
|
describe('change', function() {
|
||||||
expect(scope.buttonEnabled).to.be.true;
|
it('should set incorrect to false', function() {
|
||||||
|
scope.incorrect = true;
|
||||||
|
|
||||||
|
scope.change();
|
||||||
expect(scope.incorrect).to.be.false;
|
expect(scope.incorrect).to.be.false;
|
||||||
expect(scope.change).to.exist;
|
|
||||||
expect(scope.confirmPassphrase).to.exist;
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('functionality', function() {
|
describe('confirm passphrase', function() {
|
||||||
describe('change', function() {
|
it('should unlock crypto and start', function() {
|
||||||
it('should set incorrect to false', function() {
|
var keypair = {},
|
||||||
scope.incorrect = true;
|
pathSpy = sinon.spy(location, 'path');
|
||||||
|
scope.passphrase = passphrase;
|
||||||
|
keychainMock.getUserKeyPair.withArgs(emailAddress).yields(null, keypair);
|
||||||
|
emailDaoMock.unlock.withArgs({
|
||||||
|
keypair: keypair,
|
||||||
|
passphrase: passphrase
|
||||||
|
}).yields();
|
||||||
|
authMock.storeCredentials.yields();
|
||||||
|
|
||||||
scope.change();
|
|
||||||
expect(scope.incorrect).to.be.false;
|
scope.confirmPassphrase();
|
||||||
});
|
|
||||||
|
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
||||||
|
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
||||||
|
expect(pathSpy.calledOnce).to.be.true;
|
||||||
|
expect(pathSpy.calledWith('/desktop')).to.be.true;
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('confirm passphrase', function() {
|
it('should not do anything without passphrase', function() {
|
||||||
it('should unlock crypto and start', function() {
|
var pathSpy = sinon.spy(location, 'path');
|
||||||
var keypair = {},
|
scope.passphrase = '';
|
||||||
pathSpy = sinon.spy(location, 'path');
|
|
||||||
scope.passphrase = passphrase;
|
|
||||||
keychainMock.getUserKeyPair.withArgs(emailAddress).yields(null, keypair);
|
|
||||||
emailDaoMock.unlock.withArgs({
|
|
||||||
keypair: keypair,
|
|
||||||
passphrase: passphrase
|
|
||||||
}).yields();
|
|
||||||
authMock.storeCredentials.yields();
|
|
||||||
|
|
||||||
|
scope.confirmPassphrase();
|
||||||
|
expect(pathSpy.callCount).to.equal(0);
|
||||||
|
});
|
||||||
|
|
||||||
scope.confirmPassphrase();
|
it('should not work when keypair unavailable', function(done) {
|
||||||
|
scope.passphrase = passphrase;
|
||||||
|
keychainMock.getUserKeyPair.withArgs(emailAddress).yields(new Error('asd'));
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err.message).to.equal('asd');
|
||||||
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
||||||
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
done();
|
||||||
expect(pathSpy.calledOnce).to.be.true;
|
};
|
||||||
expect(pathSpy.calledWith('/desktop')).to.be.true;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not do anything without passphrase', function() {
|
scope.confirmPassphrase();
|
||||||
var pathSpy = sinon.spy(location, 'path');
|
|
||||||
scope.passphrase = '';
|
|
||||||
|
|
||||||
scope.confirmPassphrase();
|
|
||||||
expect(pathSpy.callCount).to.equal(0);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not work when keypair unavailable', function(done) {
|
|
||||||
scope.passphrase = passphrase;
|
|
||||||
keychainMock.getUserKeyPair.withArgs(emailAddress).yields(new Error('asd'));
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err.message).to.equal('asd');
|
|
||||||
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.confirmPassphrase();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -1,202 +1,197 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var Auth = require('../../src/js/bo/auth'),
|
||||||
angular = require('angular'),
|
mocks = angular.mocks,
|
||||||
Auth = require('js/bo/auth'),
|
LoginInitialCtrl = require('../../src/js/controller/login-initial'),
|
||||||
mocks = require('angularMocks'),
|
PGP = require('../../src/js/crypto/pgp'),
|
||||||
LoginInitialCtrl = require('js/controller/login-initial'),
|
EmailDAO = require('../../src/js/dao/email-dao'),
|
||||||
PGP = require('js/crypto/pgp'),
|
appController = require('../../src/js/app-controller');
|
||||||
EmailDAO = require('js/dao/email-dao'),
|
|
||||||
appController = require('js/app-controller');
|
|
||||||
|
|
||||||
describe('Login (initial user) Controller unit test', function() {
|
describe('Login (initial user) Controller unit test', function() {
|
||||||
var scope, ctrl, location, origEmailDao, emailDaoMock,
|
var scope, ctrl, location, origEmailDao, emailDaoMock,
|
||||||
origAuth, authMock,
|
origAuth, authMock,
|
||||||
emailAddress = 'fred@foo.com',
|
emailAddress = 'fred@foo.com',
|
||||||
keyId, expectedKeyId,
|
keyId, expectedKeyId,
|
||||||
cryptoMock;
|
cryptoMock;
|
||||||
|
|
||||||
|
beforeEach(function() {
|
||||||
|
// remember original module to restore later
|
||||||
|
origEmailDao = appController._emailDao;
|
||||||
|
origAuth = appController._auth;
|
||||||
|
|
||||||
|
appController._emailDao = emailDaoMock = sinon.createStubInstance(EmailDAO);
|
||||||
|
appController._auth = authMock = sinon.createStubInstance(Auth);
|
||||||
|
|
||||||
|
keyId = '9FEB47936E712926';
|
||||||
|
expectedKeyId = '6E712926';
|
||||||
|
cryptoMock = sinon.createStubInstance(PGP);
|
||||||
|
emailDaoMock._crypto = cryptoMock;
|
||||||
|
|
||||||
|
emailDaoMock._account = {
|
||||||
|
emailAddress: emailAddress,
|
||||||
|
};
|
||||||
|
|
||||||
|
angular.module('logininitialtest', []);
|
||||||
|
mocks.module('logininitialtest');
|
||||||
|
mocks.inject(function($rootScope, $controller, $location) {
|
||||||
|
scope = $rootScope.$new();
|
||||||
|
location = $location;
|
||||||
|
scope.state = {
|
||||||
|
ui: {}
|
||||||
|
};
|
||||||
|
ctrl = $controller(LoginInitialCtrl, {
|
||||||
|
$scope: scope,
|
||||||
|
$routeParams: {}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
// restore the module
|
||||||
|
appController._emailDao = origEmailDao;
|
||||||
|
appController._auth = origAuth;
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('initial state', function() {
|
||||||
|
it('should be well defined', function() {
|
||||||
|
expect(scope.state.ui).to.equal(1);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('signUpToNewsletter', function() {
|
||||||
|
var xhrMock, requests;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
// remember original module to restore later
|
xhrMock = sinon.useFakeXMLHttpRequest();
|
||||||
origEmailDao = appController._emailDao;
|
requests = [];
|
||||||
origAuth = appController._auth;
|
|
||||||
|
|
||||||
appController._emailDao = emailDaoMock = sinon.createStubInstance(EmailDAO);
|
xhrMock.onCreate = function(xhr) {
|
||||||
appController._auth = authMock = sinon.createStubInstance(Auth);
|
requests.push(xhr);
|
||||||
|
|
||||||
keyId = '9FEB47936E712926';
|
|
||||||
expectedKeyId = '6E712926';
|
|
||||||
cryptoMock = sinon.createStubInstance(PGP);
|
|
||||||
emailDaoMock._crypto = cryptoMock;
|
|
||||||
|
|
||||||
emailDaoMock._account = {
|
|
||||||
emailAddress: emailAddress,
|
|
||||||
};
|
};
|
||||||
|
|
||||||
angular.module('logininitialtest', []);
|
|
||||||
mocks.module('logininitialtest');
|
|
||||||
mocks.inject(function($rootScope, $controller, $location) {
|
|
||||||
scope = $rootScope.$new();
|
|
||||||
location = $location;
|
|
||||||
scope.state = {
|
|
||||||
ui: {}
|
|
||||||
};
|
|
||||||
ctrl = $controller(LoginInitialCtrl, {
|
|
||||||
$scope: scope,
|
|
||||||
$routeParams: {}
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
afterEach(function() {
|
||||||
// restore the module
|
xhrMock.restore();
|
||||||
appController._emailDao = origEmailDao;
|
|
||||||
appController._auth = origAuth;
|
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('initial state', function() {
|
it('should not signup', function() {
|
||||||
it('should be well defined', function() {
|
scope.state.newsletter = false;
|
||||||
|
|
||||||
|
scope.signUpToNewsletter();
|
||||||
|
expect(requests.length).to.equal(0);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail', function(done) {
|
||||||
|
scope.state.newsletter = true;
|
||||||
|
|
||||||
|
scope.signUpToNewsletter(function(err, xhr) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(xhr).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(requests.length).to.equal(1);
|
||||||
|
requests[0].onerror('err');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work without callback', function() {
|
||||||
|
scope.state.newsletter = true;
|
||||||
|
|
||||||
|
scope.signUpToNewsletter();
|
||||||
|
|
||||||
|
expect(requests.length).to.equal(1);
|
||||||
|
requests[0].respond(200, {
|
||||||
|
"Content-Type": "text/plain"
|
||||||
|
}, 'foobar!');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('go to import key', function() {
|
||||||
|
var signUpToNewsletterStub;
|
||||||
|
beforeEach(function() {
|
||||||
|
signUpToNewsletterStub = sinon.stub(scope, 'signUpToNewsletter');
|
||||||
|
});
|
||||||
|
afterEach(function() {
|
||||||
|
signUpToNewsletterStub.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not continue if terms are not accepted', function(done) {
|
||||||
|
scope.state.agree = undefined;
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err.message).to.contain('Terms');
|
||||||
|
expect(signUpToNewsletterStub.called).to.be.false;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.importKey();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function() {
|
||||||
|
scope.state.agree = true;
|
||||||
|
scope.importKey();
|
||||||
|
expect(signUpToNewsletterStub.calledOnce).to.be.true;
|
||||||
|
expect(location.$$path).to.equal('/login-new-device');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('generate key', function() {
|
||||||
|
var signUpToNewsletterStub;
|
||||||
|
beforeEach(function() {
|
||||||
|
signUpToNewsletterStub = sinon.stub(scope, 'signUpToNewsletter');
|
||||||
|
});
|
||||||
|
afterEach(function() {
|
||||||
|
signUpToNewsletterStub.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not continue if terms are not accepted', function(done) {
|
||||||
|
scope.state.agree = undefined;
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err.message).to.contain('Terms');
|
||||||
expect(scope.state.ui).to.equal(1);
|
expect(scope.state.ui).to.equal(1);
|
||||||
});
|
expect(signUpToNewsletterStub.called).to.be.false;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.generateKey();
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('signUpToNewsletter', function() {
|
it('should fail due to error in emailDao.unlock', function(done) {
|
||||||
var xhrMock, requests;
|
scope.state.agree = true;
|
||||||
|
|
||||||
beforeEach(function() {
|
emailDaoMock.unlock.withArgs({
|
||||||
xhrMock = sinon.useFakeXMLHttpRequest();
|
passphrase: undefined
|
||||||
requests = [];
|
}).yields(new Error());
|
||||||
|
authMock.storeCredentials.yields();
|
||||||
|
|
||||||
xhrMock.onCreate = function(xhr) {
|
scope.onError = function(err) {
|
||||||
requests.push(xhr);
|
expect(err).to.exist;
|
||||||
};
|
expect(scope.state.ui).to.equal(1);
|
||||||
});
|
expect(signUpToNewsletterStub.called).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
afterEach(function() {
|
scope.generateKey();
|
||||||
xhrMock.restore();
|
expect(scope.state.ui).to.equal(2);
|
||||||
});
|
|
||||||
|
|
||||||
it('should not signup', function() {
|
|
||||||
scope.state.newsletter = false;
|
|
||||||
|
|
||||||
scope.signUpToNewsletter();
|
|
||||||
expect(requests.length).to.equal(0);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail', function(done) {
|
|
||||||
scope.state.newsletter = true;
|
|
||||||
|
|
||||||
scope.signUpToNewsletter(function(err, xhr) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(xhr).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
|
|
||||||
expect(requests.length).to.equal(1);
|
|
||||||
requests[0].onerror('err');
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work without callback', function() {
|
|
||||||
scope.state.newsletter = true;
|
|
||||||
|
|
||||||
scope.signUpToNewsletter();
|
|
||||||
|
|
||||||
expect(requests.length).to.equal(1);
|
|
||||||
requests[0].respond(200, {
|
|
||||||
"Content-Type": "text/plain"
|
|
||||||
}, 'foobar!');
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('go to import key', function() {
|
it('should unlock crypto', function(done) {
|
||||||
var signUpToNewsletterStub;
|
scope.state.agree = true;
|
||||||
beforeEach(function() {
|
|
||||||
signUpToNewsletterStub = sinon.stub(scope, 'signUpToNewsletter');
|
|
||||||
});
|
|
||||||
afterEach(function() {
|
|
||||||
signUpToNewsletterStub.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not continue if terms are not accepted', function(done) {
|
emailDaoMock.unlock.withArgs({
|
||||||
scope.state.agree = undefined;
|
passphrase: undefined
|
||||||
|
}).yields();
|
||||||
|
authMock.storeCredentials.yields();
|
||||||
|
|
||||||
scope.onError = function(err) {
|
scope.$apply = function() {
|
||||||
expect(err.message).to.contain('Terms');
|
|
||||||
expect(signUpToNewsletterStub.called).to.be.false;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.importKey();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function() {
|
|
||||||
scope.state.agree = true;
|
|
||||||
scope.importKey();
|
|
||||||
expect(signUpToNewsletterStub.calledOnce).to.be.true;
|
|
||||||
expect(location.$$path).to.equal('/login-new-device');
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('generate key', function() {
|
|
||||||
var signUpToNewsletterStub;
|
|
||||||
beforeEach(function() {
|
|
||||||
signUpToNewsletterStub = sinon.stub(scope, 'signUpToNewsletter');
|
|
||||||
});
|
|
||||||
afterEach(function() {
|
|
||||||
signUpToNewsletterStub.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not continue if terms are not accepted', function(done) {
|
|
||||||
scope.state.agree = undefined;
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err.message).to.contain('Terms');
|
|
||||||
expect(scope.state.ui).to.equal(1);
|
|
||||||
expect(signUpToNewsletterStub.called).to.be.false;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.generateKey();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail due to error in emailDao.unlock', function(done) {
|
|
||||||
scope.state.agree = true;
|
|
||||||
|
|
||||||
emailDaoMock.unlock.withArgs({
|
|
||||||
passphrase: undefined
|
|
||||||
}).yields(new Error());
|
|
||||||
authMock.storeCredentials.yields();
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(scope.state.ui).to.equal(1);
|
|
||||||
expect(signUpToNewsletterStub.called).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.generateKey();
|
|
||||||
expect(scope.state.ui).to.equal(2);
|
expect(scope.state.ui).to.equal(2);
|
||||||
});
|
expect(location.$$path).to.equal('/desktop');
|
||||||
|
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
it('should unlock crypto', function(done) {
|
scope.generateKey();
|
||||||
scope.state.agree = true;
|
|
||||||
|
|
||||||
emailDaoMock.unlock.withArgs({
|
|
||||||
passphrase: undefined
|
|
||||||
}).yields();
|
|
||||||
authMock.storeCredentials.yields();
|
|
||||||
|
|
||||||
scope.$apply = function() {
|
|
||||||
expect(scope.state.ui).to.equal(2);
|
|
||||||
expect(location.$$path).to.equal('/desktop');
|
|
||||||
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.generateKey();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
});
|
});
|
||||||
});
|
});
|
@ -1,190 +1,186 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
PGP = require('../../src/js/crypto/pgp'),
|
||||||
mocks = require('angularMocks'),
|
LoginNewDeviceCtrl = require('../../src/js/controller/login-new-device'),
|
||||||
PGP = require('js/crypto/pgp'),
|
KeychainDAO = require('../../src/js/dao/keychain-dao'),
|
||||||
LoginNewDeviceCtrl = require('js/controller/login-new-device'),
|
EmailDAO = require('../../src/js/dao/email-dao'),
|
||||||
KeychainDAO = require('js/dao/keychain-dao'),
|
appController = require('../../src/js/app-controller');
|
||||||
EmailDAO = require('js/dao/email-dao'),
|
|
||||||
appController = require('js/app-controller');
|
|
||||||
|
|
||||||
describe('Login (new device) Controller unit test', function() {
|
describe('Login (new device) Controller unit test', function() {
|
||||||
var scope, ctrl, origEmailDao, emailDaoMock, pgpMock,
|
var scope, ctrl, origEmailDao, emailDaoMock, pgpMock,
|
||||||
emailAddress = 'fred@foo.com',
|
emailAddress = 'fred@foo.com',
|
||||||
passphrase = 'asd',
|
passphrase = 'asd',
|
||||||
keyId,
|
keyId,
|
||||||
keychainMock;
|
keychainMock;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
// remember original module to restore later
|
// remember original module to restore later
|
||||||
origEmailDao = appController._emailDao;
|
origEmailDao = appController._emailDao;
|
||||||
|
|
||||||
emailDaoMock = sinon.createStubInstance(EmailDAO);
|
emailDaoMock = sinon.createStubInstance(EmailDAO);
|
||||||
appController._emailDao = emailDaoMock;
|
appController._emailDao = emailDaoMock;
|
||||||
|
|
||||||
keyId = '9FEB47936E712926';
|
keyId = '9FEB47936E712926';
|
||||||
emailDaoMock._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
emailDaoMock._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
||||||
appController._pgp = pgpMock = sinon.createStubInstance(PGP);
|
appController._pgp = pgpMock = sinon.createStubInstance(PGP);
|
||||||
pgpMock.extractPublicKey.returns('publicKeyArmored');
|
pgpMock.extractPublicKey.returns('publicKeyArmored');
|
||||||
|
|
||||||
emailDaoMock._account = {
|
emailDaoMock._account = {
|
||||||
emailAddress: emailAddress,
|
emailAddress: emailAddress,
|
||||||
|
};
|
||||||
|
|
||||||
|
angular.module('loginnewdevicetest', []);
|
||||||
|
mocks.module('loginnewdevicetest');
|
||||||
|
mocks.inject(function($rootScope, $controller) {
|
||||||
|
scope = $rootScope.$new();
|
||||||
|
scope.state = {
|
||||||
|
ui: {}
|
||||||
};
|
};
|
||||||
|
ctrl = $controller(LoginNewDeviceCtrl, {
|
||||||
angular.module('loginnewdevicetest', []);
|
$scope: scope,
|
||||||
mocks.module('loginnewdevicetest');
|
$routeParams: {}
|
||||||
mocks.inject(function($rootScope, $controller) {
|
|
||||||
scope = $rootScope.$new();
|
|
||||||
scope.state = {
|
|
||||||
ui: {}
|
|
||||||
};
|
|
||||||
ctrl = $controller(LoginNewDeviceCtrl, {
|
|
||||||
$scope: scope,
|
|
||||||
$routeParams: {}
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
afterEach(function() {
|
|
||||||
// restore the module
|
|
||||||
appController._emailDao = origEmailDao;
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('initial state', function() {
|
|
||||||
it('should be well defined', function() {
|
|
||||||
expect(scope.incorrect).to.be.false;
|
|
||||||
expect(scope.confirmPassphrase).to.exist;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('confirm passphrase', function() {
|
|
||||||
it('should unlock crypto with a public key on the server', function() {
|
|
||||||
scope.passphrase = passphrase;
|
|
||||||
scope.key = {
|
|
||||||
privateKeyArmored: 'b'
|
|
||||||
};
|
|
||||||
|
|
||||||
pgpMock.getKeyParams.returns({
|
|
||||||
_id: 'id',
|
|
||||||
userIds: []
|
|
||||||
});
|
|
||||||
|
|
||||||
keychainMock.getUserKeyPair.withArgs(emailAddress).yields(null, {
|
|
||||||
_id: keyId,
|
|
||||||
publicKey: 'a'
|
|
||||||
});
|
|
||||||
emailDaoMock.unlock.withArgs(sinon.match.any, passphrase).yields();
|
|
||||||
keychainMock.putUserKeyPair.yields();
|
|
||||||
|
|
||||||
scope.confirmPassphrase();
|
|
||||||
|
|
||||||
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
|
||||||
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should unlock crypto with no key on the server', function() {
|
|
||||||
scope.passphrase = passphrase;
|
|
||||||
scope.key = {
|
|
||||||
privateKeyArmored: 'b',
|
|
||||||
publicKeyArmored: 'a'
|
|
||||||
};
|
|
||||||
|
|
||||||
pgpMock.getKeyParams.returns({
|
|
||||||
_id: 'id',
|
|
||||||
userIds: []
|
|
||||||
});
|
|
||||||
|
|
||||||
keychainMock.getUserKeyPair.withArgs(emailAddress).yields();
|
|
||||||
emailDaoMock.unlock.withArgs(sinon.match.any, passphrase).yields();
|
|
||||||
keychainMock.putUserKeyPair.yields();
|
|
||||||
|
|
||||||
scope.confirmPassphrase();
|
|
||||||
|
|
||||||
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
|
||||||
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not work when keypair upload fails', function(done) {
|
|
||||||
scope.passphrase = passphrase;
|
|
||||||
scope.key = {
|
|
||||||
privateKeyArmored: 'b'
|
|
||||||
};
|
|
||||||
|
|
||||||
pgpMock.getKeyParams.returns({
|
|
||||||
_id: 'id',
|
|
||||||
userIds: []
|
|
||||||
});
|
|
||||||
|
|
||||||
keychainMock.getUserKeyPair.withArgs(emailAddress).yields(null, {
|
|
||||||
_id: keyId,
|
|
||||||
publicKey: 'a'
|
|
||||||
});
|
|
||||||
emailDaoMock.unlock.yields();
|
|
||||||
keychainMock.putUserKeyPair.yields({
|
|
||||||
errMsg: 'yo mamma.'
|
|
||||||
});
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err.errMsg).to.equal('yo mamma.');
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.confirmPassphrase();
|
|
||||||
|
|
||||||
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
|
||||||
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
|
||||||
expect(keychainMock.putUserKeyPair.calledOnce).to.be.true;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not work when unlock fails', function(done) {
|
|
||||||
scope.passphrase = passphrase;
|
|
||||||
scope.key = {
|
|
||||||
privateKeyArmored: 'b'
|
|
||||||
};
|
|
||||||
|
|
||||||
pgpMock.getKeyParams.returns({
|
|
||||||
_id: 'id',
|
|
||||||
userIds: []
|
|
||||||
});
|
|
||||||
|
|
||||||
keychainMock.getUserKeyPair.withArgs(emailAddress).yields(null, {
|
|
||||||
_id: keyId,
|
|
||||||
publicKey: 'a'
|
|
||||||
});
|
|
||||||
emailDaoMock.unlock.yields({
|
|
||||||
errMsg: 'yo mamma.'
|
|
||||||
});
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err.errMsg).to.equal('yo mamma.');
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.confirmPassphrase();
|
|
||||||
|
|
||||||
expect(scope.incorrect).to.be.true;
|
|
||||||
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
|
||||||
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not work when keypair retrieval', function(done) {
|
|
||||||
scope.passphrase = passphrase;
|
|
||||||
|
|
||||||
keychainMock.getUserKeyPair.withArgs(emailAddress).yields({
|
|
||||||
errMsg: 'yo mamma.'
|
|
||||||
});
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err.errMsg).to.equal('yo mamma.');
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.confirmPassphrase();
|
|
||||||
|
|
||||||
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
// restore the module
|
||||||
|
appController._emailDao = origEmailDao;
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('initial state', function() {
|
||||||
|
it('should be well defined', function() {
|
||||||
|
expect(scope.incorrect).to.be.false;
|
||||||
|
expect(scope.confirmPassphrase).to.exist;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('confirm passphrase', function() {
|
||||||
|
it('should unlock crypto with a public key on the server', function() {
|
||||||
|
scope.passphrase = passphrase;
|
||||||
|
scope.key = {
|
||||||
|
privateKeyArmored: 'b'
|
||||||
|
};
|
||||||
|
|
||||||
|
pgpMock.getKeyParams.returns({
|
||||||
|
_id: 'id',
|
||||||
|
userIds: []
|
||||||
|
});
|
||||||
|
|
||||||
|
keychainMock.getUserKeyPair.withArgs(emailAddress).yields(null, {
|
||||||
|
_id: keyId,
|
||||||
|
publicKey: 'a'
|
||||||
|
});
|
||||||
|
emailDaoMock.unlock.withArgs(sinon.match.any, passphrase).yields();
|
||||||
|
keychainMock.putUserKeyPair.yields();
|
||||||
|
|
||||||
|
scope.confirmPassphrase();
|
||||||
|
|
||||||
|
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
||||||
|
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should unlock crypto with no key on the server', function() {
|
||||||
|
scope.passphrase = passphrase;
|
||||||
|
scope.key = {
|
||||||
|
privateKeyArmored: 'b',
|
||||||
|
publicKeyArmored: 'a'
|
||||||
|
};
|
||||||
|
|
||||||
|
pgpMock.getKeyParams.returns({
|
||||||
|
_id: 'id',
|
||||||
|
userIds: []
|
||||||
|
});
|
||||||
|
|
||||||
|
keychainMock.getUserKeyPair.withArgs(emailAddress).yields();
|
||||||
|
emailDaoMock.unlock.withArgs(sinon.match.any, passphrase).yields();
|
||||||
|
keychainMock.putUserKeyPair.yields();
|
||||||
|
|
||||||
|
scope.confirmPassphrase();
|
||||||
|
|
||||||
|
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
||||||
|
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not work when keypair upload fails', function(done) {
|
||||||
|
scope.passphrase = passphrase;
|
||||||
|
scope.key = {
|
||||||
|
privateKeyArmored: 'b'
|
||||||
|
};
|
||||||
|
|
||||||
|
pgpMock.getKeyParams.returns({
|
||||||
|
_id: 'id',
|
||||||
|
userIds: []
|
||||||
|
});
|
||||||
|
|
||||||
|
keychainMock.getUserKeyPair.withArgs(emailAddress).yields(null, {
|
||||||
|
_id: keyId,
|
||||||
|
publicKey: 'a'
|
||||||
|
});
|
||||||
|
emailDaoMock.unlock.yields();
|
||||||
|
keychainMock.putUserKeyPair.yields({
|
||||||
|
errMsg: 'yo mamma.'
|
||||||
|
});
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err.errMsg).to.equal('yo mamma.');
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.confirmPassphrase();
|
||||||
|
|
||||||
|
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
||||||
|
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
||||||
|
expect(keychainMock.putUserKeyPair.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not work when unlock fails', function(done) {
|
||||||
|
scope.passphrase = passphrase;
|
||||||
|
scope.key = {
|
||||||
|
privateKeyArmored: 'b'
|
||||||
|
};
|
||||||
|
|
||||||
|
pgpMock.getKeyParams.returns({
|
||||||
|
_id: 'id',
|
||||||
|
userIds: []
|
||||||
|
});
|
||||||
|
|
||||||
|
keychainMock.getUserKeyPair.withArgs(emailAddress).yields(null, {
|
||||||
|
_id: keyId,
|
||||||
|
publicKey: 'a'
|
||||||
|
});
|
||||||
|
emailDaoMock.unlock.yields({
|
||||||
|
errMsg: 'yo mamma.'
|
||||||
|
});
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err.errMsg).to.equal('yo mamma.');
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.confirmPassphrase();
|
||||||
|
|
||||||
|
expect(scope.incorrect).to.be.true;
|
||||||
|
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
||||||
|
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not work when keypair retrieval', function(done) {
|
||||||
|
scope.passphrase = passphrase;
|
||||||
|
|
||||||
|
keychainMock.getUserKeyPair.withArgs(emailAddress).yields({
|
||||||
|
errMsg: 'yo mamma.'
|
||||||
|
});
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err.errMsg).to.equal('yo mamma.');
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.confirmPassphrase();
|
||||||
|
|
||||||
|
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
@ -1,39 +1,250 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
Auth = require('../../src/js/bo/auth'),
|
||||||
mocks = require('angularMocks'),
|
LoginPrivateKeyDownloadCtrl = require('../../src/js/controller/login-privatekey-download'),
|
||||||
Auth = require('js/bo/auth'),
|
EmailDAO = require('../../src/js/dao/email-dao'),
|
||||||
LoginPrivateKeyDownloadCtrl = require('js/controller/login-privatekey-download'),
|
appController = require('../../src/js/app-controller'),
|
||||||
EmailDAO = require('js/dao/email-dao'),
|
KeychainDAO = require('../../src/js/dao/keychain-dao');
|
||||||
appController = require('js/app-controller'),
|
|
||||||
KeychainDAO = require('js/dao/keychain-dao');
|
|
||||||
|
|
||||||
describe('Login Private Key Download Controller unit test', function() {
|
describe('Login Private Key Download Controller unit test', function() {
|
||||||
var scope, location, ctrl,
|
var scope, location, ctrl,
|
||||||
origEmailDao, emailDaoMock,
|
origEmailDao, emailDaoMock,
|
||||||
origAuth, authMock,
|
origAuth, authMock,
|
||||||
origKeychain, keychainMock,
|
origKeychain, keychainMock,
|
||||||
emailAddress = 'fred@foo.com';
|
emailAddress = 'fred@foo.com';
|
||||||
|
|
||||||
beforeEach(function(done) {
|
beforeEach(function(done) {
|
||||||
// remember original module to restore later, then replace it
|
// remember original module to restore later, then replace it
|
||||||
origEmailDao = appController._emailDao;
|
origEmailDao = appController._emailDao;
|
||||||
origKeychain = appController._keychain;
|
origKeychain = appController._keychain;
|
||||||
origAuth = appController._auth;
|
origAuth = appController._auth;
|
||||||
|
|
||||||
appController._emailDao = emailDaoMock = sinon.createStubInstance(EmailDAO);
|
appController._emailDao = emailDaoMock = sinon.createStubInstance(EmailDAO);
|
||||||
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
||||||
appController._auth = authMock = sinon.createStubInstance(Auth);
|
appController._auth = authMock = sinon.createStubInstance(Auth);
|
||||||
|
|
||||||
emailDaoMock._account = {
|
emailDaoMock._account = {
|
||||||
emailAddress: emailAddress
|
emailAddress: emailAddress
|
||||||
|
};
|
||||||
|
|
||||||
|
angular.module('login-privatekey-download-test', []);
|
||||||
|
mocks.module('login-privatekey-download-test');
|
||||||
|
mocks.inject(function($controller, $rootScope) {
|
||||||
|
scope = $rootScope.$new();
|
||||||
|
scope.state = {};
|
||||||
|
ctrl = $controller(LoginPrivateKeyDownloadCtrl, {
|
||||||
|
$location: location,
|
||||||
|
$scope: scope,
|
||||||
|
$routeParams: {}
|
||||||
|
});
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
// restore the app controller module
|
||||||
|
appController._emailDao = origEmailDao;
|
||||||
|
appController._keychain = origKeychain;
|
||||||
|
appController._auth = origAuth;
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('initialization', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
expect(scope.step).to.equal(1);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('verifyRecoveryToken', function() {
|
||||||
|
var testKeypair = {
|
||||||
|
publicKey: {
|
||||||
|
_id: 'id'
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
it('should fail for empty recovery token', function(done) {
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
done();
|
||||||
};
|
};
|
||||||
|
|
||||||
angular.module('login-privatekey-download-test', []);
|
scope.recoveryToken = undefined;
|
||||||
mocks.module('login-privatekey-download-test');
|
scope.verifyRecoveryToken();
|
||||||
mocks.inject(function($controller, $rootScope) {
|
});
|
||||||
|
|
||||||
|
it('should fail in keychain.getUserKeyPair', function(done) {
|
||||||
|
keychainMock.getUserKeyPair.yields(42);
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.recoveryToken = 'token';
|
||||||
|
scope.verifyRecoveryToken();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail in keychain.downloadPrivateKey', function(done) {
|
||||||
|
keychainMock.getUserKeyPair.yields(null, testKeypair);
|
||||||
|
keychainMock.downloadPrivateKey.yields(42);
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
||||||
|
expect(keychainMock.downloadPrivateKey.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.recoveryToken = 'token';
|
||||||
|
scope.verifyRecoveryToken();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
keychainMock.getUserKeyPair.yields(null, testKeypair);
|
||||||
|
keychainMock.downloadPrivateKey.yields(null, 'encryptedPrivateKey');
|
||||||
|
|
||||||
|
scope.recoveryToken = 'token';
|
||||||
|
scope.verifyRecoveryToken(function() {
|
||||||
|
expect(scope.encryptedPrivateKey).to.equal('encryptedPrivateKey');
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('handlePaste', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
scope.handlePaste({
|
||||||
|
clipboardData: {
|
||||||
|
getData: function(val) {
|
||||||
|
expect(val).to.equal('text/plain');
|
||||||
|
return '1qaz-2wsx-3edc-4rfv-5tgb-6yhn';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(scope.code0).to.equal('1qaz');
|
||||||
|
expect(scope.code1).to.equal('2wsx');
|
||||||
|
expect(scope.code2).to.equal('3edc');
|
||||||
|
expect(scope.code3).to.equal('4rfv');
|
||||||
|
expect(scope.code4).to.equal('5tgb');
|
||||||
|
expect(scope.code5).to.equal('6yhn');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('decryptAndStorePrivateKeyLocally', function() {
|
||||||
|
beforeEach(function() {
|
||||||
|
scope.code0 = '0';
|
||||||
|
scope.code1 = '1';
|
||||||
|
scope.code2 = '2';
|
||||||
|
scope.code3 = '3';
|
||||||
|
scope.code4 = '4';
|
||||||
|
scope.code5 = '5';
|
||||||
|
|
||||||
|
scope.encryptedPrivateKey = {
|
||||||
|
encryptedPrivateKey: 'encryptedPrivateKey'
|
||||||
|
};
|
||||||
|
scope.cachedKeypair = {
|
||||||
|
publicKey: {
|
||||||
|
_id: 'keyId'
|
||||||
|
}
|
||||||
|
};
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail on empty code', function(done) {
|
||||||
|
scope.code0 = '';
|
||||||
|
scope.code1 = '';
|
||||||
|
scope.code2 = '';
|
||||||
|
scope.code3 = '';
|
||||||
|
scope.code4 = '';
|
||||||
|
scope.code5 = '';
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.decryptAndStorePrivateKeyLocally();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail on decryptAndStorePrivateKeyLocally', function(done) {
|
||||||
|
keychainMock.decryptAndStorePrivateKeyLocally.yields(42);
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(keychainMock.decryptAndStorePrivateKeyLocally.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.decryptAndStorePrivateKeyLocally();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should goto /login-existing on emailDao.unlock fail', function(done) {
|
||||||
|
keychainMock.decryptAndStorePrivateKeyLocally.yields(null, {
|
||||||
|
encryptedKey: 'keyArmored'
|
||||||
|
});
|
||||||
|
emailDaoMock.unlock.yields(42);
|
||||||
|
|
||||||
|
scope.goTo = function(location) {
|
||||||
|
expect(location).to.equal('/login-existing');
|
||||||
|
expect(keychainMock.decryptAndStorePrivateKeyLocally.calledOnce).to.be.true;
|
||||||
|
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.decryptAndStorePrivateKeyLocally();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should goto /desktop on emailDao.unlock success', function(done) {
|
||||||
|
keychainMock.decryptAndStorePrivateKeyLocally.yields(null, {
|
||||||
|
encryptedKey: 'keyArmored'
|
||||||
|
});
|
||||||
|
emailDaoMock.unlock.yields();
|
||||||
|
authMock.storeCredentials.yields();
|
||||||
|
|
||||||
|
scope.goTo = function(location) {
|
||||||
|
expect(location).to.equal('/desktop');
|
||||||
|
expect(keychainMock.decryptAndStorePrivateKeyLocally.calledOnce).to.be.true;
|
||||||
|
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.decryptAndStorePrivateKeyLocally();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('goForward', function() {
|
||||||
|
it('should work in step 1', function() {
|
||||||
|
var verifyRecoveryTokenStub = sinon.stub(scope, 'verifyRecoveryToken');
|
||||||
|
verifyRecoveryTokenStub.yields();
|
||||||
|
scope.step = 1;
|
||||||
|
|
||||||
|
scope.goForward();
|
||||||
|
|
||||||
|
expect(verifyRecoveryTokenStub.calledOnce).to.be.true;
|
||||||
|
expect(scope.step).to.equal(2);
|
||||||
|
verifyRecoveryTokenStub.restore();
|
||||||
|
});
|
||||||
|
it('should work in step 2', function() {
|
||||||
|
var decryptAndStorePrivateKeyLocallyStub = sinon.stub(scope, 'decryptAndStorePrivateKeyLocally');
|
||||||
|
decryptAndStorePrivateKeyLocallyStub.returns();
|
||||||
|
scope.step = 2;
|
||||||
|
|
||||||
|
scope.goForward();
|
||||||
|
|
||||||
|
expect(decryptAndStorePrivateKeyLocallyStub.calledOnce).to.be.true;
|
||||||
|
decryptAndStorePrivateKeyLocallyStub.restore();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('goTo', function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
mocks.inject(function($controller, $rootScope, $location) {
|
||||||
|
location = $location;
|
||||||
|
sinon.stub(location, 'path', function(path) {
|
||||||
|
expect(path).to.equal('/desktop');
|
||||||
|
done();
|
||||||
|
});
|
||||||
scope = $rootScope.$new();
|
scope = $rootScope.$new();
|
||||||
scope.state = {};
|
scope.state = {};
|
||||||
ctrl = $controller(LoginPrivateKeyDownloadCtrl, {
|
ctrl = $controller(LoginPrivateKeyDownloadCtrl, {
|
||||||
@ -41,224 +252,9 @@ define(function(require) {
|
|||||||
$scope: scope,
|
$scope: scope,
|
||||||
$routeParams: {}
|
$routeParams: {}
|
||||||
});
|
});
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
afterEach(function() {
|
|
||||||
// restore the app controller module
|
|
||||||
appController._emailDao = origEmailDao;
|
|
||||||
appController._keychain = origKeychain;
|
|
||||||
appController._auth = origAuth;
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('initialization', function() {
|
|
||||||
it('should work', function() {
|
|
||||||
expect(scope.step).to.equal(1);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('verifyRecoveryToken', function() {
|
|
||||||
var testKeypair = {
|
|
||||||
publicKey: {
|
|
||||||
_id: 'id'
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
it('should fail for empty recovery token', function(done) {
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.recoveryToken = undefined;
|
|
||||||
scope.verifyRecoveryToken();
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should fail in keychain.getUserKeyPair', function(done) {
|
scope.goTo('/desktop');
|
||||||
keychainMock.getUserKeyPair.yields(42);
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.recoveryToken = 'token';
|
|
||||||
scope.verifyRecoveryToken();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail in keychain.downloadPrivateKey', function(done) {
|
|
||||||
keychainMock.getUserKeyPair.yields(null, testKeypair);
|
|
||||||
keychainMock.downloadPrivateKey.yields(42);
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(keychainMock.getUserKeyPair.calledOnce).to.be.true;
|
|
||||||
expect(keychainMock.downloadPrivateKey.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.recoveryToken = 'token';
|
|
||||||
scope.verifyRecoveryToken();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
keychainMock.getUserKeyPair.yields(null, testKeypair);
|
|
||||||
keychainMock.downloadPrivateKey.yields(null, 'encryptedPrivateKey');
|
|
||||||
|
|
||||||
scope.recoveryToken = 'token';
|
|
||||||
scope.verifyRecoveryToken(function() {
|
|
||||||
expect(scope.encryptedPrivateKey).to.equal('encryptedPrivateKey');
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('handlePaste', function() {
|
|
||||||
it('should work', function() {
|
|
||||||
scope.handlePaste({
|
|
||||||
clipboardData: {
|
|
||||||
getData: function(val) {
|
|
||||||
expect(val).to.equal('text/plain');
|
|
||||||
return '1qaz-2wsx-3edc-4rfv-5tgb-6yhn';
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
expect(scope.code0).to.equal('1qaz');
|
|
||||||
expect(scope.code1).to.equal('2wsx');
|
|
||||||
expect(scope.code2).to.equal('3edc');
|
|
||||||
expect(scope.code3).to.equal('4rfv');
|
|
||||||
expect(scope.code4).to.equal('5tgb');
|
|
||||||
expect(scope.code5).to.equal('6yhn');
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('decryptAndStorePrivateKeyLocally', function() {
|
|
||||||
beforeEach(function() {
|
|
||||||
scope.code0 = '0';
|
|
||||||
scope.code1 = '1';
|
|
||||||
scope.code2 = '2';
|
|
||||||
scope.code3 = '3';
|
|
||||||
scope.code4 = '4';
|
|
||||||
scope.code5 = '5';
|
|
||||||
|
|
||||||
scope.encryptedPrivateKey = {
|
|
||||||
encryptedPrivateKey: 'encryptedPrivateKey'
|
|
||||||
};
|
|
||||||
scope.cachedKeypair = {
|
|
||||||
publicKey: {
|
|
||||||
_id: 'keyId'
|
|
||||||
}
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail on empty code', function(done) {
|
|
||||||
scope.code0 = '';
|
|
||||||
scope.code1 = '';
|
|
||||||
scope.code2 = '';
|
|
||||||
scope.code3 = '';
|
|
||||||
scope.code4 = '';
|
|
||||||
scope.code5 = '';
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.decryptAndStorePrivateKeyLocally();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail on decryptAndStorePrivateKeyLocally', function(done) {
|
|
||||||
keychainMock.decryptAndStorePrivateKeyLocally.yields(42);
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(keychainMock.decryptAndStorePrivateKeyLocally.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.decryptAndStorePrivateKeyLocally();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should goto /login-existing on emailDao.unlock fail', function(done) {
|
|
||||||
keychainMock.decryptAndStorePrivateKeyLocally.yields(null, {
|
|
||||||
encryptedKey: 'keyArmored'
|
|
||||||
});
|
|
||||||
emailDaoMock.unlock.yields(42);
|
|
||||||
|
|
||||||
scope.goTo = function(location) {
|
|
||||||
expect(location).to.equal('/login-existing');
|
|
||||||
expect(keychainMock.decryptAndStorePrivateKeyLocally.calledOnce).to.be.true;
|
|
||||||
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.decryptAndStorePrivateKeyLocally();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should goto /desktop on emailDao.unlock success', function(done) {
|
|
||||||
keychainMock.decryptAndStorePrivateKeyLocally.yields(null, {
|
|
||||||
encryptedKey: 'keyArmored'
|
|
||||||
});
|
|
||||||
emailDaoMock.unlock.yields();
|
|
||||||
authMock.storeCredentials.yields();
|
|
||||||
|
|
||||||
scope.goTo = function(location) {
|
|
||||||
expect(location).to.equal('/desktop');
|
|
||||||
expect(keychainMock.decryptAndStorePrivateKeyLocally.calledOnce).to.be.true;
|
|
||||||
expect(emailDaoMock.unlock.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.decryptAndStorePrivateKeyLocally();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('goForward', function() {
|
|
||||||
it('should work in step 1', function() {
|
|
||||||
var verifyRecoveryTokenStub = sinon.stub(scope, 'verifyRecoveryToken');
|
|
||||||
verifyRecoveryTokenStub.yields();
|
|
||||||
scope.step = 1;
|
|
||||||
|
|
||||||
scope.goForward();
|
|
||||||
|
|
||||||
expect(verifyRecoveryTokenStub.calledOnce).to.be.true;
|
|
||||||
expect(scope.step).to.equal(2);
|
|
||||||
verifyRecoveryTokenStub.restore();
|
|
||||||
});
|
|
||||||
it('should work in step 2', function() {
|
|
||||||
var decryptAndStorePrivateKeyLocallyStub = sinon.stub(scope, 'decryptAndStorePrivateKeyLocally');
|
|
||||||
decryptAndStorePrivateKeyLocallyStub.returns();
|
|
||||||
scope.step = 2;
|
|
||||||
|
|
||||||
scope.goForward();
|
|
||||||
|
|
||||||
expect(decryptAndStorePrivateKeyLocallyStub.calledOnce).to.be.true;
|
|
||||||
decryptAndStorePrivateKeyLocallyStub.restore();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('goTo', function() {
|
|
||||||
it('should work', function(done) {
|
|
||||||
mocks.inject(function($controller, $rootScope, $location) {
|
|
||||||
location = $location;
|
|
||||||
sinon.stub(location, 'path', function(path) {
|
|
||||||
expect(path).to.equal('/desktop');
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
scope = $rootScope.$new();
|
|
||||||
scope.state = {};
|
|
||||||
ctrl = $controller(LoginPrivateKeyDownloadCtrl, {
|
|
||||||
$location: location,
|
|
||||||
$scope: scope,
|
|
||||||
$routeParams: {}
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
scope.goTo('/desktop');
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
@ -1,101 +1,97 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
Auth = require('../../src/js/bo/auth'),
|
||||||
mocks = require('angularMocks'),
|
ConnectionDoctor = require('../../src/js/util/connection-doctor'),
|
||||||
Auth = require('js/bo/auth'),
|
SetCredentialsCtrl = require('../../src/js/controller/login-set-credentials'),
|
||||||
ConnectionDoctor = require('js/util/connection-doctor'),
|
appController = require('../../src/js/app-controller');
|
||||||
SetCredentialsCtrl = require('js/controller/login-set-credentials'),
|
|
||||||
appController = require('js/app-controller');
|
|
||||||
|
|
||||||
describe('Login (Set Credentials) Controller unit test', function() {
|
describe('Login (Set Credentials) Controller unit test', function() {
|
||||||
// Angular parameters
|
// Angular parameters
|
||||||
var scope, location, provider;
|
var scope, location, provider;
|
||||||
|
|
||||||
// Stubs
|
// Stubs
|
||||||
var auth, origAuth, doctor, origDoctor;
|
var auth, origAuth, doctor, origDoctor;
|
||||||
|
|
||||||
// SUT
|
// SUT
|
||||||
var setCredentialsCtrl;
|
var setCredentialsCtrl;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
// remeber pre-test state to restore later
|
// remeber pre-test state to restore later
|
||||||
origAuth = appController._auth;
|
origAuth = appController._auth;
|
||||||
origDoctor = appController._doctor;
|
origDoctor = appController._doctor;
|
||||||
auth = appController._auth = sinon.createStubInstance(Auth);
|
auth = appController._auth = sinon.createStubInstance(Auth);
|
||||||
doctor = appController._doctor = sinon.createStubInstance(ConnectionDoctor);
|
doctor = appController._doctor = sinon.createStubInstance(ConnectionDoctor);
|
||||||
|
|
||||||
// setup the controller
|
// setup the controller
|
||||||
angular.module('setcredentialstest', []);
|
angular.module('setcredentialstest', []);
|
||||||
mocks.module('setcredentialstest');
|
mocks.module('setcredentialstest');
|
||||||
mocks.inject(function($rootScope, $controller, $location) {
|
mocks.inject(function($rootScope, $controller, $location) {
|
||||||
scope = $rootScope.$new();
|
scope = $rootScope.$new();
|
||||||
location = $location;
|
location = $location;
|
||||||
location.search({
|
location.search({
|
||||||
provider: provider
|
provider: provider
|
||||||
});
|
|
||||||
|
|
||||||
scope.state = {};
|
|
||||||
setCredentialsCtrl = $controller(SetCredentialsCtrl, {
|
|
||||||
$scope: scope,
|
|
||||||
$routeParams: {}
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
|
||||||
|
|
||||||
afterEach(function() {
|
scope.state = {};
|
||||||
// restore pre-test state
|
setCredentialsCtrl = $controller(SetCredentialsCtrl, {
|
||||||
appController._auth = origAuth;
|
$scope: scope,
|
||||||
appController._doctor = origDoctor;
|
$routeParams: {}
|
||||||
});
|
|
||||||
|
|
||||||
describe('set credentials', function() {
|
|
||||||
it('should work', function() {
|
|
||||||
scope.emailAddress = 'emailemailemailemail';
|
|
||||||
scope.password = 'passwdpasswdpasswdpasswd';
|
|
||||||
scope.smtpHost = 'hosthosthost';
|
|
||||||
scope.smtpPort = 1337;
|
|
||||||
scope.smtpEncryption = '1'; // STARTTLS
|
|
||||||
scope.imapHost = 'hosthosthost';
|
|
||||||
scope.imapPort = 1337;
|
|
||||||
scope.imapEncryption = '2'; // TLS
|
|
||||||
scope.realname = 'peter pan';
|
|
||||||
|
|
||||||
var expectedCredentials = {
|
|
||||||
provider: provider,
|
|
||||||
emailAddress: scope.emailAddress,
|
|
||||||
username: scope.username || scope.emailAddress,
|
|
||||||
realname: scope.realname,
|
|
||||||
password: scope.password,
|
|
||||||
xoauth2: undefined,
|
|
||||||
imap: {
|
|
||||||
host: scope.imapHost.toLowerCase(),
|
|
||||||
port: scope.imapPort,
|
|
||||||
secure: true,
|
|
||||||
ignoreTLS: false,
|
|
||||||
ca: undefined,
|
|
||||||
pinned: false
|
|
||||||
},
|
|
||||||
smtp: {
|
|
||||||
host: scope.smtpHost.toLowerCase(),
|
|
||||||
port: scope.smtpPort,
|
|
||||||
secure: false,
|
|
||||||
ignoreTLS: false,
|
|
||||||
ca: undefined,
|
|
||||||
pinned: false
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
doctor.check.yields(); // synchronous yields!
|
|
||||||
|
|
||||||
scope.test();
|
|
||||||
|
|
||||||
expect(doctor.check.calledOnce).to.be.true;
|
|
||||||
expect(doctor.configure.calledOnce).to.be.true;
|
|
||||||
expect(doctor.configure.calledWith(expectedCredentials)).to.be.true;
|
|
||||||
expect(auth.setCredentials.calledOnce).to.be.true;
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
// restore pre-test state
|
||||||
|
appController._auth = origAuth;
|
||||||
|
appController._doctor = origDoctor;
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('set credentials', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
scope.emailAddress = 'emailemailemailemail';
|
||||||
|
scope.password = 'passwdpasswdpasswdpasswd';
|
||||||
|
scope.smtpHost = 'hosthosthost';
|
||||||
|
scope.smtpPort = 1337;
|
||||||
|
scope.smtpEncryption = '1'; // STARTTLS
|
||||||
|
scope.imapHost = 'hosthosthost';
|
||||||
|
scope.imapPort = 1337;
|
||||||
|
scope.imapEncryption = '2'; // TLS
|
||||||
|
scope.realname = 'peter pan';
|
||||||
|
|
||||||
|
var expectedCredentials = {
|
||||||
|
provider: provider,
|
||||||
|
emailAddress: scope.emailAddress,
|
||||||
|
username: scope.username || scope.emailAddress,
|
||||||
|
realname: scope.realname,
|
||||||
|
password: scope.password,
|
||||||
|
xoauth2: undefined,
|
||||||
|
imap: {
|
||||||
|
host: scope.imapHost.toLowerCase(),
|
||||||
|
port: scope.imapPort,
|
||||||
|
secure: true,
|
||||||
|
ignoreTLS: false,
|
||||||
|
ca: undefined,
|
||||||
|
pinned: false
|
||||||
|
},
|
||||||
|
smtp: {
|
||||||
|
host: scope.smtpHost.toLowerCase(),
|
||||||
|
port: scope.smtpPort,
|
||||||
|
secure: false,
|
||||||
|
ignoreTLS: false,
|
||||||
|
ca: undefined,
|
||||||
|
pinned: false
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
doctor.check.yields(); // synchronous yields!
|
||||||
|
|
||||||
|
scope.test();
|
||||||
|
|
||||||
|
expect(doctor.check.calledOnce).to.be.true;
|
||||||
|
expect(doctor.configure.calledOnce).to.be.true;
|
||||||
|
expect(doctor.configure.calledWith(expectedCredentials)).to.be.true;
|
||||||
|
expect(auth.setCredentials.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
@ -1,451 +1,447 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
MailListCtrl = require('../../src/js/controller/mail-list'),
|
||||||
mocks = require('angularMocks'),
|
EmailDAO = require('../../src/js/dao/email-dao'),
|
||||||
MailListCtrl = require('js/controller/mail-list'),
|
DeviceStorageDAO = require('../../src/js/dao/devicestorage-dao'),
|
||||||
EmailDAO = require('js/dao/email-dao'),
|
KeychainDAO = require('../../src/js/dao/keychain-dao'),
|
||||||
DeviceStorageDAO = require('js/dao/devicestorage-dao'),
|
appController = require('../../src/js/app-controller'),
|
||||||
KeychainDAO = require('js/dao/keychain-dao'),
|
notification = require('../../src/js/util/notification');
|
||||||
appController = require('js/app-controller'),
|
|
||||||
notification = require('js/util/notification');
|
|
||||||
|
|
||||||
chai.Assertion.includeStack = true;
|
chai.Assertion.includeStack = true;
|
||||||
|
|
||||||
describe('Mail List controller unit test', function() {
|
describe('Mail List controller unit test', function() {
|
||||||
var scope, ctrl, origEmailDao, emailDaoMock, keychainMock, deviceStorageMock,
|
var scope, ctrl, origEmailDao, emailDaoMock, keychainMock, deviceStorageMock,
|
||||||
emailAddress, emails,
|
emailAddress, emails,
|
||||||
hasChrome, hasSocket, hasRuntime, hasIdentity;
|
hasChrome, hasSocket, hasRuntime, hasIdentity;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
hasChrome = !!window.chrome;
|
hasChrome = !!window.chrome;
|
||||||
hasSocket = !!window.chrome.socket;
|
hasSocket = !!window.chrome.socket;
|
||||||
hasIdentity = !!window.chrome.identity;
|
hasIdentity = !!window.chrome.identity;
|
||||||
if (!hasChrome) {
|
if (!hasChrome) {
|
||||||
window.chrome = {};
|
window.chrome = {};
|
||||||
}
|
}
|
||||||
if (!hasSocket) {
|
if (!hasSocket) {
|
||||||
window.chrome.socket = {};
|
window.chrome.socket = {};
|
||||||
}
|
}
|
||||||
if (!hasRuntime) {
|
if (!hasRuntime) {
|
||||||
window.chrome.runtime = {
|
window.chrome.runtime = {
|
||||||
getURL: function() {}
|
getURL: function() {}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
if (!hasIdentity) {
|
if (!hasIdentity) {
|
||||||
window.chrome.identity = {};
|
window.chrome.identity = {};
|
||||||
}
|
}
|
||||||
|
|
||||||
emails = [{
|
emails = [{
|
||||||
unread: true
|
unread: true
|
||||||
}, {
|
}, {
|
||||||
unread: true
|
unread: true
|
||||||
}, {
|
}, {
|
||||||
unread: true
|
unread: true
|
||||||
}];
|
}];
|
||||||
appController._outboxBo = {
|
appController._outboxBo = {
|
||||||
pendingEmails: emails
|
pendingEmails: emails
|
||||||
|
};
|
||||||
|
|
||||||
|
origEmailDao = appController._emailDao;
|
||||||
|
emailDaoMock = sinon.createStubInstance(EmailDAO);
|
||||||
|
appController._emailDao = emailDaoMock;
|
||||||
|
emailAddress = 'fred@foo.com';
|
||||||
|
emailDaoMock._account = {
|
||||||
|
emailAddress: emailAddress,
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
keychainMock = sinon.createStubInstance(KeychainDAO);
|
||||||
|
appController._keychain = keychainMock;
|
||||||
|
|
||||||
|
deviceStorageMock = sinon.createStubInstance(DeviceStorageDAO);
|
||||||
|
emailDaoMock._devicestorage = deviceStorageMock;
|
||||||
|
|
||||||
|
angular.module('maillisttest', []);
|
||||||
|
mocks.module('maillisttest');
|
||||||
|
mocks.inject(function($rootScope, $controller) {
|
||||||
|
scope = $rootScope.$new();
|
||||||
|
scope.state = {
|
||||||
|
read: {
|
||||||
|
toggle: function() {}
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
origEmailDao = appController._emailDao;
|
scope.loadVisibleBodies = function() {};
|
||||||
emailDaoMock = sinon.createStubInstance(EmailDAO);
|
ctrl = $controller(MailListCtrl, {
|
||||||
appController._emailDao = emailDaoMock;
|
$scope: scope,
|
||||||
emailAddress = 'fred@foo.com';
|
$routeParams: {}
|
||||||
emailDaoMock._account = {
|
|
||||||
emailAddress: emailAddress,
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
keychainMock = sinon.createStubInstance(KeychainDAO);
|
|
||||||
appController._keychain = keychainMock;
|
|
||||||
|
|
||||||
deviceStorageMock = sinon.createStubInstance(DeviceStorageDAO);
|
|
||||||
emailDaoMock._devicestorage = deviceStorageMock;
|
|
||||||
|
|
||||||
angular.module('maillisttest', []);
|
|
||||||
mocks.module('maillisttest');
|
|
||||||
mocks.inject(function($rootScope, $controller) {
|
|
||||||
scope = $rootScope.$new();
|
|
||||||
scope.state = {
|
|
||||||
read: {
|
|
||||||
toggle: function() {}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.loadVisibleBodies = function() {};
|
|
||||||
ctrl = $controller(MailListCtrl, {
|
|
||||||
$scope: scope,
|
|
||||||
$routeParams: {}
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
afterEach(function() {
|
|
||||||
if (!hasSocket) {
|
|
||||||
delete window.chrome.socket;
|
|
||||||
}
|
|
||||||
if (!hasRuntime) {
|
|
||||||
delete window.chrome.runtime;
|
|
||||||
}
|
|
||||||
if (!hasChrome) {
|
|
||||||
delete window.chrome;
|
|
||||||
}
|
|
||||||
if (!hasIdentity) {
|
|
||||||
delete window.chrome.identity;
|
|
||||||
}
|
|
||||||
|
|
||||||
// restore the module
|
|
||||||
appController._emailDao = origEmailDao;
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('displayMore', function() {
|
|
||||||
beforeEach(function() {
|
|
||||||
scope.state.nav = {
|
|
||||||
currentFolder: {
|
|
||||||
messages: ['a', 'b']
|
|
||||||
}
|
|
||||||
};
|
|
||||||
});
|
|
||||||
it('should not do anything when display length equals messages length', function() {
|
|
||||||
scope.displayMessages = ['a', 'b'];
|
|
||||||
|
|
||||||
scope.displayMore();
|
|
||||||
expect(scope.displayMessages.length).to.equal(scope.state.nav.currentFolder.messages.length);
|
|
||||||
});
|
|
||||||
it('should append next message interval', function() {
|
|
||||||
scope.displayMessages = ['a'];
|
|
||||||
|
|
||||||
scope.displayMore();
|
|
||||||
expect(scope.displayMessages.length).to.equal(scope.state.nav.currentFolder.messages.length);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('displaySearchResults', function() {
|
|
||||||
var clock;
|
|
||||||
|
|
||||||
beforeEach(function() {
|
|
||||||
scope.state.nav = {
|
|
||||||
currentFolder: {
|
|
||||||
messages: ['a', 'b']
|
|
||||||
}
|
|
||||||
};
|
|
||||||
scope.watchMessages();
|
|
||||||
scope.watchOnline();
|
|
||||||
clock = sinon.useFakeTimers();
|
|
||||||
});
|
|
||||||
afterEach(function() {
|
|
||||||
clock.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should show initial message on empty', function() {
|
|
||||||
scope.displaySearchResults();
|
|
||||||
expect(scope.searching).to.be.false;
|
|
||||||
expect(scope.lastUpdateLbl).to.equal('Online');
|
|
||||||
expect(scope.displayMessages.length).to.equal(2);
|
|
||||||
});
|
|
||||||
it('should show initial message on empty', function() {
|
|
||||||
var searchStub = sinon.stub(scope, 'search');
|
|
||||||
searchStub.returns(['a']);
|
|
||||||
|
|
||||||
|
|
||||||
scope.displaySearchResults('query');
|
|
||||||
expect(scope.searching).to.be.true;
|
|
||||||
expect(scope.lastUpdateLbl).to.equal('Searching ...');
|
|
||||||
clock.tick(500);
|
|
||||||
|
|
||||||
expect(scope.displayMessages).to.deep.equal(['a']);
|
|
||||||
expect(scope.searching).to.be.false;
|
|
||||||
expect(scope.lastUpdateLbl).to.equal('Matches in this folder');
|
|
||||||
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('search', function() {
|
|
||||||
var message1 = {
|
|
||||||
to: [{
|
|
||||||
name: 'name1',
|
|
||||||
address: 'address1'
|
|
||||||
}],
|
|
||||||
subject: 'subject1',
|
|
||||||
body: 'body1',
|
|
||||||
html: 'html1'
|
|
||||||
},
|
|
||||||
message2 = {
|
|
||||||
to: [{
|
|
||||||
name: 'name2',
|
|
||||||
address: 'address2'
|
|
||||||
}],
|
|
||||||
subject: 'subject2',
|
|
||||||
body: 'body2',
|
|
||||||
html: 'html2'
|
|
||||||
},
|
|
||||||
message3 = {
|
|
||||||
to: [{
|
|
||||||
name: 'name3',
|
|
||||||
address: 'address3'
|
|
||||||
}],
|
|
||||||
subject: 'subject3',
|
|
||||||
body: 'body1',
|
|
||||||
html: 'html1',
|
|
||||||
encrypted: true
|
|
||||||
},
|
|
||||||
message4 = {
|
|
||||||
to: [{
|
|
||||||
name: 'name4',
|
|
||||||
address: 'address4'
|
|
||||||
}],
|
|
||||||
subject: 'subject4',
|
|
||||||
body: 'body1',
|
|
||||||
html: 'html1',
|
|
||||||
encrypted: true,
|
|
||||||
decrypted: true
|
|
||||||
},
|
|
||||||
testMessages = [message1, message2, message3, message4];
|
|
||||||
|
|
||||||
it('return same messages array on empty query string', function() {
|
|
||||||
var result = scope.search(testMessages, '');
|
|
||||||
expect(result).to.equal(testMessages);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('return message1 on matching subject', function() {
|
|
||||||
var result = scope.search(testMessages, 'subject1');
|
|
||||||
expect(result.length).to.equal(1);
|
|
||||||
expect(result[0]).to.equal(message1);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('return message1 on matching name', function() {
|
|
||||||
var result = scope.search(testMessages, 'name1');
|
|
||||||
expect(result.length).to.equal(1);
|
|
||||||
expect(result[0]).to.equal(message1);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('return message1 on matching address', function() {
|
|
||||||
var result = scope.search(testMessages, 'address1');
|
|
||||||
expect(result.length).to.equal(1);
|
|
||||||
expect(result[0]).to.equal(message1);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('return plaintext and decrypted messages on matching body', function() {
|
|
||||||
var result = scope.search(testMessages, 'body1');
|
|
||||||
expect(result.length).to.equal(2);
|
|
||||||
expect(result[0]).to.equal(message1);
|
|
||||||
expect(result[1]).to.equal(message4);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('return plaintext and decrypted messages on matching html', function() {
|
|
||||||
var result = scope.search(testMessages, 'html1');
|
|
||||||
expect(result.length).to.equal(2);
|
|
||||||
expect(result[0]).to.equal(message1);
|
|
||||||
expect(result[1]).to.equal(message4);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('scope variables', function() {
|
|
||||||
it('should be set correctly', function() {
|
|
||||||
expect(scope.select).to.exist;
|
|
||||||
expect(scope.remove).to.exist;
|
|
||||||
expect(scope.state.mailList).to.exist;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('push notification', function() {
|
|
||||||
beforeEach(function() {
|
|
||||||
scope._stopWatchTask();
|
|
||||||
});
|
|
||||||
|
|
||||||
afterEach(function() {
|
|
||||||
notification.create.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should succeed for single mail', function(done) {
|
|
||||||
var mail = {
|
|
||||||
uid: 123,
|
|
||||||
from: [{
|
|
||||||
address: 'asd'
|
|
||||||
}],
|
|
||||||
subject: 'this is the subject!',
|
|
||||||
unread: true
|
|
||||||
};
|
|
||||||
|
|
||||||
sinon.stub(notification, 'create', function(opts) {
|
|
||||||
expect(opts.title).to.equal(mail.from[0].address);
|
|
||||||
expect(opts.message).to.equal(mail.subject);
|
|
||||||
|
|
||||||
opts.onClick();
|
|
||||||
expect(scope.state.mailList.selected).to.equal(mail);
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
|
|
||||||
scope.state.nav = {
|
|
||||||
currentFolder: {
|
|
||||||
type: 'asd',
|
|
||||||
messages: [mail]
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
emailDaoMock.onIncomingMessage([mail]);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should succeed for multiple mails', function(done) {
|
|
||||||
var mails = [{
|
|
||||||
uid: 1,
|
|
||||||
from: [{
|
|
||||||
address: 'asd'
|
|
||||||
}],
|
|
||||||
subject: 'this is the subject!',
|
|
||||||
unread: true
|
|
||||||
}, {
|
|
||||||
uid: 2,
|
|
||||||
from: [{
|
|
||||||
address: 'qwe'
|
|
||||||
}],
|
|
||||||
subject: 'this is the other subject!',
|
|
||||||
unread: true
|
|
||||||
}, {
|
|
||||||
uid: 3,
|
|
||||||
from: [{
|
|
||||||
address: 'qwe'
|
|
||||||
}],
|
|
||||||
subject: 'this is the other subject!',
|
|
||||||
unread: false
|
|
||||||
}];
|
|
||||||
|
|
||||||
sinon.stub(notification, 'create', function(opts) {
|
|
||||||
expect(opts.title).to.equal('2 new messages');
|
|
||||||
expect(opts.message).to.equal(mails[0].subject + '\n' + mails[1].subject);
|
|
||||||
|
|
||||||
opts.onClick();
|
|
||||||
expect(scope.state.mailList.selected).to.equal(mails[0]);
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
|
|
||||||
scope.state.nav = {
|
|
||||||
currentFolder: {
|
|
||||||
type: 'asd',
|
|
||||||
messages: mails
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
emailDaoMock.onIncomingMessage(mails);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('getBody', function() {
|
|
||||||
it('should get the mail content', function() {
|
|
||||||
scope.state.nav = {
|
|
||||||
currentFolder: {
|
|
||||||
type: 'asd',
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.getBody();
|
|
||||||
expect(emailDaoMock.getBody.calledOnce).to.be.true;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('select', function() {
|
|
||||||
it('should decrypt, focus mark an unread mail as read', function() {
|
|
||||||
scope.pendingNotifications = ['asd'];
|
|
||||||
sinon.stub(notification, 'close');
|
|
||||||
|
|
||||||
var mail = {
|
|
||||||
from: [{
|
|
||||||
address: 'asd'
|
|
||||||
}],
|
|
||||||
unread: true,
|
|
||||||
};
|
|
||||||
scope.state = {
|
|
||||||
nav: {
|
|
||||||
currentFolder: {
|
|
||||||
type: 'Inbox'
|
|
||||||
}
|
|
||||||
},
|
|
||||||
mailList: {},
|
|
||||||
read: {
|
|
||||||
toggle: function() {}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
keychainMock.refreshKeyForUserId.withArgs(mail.from[0].address).yields();
|
|
||||||
|
|
||||||
scope.select(mail);
|
|
||||||
|
|
||||||
expect(emailDaoMock.decryptBody.calledOnce).to.be.true;
|
|
||||||
expect(keychainMock.refreshKeyForUserId.calledOnce).to.be.true;
|
|
||||||
expect(scope.state.mailList.selected).to.equal(mail);
|
|
||||||
expect(notification.close.calledWith('asd')).to.be.true;
|
|
||||||
expect(notification.close.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
notification.close.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should decrypt and focus a read mail', function() {
|
|
||||||
var mail = {
|
|
||||||
from: [{
|
|
||||||
address: 'asd'
|
|
||||||
}],
|
|
||||||
unread: false
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.state = {
|
|
||||||
mailList: {},
|
|
||||||
read: {
|
|
||||||
toggle: function() {}
|
|
||||||
},
|
|
||||||
nav: {
|
|
||||||
currentFolder: {
|
|
||||||
type: 'asd'
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
keychainMock.refreshKeyForUserId.withArgs(mail.from[0].address).yields();
|
|
||||||
|
|
||||||
scope.select(mail);
|
|
||||||
|
|
||||||
expect(emailDaoMock.decryptBody.calledOnce).to.be.true;
|
|
||||||
expect(keychainMock.refreshKeyForUserId.calledOnce).to.be.true;
|
|
||||||
expect(scope.state.mailList.selected).to.equal(mail);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('remove', function() {
|
|
||||||
it('should not delete without a selected mail', function() {
|
|
||||||
scope.remove();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should delete the selected mail', function() {
|
|
||||||
var uid, mail, currentFolder;
|
|
||||||
|
|
||||||
scope._stopWatchTask();
|
|
||||||
|
|
||||||
scope.account = {};
|
|
||||||
uid = 123;
|
|
||||||
mail = {
|
|
||||||
uid: uid,
|
|
||||||
from: [{
|
|
||||||
address: 'asd'
|
|
||||||
}],
|
|
||||||
subject: '[whiteout] asdasd',
|
|
||||||
unread: true
|
|
||||||
};
|
|
||||||
currentFolder = {
|
|
||||||
type: 'Inbox',
|
|
||||||
path: 'INBOX',
|
|
||||||
messages: [mail]
|
|
||||||
};
|
|
||||||
scope.account.folders = [currentFolder];
|
|
||||||
scope.state.nav = {
|
|
||||||
currentFolder: currentFolder
|
|
||||||
};
|
|
||||||
emailDaoMock.deleteMessage.yields();
|
|
||||||
|
|
||||||
scope.remove(mail);
|
|
||||||
|
|
||||||
expect(emailDaoMock.deleteMessage.calledOnce).to.be.true;
|
|
||||||
expect(scope.state.mailList.selected).to.exist;
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
if (!hasSocket) {
|
||||||
|
delete window.chrome.socket;
|
||||||
|
}
|
||||||
|
if (!hasRuntime) {
|
||||||
|
delete window.chrome.runtime;
|
||||||
|
}
|
||||||
|
if (!hasChrome) {
|
||||||
|
delete window.chrome;
|
||||||
|
}
|
||||||
|
if (!hasIdentity) {
|
||||||
|
delete window.chrome.identity;
|
||||||
|
}
|
||||||
|
|
||||||
|
// restore the module
|
||||||
|
appController._emailDao = origEmailDao;
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('displayMore', function() {
|
||||||
|
beforeEach(function() {
|
||||||
|
scope.state.nav = {
|
||||||
|
currentFolder: {
|
||||||
|
messages: ['a', 'b']
|
||||||
|
}
|
||||||
|
};
|
||||||
|
});
|
||||||
|
it('should not do anything when display length equals messages length', function() {
|
||||||
|
scope.displayMessages = ['a', 'b'];
|
||||||
|
|
||||||
|
scope.displayMore();
|
||||||
|
expect(scope.displayMessages.length).to.equal(scope.state.nav.currentFolder.messages.length);
|
||||||
|
});
|
||||||
|
it('should append next message interval', function() {
|
||||||
|
scope.displayMessages = ['a'];
|
||||||
|
|
||||||
|
scope.displayMore();
|
||||||
|
expect(scope.displayMessages.length).to.equal(scope.state.nav.currentFolder.messages.length);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('displaySearchResults', function() {
|
||||||
|
var clock;
|
||||||
|
|
||||||
|
beforeEach(function() {
|
||||||
|
scope.state.nav = {
|
||||||
|
currentFolder: {
|
||||||
|
messages: ['a', 'b']
|
||||||
|
}
|
||||||
|
};
|
||||||
|
scope.watchMessages();
|
||||||
|
scope.watchOnline();
|
||||||
|
clock = sinon.useFakeTimers();
|
||||||
|
});
|
||||||
|
afterEach(function() {
|
||||||
|
clock.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should show initial message on empty', function() {
|
||||||
|
scope.displaySearchResults();
|
||||||
|
expect(scope.searching).to.be.false;
|
||||||
|
expect(scope.lastUpdateLbl).to.equal('Online');
|
||||||
|
expect(scope.displayMessages.length).to.equal(2);
|
||||||
|
});
|
||||||
|
it('should show initial message on empty', function() {
|
||||||
|
var searchStub = sinon.stub(scope, 'search');
|
||||||
|
searchStub.returns(['a']);
|
||||||
|
|
||||||
|
|
||||||
|
scope.displaySearchResults('query');
|
||||||
|
expect(scope.searching).to.be.true;
|
||||||
|
expect(scope.lastUpdateLbl).to.equal('Searching ...');
|
||||||
|
clock.tick(500);
|
||||||
|
|
||||||
|
expect(scope.displayMessages).to.deep.equal(['a']);
|
||||||
|
expect(scope.searching).to.be.false;
|
||||||
|
expect(scope.lastUpdateLbl).to.equal('Matches in this folder');
|
||||||
|
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('search', function() {
|
||||||
|
var message1 = {
|
||||||
|
to: [{
|
||||||
|
name: 'name1',
|
||||||
|
address: 'address1'
|
||||||
|
}],
|
||||||
|
subject: 'subject1',
|
||||||
|
body: 'body1',
|
||||||
|
html: 'html1'
|
||||||
|
},
|
||||||
|
message2 = {
|
||||||
|
to: [{
|
||||||
|
name: 'name2',
|
||||||
|
address: 'address2'
|
||||||
|
}],
|
||||||
|
subject: 'subject2',
|
||||||
|
body: 'body2',
|
||||||
|
html: 'html2'
|
||||||
|
},
|
||||||
|
message3 = {
|
||||||
|
to: [{
|
||||||
|
name: 'name3',
|
||||||
|
address: 'address3'
|
||||||
|
}],
|
||||||
|
subject: 'subject3',
|
||||||
|
body: 'body1',
|
||||||
|
html: 'html1',
|
||||||
|
encrypted: true
|
||||||
|
},
|
||||||
|
message4 = {
|
||||||
|
to: [{
|
||||||
|
name: 'name4',
|
||||||
|
address: 'address4'
|
||||||
|
}],
|
||||||
|
subject: 'subject4',
|
||||||
|
body: 'body1',
|
||||||
|
html: 'html1',
|
||||||
|
encrypted: true,
|
||||||
|
decrypted: true
|
||||||
|
},
|
||||||
|
testMessages = [message1, message2, message3, message4];
|
||||||
|
|
||||||
|
it('return same messages array on empty query string', function() {
|
||||||
|
var result = scope.search(testMessages, '');
|
||||||
|
expect(result).to.equal(testMessages);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('return message1 on matching subject', function() {
|
||||||
|
var result = scope.search(testMessages, 'subject1');
|
||||||
|
expect(result.length).to.equal(1);
|
||||||
|
expect(result[0]).to.equal(message1);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('return message1 on matching name', function() {
|
||||||
|
var result = scope.search(testMessages, 'name1');
|
||||||
|
expect(result.length).to.equal(1);
|
||||||
|
expect(result[0]).to.equal(message1);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('return message1 on matching address', function() {
|
||||||
|
var result = scope.search(testMessages, 'address1');
|
||||||
|
expect(result.length).to.equal(1);
|
||||||
|
expect(result[0]).to.equal(message1);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('return plaintext and decrypted messages on matching body', function() {
|
||||||
|
var result = scope.search(testMessages, 'body1');
|
||||||
|
expect(result.length).to.equal(2);
|
||||||
|
expect(result[0]).to.equal(message1);
|
||||||
|
expect(result[1]).to.equal(message4);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('return plaintext and decrypted messages on matching html', function() {
|
||||||
|
var result = scope.search(testMessages, 'html1');
|
||||||
|
expect(result.length).to.equal(2);
|
||||||
|
expect(result[0]).to.equal(message1);
|
||||||
|
expect(result[1]).to.equal(message4);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('scope variables', function() {
|
||||||
|
it('should be set correctly', function() {
|
||||||
|
expect(scope.select).to.exist;
|
||||||
|
expect(scope.remove).to.exist;
|
||||||
|
expect(scope.state.mailList).to.exist;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('push notification', function() {
|
||||||
|
beforeEach(function() {
|
||||||
|
scope._stopWatchTask();
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
notification.create.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should succeed for single mail', function(done) {
|
||||||
|
var mail = {
|
||||||
|
uid: 123,
|
||||||
|
from: [{
|
||||||
|
address: 'asd'
|
||||||
|
}],
|
||||||
|
subject: 'this is the subject!',
|
||||||
|
unread: true
|
||||||
|
};
|
||||||
|
|
||||||
|
sinon.stub(notification, 'create', function(opts) {
|
||||||
|
expect(opts.title).to.equal(mail.from[0].address);
|
||||||
|
expect(opts.message).to.equal(mail.subject);
|
||||||
|
|
||||||
|
opts.onClick();
|
||||||
|
expect(scope.state.mailList.selected).to.equal(mail);
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
|
||||||
|
scope.state.nav = {
|
||||||
|
currentFolder: {
|
||||||
|
type: 'asd',
|
||||||
|
messages: [mail]
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
emailDaoMock.onIncomingMessage([mail]);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should succeed for multiple mails', function(done) {
|
||||||
|
var mails = [{
|
||||||
|
uid: 1,
|
||||||
|
from: [{
|
||||||
|
address: 'asd'
|
||||||
|
}],
|
||||||
|
subject: 'this is the subject!',
|
||||||
|
unread: true
|
||||||
|
}, {
|
||||||
|
uid: 2,
|
||||||
|
from: [{
|
||||||
|
address: 'qwe'
|
||||||
|
}],
|
||||||
|
subject: 'this is the other subject!',
|
||||||
|
unread: true
|
||||||
|
}, {
|
||||||
|
uid: 3,
|
||||||
|
from: [{
|
||||||
|
address: 'qwe'
|
||||||
|
}],
|
||||||
|
subject: 'this is the other subject!',
|
||||||
|
unread: false
|
||||||
|
}];
|
||||||
|
|
||||||
|
sinon.stub(notification, 'create', function(opts) {
|
||||||
|
expect(opts.title).to.equal('2 new messages');
|
||||||
|
expect(opts.message).to.equal(mails[0].subject + '\n' + mails[1].subject);
|
||||||
|
|
||||||
|
opts.onClick();
|
||||||
|
expect(scope.state.mailList.selected).to.equal(mails[0]);
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
|
||||||
|
scope.state.nav = {
|
||||||
|
currentFolder: {
|
||||||
|
type: 'asd',
|
||||||
|
messages: mails
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
emailDaoMock.onIncomingMessage(mails);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('getBody', function() {
|
||||||
|
it('should get the mail content', function() {
|
||||||
|
scope.state.nav = {
|
||||||
|
currentFolder: {
|
||||||
|
type: 'asd',
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.getBody();
|
||||||
|
expect(emailDaoMock.getBody.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('select', function() {
|
||||||
|
it('should decrypt, focus mark an unread mail as read', function() {
|
||||||
|
scope.pendingNotifications = ['asd'];
|
||||||
|
sinon.stub(notification, 'close');
|
||||||
|
|
||||||
|
var mail = {
|
||||||
|
from: [{
|
||||||
|
address: 'asd'
|
||||||
|
}],
|
||||||
|
unread: true,
|
||||||
|
};
|
||||||
|
scope.state = {
|
||||||
|
nav: {
|
||||||
|
currentFolder: {
|
||||||
|
type: 'Inbox'
|
||||||
|
}
|
||||||
|
},
|
||||||
|
mailList: {},
|
||||||
|
read: {
|
||||||
|
toggle: function() {}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
keychainMock.refreshKeyForUserId.withArgs(mail.from[0].address).yields();
|
||||||
|
|
||||||
|
scope.select(mail);
|
||||||
|
|
||||||
|
expect(emailDaoMock.decryptBody.calledOnce).to.be.true;
|
||||||
|
expect(keychainMock.refreshKeyForUserId.calledOnce).to.be.true;
|
||||||
|
expect(scope.state.mailList.selected).to.equal(mail);
|
||||||
|
expect(notification.close.calledWith('asd')).to.be.true;
|
||||||
|
expect(notification.close.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
notification.close.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should decrypt and focus a read mail', function() {
|
||||||
|
var mail = {
|
||||||
|
from: [{
|
||||||
|
address: 'asd'
|
||||||
|
}],
|
||||||
|
unread: false
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.state = {
|
||||||
|
mailList: {},
|
||||||
|
read: {
|
||||||
|
toggle: function() {}
|
||||||
|
},
|
||||||
|
nav: {
|
||||||
|
currentFolder: {
|
||||||
|
type: 'asd'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
keychainMock.refreshKeyForUserId.withArgs(mail.from[0].address).yields();
|
||||||
|
|
||||||
|
scope.select(mail);
|
||||||
|
|
||||||
|
expect(emailDaoMock.decryptBody.calledOnce).to.be.true;
|
||||||
|
expect(keychainMock.refreshKeyForUserId.calledOnce).to.be.true;
|
||||||
|
expect(scope.state.mailList.selected).to.equal(mail);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('remove', function() {
|
||||||
|
it('should not delete without a selected mail', function() {
|
||||||
|
scope.remove();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should delete the selected mail', function() {
|
||||||
|
var uid, mail, currentFolder;
|
||||||
|
|
||||||
|
scope._stopWatchTask();
|
||||||
|
|
||||||
|
scope.account = {};
|
||||||
|
uid = 123;
|
||||||
|
mail = {
|
||||||
|
uid: uid,
|
||||||
|
from: [{
|
||||||
|
address: 'asd'
|
||||||
|
}],
|
||||||
|
subject: '[whiteout] asdasd',
|
||||||
|
unread: true
|
||||||
|
};
|
||||||
|
currentFolder = {
|
||||||
|
type: 'Inbox',
|
||||||
|
path: 'INBOX',
|
||||||
|
messages: [mail]
|
||||||
|
};
|
||||||
|
scope.account.folders = [currentFolder];
|
||||||
|
scope.state.nav = {
|
||||||
|
currentFolder: currentFolder
|
||||||
|
};
|
||||||
|
emailDaoMock.deleteMessage.yields();
|
||||||
|
|
||||||
|
scope.remove(mail);
|
||||||
|
|
||||||
|
expect(emailDaoMock.deleteMessage.calledOnce).to.be.true;
|
||||||
|
expect(scope.state.mailList.selected).to.exist;
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
@ -1,113 +0,0 @@
|
|||||||
'use strict';
|
|
||||||
|
|
||||||
// Mozilla bind polyfill because phantomjs is stupid
|
|
||||||
if (!Function.prototype.bind) {
|
|
||||||
Function.prototype.bind = function(oThis) {
|
|
||||||
if (typeof this !== "function") {
|
|
||||||
// closest thing possible to the ECMAScript 5 internal IsCallable function
|
|
||||||
throw new TypeError("Function.prototype.bind - what is trying to be bound is not callable");
|
|
||||||
}
|
|
||||||
|
|
||||||
var aArgs = Array.prototype.slice.call(arguments, 1),
|
|
||||||
fToBind = this,
|
|
||||||
FNOP = function() {},
|
|
||||||
fBound = function() {
|
|
||||||
return fToBind.apply(this instanceof FNOP && oThis ? this : oThis, aArgs.concat(Array.prototype.slice.call(arguments)));
|
|
||||||
};
|
|
||||||
|
|
||||||
FNOP.prototype = this.prototype;
|
|
||||||
fBound.prototype = new FNOP();
|
|
||||||
|
|
||||||
return fBound;
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
// a warm round of applause for phantomjs for missing events
|
|
||||||
(function() {
|
|
||||||
function CustomEvent(event, params) {
|
|
||||||
params = params || {
|
|
||||||
bubbles: false,
|
|
||||||
cancelable: false,
|
|
||||||
detail: undefined
|
|
||||||
};
|
|
||||||
var evt = document.createEvent('CustomEvent');
|
|
||||||
evt.initCustomEvent(event, params.bubbles, params.cancelable, params.detail);
|
|
||||||
return evt;
|
|
||||||
}
|
|
||||||
|
|
||||||
CustomEvent.prototype = window.Event.prototype;
|
|
||||||
|
|
||||||
window.CustomEvent = CustomEvent;
|
|
||||||
})();
|
|
||||||
|
|
||||||
require(['../../src/require-config'], function() {
|
|
||||||
require.config({
|
|
||||||
baseUrl: '../../src/lib',
|
|
||||||
paths: {
|
|
||||||
angularMocks: '../../test/lib/angular-mocks'
|
|
||||||
},
|
|
||||||
shim: {
|
|
||||||
angularMocks: {
|
|
||||||
exports: 'angular.mock',
|
|
||||||
deps: ['angular']
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
|
|
||||||
// Start the main app logic.
|
|
||||||
require(['js/app-config', 'axe'], function(app, axe) {
|
|
||||||
app.config.workerPath = '../../src/js';
|
|
||||||
|
|
||||||
// turn off logging in the test
|
|
||||||
axe.removeAppender(axe.defaultAppender);
|
|
||||||
|
|
||||||
startTests();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
function startTests() {
|
|
||||||
mocha.setup('bdd');
|
|
||||||
|
|
||||||
require(
|
|
||||||
[
|
|
||||||
'test/unit/oauth-test',
|
|
||||||
'test/unit/auth-test',
|
|
||||||
'test/unit/email-dao-test',
|
|
||||||
'test/unit/app-controller-test',
|
|
||||||
'test/unit/pgp-test',
|
|
||||||
'test/unit/crypto-test',
|
|
||||||
'test/unit/backbutton-handler-test',
|
|
||||||
'test/unit/rest-dao-test',
|
|
||||||
'test/unit/admin-dao-test',
|
|
||||||
'test/unit/publickey-dao-test',
|
|
||||||
'test/unit/privatekey-dao-test',
|
|
||||||
'test/unit/lawnchair-dao-test',
|
|
||||||
'test/unit/keychain-dao-test',
|
|
||||||
'test/unit/devicestorage-dao-test',
|
|
||||||
'test/unit/dialog-ctrl-test',
|
|
||||||
'test/unit/add-account-ctrl-test',
|
|
||||||
'test/unit/account-ctrl-test',
|
|
||||||
'test/unit/set-passphrase-ctrl-test',
|
|
||||||
'test/unit/contacts-ctrl-test',
|
|
||||||
'test/unit/login-existing-ctrl-test',
|
|
||||||
'test/unit/login-initial-ctrl-test',
|
|
||||||
'test/unit/login-new-device-ctrl-test',
|
|
||||||
'test/unit/login-privatekey-download-ctrl-test',
|
|
||||||
'test/unit/login-set-credentials-ctrl-test',
|
|
||||||
'test/unit/privatekey-upload-ctrl-test',
|
|
||||||
'test/unit/login-ctrl-test',
|
|
||||||
'test/unit/read-ctrl-test',
|
|
||||||
'test/unit/navigation-ctrl-test',
|
|
||||||
'test/unit/mail-list-ctrl-test',
|
|
||||||
'test/unit/write-ctrl-test',
|
|
||||||
'test/unit/outbox-bo-test',
|
|
||||||
'test/unit/invitation-dao-test',
|
|
||||||
'test/unit/update-handler-test',
|
|
||||||
'test/unit/connection-doctor-test'
|
|
||||||
], function() {
|
|
||||||
//Tests loaded, run tests
|
|
||||||
mocha.run();
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
@ -1,101 +1,97 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
NavigationCtrl = require('../../src/js/controller/navigation'),
|
||||||
mocks = require('angularMocks'),
|
EmailDAO = require('../../src/js/dao/email-dao'),
|
||||||
NavigationCtrl = require('js/controller/navigation'),
|
OutboxBO = require('../../src/js/bo/outbox'),
|
||||||
EmailDAO = require('js/dao/email-dao'),
|
appController = require('../../src/js/app-controller');
|
||||||
OutboxBO = require('js/bo/outbox'),
|
|
||||||
appController = require('js/app-controller');
|
|
||||||
|
|
||||||
describe('Navigation Controller unit test', function() {
|
describe('Navigation Controller unit test', function() {
|
||||||
var scope, ctrl, origEmailDao, emailDaoMock, outboxBoMock, outboxFolder, onConnectStub;
|
var scope, ctrl, origEmailDao, emailDaoMock, outboxBoMock, outboxFolder, onConnectStub;
|
||||||
|
|
||||||
beforeEach(function(done) {
|
beforeEach(function(done) {
|
||||||
// remember original module to restore later
|
// remember original module to restore later
|
||||||
origEmailDao = appController._emailDao;
|
origEmailDao = appController._emailDao;
|
||||||
emailDaoMock = sinon.createStubInstance(EmailDAO);
|
emailDaoMock = sinon.createStubInstance(EmailDAO);
|
||||||
emailDaoMock._account = {
|
emailDaoMock._account = {
|
||||||
folders: [{
|
folders: [{
|
||||||
type: 'Inbox',
|
type: 'Inbox',
|
||||||
count: 2,
|
count: 2,
|
||||||
path: 'INBOX'
|
path: 'INBOX'
|
||||||
}, {
|
}, {
|
||||||
type: 'Outbox',
|
type: 'Outbox',
|
||||||
count: 0,
|
count: 0,
|
||||||
path: 'OUTBOX'
|
path: 'OUTBOX'
|
||||||
}]
|
}]
|
||||||
};
|
};
|
||||||
outboxFolder = emailDaoMock._account.folders[1];
|
outboxFolder = emailDaoMock._account.folders[1];
|
||||||
appController._emailDao = emailDaoMock;
|
appController._emailDao = emailDaoMock;
|
||||||
outboxBoMock = sinon.createStubInstance(OutboxBO);
|
outboxBoMock = sinon.createStubInstance(OutboxBO);
|
||||||
appController._outboxBo = outboxBoMock;
|
appController._outboxBo = outboxBoMock;
|
||||||
outboxBoMock.startChecking.returns();
|
outboxBoMock.startChecking.returns();
|
||||||
onConnectStub = sinon.stub(appController, 'onConnect');
|
onConnectStub = sinon.stub(appController, 'onConnect');
|
||||||
onConnectStub.yields();
|
onConnectStub.yields();
|
||||||
|
|
||||||
angular.module('navigationtest', []);
|
angular.module('navigationtest', []);
|
||||||
mocks.module('navigationtest');
|
mocks.module('navigationtest');
|
||||||
mocks.inject(function($rootScope, $controller) {
|
mocks.inject(function($rootScope, $controller) {
|
||||||
scope = $rootScope.$new();
|
scope = $rootScope.$new();
|
||||||
scope.state = {};
|
scope.state = {};
|
||||||
ctrl = $controller(NavigationCtrl, {
|
ctrl = $controller(NavigationCtrl, {
|
||||||
$scope: scope,
|
$scope: scope,
|
||||||
$routeParams: {}
|
$routeParams: {}
|
||||||
});
|
|
||||||
done();
|
|
||||||
});
|
});
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
afterEach(function() {
|
||||||
// restore the module
|
// restore the module
|
||||||
appController._emailDao = origEmailDao;
|
appController._emailDao = origEmailDao;
|
||||||
onConnectStub.restore();
|
onConnectStub.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('initial state', function() {
|
||||||
|
it('should be well defined', function() {
|
||||||
|
expect(scope.state).to.exist;
|
||||||
|
expect(scope.state.lightbox).to.be.undefined;
|
||||||
|
expect(scope.account.folders).to.not.be.empty;
|
||||||
|
expect(scope.openFolder).to.exist;
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe('initial state', function() {
|
describe('open/close nav view', function() {
|
||||||
it('should be well defined', function() {
|
it('should open/close', function() {
|
||||||
expect(scope.state).to.exist;
|
expect(scope.state.nav.open).to.be.false;
|
||||||
expect(scope.state.lightbox).to.be.undefined;
|
scope.state.nav.toggle(true);
|
||||||
expect(scope.account.folders).to.not.be.empty;
|
expect(scope.state.nav.open).to.be.true;
|
||||||
expect(scope.openFolder).to.exist;
|
scope.state.nav.toggle(false);
|
||||||
});
|
expect(scope.state.nav.open).to.be.false;
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe('open/close nav view', function() {
|
describe('open folder', function() {
|
||||||
it('should open/close', function() {
|
it('should work', function() {
|
||||||
expect(scope.state.nav.open).to.be.false;
|
scope.state.nav.open = true;
|
||||||
scope.state.nav.toggle(true);
|
|
||||||
expect(scope.state.nav.open).to.be.true;
|
scope.openFolder('asd');
|
||||||
scope.state.nav.toggle(false);
|
expect(scope.state.nav.currentFolder).to.equal('asd');
|
||||||
expect(scope.state.nav.open).to.be.false;
|
expect(scope.state.nav.open).to.be.false;
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe('open folder', function() {
|
describe('empty outbox', function() {
|
||||||
it('should work', function() {
|
it('should work', function() {
|
||||||
scope.state.nav.open = true;
|
var callback;
|
||||||
|
|
||||||
scope.openFolder('asd');
|
expect(outboxBoMock.startChecking.callCount).to.equal(1);
|
||||||
expect(scope.state.nav.currentFolder).to.equal('asd');
|
|
||||||
expect(scope.state.nav.open).to.be.false;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('empty outbox', function() {
|
outboxBoMock.startChecking.calledWith(sinon.match(function(cb) {
|
||||||
it('should work', function() {
|
callback = cb;
|
||||||
var callback;
|
}));
|
||||||
|
|
||||||
expect(outboxBoMock.startChecking.callCount).to.equal(1);
|
callback(null, 5);
|
||||||
|
expect(outboxFolder.count).to.equal(5);
|
||||||
outboxBoMock.startChecking.calledWith(sinon.match(function(cb) {
|
|
||||||
callback = cb;
|
|
||||||
}));
|
|
||||||
|
|
||||||
callback(null, 5);
|
|
||||||
expect(outboxFolder.count).to.equal(5);
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
@ -1,201 +1,198 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var OAuth = require('js/util/oauth'),
|
var OAuth = require('../../src/js/util/oauth'),
|
||||||
RestDAO = require('js/dao/rest-dao'),
|
RestDAO = require('../../src/js/dao/rest-dao');
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
describe('OAuth unit tests', function() {
|
describe('OAuth unit tests', function() {
|
||||||
var oauth, googleApiStub, identityStub, getPlatformInfoStub, removeCachedStub,
|
var oauth, googleApiStub, identityStub, getPlatformInfoStub, removeCachedStub,
|
||||||
testEmail = 'test@example.com';
|
testEmail = 'test@example.com';
|
||||||
|
|
||||||
|
beforeEach(function() {
|
||||||
|
googleApiStub = sinon.createStubInstance(RestDAO);
|
||||||
|
oauth = new OAuth(googleApiStub);
|
||||||
|
|
||||||
|
window.chrome = window.chrome || {};
|
||||||
|
|
||||||
|
window.chrome.identity = window.chrome.identity || {};
|
||||||
|
if (typeof window.chrome.identity.getAuthToken !== 'function') {
|
||||||
|
window.chrome.identity.getAuthToken = function() {};
|
||||||
|
}
|
||||||
|
identityStub = sinon.stub(window.chrome.identity, 'getAuthToken');
|
||||||
|
|
||||||
|
if (typeof window.chrome.identity.removeCachedAuthToken !== 'function') {
|
||||||
|
window.chrome.identity.removeCachedAuthToken = function() {};
|
||||||
|
}
|
||||||
|
removeCachedStub = sinon.stub(window.chrome.identity, 'removeCachedAuthToken');
|
||||||
|
|
||||||
|
window.chrome.runtime = window.chrome.runtime || {};
|
||||||
|
if (typeof window.chrome.runtime.getPlatformInfo !== 'function') {
|
||||||
|
window.chrome.runtime.getPlatformInfo = function() {};
|
||||||
|
}
|
||||||
|
getPlatformInfoStub = sinon.stub(window.chrome.runtime, 'getPlatformInfo');
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
identityStub.restore();
|
||||||
|
getPlatformInfoStub.restore();
|
||||||
|
removeCachedStub.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('isSupported', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
expect(oauth.isSupported()).to.be.true;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('refreshToken', function() {
|
||||||
|
var getOAuthTokenStub;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
googleApiStub = sinon.createStubInstance(RestDAO);
|
getOAuthTokenStub = sinon.stub(oauth, 'getOAuthToken');
|
||||||
oauth = new OAuth(googleApiStub);
|
|
||||||
|
|
||||||
window.chrome = window.chrome || {};
|
|
||||||
|
|
||||||
window.chrome.identity = window.chrome.identity || {};
|
|
||||||
if (typeof window.chrome.identity.getAuthToken !== 'function') {
|
|
||||||
window.chrome.identity.getAuthToken = function() {};
|
|
||||||
}
|
|
||||||
identityStub = sinon.stub(window.chrome.identity, 'getAuthToken');
|
|
||||||
|
|
||||||
if (typeof window.chrome.identity.removeCachedAuthToken !== 'function') {
|
|
||||||
window.chrome.identity.removeCachedAuthToken = function() {};
|
|
||||||
}
|
|
||||||
removeCachedStub = sinon.stub(window.chrome.identity, 'removeCachedAuthToken');
|
|
||||||
|
|
||||||
window.chrome.runtime = window.chrome.runtime || {};
|
|
||||||
if (typeof window.chrome.runtime.getPlatformInfo !== 'function') {
|
|
||||||
window.chrome.runtime.getPlatformInfo = function() {};
|
|
||||||
}
|
|
||||||
getPlatformInfoStub = sinon.stub(window.chrome.runtime, 'getPlatformInfo');
|
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
afterEach(function() {
|
||||||
identityStub.restore();
|
getOAuthTokenStub.restore();
|
||||||
getPlatformInfoStub.restore();
|
|
||||||
removeCachedStub.restore();
|
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('isSupported', function() {
|
it('should work', function() {
|
||||||
it('should work', function() {
|
removeCachedStub.withArgs({
|
||||||
expect(oauth.isSupported()).to.be.true;
|
token: 'oldToken'
|
||||||
|
}).yields();
|
||||||
|
|
||||||
|
getOAuthTokenStub.withArgs(testEmail).yields();
|
||||||
|
|
||||||
|
oauth.refreshToken({
|
||||||
|
oldToken: 'oldToken',
|
||||||
|
emailAddress: testEmail
|
||||||
|
}, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(removeCachedStub.calledOnce).to.be.true;
|
||||||
|
expect(getOAuthTokenStub.calledOnce).to.be.true;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('refreshToken', function() {
|
it('should work without email', function() {
|
||||||
var getOAuthTokenStub;
|
removeCachedStub.withArgs({
|
||||||
|
token: 'oldToken'
|
||||||
|
}).yields();
|
||||||
|
|
||||||
beforeEach(function() {
|
getOAuthTokenStub.withArgs(undefined).yields();
|
||||||
getOAuthTokenStub = sinon.stub(oauth, 'getOAuthToken');
|
|
||||||
});
|
|
||||||
afterEach(function() {
|
|
||||||
getOAuthTokenStub.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function() {
|
oauth.refreshToken({
|
||||||
removeCachedStub.withArgs({
|
oldToken: 'oldToken',
|
||||||
token: 'oldToken'
|
}, function(err) {
|
||||||
}).yields();
|
expect(err).to.not.exist;
|
||||||
|
expect(removeCachedStub.calledOnce).to.be.true;
|
||||||
getOAuthTokenStub.withArgs(testEmail).yields();
|
expect(getOAuthTokenStub.calledOnce).to.be.true;
|
||||||
|
expect(getOAuthTokenStub.calledWith(undefined)).to.be.true;
|
||||||
oauth.refreshToken({
|
|
||||||
oldToken: 'oldToken',
|
|
||||||
emailAddress: testEmail
|
|
||||||
}, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(removeCachedStub.calledOnce).to.be.true;
|
|
||||||
expect(getOAuthTokenStub.calledOnce).to.be.true;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work without email', function() {
|
|
||||||
removeCachedStub.withArgs({
|
|
||||||
token: 'oldToken'
|
|
||||||
}).yields();
|
|
||||||
|
|
||||||
getOAuthTokenStub.withArgs(undefined).yields();
|
|
||||||
|
|
||||||
oauth.refreshToken({
|
|
||||||
oldToken: 'oldToken',
|
|
||||||
}, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(removeCachedStub.calledOnce).to.be.true;
|
|
||||||
expect(getOAuthTokenStub.calledOnce).to.be.true;
|
|
||||||
expect(getOAuthTokenStub.calledWith(undefined)).to.be.true;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail without all options', function() {
|
|
||||||
oauth.refreshToken({
|
|
||||||
emailAddress: testEmail
|
|
||||||
}, function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(removeCachedStub.called).to.be.false;
|
|
||||||
expect(getOAuthTokenStub.called).to.be.false;
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('getOAuthToken', function() {
|
it('should fail without all options', function() {
|
||||||
it('should work for empty emailAddress', function(done) {
|
oauth.refreshToken({
|
||||||
getPlatformInfoStub.yields({
|
emailAddress: testEmail
|
||||||
os: 'android'
|
}, function(err) {
|
||||||
});
|
expect(err).to.exist;
|
||||||
identityStub.withArgs({
|
expect(removeCachedStub.called).to.be.false;
|
||||||
interactive: true
|
expect(getOAuthTokenStub.called).to.be.false;
|
||||||
}).yields('token');
|
|
||||||
|
|
||||||
oauth.getOAuthToken(undefined, function(err, token) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(token).to.equal('token');
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work on android app', function(done) {
|
|
||||||
getPlatformInfoStub.yields({
|
|
||||||
os: 'android'
|
|
||||||
});
|
|
||||||
identityStub.withArgs({
|
|
||||||
interactive: true,
|
|
||||||
accountHint: testEmail
|
|
||||||
}).yields('token');
|
|
||||||
|
|
||||||
oauth.getOAuthToken(testEmail, function(err, token) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(token).to.equal('token');
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work on desktop chrome', function(done) {
|
|
||||||
getPlatformInfoStub.yields({
|
|
||||||
os: 'mac'
|
|
||||||
});
|
|
||||||
identityStub.withArgs({
|
|
||||||
interactive: true
|
|
||||||
}).yields('token');
|
|
||||||
|
|
||||||
oauth.getOAuthToken(testEmail, function(err, token) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(token).to.equal('token');
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail', function(done) {
|
|
||||||
getPlatformInfoStub.yields({
|
|
||||||
os: 'android'
|
|
||||||
});
|
|
||||||
identityStub.yields();
|
|
||||||
|
|
||||||
oauth.getOAuthToken(testEmail, function(err, token) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(token).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('queryEmailAddress', function() {
|
|
||||||
it('should work', function(done) {
|
|
||||||
googleApiStub.get.withArgs({
|
|
||||||
uri: '/oauth2/v3/userinfo?access_token=token'
|
|
||||||
}).yields(null, {
|
|
||||||
email: 'asdf@example.com'
|
|
||||||
});
|
|
||||||
|
|
||||||
oauth.queryEmailAddress('token', function(err, emailAddress) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(emailAddress).to.equal('asdf@example.com');
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail due to invalid token', function(done) {
|
|
||||||
oauth.queryEmailAddress('', function(err, emailAddress) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(emailAddress).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail due to error in rest api', function(done) {
|
|
||||||
googleApiStub.get.withArgs({
|
|
||||||
uri: '/oauth2/v3/userinfo?access_token=token'
|
|
||||||
}).yields(new Error());
|
|
||||||
|
|
||||||
oauth.queryEmailAddress('token', function(err, emailAddress) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(emailAddress).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe('getOAuthToken', function() {
|
||||||
|
it('should work for empty emailAddress', function(done) {
|
||||||
|
getPlatformInfoStub.yields({
|
||||||
|
os: 'android'
|
||||||
|
});
|
||||||
|
identityStub.withArgs({
|
||||||
|
interactive: true
|
||||||
|
}).yields('token');
|
||||||
|
|
||||||
|
oauth.getOAuthToken(undefined, function(err, token) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(token).to.equal('token');
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work on android app', function(done) {
|
||||||
|
getPlatformInfoStub.yields({
|
||||||
|
os: 'android'
|
||||||
|
});
|
||||||
|
identityStub.withArgs({
|
||||||
|
interactive: true,
|
||||||
|
accountHint: testEmail
|
||||||
|
}).yields('token');
|
||||||
|
|
||||||
|
oauth.getOAuthToken(testEmail, function(err, token) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(token).to.equal('token');
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work on desktop chrome', function(done) {
|
||||||
|
getPlatformInfoStub.yields({
|
||||||
|
os: 'mac'
|
||||||
|
});
|
||||||
|
identityStub.withArgs({
|
||||||
|
interactive: true
|
||||||
|
}).yields('token');
|
||||||
|
|
||||||
|
oauth.getOAuthToken(testEmail, function(err, token) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(token).to.equal('token');
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail', function(done) {
|
||||||
|
getPlatformInfoStub.yields({
|
||||||
|
os: 'android'
|
||||||
|
});
|
||||||
|
identityStub.yields();
|
||||||
|
|
||||||
|
oauth.getOAuthToken(testEmail, function(err, token) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(token).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('queryEmailAddress', function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
googleApiStub.get.withArgs({
|
||||||
|
uri: '/oauth2/v3/userinfo?access_token=token'
|
||||||
|
}).yields(null, {
|
||||||
|
email: 'asdf@example.com'
|
||||||
|
});
|
||||||
|
|
||||||
|
oauth.queryEmailAddress('token', function(err, emailAddress) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(emailAddress).to.equal('asdf@example.com');
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail due to invalid token', function(done) {
|
||||||
|
oauth.queryEmailAddress('', function(err, emailAddress) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(emailAddress).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail due to error in rest api', function(done) {
|
||||||
|
googleApiStub.get.withArgs({
|
||||||
|
uri: '/oauth2/v3/userinfo?access_token=token'
|
||||||
|
}).yields(new Error());
|
||||||
|
|
||||||
|
oauth.queryEmailAddress('token', function(err, emailAddress) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(emailAddress).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
});
|
});
|
@ -1,279 +1,276 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var OutboxBO = require('../../src/js/bo/outbox'),
|
||||||
OutboxBO = require('js/bo/outbox'),
|
KeychainDAO = require('../../src/js/dao/keychain-dao'),
|
||||||
KeychainDAO = require('js/dao/keychain-dao'),
|
EmailDAO = require('../../src/js/dao/email-dao'),
|
||||||
EmailDAO = require('js/dao/email-dao'),
|
DeviceStorageDAO = require('../../src/js/dao/devicestorage-dao');
|
||||||
DeviceStorageDAO = require('js/dao/devicestorage-dao');
|
|
||||||
|
|
||||||
chai.Assertion.includeStack = true;
|
chai.Assertion.includeStack = true;
|
||||||
|
|
||||||
describe('Outbox Business Object unit test', function() {
|
describe('Outbox Business Object unit test', function() {
|
||||||
var outbox, emailDaoStub, devicestorageStub, keychainStub,
|
var outbox, emailDaoStub, devicestorageStub, keychainStub,
|
||||||
dummyUser = 'spiderpig@springfield.com';
|
dummyUser = 'spiderpig@springfield.com';
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
emailDaoStub = sinon.createStubInstance(EmailDAO);
|
emailDaoStub = sinon.createStubInstance(EmailDAO);
|
||||||
emailDaoStub._account = {
|
emailDaoStub._account = {
|
||||||
emailAddress: dummyUser,
|
emailAddress: dummyUser,
|
||||||
folders: [{
|
folders: [{
|
||||||
type: 'Outbox'
|
type: 'Outbox'
|
||||||
}],
|
}],
|
||||||
online: true
|
online: true
|
||||||
|
};
|
||||||
|
devicestorageStub = sinon.createStubInstance(DeviceStorageDAO);
|
||||||
|
keychainStub = sinon.createStubInstance(KeychainDAO);
|
||||||
|
outbox = new OutboxBO(emailDaoStub, keychainStub, devicestorageStub);
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {});
|
||||||
|
|
||||||
|
describe('start/stop checking', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
function onOutboxUpdate(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
}
|
||||||
|
|
||||||
|
outbox.startChecking(onOutboxUpdate);
|
||||||
|
expect(outbox._intervalId).to.exist;
|
||||||
|
|
||||||
|
outbox.stopChecking();
|
||||||
|
expect(outbox._intervalId).to.not.exist;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('put', function() {
|
||||||
|
it('should not encrypt and store a mail', function(done) {
|
||||||
|
var mail, senderKey, receiverKey;
|
||||||
|
|
||||||
|
senderKey = {
|
||||||
|
publicKey: 'SENDER PUBLIC KEY'
|
||||||
};
|
};
|
||||||
devicestorageStub = sinon.createStubInstance(DeviceStorageDAO);
|
receiverKey = {
|
||||||
keychainStub = sinon.createStubInstance(KeychainDAO);
|
publicKey: 'RECEIVER PUBLIC KEY'
|
||||||
outbox = new OutboxBO(emailDaoStub, keychainStub, devicestorageStub);
|
};
|
||||||
});
|
mail = {
|
||||||
|
from: [{
|
||||||
afterEach(function() {});
|
|
||||||
|
|
||||||
describe('start/stop checking', function() {
|
|
||||||
it('should work', function() {
|
|
||||||
function onOutboxUpdate(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
}
|
|
||||||
|
|
||||||
outbox.startChecking(onOutboxUpdate);
|
|
||||||
expect(outbox._intervalId).to.exist;
|
|
||||||
|
|
||||||
outbox.stopChecking();
|
|
||||||
expect(outbox._intervalId).to.not.exist;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('put', function() {
|
|
||||||
it('should not encrypt and store a mail', function(done) {
|
|
||||||
var mail, senderKey, receiverKey;
|
|
||||||
|
|
||||||
senderKey = {
|
|
||||||
publicKey: 'SENDER PUBLIC KEY'
|
|
||||||
};
|
|
||||||
receiverKey = {
|
|
||||||
publicKey: 'RECEIVER PUBLIC KEY'
|
|
||||||
};
|
|
||||||
mail = {
|
|
||||||
from: [{
|
|
||||||
name: 'member',
|
|
||||||
address: 'member@whiteout.io'
|
|
||||||
}],
|
|
||||||
to: [{
|
|
||||||
name: 'member',
|
|
||||||
address: 'member'
|
|
||||||
}, {
|
|
||||||
name: 'notamember',
|
|
||||||
address: 'notamember'
|
|
||||||
}],
|
|
||||||
cc: [],
|
|
||||||
bcc: []
|
|
||||||
};
|
|
||||||
|
|
||||||
keychainStub.getReceiverPublicKey.withArgs(mail.from[0].address).yieldsAsync(null, senderKey);
|
|
||||||
keychainStub.getReceiverPublicKey.withArgs(mail.to[0].address).yieldsAsync(null, receiverKey);
|
|
||||||
keychainStub.getReceiverPublicKey.withArgs(mail.to[1].address).yieldsAsync();
|
|
||||||
|
|
||||||
devicestorageStub.storeList.withArgs([mail]).yieldsAsync();
|
|
||||||
|
|
||||||
outbox.put(mail, function(error) {
|
|
||||||
expect(error).to.not.exist;
|
|
||||||
|
|
||||||
expect(mail.publicKeysArmored.length).to.equal(2);
|
|
||||||
expect(emailDaoStub.encrypt.called).to.be.false;
|
|
||||||
expect(devicestorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not encrypt a mail with bcc and store a mail', function(done) {
|
|
||||||
var mail;
|
|
||||||
|
|
||||||
mail = {
|
|
||||||
from: [{
|
|
||||||
name: 'member',
|
|
||||||
address: 'member@whiteout.io'
|
|
||||||
}],
|
|
||||||
to: [{
|
|
||||||
name: 'member',
|
|
||||||
address: 'member@whiteout.io'
|
|
||||||
}],
|
|
||||||
cc: [],
|
|
||||||
bcc: [{
|
|
||||||
name: 'member',
|
|
||||||
address: 'member@whiteout.io'
|
|
||||||
}]
|
|
||||||
};
|
|
||||||
|
|
||||||
devicestorageStub.storeList.withArgs([mail]).yieldsAsync();
|
|
||||||
|
|
||||||
outbox.put(mail, function(error) {
|
|
||||||
expect(error).to.not.exist;
|
|
||||||
|
|
||||||
expect(mail.publicKeysArmored.length).to.equal(0);
|
|
||||||
expect(keychainStub.getReceiverPublicKey.called).to.be.false;
|
|
||||||
expect(emailDaoStub.encrypt.called).to.be.false;
|
|
||||||
expect(devicestorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should encrypt and store a mail', function(done) {
|
|
||||||
var mail, senderKey, receiverKey;
|
|
||||||
|
|
||||||
senderKey = {
|
|
||||||
publicKey: 'SENDER PUBLIC KEY'
|
|
||||||
};
|
|
||||||
receiverKey = {
|
|
||||||
publicKey: 'RECEIVER PUBLIC KEY'
|
|
||||||
};
|
|
||||||
mail = {
|
|
||||||
from: [{
|
|
||||||
name: 'member',
|
|
||||||
address: 'member@whiteout.io'
|
|
||||||
}],
|
|
||||||
to: [{
|
|
||||||
name: 'member',
|
|
||||||
address: 'member'
|
|
||||||
}, {
|
|
||||||
name: 'notamember',
|
|
||||||
address: 'notamember'
|
|
||||||
}],
|
|
||||||
cc: [],
|
|
||||||
bcc: []
|
|
||||||
};
|
|
||||||
|
|
||||||
keychainStub.getReceiverPublicKey.withArgs(mail.from[0].address).yieldsAsync(null, senderKey);
|
|
||||||
keychainStub.getReceiverPublicKey.withArgs(mail.to[0].address).yieldsAsync(null, receiverKey);
|
|
||||||
keychainStub.getReceiverPublicKey.withArgs(mail.to[1].address).yieldsAsync(null, receiverKey);
|
|
||||||
|
|
||||||
emailDaoStub.encrypt.withArgs({
|
|
||||||
mail: mail,
|
|
||||||
publicKeysArmored: [senderKey.publicKey, receiverKey.publicKey, receiverKey.publicKey]
|
|
||||||
}).yieldsAsync();
|
|
||||||
|
|
||||||
devicestorageStub.storeList.withArgs([mail]).yieldsAsync();
|
|
||||||
|
|
||||||
outbox.put(mail, function(error) {
|
|
||||||
expect(error).to.not.exist;
|
|
||||||
|
|
||||||
expect(mail.publicKeysArmored.length).to.equal(3);
|
|
||||||
expect(emailDaoStub.encrypt.calledOnce).to.be.true;
|
|
||||||
expect(devicestorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('process outbox', function() {
|
|
||||||
it('should send to registered users and update pending mails', function(done) {
|
|
||||||
var from, member, invited, notinvited, newlyjoined, dummyMails, newlyjoinedKey;
|
|
||||||
|
|
||||||
from = [{
|
|
||||||
name: 'member',
|
name: 'member',
|
||||||
address: 'member@whiteout.io'
|
address: 'member@whiteout.io'
|
||||||
}];
|
}],
|
||||||
member = {
|
to: [{
|
||||||
id: '12',
|
name: 'member',
|
||||||
from: from,
|
address: 'member'
|
||||||
to: [{
|
}, {
|
||||||
name: 'member',
|
name: 'notamember',
|
||||||
address: 'member'
|
address: 'notamember'
|
||||||
}],
|
}],
|
||||||
encrypted: true,
|
cc: [],
|
||||||
publicKeysArmored: ['ARMORED KEY OF MEMBER'],
|
bcc: []
|
||||||
unregisteredUsers: []
|
};
|
||||||
};
|
|
||||||
invited = {
|
|
||||||
id: '34',
|
|
||||||
from: from,
|
|
||||||
to: [{
|
|
||||||
name: 'invited',
|
|
||||||
address: 'invited'
|
|
||||||
}],
|
|
||||||
publicKeysArmored: [],
|
|
||||||
unregisteredUsers: [{
|
|
||||||
name: 'invited',
|
|
||||||
address: 'invited'
|
|
||||||
}]
|
|
||||||
};
|
|
||||||
notinvited = {
|
|
||||||
id: '56',
|
|
||||||
from: from,
|
|
||||||
to: [{
|
|
||||||
name: 'notinvited',
|
|
||||||
address: 'notinvited'
|
|
||||||
}],
|
|
||||||
publicKeysArmored: [],
|
|
||||||
unregisteredUsers: [{
|
|
||||||
name: 'notinvited',
|
|
||||||
address: 'notinvited'
|
|
||||||
}]
|
|
||||||
};
|
|
||||||
newlyjoined = {
|
|
||||||
id: '78',
|
|
||||||
from: from,
|
|
||||||
to: [{
|
|
||||||
name: 'newlyjoined',
|
|
||||||
address: 'newlyjoined'
|
|
||||||
}],
|
|
||||||
encrypted: true,
|
|
||||||
publicKeysArmored: [],
|
|
||||||
unregisteredUsers: [{
|
|
||||||
name: 'newlyjoined',
|
|
||||||
address: 'newlyjoined'
|
|
||||||
}]
|
|
||||||
};
|
|
||||||
newlyjoinedKey = {
|
|
||||||
publicKey: 'THIS IS THE NEWLY JOINED PUBLIC KEY!'
|
|
||||||
};
|
|
||||||
|
|
||||||
dummyMails = [member, invited, notinvited, newlyjoined];
|
keychainStub.getReceiverPublicKey.withArgs(mail.from[0].address).yieldsAsync(null, senderKey);
|
||||||
|
keychainStub.getReceiverPublicKey.withArgs(mail.to[0].address).yieldsAsync(null, receiverKey);
|
||||||
|
keychainStub.getReceiverPublicKey.withArgs(mail.to[1].address).yieldsAsync();
|
||||||
|
|
||||||
devicestorageStub.listItems.yieldsAsync(null, dummyMails);
|
devicestorageStub.storeList.withArgs([mail]).yieldsAsync();
|
||||||
|
|
||||||
emailDaoStub.sendPlaintext.yieldsAsync();
|
outbox.put(mail, function(error) {
|
||||||
|
expect(error).to.not.exist;
|
||||||
|
|
||||||
emailDaoStub.sendEncrypted.withArgs({
|
expect(mail.publicKeysArmored.length).to.equal(2);
|
||||||
email: newlyjoined
|
expect(emailDaoStub.encrypt.called).to.be.false;
|
||||||
}).yieldsAsync();
|
expect(devicestorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
|
||||||
emailDaoStub.sendEncrypted.withArgs({
|
done();
|
||||||
email: member
|
|
||||||
}).yieldsAsync();
|
|
||||||
|
|
||||||
devicestorageStub.removeList.yieldsAsync();
|
|
||||||
|
|
||||||
function onOutboxUpdate(err, count) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(count).to.equal(0);
|
|
||||||
|
|
||||||
expect(outbox._outboxBusy).to.be.false;
|
|
||||||
expect(emailDaoStub.sendEncrypted.callCount).to.equal(2);
|
|
||||||
expect(emailDaoStub.sendPlaintext.callCount).to.equal(2);
|
|
||||||
expect(devicestorageStub.listItems.callCount).to.equal(1);
|
|
||||||
expect(devicestorageStub.removeList.callCount).to.equal(4);
|
|
||||||
expect(keychainStub.getReceiverPublicKey.callCount).to.equal(0);
|
|
||||||
|
|
||||||
done();
|
|
||||||
}
|
|
||||||
|
|
||||||
outbox._processOutbox(onOutboxUpdate);
|
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should not process outbox in offline mode', function(done) {
|
it('should not encrypt a mail with bcc and store a mail', function(done) {
|
||||||
emailDaoStub._account.online = false;
|
var mail;
|
||||||
devicestorageStub.listItems.yieldsAsync(null, [{}]);
|
|
||||||
|
|
||||||
outbox._processOutbox(function(err, count) {
|
mail = {
|
||||||
expect(err).to.not.exist;
|
from: [{
|
||||||
expect(count).to.equal(1);
|
name: 'member',
|
||||||
expect(devicestorageStub.listItems.callCount).to.equal(1);
|
address: 'member@whiteout.io'
|
||||||
expect(outbox._outboxBusy).to.be.false;
|
}],
|
||||||
done();
|
to: [{
|
||||||
});
|
name: 'member',
|
||||||
|
address: 'member@whiteout.io'
|
||||||
|
}],
|
||||||
|
cc: [],
|
||||||
|
bcc: [{
|
||||||
|
name: 'member',
|
||||||
|
address: 'member@whiteout.io'
|
||||||
|
}]
|
||||||
|
};
|
||||||
|
|
||||||
|
devicestorageStub.storeList.withArgs([mail]).yieldsAsync();
|
||||||
|
|
||||||
|
outbox.put(mail, function(error) {
|
||||||
|
expect(error).to.not.exist;
|
||||||
|
|
||||||
|
expect(mail.publicKeysArmored.length).to.equal(0);
|
||||||
|
expect(keychainStub.getReceiverPublicKey.called).to.be.false;
|
||||||
|
expect(emailDaoStub.encrypt.called).to.be.false;
|
||||||
|
expect(devicestorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should encrypt and store a mail', function(done) {
|
||||||
|
var mail, senderKey, receiverKey;
|
||||||
|
|
||||||
|
senderKey = {
|
||||||
|
publicKey: 'SENDER PUBLIC KEY'
|
||||||
|
};
|
||||||
|
receiverKey = {
|
||||||
|
publicKey: 'RECEIVER PUBLIC KEY'
|
||||||
|
};
|
||||||
|
mail = {
|
||||||
|
from: [{
|
||||||
|
name: 'member',
|
||||||
|
address: 'member@whiteout.io'
|
||||||
|
}],
|
||||||
|
to: [{
|
||||||
|
name: 'member',
|
||||||
|
address: 'member'
|
||||||
|
}, {
|
||||||
|
name: 'notamember',
|
||||||
|
address: 'notamember'
|
||||||
|
}],
|
||||||
|
cc: [],
|
||||||
|
bcc: []
|
||||||
|
};
|
||||||
|
|
||||||
|
keychainStub.getReceiverPublicKey.withArgs(mail.from[0].address).yieldsAsync(null, senderKey);
|
||||||
|
keychainStub.getReceiverPublicKey.withArgs(mail.to[0].address).yieldsAsync(null, receiverKey);
|
||||||
|
keychainStub.getReceiverPublicKey.withArgs(mail.to[1].address).yieldsAsync(null, receiverKey);
|
||||||
|
|
||||||
|
emailDaoStub.encrypt.withArgs({
|
||||||
|
mail: mail,
|
||||||
|
publicKeysArmored: [senderKey.publicKey, receiverKey.publicKey, receiverKey.publicKey]
|
||||||
|
}).yieldsAsync();
|
||||||
|
|
||||||
|
devicestorageStub.storeList.withArgs([mail]).yieldsAsync();
|
||||||
|
|
||||||
|
outbox.put(mail, function(error) {
|
||||||
|
expect(error).to.not.exist;
|
||||||
|
|
||||||
|
expect(mail.publicKeysArmored.length).to.equal(3);
|
||||||
|
expect(emailDaoStub.encrypt.calledOnce).to.be.true;
|
||||||
|
expect(devicestorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('process outbox', function() {
|
||||||
|
it('should send to registered users and update pending mails', function(done) {
|
||||||
|
var from, member, invited, notinvited, newlyjoined, dummyMails, newlyjoinedKey;
|
||||||
|
|
||||||
|
from = [{
|
||||||
|
name: 'member',
|
||||||
|
address: 'member@whiteout.io'
|
||||||
|
}];
|
||||||
|
member = {
|
||||||
|
id: '12',
|
||||||
|
from: from,
|
||||||
|
to: [{
|
||||||
|
name: 'member',
|
||||||
|
address: 'member'
|
||||||
|
}],
|
||||||
|
encrypted: true,
|
||||||
|
publicKeysArmored: ['ARMORED KEY OF MEMBER'],
|
||||||
|
unregisteredUsers: []
|
||||||
|
};
|
||||||
|
invited = {
|
||||||
|
id: '34',
|
||||||
|
from: from,
|
||||||
|
to: [{
|
||||||
|
name: 'invited',
|
||||||
|
address: 'invited'
|
||||||
|
}],
|
||||||
|
publicKeysArmored: [],
|
||||||
|
unregisteredUsers: [{
|
||||||
|
name: 'invited',
|
||||||
|
address: 'invited'
|
||||||
|
}]
|
||||||
|
};
|
||||||
|
notinvited = {
|
||||||
|
id: '56',
|
||||||
|
from: from,
|
||||||
|
to: [{
|
||||||
|
name: 'notinvited',
|
||||||
|
address: 'notinvited'
|
||||||
|
}],
|
||||||
|
publicKeysArmored: [],
|
||||||
|
unregisteredUsers: [{
|
||||||
|
name: 'notinvited',
|
||||||
|
address: 'notinvited'
|
||||||
|
}]
|
||||||
|
};
|
||||||
|
newlyjoined = {
|
||||||
|
id: '78',
|
||||||
|
from: from,
|
||||||
|
to: [{
|
||||||
|
name: 'newlyjoined',
|
||||||
|
address: 'newlyjoined'
|
||||||
|
}],
|
||||||
|
encrypted: true,
|
||||||
|
publicKeysArmored: [],
|
||||||
|
unregisteredUsers: [{
|
||||||
|
name: 'newlyjoined',
|
||||||
|
address: 'newlyjoined'
|
||||||
|
}]
|
||||||
|
};
|
||||||
|
newlyjoinedKey = {
|
||||||
|
publicKey: 'THIS IS THE NEWLY JOINED PUBLIC KEY!'
|
||||||
|
};
|
||||||
|
|
||||||
|
dummyMails = [member, invited, notinvited, newlyjoined];
|
||||||
|
|
||||||
|
devicestorageStub.listItems.yieldsAsync(null, dummyMails);
|
||||||
|
|
||||||
|
emailDaoStub.sendPlaintext.yieldsAsync();
|
||||||
|
|
||||||
|
emailDaoStub.sendEncrypted.withArgs({
|
||||||
|
email: newlyjoined
|
||||||
|
}).yieldsAsync();
|
||||||
|
|
||||||
|
emailDaoStub.sendEncrypted.withArgs({
|
||||||
|
email: member
|
||||||
|
}).yieldsAsync();
|
||||||
|
|
||||||
|
devicestorageStub.removeList.yieldsAsync();
|
||||||
|
|
||||||
|
function onOutboxUpdate(err, count) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(count).to.equal(0);
|
||||||
|
|
||||||
|
expect(outbox._outboxBusy).to.be.false;
|
||||||
|
expect(emailDaoStub.sendEncrypted.callCount).to.equal(2);
|
||||||
|
expect(emailDaoStub.sendPlaintext.callCount).to.equal(2);
|
||||||
|
expect(devicestorageStub.listItems.callCount).to.equal(1);
|
||||||
|
expect(devicestorageStub.removeList.callCount).to.equal(4);
|
||||||
|
expect(keychainStub.getReceiverPublicKey.callCount).to.equal(0);
|
||||||
|
|
||||||
|
done();
|
||||||
|
}
|
||||||
|
|
||||||
|
outbox._processOutbox(onOutboxUpdate);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not process outbox in offline mode', function(done) {
|
||||||
|
emailDaoStub._account.online = false;
|
||||||
|
devicestorageStub.listItems.yieldsAsync(null, [{}]);
|
||||||
|
|
||||||
|
outbox._processOutbox(function(err, count) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(count).to.equal(1);
|
||||||
|
expect(devicestorageStub.listItems.callCount).to.equal(1);
|
||||||
|
expect(outbox._outboxBusy).to.be.false;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -1,464 +1,460 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var PGP = require('js/crypto/pgp'),
|
var PGP = require('../../src/js/crypto/pgp');
|
||||||
openpgp = require('openpgp'),
|
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
describe('PGP Crypto Api unit tests', function() {
|
describe('PGP Crypto Api unit tests', function() {
|
||||||
this.timeout(20000);
|
this.timeout(20000);
|
||||||
|
|
||||||
var pgp,
|
var pgp,
|
||||||
user = 'whiteout.test@t-online.de',
|
user = 'whiteout.test@t-online.de',
|
||||||
passphrase = 'asdf',
|
passphrase = 'asdf',
|
||||||
keySize = 512,
|
keySize = 512,
|
||||||
keyId = 'F6F60E9B42CDFF4C',
|
keyId = 'F6F60E9B42CDFF4C',
|
||||||
pubkey = '-----BEGIN PGP PUBLIC KEY BLOCK-----\r\n' +
|
pubkey = '-----BEGIN PGP PUBLIC KEY BLOCK-----\r\n' +
|
||||||
'Version: OpenPGP.js v0.7.2\r\n' +
|
'Version: OpenPGP.js v0.7.2\r\n' +
|
||||||
'Comment: Whiteout Mail - https://whiteout.io\r\n' +
|
'Comment: Whiteout Mail - https://whiteout.io\r\n' +
|
||||||
'\r\n' +
|
'\r\n' +
|
||||||
'xk0EUlhMvAEB/2MZtCUOAYvyLFjDp3OBMGn3Ev8FwjzyPbIF0JUw+L7y2XR5\r\n' +
|
'xk0EUlhMvAEB/2MZtCUOAYvyLFjDp3OBMGn3Ev8FwjzyPbIF0JUw+L7y2XR5\r\n' +
|
||||||
'RVGvbK88unV3cU/1tOYdNsXI6pSp/Ztjyv7vbBUAEQEAAc0pV2hpdGVvdXQg\r\n' +
|
'RVGvbK88unV3cU/1tOYdNsXI6pSp/Ztjyv7vbBUAEQEAAc0pV2hpdGVvdXQg\r\n' +
|
||||||
'VXNlciA8d2hpdGVvdXQudGVzdEB0LW9ubGluZS5kZT7CXAQQAQgAEAUCUlhM\r\n' +
|
'VXNlciA8d2hpdGVvdXQudGVzdEB0LW9ubGluZS5kZT7CXAQQAQgAEAUCUlhM\r\n' +
|
||||||
'vQkQ9vYOm0LN/0wAAAW4Af9C+kYW1AvNWmivdtr0M0iYCUjM9DNOQH1fcvXq\r\n' +
|
'vQkQ9vYOm0LN/0wAAAW4Af9C+kYW1AvNWmivdtr0M0iYCUjM9DNOQH1fcvXq\r\n' +
|
||||||
'IiN602mWrkd8jcEzLsW5IUNzVPLhrFIuKyBDTpLnC07Loce1\r\n' +
|
'IiN602mWrkd8jcEzLsW5IUNzVPLhrFIuKyBDTpLnC07Loce1\r\n' +
|
||||||
'=6XMW\r\n' +
|
'=6XMW\r\n' +
|
||||||
'-----END PGP PUBLIC KEY BLOCK-----\r\n\r\n',
|
'-----END PGP PUBLIC KEY BLOCK-----\r\n\r\n',
|
||||||
privkey = '-----BEGIN PGP PRIVATE KEY BLOCK-----\r\n' +
|
privkey = '-----BEGIN PGP PRIVATE KEY BLOCK-----\r\n' +
|
||||||
'Version: OpenPGP.js v0.7.2\r\n' +
|
'Version: OpenPGP.js v0.7.2\r\n' +
|
||||||
'Comment: Whiteout Mail - https://whiteout.io\r\n' +
|
'Comment: Whiteout Mail - https://whiteout.io\r\n' +
|
||||||
'\r\n' +
|
'\r\n' +
|
||||||
'xcBeBFJYTLwBAf9jGbQlDgGL8ixYw6dzgTBp9xL/BcI88j2yBdCVMPi+8tl0\r\n' +
|
'xcBeBFJYTLwBAf9jGbQlDgGL8ixYw6dzgTBp9xL/BcI88j2yBdCVMPi+8tl0\r\n' +
|
||||||
'eUVRr2yvPLp1d3FP9bTmHTbFyOqUqf2bY8r+72wVABEBAAH+AwMIhNB4ivtv\r\n' +
|
'eUVRr2yvPLp1d3FP9bTmHTbFyOqUqf2bY8r+72wVABEBAAH+AwMIhNB4ivtv\r\n' +
|
||||||
'Y2xg6VeMcjjHxZayESHACV+nQx5Tx6ev6xzIF1Qh72fNPDppLhFSFOuTTMsU\r\n' +
|
'Y2xg6VeMcjjHxZayESHACV+nQx5Tx6ev6xzIF1Qh72fNPDppLhFSFOuTTMsU\r\n' +
|
||||||
'kTN4c+BVYt29spH+cA1jcDAxQ2ULrNAXo+hheOqhpedTs8aCbcLFkJAS16hk\r\n' +
|
'kTN4c+BVYt29spH+cA1jcDAxQ2ULrNAXo+hheOqhpedTs8aCbcLFkJAS16hk\r\n' +
|
||||||
'YSk4OnJgp/z24rVju1SHRSFbgundPzmNgXeX9e8IkviGhhQ11Wc5YwVkx03t\r\n' +
|
'YSk4OnJgp/z24rVju1SHRSFbgundPzmNgXeX9e8IkviGhhQ11Wc5YwVkx03t\r\n' +
|
||||||
'Z3MdDMF0jyhopbPIoBdyJB0dhvBh98w3JmwpYh9wjUA9MBHD1tvHpRmSZ3BM\r\n' +
|
'Z3MdDMF0jyhopbPIoBdyJB0dhvBh98w3JmwpYh9wjUA9MBHD1tvHpRmSZ3BM\r\n' +
|
||||||
'UCmATn2ZLWBRWiYqFbgDnL1GM80pV2hpdGVvdXQgVXNlciA8d2hpdGVvdXQu\r\n' +
|
'UCmATn2ZLWBRWiYqFbgDnL1GM80pV2hpdGVvdXQgVXNlciA8d2hpdGVvdXQu\r\n' +
|
||||||
'dGVzdEB0LW9ubGluZS5kZT7CXAQQAQgAEAUCUlhMvQkQ9vYOm0LN/0wAAAW4\r\n' +
|
'dGVzdEB0LW9ubGluZS5kZT7CXAQQAQgAEAUCUlhMvQkQ9vYOm0LN/0wAAAW4\r\n' +
|
||||||
'Af9C+kYW1AvNWmivdtr0M0iYCUjM9DNOQH1fcvXqIiN602mWrkd8jcEzLsW5\r\n' +
|
'Af9C+kYW1AvNWmivdtr0M0iYCUjM9DNOQH1fcvXqIiN602mWrkd8jcEzLsW5\r\n' +
|
||||||
'IUNzVPLhrFIuKyBDTpLnC07Loce1\r\n' +
|
'IUNzVPLhrFIuKyBDTpLnC07Loce1\r\n' +
|
||||||
'=ULta\r\n' +
|
'=ULta\r\n' +
|
||||||
'-----END PGP PRIVATE KEY BLOCK-----\r\n';
|
'-----END PGP PRIVATE KEY BLOCK-----\r\n';
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
pgp = new PGP();
|
pgp = new PGP();
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {});
|
||||||
|
|
||||||
|
describe('Generate key pair', function() {
|
||||||
|
it('should fail', function(done) {
|
||||||
|
pgp.generateKeys({
|
||||||
|
emailAddress: 'whiteout.test@t-onlinede',
|
||||||
|
keySize: keySize,
|
||||||
|
passphrase: passphrase
|
||||||
|
}, function(err, keys) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(keys).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
it('should fail', function(done) {
|
||||||
afterEach(function() {});
|
pgp.generateKeys({
|
||||||
|
emailAddress: 'whiteout.testt-online.de',
|
||||||
describe('Generate key pair', function() {
|
keySize: keySize,
|
||||||
it('should fail', function(done) {
|
passphrase: passphrase
|
||||||
pgp.generateKeys({
|
}, function(err, keys) {
|
||||||
emailAddress: 'whiteout.test@t-onlinede',
|
expect(err).to.exist;
|
||||||
keySize: keySize,
|
expect(keys).to.not.exist;
|
||||||
passphrase: passphrase
|
done();
|
||||||
}, function(err, keys) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(keys).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
it('should fail', function(done) {
|
});
|
||||||
pgp.generateKeys({
|
it('should work with passphrase', function(done) {
|
||||||
emailAddress: 'whiteout.testt-online.de',
|
pgp.generateKeys({
|
||||||
keySize: keySize,
|
emailAddress: user,
|
||||||
passphrase: passphrase
|
keySize: keySize,
|
||||||
}, function(err, keys) {
|
passphrase: passphrase
|
||||||
expect(err).to.exist;
|
}, function(err, keys) {
|
||||||
expect(keys).to.not.exist;
|
expect(err).to.not.exist;
|
||||||
done();
|
expect(keys.keyId).to.exist;
|
||||||
});
|
expect(keys.privateKeyArmored).to.exist;
|
||||||
});
|
expect(keys.publicKeyArmored).to.exist;
|
||||||
it('should work with passphrase', function(done) {
|
|
||||||
pgp.generateKeys({
|
// test encrypt/decrypt
|
||||||
emailAddress: user,
|
pgp.importKeys({
|
||||||
keySize: keySize,
|
passphrase: passphrase,
|
||||||
passphrase: passphrase
|
privateKeyArmored: keys.privateKeyArmored,
|
||||||
}, function(err, keys) {
|
publicKeyArmored: keys.publicKeyArmored
|
||||||
|
}, function(err) {
|
||||||
expect(err).to.not.exist;
|
expect(err).to.not.exist;
|
||||||
expect(keys.keyId).to.exist;
|
|
||||||
expect(keys.privateKeyArmored).to.exist;
|
|
||||||
expect(keys.publicKeyArmored).to.exist;
|
|
||||||
|
|
||||||
// test encrypt/decrypt
|
pgp.encrypt('secret', [keys.publicKeyArmored], function(err, ct) {
|
||||||
pgp.importKeys({
|
|
||||||
passphrase: passphrase,
|
|
||||||
privateKeyArmored: keys.privateKeyArmored,
|
|
||||||
publicKeyArmored: keys.publicKeyArmored
|
|
||||||
}, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
expect(err).to.not.exist;
|
||||||
|
expect(ct).to.exist;
|
||||||
|
|
||||||
pgp.encrypt('secret', [keys.publicKeyArmored], function(err, ct) {
|
pgp.decrypt(ct, keys.publicKeyArmored, function(err, pt, signValid) {
|
||||||
expect(err).to.not.exist;
|
expect(err).to.not.exist;
|
||||||
expect(ct).to.exist;
|
expect(pt).to.equal('secret');
|
||||||
|
expect(signValid).to.be.true;
|
||||||
pgp.decrypt(ct, keys.publicKeyArmored, function(err, pt, signValid) {
|
done();
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(pt).to.equal('secret');
|
|
||||||
expect(signValid).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should work without passphrase', function(done) {
|
|
||||||
pgp.generateKeys({
|
|
||||||
emailAddress: user,
|
|
||||||
keySize: keySize,
|
|
||||||
passphrase: ''
|
|
||||||
}, function(err, keys) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(keys.keyId).to.exist;
|
|
||||||
expect(keys.privateKeyArmored).to.exist;
|
|
||||||
expect(keys.publicKeyArmored).to.exist;
|
|
||||||
|
|
||||||
// test encrypt/decrypt
|
|
||||||
pgp.importKeys({
|
|
||||||
passphrase: undefined,
|
|
||||||
privateKeyArmored: keys.privateKeyArmored,
|
|
||||||
publicKeyArmored: keys.publicKeyArmored
|
|
||||||
}, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
|
|
||||||
pgp.encrypt('secret', [keys.publicKeyArmored], function(err, ct) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(ct).to.exist;
|
|
||||||
|
|
||||||
pgp.decrypt(ct, keys.publicKeyArmored, function(err, pt, signValid) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(pt).to.equal('secret');
|
|
||||||
expect(signValid).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
it('should work without passphrase', function(done) {
|
||||||
|
pgp.generateKeys({
|
||||||
|
emailAddress: user,
|
||||||
|
keySize: keySize,
|
||||||
|
passphrase: ''
|
||||||
|
}, function(err, keys) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(keys.keyId).to.exist;
|
||||||
|
expect(keys.privateKeyArmored).to.exist;
|
||||||
|
expect(keys.publicKeyArmored).to.exist;
|
||||||
|
|
||||||
describe('Import/Export key pair', function() {
|
// test encrypt/decrypt
|
||||||
it('should fail', function(done) {
|
|
||||||
pgp.importKeys({
|
pgp.importKeys({
|
||||||
passphrase: 'asd',
|
passphrase: undefined,
|
||||||
privateKeyArmored: privkey,
|
privateKeyArmored: keys.privateKeyArmored,
|
||||||
publicKeyArmored: pubkey
|
publicKeyArmored: keys.publicKeyArmored
|
||||||
}, function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(err.message).to.equal('Incorrect passphrase!');
|
|
||||||
|
|
||||||
pgp.exportKeys(function(err, keys) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(keys).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should work', function(done) {
|
|
||||||
pgp.importKeys({
|
|
||||||
passphrase: passphrase,
|
|
||||||
privateKeyArmored: privkey,
|
|
||||||
publicKeyArmored: pubkey
|
|
||||||
}, function(err) {
|
}, function(err) {
|
||||||
expect(err).to.not.exist;
|
expect(err).to.not.exist;
|
||||||
|
|
||||||
pgp.exportKeys(function(err, keys) {
|
pgp.encrypt('secret', [keys.publicKeyArmored], function(err, ct) {
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(keys.keyId).to.equal(keyId);
|
|
||||||
expect(keys.privateKeyArmored.replace(/\r/g, '')).to.equal(privkey.replace(/\r/g, ''));
|
|
||||||
expect(keys.publicKeyArmored.replace(/\r/g, '')).to.equal(pubkey.replace(/\r/g, ''));
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('Change passphrase of private key', function() {
|
|
||||||
it('should work with new passphrase', function(done) {
|
|
||||||
pgp.changePassphrase({
|
|
||||||
privateKeyArmored: privkey,
|
|
||||||
oldPassphrase: passphrase,
|
|
||||||
newPassphrase: 'yxcv'
|
|
||||||
}, function(err, reEncryptedKey) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(reEncryptedKey).to.exist;
|
|
||||||
|
|
||||||
pgp.importKeys({
|
|
||||||
passphrase: 'yxcv',
|
|
||||||
privateKeyArmored: reEncryptedKey,
|
|
||||||
publicKeyArmored: pubkey
|
|
||||||
}, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should work with empty passphrase', function(done) {
|
|
||||||
pgp.changePassphrase({
|
|
||||||
privateKeyArmored: privkey,
|
|
||||||
oldPassphrase: passphrase,
|
|
||||||
newPassphrase: undefined
|
|
||||||
}, function(err, reEncryptedKey) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(reEncryptedKey).to.exist;
|
|
||||||
|
|
||||||
pgp.importKeys({
|
|
||||||
passphrase: undefined,
|
|
||||||
privateKeyArmored: reEncryptedKey,
|
|
||||||
publicKeyArmored: pubkey
|
|
||||||
}, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should fail when passphrases are equal', function(done) {
|
|
||||||
pgp.changePassphrase({
|
|
||||||
privateKeyArmored: privkey,
|
|
||||||
oldPassphrase: passphrase,
|
|
||||||
newPassphrase: passphrase
|
|
||||||
}, function(err, reEncryptedKey) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(reEncryptedKey).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should fail when old passphrase is incorrect', function(done) {
|
|
||||||
pgp.changePassphrase({
|
|
||||||
privateKeyArmored: privkey,
|
|
||||||
oldPassphrase: 'asd',
|
|
||||||
newPassphrase: 'yxcv'
|
|
||||||
}, function(err, reEncryptedKey) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(reEncryptedKey).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('Encrypt/Sign/Decrypt/Verify', function() {
|
|
||||||
var message = 'asdfs\n\nThursday, Nov 21, 2013 7:38 PM asdf@example.com wrote:\n' +
|
|
||||||
'> asdf\n' +
|
|
||||||
'> \n' +
|
|
||||||
'> Thursday, Nov 21, 2013 7:32 PM asdf@example.com wrote:\n' +
|
|
||||||
'> > secret 3';
|
|
||||||
var wrongPubkey = '-----BEGIN PGP PUBLIC KEY BLOCK-----\r\nVersion: OpenPGP.js v.1.20131116\r\nComment: Whiteout Mail - http://whiteout.io\r\n\r\nxsBNBFKODs4BB/9iOF4THsjQMY+WEpT7ShgKxj4bHzRRaQkqczS4nZvP0U3g\r\nqeqCnbpagyeKXA+bhWFQW4GmXtgAoeD5PXs6AZYrw3tWNxLKu2Oe6Tp9K/XI\r\nxTMQ2wl4qZKDXHvuPsJ7cmgaWqpPyXtxA4zHHS3WrkI/6VzHAcI/y6x4szSB\r\nKgSuhI3hjh3s7TybUC1U6AfoQGx/S7e3WwlCOrK8GTClirN/2mCPRC5wuIft\r\nnkoMfA6jK8d2OPrJ63shy5cgwHOjQg/xuk46dNS7tkvGmbaa+X0PgqSKB+Hf\r\nYPPNS/ylg911DH9qa8BqYU2QpNh9jUKXSF+HbaOM+plWkCSAL7czV+R3ABEB\r\nAAHNLVdoaXRlb3V0IFVzZXIgPHNhZmV3aXRobWUudGVzdHVzZXJAZ21haWwu\r\nY29tPsLAXAQQAQgAEAUCUo4O2gkQ1/uT/N+/wjwAAN2cB/9gFRmAfvEQ2qz+\r\nWubmT2EsSSnjPMxzG4uyykFoa+TaZCWo2Xa2tQghmU103kEkQb1OEjRjpgwJ\r\nYX9Kghnl8DByM686L5AXnRyHP78qRJCLXSXl0AGicboUDp5sovaa4rswQceH\r\nvcdWgZ/mgHTRoiQeJddy9k+H6MPFiyFaVcFwegVsmpc+dCcC8yT+qh8ZIbyG\r\nRJU60PmKKN7LUusP+8DbSv39zCGJCBlVVKyA4MzdF5uM+sqTdXbKzOrT5DGd\r\nCZaox4s+w16Sq1rHzZKFWfQPfKLDB9pyA0ufCVRA3AF6BUi7G3ZqhZiHNhMP\r\nNvE45V/hS1PbZcfPVoUjE2qc1Ix1\r\n=7Wpe\r\n-----END PGP PUBLIC KEY BLOCK-----';
|
|
||||||
|
|
||||||
beforeEach(function(done) {
|
|
||||||
pgp.importKeys({
|
|
||||||
passphrase: passphrase,
|
|
||||||
privateKeyArmored: privkey,
|
|
||||||
publicKeyArmored: pubkey
|
|
||||||
}, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('Get KeyId', function() {
|
|
||||||
it('should work without param', function() {
|
|
||||||
var keyId = pgp.getKeyId();
|
|
||||||
expect(keyId).to.equal('F6F60E9B42CDFF4C');
|
|
||||||
});
|
|
||||||
it('should work with param', function() {
|
|
||||||
var keyId = pgp.getKeyId(pubkey);
|
|
||||||
expect(keyId).to.equal('F6F60E9B42CDFF4C');
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('Get Fingerprint', function() {
|
|
||||||
it('should work without param', function() {
|
|
||||||
var fingerprint = pgp.getFingerprint();
|
|
||||||
expect(fingerprint).to.equal('5856CEF789C3A307E8A1B976F6F60E9B42CDFF4C');
|
|
||||||
});
|
|
||||||
it('should work with param', function() {
|
|
||||||
var fingerprint = pgp.getFingerprint(pubkey);
|
|
||||||
expect(fingerprint).to.equal('5856CEF789C3A307E8A1B976F6F60E9B42CDFF4C');
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('getKeyParams', function() {
|
|
||||||
it('should work with param', function() {
|
|
||||||
var params = pgp.getKeyParams(pubkey);
|
|
||||||
expect(params.fingerprint).to.equal('5856CEF789C3A307E8A1B976F6F60E9B42CDFF4C');
|
|
||||||
expect(params._id).to.equal("F6F60E9B42CDFF4C");
|
|
||||||
expect(params.bitSize).to.equal(keySize);
|
|
||||||
expect(params.userId).to.equal("whiteout.test@t-online.de");
|
|
||||||
expect(params.userIds[0].name).to.equal("Whiteout User");
|
|
||||||
expect(params.userIds[0].emailAddress).to.equal("whiteout.test@t-online.de");
|
|
||||||
expect(params.algorithm).to.equal("rsa_encrypt_sign");
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work without param', function() {
|
|
||||||
var params = pgp.getKeyParams();
|
|
||||||
expect(params.fingerprint).to.equal('5856CEF789C3A307E8A1B976F6F60E9B42CDFF4C');
|
|
||||||
expect(params._id).to.equal("F6F60E9B42CDFF4C");
|
|
||||||
expect(params.bitSize).to.equal(keySize);
|
|
||||||
expect(params.userId).to.equal("whiteout.test@t-online.de");
|
|
||||||
expect(params.userIds[0].name).to.equal("Whiteout User");
|
|
||||||
expect(params.userIds[0].emailAddress).to.equal("whiteout.test@t-online.de");
|
|
||||||
expect(params.algorithm).to.equal("rsa_encrypt_sign");
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('extractPublicKey', function() {
|
|
||||||
it('should work', function() {
|
|
||||||
var pk = pgp.extractPublicKey(privkey);
|
|
||||||
expect(pk).to.exist;
|
|
||||||
expect(pk).to.contain('-----BEGIN PGP PUBLIC KEY BLOCK-----');
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('Encrypt and sign', function() {
|
|
||||||
it('should fail', function(done) {
|
|
||||||
var input = null;
|
|
||||||
|
|
||||||
pgp.encrypt(input, [pubkey], function(err, ct) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(ct).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should work', function(done) {
|
|
||||||
pgp.encrypt(message, [pubkey], function(err, ct) {
|
|
||||||
expect(err).to.not.exist;
|
expect(err).to.not.exist;
|
||||||
expect(ct).to.exist;
|
expect(ct).to.exist;
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should encrypt to myself if public keys are empty', function(done) {
|
|
||||||
pgp.encrypt(message, undefined, function(err, ct) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(ct).to.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('Decrypt and verify', function() {
|
pgp.decrypt(ct, keys.publicKeyArmored, function(err, pt, signValid) {
|
||||||
var ciphertext;
|
expect(err).to.not.exist;
|
||||||
|
expect(pt).to.equal('secret');
|
||||||
beforeEach(function(done) {
|
expect(signValid).to.be.true;
|
||||||
pgp.encrypt(message, [pubkey], function(err, ct) {
|
done();
|
||||||
expect(err).to.not.exist;
|
});
|
||||||
expect(ct).to.exist;
|
|
||||||
ciphertext = ct;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail', function(done) {
|
|
||||||
var input = 'asdfa\rsdf';
|
|
||||||
|
|
||||||
pgp.decrypt(input, pubkey, function(err, pt) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(pt).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should work', function(done) {
|
|
||||||
pgp.decrypt(ciphertext, pubkey, function(err, pt, signValid) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(pt).to.equal(message);
|
|
||||||
expect(signValid).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should work without signature', function(done) {
|
|
||||||
var ct = openpgp.encryptMessage([pgp._publicKey], message);
|
|
||||||
|
|
||||||
pgp.decrypt(ct, undefined, function(err, pt, signValid) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(pt).to.equal(message);
|
|
||||||
expect(signValid).to.be.undefined;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should fail to verify if public keys are empty', function(done) {
|
|
||||||
// setup another public key so that signature verification fails
|
|
||||||
pgp._publicKey = openpgp.key.readArmored(wrongPubkey).keys[0];
|
|
||||||
pgp.decrypt(ciphertext, undefined, function(err, pt, signValid) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(pt).to.equal(message);
|
|
||||||
expect(signValid).to.be.null;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should decrypt but signValid should be null for wrong public key', function(done) {
|
|
||||||
pgp.decrypt(ciphertext, wrongPubkey, function(err, pt, signValid) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(pt).to.equal(message);
|
|
||||||
expect(signValid).to.be.null;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('Verify clearsigned message', function() {
|
|
||||||
var clearsigned;
|
|
||||||
|
|
||||||
beforeEach(function() {
|
|
||||||
clearsigned = openpgp.signClearMessage(pgp._privateKey, 'this is a clearsigned message');
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
pgp.verifyClearSignedMessage(clearsigned, pubkey, function(err, signaturesValid) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(signaturesValid).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail', function(done) {
|
|
||||||
pgp.verifyClearSignedMessage(clearsigned.replace('clearsigned', 'invalid'), pubkey, function(err, signaturesValid) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(signaturesValid).to.be.false;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should be null for wrong public key', function(done) {
|
|
||||||
pgp.verifyClearSignedMessage(clearsigned, wrongPubkey, function(err, signaturesValid) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(signaturesValid).to.be.null;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('Verify detached signature', function() {
|
|
||||||
var signedMessage, signature;
|
|
||||||
|
|
||||||
beforeEach(function() {
|
|
||||||
signedMessage = 'this is a signed message';
|
|
||||||
var clearsigned = openpgp.signClearMessage(pgp._privateKey, signedMessage);
|
|
||||||
var signatureHeader = '-----BEGIN PGP SIGNATURE-----';
|
|
||||||
signature = signatureHeader + clearsigned.split(signatureHeader).pop();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
pgp.verifySignedMessage(signedMessage, signature, pubkey, function(err, signaturesValid) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(signaturesValid).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail', function(done) {
|
|
||||||
pgp.verifySignedMessage(signedMessage.replace('signed', 'invalid'), signature, pubkey, function(err, signaturesValid) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(signaturesValid).to.be.false;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
it('should be null for wrong public key', function(done) {
|
|
||||||
pgp.verifySignedMessage(signedMessage, signature, wrongPubkey, function(err, signaturesValid) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(signaturesValid).to.be.null;
|
|
||||||
done();
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe('Import/Export key pair', function() {
|
||||||
|
it('should fail', function(done) {
|
||||||
|
pgp.importKeys({
|
||||||
|
passphrase: 'asd',
|
||||||
|
privateKeyArmored: privkey,
|
||||||
|
publicKeyArmored: pubkey
|
||||||
|
}, function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(err.message).to.equal('Incorrect passphrase!');
|
||||||
|
|
||||||
|
pgp.exportKeys(function(err, keys) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(keys).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
it('should work', function(done) {
|
||||||
|
pgp.importKeys({
|
||||||
|
passphrase: passphrase,
|
||||||
|
privateKeyArmored: privkey,
|
||||||
|
publicKeyArmored: pubkey
|
||||||
|
}, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
|
||||||
|
pgp.exportKeys(function(err, keys) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(keys.keyId).to.equal(keyId);
|
||||||
|
expect(keys.privateKeyArmored.replace(/\r/g, '')).to.equal(privkey.replace(/\r/g, ''));
|
||||||
|
expect(keys.publicKeyArmored.replace(/\r/g, '')).to.equal(pubkey.replace(/\r/g, ''));
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('Change passphrase of private key', function() {
|
||||||
|
it('should work with new passphrase', function(done) {
|
||||||
|
pgp.changePassphrase({
|
||||||
|
privateKeyArmored: privkey,
|
||||||
|
oldPassphrase: passphrase,
|
||||||
|
newPassphrase: 'yxcv'
|
||||||
|
}, function(err, reEncryptedKey) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(reEncryptedKey).to.exist;
|
||||||
|
|
||||||
|
pgp.importKeys({
|
||||||
|
passphrase: 'yxcv',
|
||||||
|
privateKeyArmored: reEncryptedKey,
|
||||||
|
publicKeyArmored: pubkey
|
||||||
|
}, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
it('should work with empty passphrase', function(done) {
|
||||||
|
pgp.changePassphrase({
|
||||||
|
privateKeyArmored: privkey,
|
||||||
|
oldPassphrase: passphrase,
|
||||||
|
newPassphrase: undefined
|
||||||
|
}, function(err, reEncryptedKey) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(reEncryptedKey).to.exist;
|
||||||
|
|
||||||
|
pgp.importKeys({
|
||||||
|
passphrase: undefined,
|
||||||
|
privateKeyArmored: reEncryptedKey,
|
||||||
|
publicKeyArmored: pubkey
|
||||||
|
}, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
it('should fail when passphrases are equal', function(done) {
|
||||||
|
pgp.changePassphrase({
|
||||||
|
privateKeyArmored: privkey,
|
||||||
|
oldPassphrase: passphrase,
|
||||||
|
newPassphrase: passphrase
|
||||||
|
}, function(err, reEncryptedKey) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(reEncryptedKey).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
it('should fail when old passphrase is incorrect', function(done) {
|
||||||
|
pgp.changePassphrase({
|
||||||
|
privateKeyArmored: privkey,
|
||||||
|
oldPassphrase: 'asd',
|
||||||
|
newPassphrase: 'yxcv'
|
||||||
|
}, function(err, reEncryptedKey) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(reEncryptedKey).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('Encrypt/Sign/Decrypt/Verify', function() {
|
||||||
|
var message = 'asdfs\n\nThursday, Nov 21, 2013 7:38 PM asdf@example.com wrote:\n' +
|
||||||
|
'> asdf\n' +
|
||||||
|
'> \n' +
|
||||||
|
'> Thursday, Nov 21, 2013 7:32 PM asdf@example.com wrote:\n' +
|
||||||
|
'> > secret 3';
|
||||||
|
var wrongPubkey = '-----BEGIN PGP PUBLIC KEY BLOCK-----\r\nVersion: OpenPGP.js v.1.20131116\r\nComment: Whiteout Mail - http://whiteout.io\r\n\r\nxsBNBFKODs4BB/9iOF4THsjQMY+WEpT7ShgKxj4bHzRRaQkqczS4nZvP0U3g\r\nqeqCnbpagyeKXA+bhWFQW4GmXtgAoeD5PXs6AZYrw3tWNxLKu2Oe6Tp9K/XI\r\nxTMQ2wl4qZKDXHvuPsJ7cmgaWqpPyXtxA4zHHS3WrkI/6VzHAcI/y6x4szSB\r\nKgSuhI3hjh3s7TybUC1U6AfoQGx/S7e3WwlCOrK8GTClirN/2mCPRC5wuIft\r\nnkoMfA6jK8d2OPrJ63shy5cgwHOjQg/xuk46dNS7tkvGmbaa+X0PgqSKB+Hf\r\nYPPNS/ylg911DH9qa8BqYU2QpNh9jUKXSF+HbaOM+plWkCSAL7czV+R3ABEB\r\nAAHNLVdoaXRlb3V0IFVzZXIgPHNhZmV3aXRobWUudGVzdHVzZXJAZ21haWwu\r\nY29tPsLAXAQQAQgAEAUCUo4O2gkQ1/uT/N+/wjwAAN2cB/9gFRmAfvEQ2qz+\r\nWubmT2EsSSnjPMxzG4uyykFoa+TaZCWo2Xa2tQghmU103kEkQb1OEjRjpgwJ\r\nYX9Kghnl8DByM686L5AXnRyHP78qRJCLXSXl0AGicboUDp5sovaa4rswQceH\r\nvcdWgZ/mgHTRoiQeJddy9k+H6MPFiyFaVcFwegVsmpc+dCcC8yT+qh8ZIbyG\r\nRJU60PmKKN7LUusP+8DbSv39zCGJCBlVVKyA4MzdF5uM+sqTdXbKzOrT5DGd\r\nCZaox4s+w16Sq1rHzZKFWfQPfKLDB9pyA0ufCVRA3AF6BUi7G3ZqhZiHNhMP\r\nNvE45V/hS1PbZcfPVoUjE2qc1Ix1\r\n=7Wpe\r\n-----END PGP PUBLIC KEY BLOCK-----';
|
||||||
|
|
||||||
|
beforeEach(function(done) {
|
||||||
|
pgp.importKeys({
|
||||||
|
passphrase: passphrase,
|
||||||
|
privateKeyArmored: privkey,
|
||||||
|
publicKeyArmored: pubkey
|
||||||
|
}, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('Get KeyId', function() {
|
||||||
|
it('should work without param', function() {
|
||||||
|
var keyId = pgp.getKeyId();
|
||||||
|
expect(keyId).to.equal('F6F60E9B42CDFF4C');
|
||||||
|
});
|
||||||
|
it('should work with param', function() {
|
||||||
|
var keyId = pgp.getKeyId(pubkey);
|
||||||
|
expect(keyId).to.equal('F6F60E9B42CDFF4C');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('Get Fingerprint', function() {
|
||||||
|
it('should work without param', function() {
|
||||||
|
var fingerprint = pgp.getFingerprint();
|
||||||
|
expect(fingerprint).to.equal('5856CEF789C3A307E8A1B976F6F60E9B42CDFF4C');
|
||||||
|
});
|
||||||
|
it('should work with param', function() {
|
||||||
|
var fingerprint = pgp.getFingerprint(pubkey);
|
||||||
|
expect(fingerprint).to.equal('5856CEF789C3A307E8A1B976F6F60E9B42CDFF4C');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('getKeyParams', function() {
|
||||||
|
it('should work with param', function() {
|
||||||
|
var params = pgp.getKeyParams(pubkey);
|
||||||
|
expect(params.fingerprint).to.equal('5856CEF789C3A307E8A1B976F6F60E9B42CDFF4C');
|
||||||
|
expect(params._id).to.equal("F6F60E9B42CDFF4C");
|
||||||
|
expect(params.bitSize).to.equal(keySize);
|
||||||
|
expect(params.userId).to.equal("whiteout.test@t-online.de");
|
||||||
|
expect(params.userIds[0].name).to.equal("Whiteout User");
|
||||||
|
expect(params.userIds[0].emailAddress).to.equal("whiteout.test@t-online.de");
|
||||||
|
expect(params.algorithm).to.equal("rsa_encrypt_sign");
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work without param', function() {
|
||||||
|
var params = pgp.getKeyParams();
|
||||||
|
expect(params.fingerprint).to.equal('5856CEF789C3A307E8A1B976F6F60E9B42CDFF4C');
|
||||||
|
expect(params._id).to.equal("F6F60E9B42CDFF4C");
|
||||||
|
expect(params.bitSize).to.equal(keySize);
|
||||||
|
expect(params.userId).to.equal("whiteout.test@t-online.de");
|
||||||
|
expect(params.userIds[0].name).to.equal("Whiteout User");
|
||||||
|
expect(params.userIds[0].emailAddress).to.equal("whiteout.test@t-online.de");
|
||||||
|
expect(params.algorithm).to.equal("rsa_encrypt_sign");
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('extractPublicKey', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
var pk = pgp.extractPublicKey(privkey);
|
||||||
|
expect(pk).to.exist;
|
||||||
|
expect(pk).to.contain('-----BEGIN PGP PUBLIC KEY BLOCK-----');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('Encrypt and sign', function() {
|
||||||
|
it('should fail', function(done) {
|
||||||
|
var input = null;
|
||||||
|
|
||||||
|
pgp.encrypt(input, [pubkey], function(err, ct) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(ct).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
it('should work', function(done) {
|
||||||
|
pgp.encrypt(message, [pubkey], function(err, ct) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(ct).to.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
it('should encrypt to myself if public keys are empty', function(done) {
|
||||||
|
pgp.encrypt(message, undefined, function(err, ct) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(ct).to.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('Decrypt and verify', function() {
|
||||||
|
var ciphertext;
|
||||||
|
|
||||||
|
beforeEach(function(done) {
|
||||||
|
pgp.encrypt(message, [pubkey], function(err, ct) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(ct).to.exist;
|
||||||
|
ciphertext = ct;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail', function(done) {
|
||||||
|
var input = 'asdfa\rsdf';
|
||||||
|
|
||||||
|
pgp.decrypt(input, pubkey, function(err, pt) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(pt).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
it('should work', function(done) {
|
||||||
|
pgp.decrypt(ciphertext, pubkey, function(err, pt, signValid) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(pt).to.equal(message);
|
||||||
|
expect(signValid).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
it('should work without signature', function(done) {
|
||||||
|
var ct = openpgp.encryptMessage([pgp._publicKey], message);
|
||||||
|
|
||||||
|
pgp.decrypt(ct, undefined, function(err, pt, signValid) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(pt).to.equal(message);
|
||||||
|
expect(signValid).to.be.undefined;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
it('should fail to verify if public keys are empty', function(done) {
|
||||||
|
// setup another public key so that signature verification fails
|
||||||
|
pgp._publicKey = openpgp.key.readArmored(wrongPubkey).keys[0];
|
||||||
|
pgp.decrypt(ciphertext, undefined, function(err, pt, signValid) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(pt).to.equal(message);
|
||||||
|
expect(signValid).to.be.null;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
it('should decrypt but signValid should be null for wrong public key', function(done) {
|
||||||
|
pgp.decrypt(ciphertext, wrongPubkey, function(err, pt, signValid) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(pt).to.equal(message);
|
||||||
|
expect(signValid).to.be.null;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('Verify clearsigned message', function() {
|
||||||
|
var clearsigned;
|
||||||
|
|
||||||
|
beforeEach(function() {
|
||||||
|
clearsigned = openpgp.signClearMessage(pgp._privateKey, 'this is a clearsigned message');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
pgp.verifyClearSignedMessage(clearsigned, pubkey, function(err, signaturesValid) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(signaturesValid).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail', function(done) {
|
||||||
|
pgp.verifyClearSignedMessage(clearsigned.replace('clearsigned', 'invalid'), pubkey, function(err, signaturesValid) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(signaturesValid).to.be.false;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
it('should be null for wrong public key', function(done) {
|
||||||
|
pgp.verifyClearSignedMessage(clearsigned, wrongPubkey, function(err, signaturesValid) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(signaturesValid).to.be.null;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('Verify detached signature', function() {
|
||||||
|
var signedMessage, signature;
|
||||||
|
|
||||||
|
beforeEach(function() {
|
||||||
|
signedMessage = 'this is a signed message';
|
||||||
|
var clearsigned = openpgp.signClearMessage(pgp._privateKey, signedMessage);
|
||||||
|
var signatureHeader = '-----BEGIN PGP SIGNATURE-----';
|
||||||
|
signature = signatureHeader + clearsigned.split(signatureHeader).pop();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
pgp.verifySignedMessage(signedMessage, signature, pubkey, function(err, signaturesValid) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(signaturesValid).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail', function(done) {
|
||||||
|
pgp.verifySignedMessage(signedMessage.replace('signed', 'invalid'), signature, pubkey, function(err, signaturesValid) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(signaturesValid).to.be.false;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
it('should be null for wrong public key', function(done) {
|
||||||
|
pgp.verifySignedMessage(signedMessage, signature, wrongPubkey, function(err, signaturesValid) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(signaturesValid).to.be.null;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
@ -1,226 +1,222 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var RestDAO = require('js/dao/rest-dao'),
|
var RestDAO = require('../../src/js/dao/rest-dao'),
|
||||||
PrivateKeyDAO = require('js/dao/privatekey-dao'),
|
PrivateKeyDAO = require('../../src/js/dao/privatekey-dao');
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
describe('Private Key DAO unit tests', function() {
|
describe('Private Key DAO unit tests', function() {
|
||||||
|
|
||||||
var privkeyDao, restDaoStub,
|
var privkeyDao, restDaoStub,
|
||||||
emailAddress = 'test@example.com',
|
emailAddress = 'test@example.com',
|
||||||
deviceName = 'iPhone Work';
|
deviceName = 'iPhone Work';
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
restDaoStub = sinon.createStubInstance(RestDAO);
|
restDaoStub = sinon.createStubInstance(RestDAO);
|
||||||
privkeyDao = new PrivateKeyDAO(restDaoStub);
|
privkeyDao = new PrivateKeyDAO(restDaoStub);
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {});
|
afterEach(function() {});
|
||||||
|
|
||||||
describe('requestDeviceRegistration', function() {
|
describe('requestDeviceRegistration', function() {
|
||||||
it('should fail due to invalid args', function(done) {
|
it('should fail due to invalid args', function(done) {
|
||||||
privkeyDao.requestDeviceRegistration({}, function(err, sessionKey) {
|
privkeyDao.requestDeviceRegistration({}, function(err, sessionKey) {
|
||||||
expect(err).to.exist;
|
expect(err).to.exist;
|
||||||
expect(sessionKey).to.not.exist;
|
expect(sessionKey).to.not.exist;
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
restDaoStub.post.yields(null, {
|
|
||||||
encryptedRegSessionKey: 'asdf'
|
|
||||||
});
|
|
||||||
|
|
||||||
privkeyDao.requestDeviceRegistration({
|
|
||||||
userId: emailAddress,
|
|
||||||
deviceName: deviceName
|
|
||||||
}, function(err, sessionKey) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(sessionKey).to.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('uploadDeviceSecret', function() {
|
it('should work', function(done) {
|
||||||
it('should fail due to invalid args', function(done) {
|
restDaoStub.post.yields(null, {
|
||||||
privkeyDao.uploadDeviceSecret({}, function(err) {
|
encryptedRegSessionKey: 'asdf'
|
||||||
expect(err).to.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should work', function(done) {
|
privkeyDao.requestDeviceRegistration({
|
||||||
restDaoStub.put.yields();
|
userId: emailAddress,
|
||||||
|
deviceName: deviceName
|
||||||
|
}, function(err, sessionKey) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(sessionKey).to.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
privkeyDao.uploadDeviceSecret({
|
describe('uploadDeviceSecret', function() {
|
||||||
userId: emailAddress,
|
it('should fail due to invalid args', function(done) {
|
||||||
deviceName: deviceName,
|
privkeyDao.uploadDeviceSecret({}, function(err) {
|
||||||
encryptedDeviceSecret: 'asdf',
|
expect(err).to.exist;
|
||||||
iv: 'iv'
|
done();
|
||||||
}, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('requestAuthSessionKey', function() {
|
it('should work', function(done) {
|
||||||
it('should fail due to invalid args', function(done) {
|
restDaoStub.put.yields();
|
||||||
privkeyDao.requestAuthSessionKey({}, function(err) {
|
|
||||||
expect(err).to.exist;
|
privkeyDao.uploadDeviceSecret({
|
||||||
done();
|
userId: emailAddress,
|
||||||
});
|
deviceName: deviceName,
|
||||||
|
encryptedDeviceSecret: 'asdf',
|
||||||
|
iv: 'iv'
|
||||||
|
}, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should work', function(done) {
|
describe('requestAuthSessionKey', function() {
|
||||||
restDaoStub.post.withArgs(undefined, '/auth/user/' + emailAddress).yields();
|
it('should fail due to invalid args', function(done) {
|
||||||
|
privkeyDao.requestAuthSessionKey({}, function(err) {
|
||||||
privkeyDao.requestAuthSessionKey({
|
expect(err).to.exist;
|
||||||
userId: emailAddress
|
done();
|
||||||
}, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('verifyAuthentication', function() {
|
it('should work', function(done) {
|
||||||
it('should fail due to invalid args', function(done) {
|
restDaoStub.post.withArgs(undefined, '/auth/user/' + emailAddress).yields();
|
||||||
privkeyDao.verifyAuthentication({}, function(err) {
|
|
||||||
expect(err).to.exist;
|
privkeyDao.requestAuthSessionKey({
|
||||||
done();
|
userId: emailAddress
|
||||||
});
|
}, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should work', function(done) {
|
describe('verifyAuthentication', function() {
|
||||||
var sessionId = '1';
|
it('should fail due to invalid args', function(done) {
|
||||||
|
privkeyDao.verifyAuthentication({}, function(err) {
|
||||||
var options = {
|
expect(err).to.exist;
|
||||||
userId: emailAddress,
|
done();
|
||||||
sessionId: sessionId,
|
|
||||||
encryptedChallenge: 'asdf',
|
|
||||||
encryptedDeviceSecret: 'qwer',
|
|
||||||
iv: ' iv'
|
|
||||||
};
|
|
||||||
|
|
||||||
restDaoStub.put.withArgs(options, '/auth/user/' + emailAddress + '/session/' + sessionId).yields();
|
|
||||||
|
|
||||||
privkeyDao.verifyAuthentication(options, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('upload', function() {
|
it('should work', function(done) {
|
||||||
it('should fail due to invalid args', function(done) {
|
var sessionId = '1';
|
||||||
privkeyDao.upload({}, function(err) {
|
|
||||||
expect(err).to.exist;
|
var options = {
|
||||||
done();
|
userId: emailAddress,
|
||||||
});
|
sessionId: sessionId,
|
||||||
|
encryptedChallenge: 'asdf',
|
||||||
|
encryptedDeviceSecret: 'qwer',
|
||||||
|
iv: ' iv'
|
||||||
|
};
|
||||||
|
|
||||||
|
restDaoStub.put.withArgs(options, '/auth/user/' + emailAddress + '/session/' + sessionId).yields();
|
||||||
|
|
||||||
|
privkeyDao.verifyAuthentication(options, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should work', function(done) {
|
describe('upload', function() {
|
||||||
var options = {
|
it('should fail due to invalid args', function(done) {
|
||||||
_id: '12345',
|
privkeyDao.upload({}, function(err) {
|
||||||
userId: emailAddress,
|
expect(err).to.exist;
|
||||||
encryptedPrivateKey: 'asdf',
|
done();
|
||||||
sessionId: '1',
|
|
||||||
salt: 'salt',
|
|
||||||
iv: 'iv'
|
|
||||||
};
|
|
||||||
|
|
||||||
restDaoStub.post.withArgs(options, '/privatekey/user/' + emailAddress + '/session/' + options.sessionId).yields();
|
|
||||||
|
|
||||||
privkeyDao.upload(options, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('requestDownload', function() {
|
it('should work', function(done) {
|
||||||
it('should fail due to invalid args', function(done) {
|
var options = {
|
||||||
privkeyDao.requestDownload({}, function(err) {
|
_id: '12345',
|
||||||
expect(err).to.exist;
|
userId: emailAddress,
|
||||||
done();
|
encryptedPrivateKey: 'asdf',
|
||||||
});
|
sessionId: '1',
|
||||||
|
salt: 'salt',
|
||||||
|
iv: 'iv'
|
||||||
|
};
|
||||||
|
|
||||||
|
restDaoStub.post.withArgs(options, '/privatekey/user/' + emailAddress + '/session/' + options.sessionId).yields();
|
||||||
|
|
||||||
|
privkeyDao.upload(options, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should work', function(done) {
|
describe('requestDownload', function() {
|
||||||
var keyId = '12345';
|
it('should fail due to invalid args', function(done) {
|
||||||
|
privkeyDao.requestDownload({}, function(err) {
|
||||||
restDaoStub.get.withArgs({
|
expect(err).to.exist;
|
||||||
uri: '/privatekey/user/' + emailAddress + '/key/' + keyId
|
done();
|
||||||
}).yields();
|
|
||||||
|
|
||||||
privkeyDao.requestDownload({
|
|
||||||
userId: emailAddress,
|
|
||||||
keyId: keyId
|
|
||||||
}, function(err, found) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(found).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('hasPrivateKey', function() {
|
it('should work', function(done) {
|
||||||
it('should fail due to invalid args', function(done) {
|
var keyId = '12345';
|
||||||
privkeyDao.hasPrivateKey({}, function(err) {
|
|
||||||
expect(err).to.exist;
|
restDaoStub.get.withArgs({
|
||||||
done();
|
uri: '/privatekey/user/' + emailAddress + '/key/' + keyId
|
||||||
});
|
}).yields();
|
||||||
|
|
||||||
|
privkeyDao.requestDownload({
|
||||||
|
userId: emailAddress,
|
||||||
|
keyId: keyId
|
||||||
|
}, function(err, found) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(found).to.be.true;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should work', function(done) {
|
describe('hasPrivateKey', function() {
|
||||||
var keyId = '12345';
|
it('should fail due to invalid args', function(done) {
|
||||||
|
privkeyDao.hasPrivateKey({}, function(err) {
|
||||||
restDaoStub.get.withArgs({
|
expect(err).to.exist;
|
||||||
uri: '/privatekey/user/' + emailAddress + '/key/' + keyId + '?ignoreRecovery=true'
|
done();
|
||||||
}).yields();
|
|
||||||
|
|
||||||
privkeyDao.hasPrivateKey({
|
|
||||||
userId: emailAddress,
|
|
||||||
keyId: keyId
|
|
||||||
}, function(err, found) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(found).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('download', function() {
|
it('should work', function(done) {
|
||||||
it('should fail due to invalid args', function(done) {
|
var keyId = '12345';
|
||||||
privkeyDao.download({}, function(err) {
|
|
||||||
expect(err).to.exist;
|
restDaoStub.get.withArgs({
|
||||||
done();
|
uri: '/privatekey/user/' + emailAddress + '/key/' + keyId + '?ignoreRecovery=true'
|
||||||
});
|
}).yields();
|
||||||
|
|
||||||
|
privkeyDao.hasPrivateKey({
|
||||||
|
userId: emailAddress,
|
||||||
|
keyId: keyId
|
||||||
|
}, function(err, found) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(found).to.be.true;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should work', function(done) {
|
describe('download', function() {
|
||||||
var key = {
|
it('should fail due to invalid args', function(done) {
|
||||||
_id: '12345'
|
privkeyDao.download({}, function(err) {
|
||||||
};
|
expect(err).to.exist;
|
||||||
|
done();
|
||||||
restDaoStub.get.withArgs({
|
|
||||||
uri: '/privatekey/user/' + emailAddress + '/key/' + key._id + '/recovery/token'
|
|
||||||
}).yields();
|
|
||||||
|
|
||||||
privkeyDao.download({
|
|
||||||
userId: emailAddress,
|
|
||||||
keyId: key._id,
|
|
||||||
recoveryToken: 'token'
|
|
||||||
}, function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
var key = {
|
||||||
|
_id: '12345'
|
||||||
|
};
|
||||||
|
|
||||||
|
restDaoStub.get.withArgs({
|
||||||
|
uri: '/privatekey/user/' + emailAddress + '/key/' + key._id + '/recovery/token'
|
||||||
|
}).yields();
|
||||||
|
|
||||||
|
privkeyDao.download({
|
||||||
|
userId: emailAddress,
|
||||||
|
keyId: key._id,
|
||||||
|
recoveryToken: 'token'
|
||||||
|
}, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
});
|
});
|
@ -1,286 +1,281 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
PrivateKeyUploadCtrl = require('../../src/js/controller/privatekey-upload'),
|
||||||
mocks = require('angularMocks'),
|
appController = require('../../src/js/app-controller'),
|
||||||
PrivateKeyUploadCtrl = require('js/controller/privatekey-upload'),
|
KeychainDAO = require('../../src/js/dao/keychain-dao'),
|
||||||
appController = require('js/app-controller'),
|
PGP = require('../../src/js/crypto/pgp');
|
||||||
KeychainDAO = require('js/dao/keychain-dao'),
|
|
||||||
PGP = require('js/crypto/pgp');
|
|
||||||
|
|
||||||
describe('Private Key Upload Controller unit test', function() {
|
describe('Private Key Upload Controller unit test', function() {
|
||||||
var scope, location, ctrl,
|
var scope, location, ctrl,
|
||||||
origEmailDao, emailDaoMock,
|
origEmailDao, emailDaoMock,
|
||||||
origKeychain, keychainMock,
|
origKeychain, keychainMock,
|
||||||
pgpStub,
|
pgpStub,
|
||||||
emailAddress = 'fred@foo.com';
|
emailAddress = 'fred@foo.com';
|
||||||
|
|
||||||
beforeEach(function(done) {
|
beforeEach(function(done) {
|
||||||
// remember original module to restore later, then replace it
|
// remember original module to restore later, then replace it
|
||||||
origEmailDao = appController._emailDao;
|
origEmailDao = appController._emailDao;
|
||||||
appController._emailDao = emailDaoMock = {
|
appController._emailDao = emailDaoMock = {
|
||||||
_account: {
|
_account: {
|
||||||
emailAddress: emailAddress
|
emailAddress: emailAddress
|
||||||
}
|
}
|
||||||
|
};
|
||||||
|
origKeychain = appController._keychain;
|
||||||
|
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
||||||
|
keychainMock._pgp = pgpStub = sinon.createStubInstance(PGP);
|
||||||
|
|
||||||
|
angular.module('login-privatekey-download-test', []);
|
||||||
|
mocks.module('login-privatekey-download-test');
|
||||||
|
mocks.inject(function($controller, $rootScope) {
|
||||||
|
scope = $rootScope.$new();
|
||||||
|
scope.state = {};
|
||||||
|
ctrl = $controller(PrivateKeyUploadCtrl, {
|
||||||
|
$location: location,
|
||||||
|
$scope: scope
|
||||||
|
});
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
// restore the app controller module
|
||||||
|
appController._keychain = origKeychain;
|
||||||
|
appController._emailDao = origEmailDao;
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('checkServerForKey', function() {
|
||||||
|
var keyParams = {
|
||||||
|
userId: emailAddress,
|
||||||
|
_id: 'keyId',
|
||||||
|
};
|
||||||
|
|
||||||
|
it('should fail', function(done) {
|
||||||
|
pgpStub.getKeyParams.returns(keyParams);
|
||||||
|
keychainMock.hasPrivateKey.yields(42);
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(keychainMock.hasPrivateKey.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
};
|
};
|
||||||
origKeychain = appController._keychain;
|
|
||||||
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
|
||||||
keychainMock._pgp = pgpStub = sinon.createStubInstance(PGP);
|
|
||||||
|
|
||||||
angular.module('login-privatekey-download-test', []);
|
scope.checkServerForKey();
|
||||||
mocks.module('login-privatekey-download-test');
|
});
|
||||||
mocks.inject(function($controller, $rootScope) {
|
|
||||||
scope = $rootScope.$new();
|
it('should return true', function(done) {
|
||||||
scope.state = {};
|
pgpStub.getKeyParams.returns(keyParams);
|
||||||
ctrl = $controller(PrivateKeyUploadCtrl, {
|
keychainMock.hasPrivateKey.withArgs({
|
||||||
$location: location,
|
userId: keyParams.userId,
|
||||||
$scope: scope
|
keyId: keyParams._id
|
||||||
});
|
}).yields(null, true);
|
||||||
|
|
||||||
|
scope.checkServerForKey(function(privateKeySynced) {
|
||||||
|
expect(privateKeySynced).to.be.true;
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
it('should return undefined', function(done) {
|
||||||
// restore the app controller module
|
pgpStub.getKeyParams.returns(keyParams);
|
||||||
appController._keychain = origKeychain;
|
keychainMock.hasPrivateKey.withArgs({
|
||||||
appController._emailDao = origEmailDao;
|
userId: keyParams.userId,
|
||||||
|
keyId: keyParams._id
|
||||||
|
}).yields(null, false);
|
||||||
|
|
||||||
|
scope.checkServerForKey(function(privateKeySynced) {
|
||||||
|
expect(privateKeySynced).to.be.undefined;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('handlePaste', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
scope.handlePaste({
|
||||||
|
clipboardData: {
|
||||||
|
getData: function(val) {
|
||||||
|
expect(val).to.equal('text/plain');
|
||||||
|
return '1qaz-2wsx-3edc-4rfv-5tgb-6yhn';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(scope.code0).to.equal('1qaz');
|
||||||
|
expect(scope.code1).to.equal('2wsx');
|
||||||
|
expect(scope.code2).to.equal('3edc');
|
||||||
|
expect(scope.code3).to.equal('4rfv');
|
||||||
|
expect(scope.code4).to.equal('5tgb');
|
||||||
|
expect(scope.code5).to.equal('6yhn');
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('displayUploadUi', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
// add some artifacts from a previous key input
|
||||||
|
scope.code0 = scope.code1 = scope.code2 = scope.code3 = scope.code4 = scope.code5 = 'asdasd';
|
||||||
|
|
||||||
|
scope.displayUploadUi();
|
||||||
|
expect(scope.step).to.equal(1);
|
||||||
|
expect(scope.code.length).to.equal(24);
|
||||||
|
|
||||||
|
// artifacts should be cleared
|
||||||
|
expect(scope.code0).to.be.empty;
|
||||||
|
expect(scope.code1).to.be.empty;
|
||||||
|
expect(scope.code2).to.be.empty;
|
||||||
|
expect(scope.code3).to.be.empty;
|
||||||
|
expect(scope.code4).to.be.empty;
|
||||||
|
expect(scope.code5).to.be.empty;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('verifyCode', function() {
|
||||||
|
it('should fail for wrong code', function() {
|
||||||
|
scope.code0 = 'b';
|
||||||
|
scope.code1 = 'b';
|
||||||
|
scope.code2 = 'b';
|
||||||
|
scope.code3 = 'b';
|
||||||
|
scope.code4 = 'b';
|
||||||
|
scope.code5 = 'b';
|
||||||
|
scope.code = 'aaaaaa';
|
||||||
|
|
||||||
|
scope.onError = function() {};
|
||||||
|
expect(scope.verifyCode()).to.be.false;
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('checkServerForKey', function() {
|
it('should work', function() {
|
||||||
var keyParams = {
|
scope.code0 = 'a';
|
||||||
userId: emailAddress,
|
scope.code1 = 'a';
|
||||||
_id: 'keyId',
|
scope.code2 = 'a';
|
||||||
|
scope.code3 = 'a';
|
||||||
|
scope.code4 = 'a';
|
||||||
|
scope.code5 = 'a';
|
||||||
|
scope.code = 'aaaaaa';
|
||||||
|
|
||||||
|
scope.onError = function() {};
|
||||||
|
expect(scope.verifyCode()).to.be.false;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('setDeviceName', function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
keychainMock.setDeviceName.yields();
|
||||||
|
scope.setDeviceName(done);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('encryptAndUploadKey', function() {
|
||||||
|
it('should fail due to keychain.registerDevice', function(done) {
|
||||||
|
keychainMock.registerDevice.yields(42);
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(keychainMock.registerDevice.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
};
|
};
|
||||||
|
|
||||||
it('should fail', function(done) {
|
scope.encryptAndUploadKey();
|
||||||
pgpStub.getKeyParams.returns(keyParams);
|
|
||||||
keychainMock.hasPrivateKey.yields(42);
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(keychainMock.hasPrivateKey.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.checkServerForKey();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should return true', function(done) {
|
|
||||||
pgpStub.getKeyParams.returns(keyParams);
|
|
||||||
keychainMock.hasPrivateKey.withArgs({
|
|
||||||
userId: keyParams.userId,
|
|
||||||
keyId: keyParams._id
|
|
||||||
}).yields(null, true);
|
|
||||||
|
|
||||||
scope.checkServerForKey(function(privateKeySynced) {
|
|
||||||
expect(privateKeySynced).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should return undefined', function(done) {
|
|
||||||
pgpStub.getKeyParams.returns(keyParams);
|
|
||||||
keychainMock.hasPrivateKey.withArgs({
|
|
||||||
userId: keyParams.userId,
|
|
||||||
keyId: keyParams._id
|
|
||||||
}).yields(null, false);
|
|
||||||
|
|
||||||
scope.checkServerForKey(function(privateKeySynced) {
|
|
||||||
expect(privateKeySynced).to.be.undefined;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('handlePaste', function() {
|
it('should work', function(done) {
|
||||||
it('should work', function() {
|
keychainMock.registerDevice.yields();
|
||||||
scope.handlePaste({
|
keychainMock.uploadPrivateKey.yields();
|
||||||
clipboardData: {
|
|
||||||
getData: function(val) {
|
|
||||||
expect(val).to.equal('text/plain');
|
|
||||||
return '1qaz-2wsx-3edc-4rfv-5tgb-6yhn';
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
expect(scope.code0).to.equal('1qaz');
|
scope.encryptAndUploadKey(function(err) {
|
||||||
expect(scope.code1).to.equal('2wsx');
|
expect(err).to.not.exist;
|
||||||
expect(scope.code2).to.equal('3edc');
|
expect(keychainMock.registerDevice.calledOnce).to.be.true;
|
||||||
expect(scope.code3).to.equal('4rfv');
|
expect(keychainMock.uploadPrivateKey.calledOnce).to.be.true;
|
||||||
expect(scope.code4).to.equal('5tgb');
|
done();
|
||||||
expect(scope.code5).to.equal('6yhn');
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe('displayUploadUi', function() {
|
describe('goBack', function() {
|
||||||
it('should work', function() {
|
it('should work', function() {
|
||||||
// add some artifacts from a previous key input
|
scope.step = 2;
|
||||||
scope.code0 = scope.code1 = scope.code2 = scope.code3 = scope.code4 = scope.code5 = 'asdasd';
|
scope.goBack();
|
||||||
|
expect(scope.step).to.equal(1);
|
||||||
scope.displayUploadUi();
|
|
||||||
expect(scope.step).to.equal(1);
|
|
||||||
expect(scope.code.length).to.equal(24);
|
|
||||||
|
|
||||||
// artifacts should be cleared
|
|
||||||
expect(scope.code0).to.be.empty;
|
|
||||||
expect(scope.code1).to.be.empty;
|
|
||||||
expect(scope.code2).to.be.empty;
|
|
||||||
expect(scope.code3).to.be.empty;
|
|
||||||
expect(scope.code4).to.be.empty;
|
|
||||||
expect(scope.code5).to.be.empty;
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('verifyCode', function() {
|
it('should not work for < 2', function() {
|
||||||
it('should fail for wrong code', function() {
|
scope.step = 1;
|
||||||
scope.code0 = 'b';
|
scope.goBack();
|
||||||
scope.code1 = 'b';
|
expect(scope.step).to.equal(1);
|
||||||
scope.code2 = 'b';
|
});
|
||||||
scope.code3 = 'b';
|
});
|
||||||
scope.code4 = 'b';
|
|
||||||
scope.code5 = 'b';
|
|
||||||
scope.code = 'aaaaaa';
|
|
||||||
|
|
||||||
scope.onError = function() {};
|
describe('goForward', function() {
|
||||||
expect(scope.verifyCode()).to.be.false;
|
var verifyCodeStub, setDeviceNameStub, encryptAndUploadKeyStub;
|
||||||
});
|
beforeEach(function() {
|
||||||
|
verifyCodeStub = sinon.stub(scope, 'verifyCode');
|
||||||
it('should work', function() {
|
setDeviceNameStub = sinon.stub(scope, 'setDeviceName');
|
||||||
scope.code0 = 'a';
|
encryptAndUploadKeyStub = sinon.stub(scope, 'encryptAndUploadKey');
|
||||||
scope.code1 = 'a';
|
});
|
||||||
scope.code2 = 'a';
|
afterEach(function() {
|
||||||
scope.code3 = 'a';
|
verifyCodeStub.restore();
|
||||||
scope.code4 = 'a';
|
setDeviceNameStub.restore();
|
||||||
scope.code5 = 'a';
|
encryptAndUploadKeyStub.restore();
|
||||||
scope.code = 'aaaaaa';
|
|
||||||
|
|
||||||
scope.onError = function() {};
|
|
||||||
expect(scope.verifyCode()).to.be.false;
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('setDeviceName', function() {
|
it('should work for < 2', function() {
|
||||||
it('should work', function(done) {
|
scope.step = 1;
|
||||||
keychainMock.setDeviceName.yields();
|
scope.goForward();
|
||||||
scope.setDeviceName(done);
|
expect(scope.step).to.equal(2);
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('encryptAndUploadKey', function() {
|
it('should work for 2', function() {
|
||||||
it('should fail due to keychain.registerDevice', function(done) {
|
verifyCodeStub.returns(true);
|
||||||
keychainMock.registerDevice.yields(42);
|
scope.step = 2;
|
||||||
|
scope.goForward();
|
||||||
scope.onError = function(err) {
|
expect(scope.step).to.equal(3);
|
||||||
expect(err).to.exist;
|
|
||||||
expect(keychainMock.registerDevice.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.encryptAndUploadKey();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
keychainMock.registerDevice.yields();
|
|
||||||
keychainMock.uploadPrivateKey.yields();
|
|
||||||
|
|
||||||
scope.encryptAndUploadKey(function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(keychainMock.registerDevice.calledOnce).to.be.true;
|
|
||||||
expect(keychainMock.uploadPrivateKey.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('goBack', function() {
|
it('should not work for 2 when code invalid', function() {
|
||||||
it('should work', function() {
|
verifyCodeStub.returns(false);
|
||||||
scope.step = 2;
|
scope.step = 2;
|
||||||
scope.goBack();
|
scope.goForward();
|
||||||
expect(scope.step).to.equal(1);
|
expect(scope.step).to.equal(2);
|
||||||
});
|
|
||||||
|
|
||||||
it('should not work for < 2', function() {
|
|
||||||
scope.step = 1;
|
|
||||||
scope.goBack();
|
|
||||||
expect(scope.step).to.equal(1);
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('goForward', function() {
|
it('should fail for 3 due to error in setDeviceName', function(done) {
|
||||||
var verifyCodeStub, setDeviceNameStub, encryptAndUploadKeyStub;
|
scope.step = 3;
|
||||||
beforeEach(function() {
|
setDeviceNameStub.yields(42);
|
||||||
verifyCodeStub = sinon.stub(scope, 'verifyCode');
|
|
||||||
setDeviceNameStub = sinon.stub(scope, 'setDeviceName');
|
|
||||||
encryptAndUploadKeyStub = sinon.stub(scope, 'encryptAndUploadKey');
|
|
||||||
});
|
|
||||||
afterEach(function() {
|
|
||||||
verifyCodeStub.restore();
|
|
||||||
setDeviceNameStub.restore();
|
|
||||||
encryptAndUploadKeyStub.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work for < 2', function() {
|
scope.onError = function(err) {
|
||||||
scope.step = 1;
|
expect(err).to.exist;
|
||||||
scope.goForward();
|
|
||||||
expect(scope.step).to.equal(2);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work for 2', function() {
|
|
||||||
verifyCodeStub.returns(true);
|
|
||||||
scope.step = 2;
|
|
||||||
scope.goForward();
|
|
||||||
expect(scope.step).to.equal(3);
|
expect(scope.step).to.equal(3);
|
||||||
});
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
it('should not work for 2 when code invalid', function() {
|
scope.goForward();
|
||||||
verifyCodeStub.returns(false);
|
|
||||||
scope.step = 2;
|
|
||||||
scope.goForward();
|
|
||||||
expect(scope.step).to.equal(2);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail for 3 due to error in setDeviceName', function(done) {
|
|
||||||
scope.step = 3;
|
|
||||||
setDeviceNameStub.yields(42);
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(scope.step).to.equal(3);
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.goForward();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail for 3 due to error in encryptAndUploadKey', function(done) {
|
|
||||||
scope.step = 3;
|
|
||||||
setDeviceNameStub.yields();
|
|
||||||
encryptAndUploadKeyStub.yields(42);
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(scope.step).to.equal(4);
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.goForward();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work for 3', function(done) {
|
|
||||||
scope.step = 3;
|
|
||||||
setDeviceNameStub.yields();
|
|
||||||
encryptAndUploadKeyStub.yields();
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err.title).to.equal('Success');
|
|
||||||
expect(scope.step).to.equal(4);
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.goForward();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should fail for 3 due to error in encryptAndUploadKey', function(done) {
|
||||||
|
scope.step = 3;
|
||||||
|
setDeviceNameStub.yields();
|
||||||
|
encryptAndUploadKeyStub.yields(42);
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(scope.step).to.equal(4);
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.goForward();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work for 3', function(done) {
|
||||||
|
scope.step = 3;
|
||||||
|
setDeviceNameStub.yields();
|
||||||
|
encryptAndUploadKeyStub.yields();
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err.title).to.equal('Success');
|
||||||
|
expect(scope.step).to.equal(4);
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.goForward();
|
||||||
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
@ -1,165 +1,161 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var RestDAO = require('js/dao/rest-dao'),
|
var RestDAO = require('../../src/js/dao/rest-dao'),
|
||||||
PublicKeyDAO = require('js/dao/publickey-dao'),
|
PublicKeyDAO = require('../../src/js/dao/publickey-dao');
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
describe('Public Key DAO unit tests', function() {
|
describe('Public Key DAO unit tests', function() {
|
||||||
|
|
||||||
var pubkeyDao, restDaoStub;
|
var pubkeyDao, restDaoStub;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
restDaoStub = sinon.createStubInstance(RestDAO);
|
restDaoStub = sinon.createStubInstance(RestDAO);
|
||||||
pubkeyDao = new PublicKeyDAO(restDaoStub);
|
pubkeyDao = new PublicKeyDAO(restDaoStub);
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {});
|
afterEach(function() {});
|
||||||
|
|
||||||
describe('get', function() {
|
describe('get', function() {
|
||||||
it('should fail', function(done) {
|
it('should fail', function(done) {
|
||||||
restDaoStub.get.yields(42);
|
restDaoStub.get.yields(42);
|
||||||
|
|
||||||
pubkeyDao.get('id', function(err, key) {
|
pubkeyDao.get('id', function(err, key) {
|
||||||
expect(err).to.exist;
|
expect(err).to.exist;
|
||||||
expect(key).to.not.exist;
|
expect(key).to.not.exist;
|
||||||
expect(restDaoStub.get.calledOnce).to.be.true;
|
expect(restDaoStub.get.calledOnce).to.be.true;
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
restDaoStub.get.yields(null, {
|
|
||||||
_id: '12345',
|
|
||||||
publicKey: 'asdf'
|
|
||||||
});
|
|
||||||
|
|
||||||
pubkeyDao.get('id', function(err, key) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(key).to.exist;
|
|
||||||
expect(key._id).to.exist;
|
|
||||||
expect(key.publicKey).to.exist;
|
|
||||||
expect(restDaoStub.get.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('verify', function() {
|
it('should work', function(done) {
|
||||||
it('should fail', function(done) {
|
restDaoStub.get.yields(null, {
|
||||||
restDaoStub.get.yields(42);
|
_id: '12345',
|
||||||
|
publicKey: 'asdf'
|
||||||
pubkeyDao.verify('id', function(err) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should not error for 400', function(done) {
|
pubkeyDao.get('id', function(err, key) {
|
||||||
restDaoStub.get.yields({
|
expect(err).to.not.exist;
|
||||||
code: 400
|
expect(key).to.exist;
|
||||||
});
|
expect(key._id).to.exist;
|
||||||
|
expect(key.publicKey).to.exist;
|
||||||
pubkeyDao.verify('id', function(err) {
|
expect(restDaoStub.get.calledOnce).to.be.true;
|
||||||
expect(err).to.not.exist;
|
done();
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should work', function(done) {
|
describe('verify', function() {
|
||||||
var uuid = 'c621e328-8548-40a1-8309-adf1955e98a9';
|
it('should fail', function(done) {
|
||||||
restDaoStub.get.yields(null);
|
restDaoStub.get.yields(42);
|
||||||
|
|
||||||
pubkeyDao.verify(uuid, function(err) {
|
pubkeyDao.verify('id', function(err) {
|
||||||
expect(err).to.not.exist;
|
expect(err).to.exist;
|
||||||
expect(restDaoStub.get.calledWith(sinon.match(function(arg){
|
done();
|
||||||
return arg.uri === '/verify/' + uuid && arg.type === 'text';
|
|
||||||
}))).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('get by userId', function() {
|
it('should not error for 400', function(done) {
|
||||||
it('should fail', function(done) {
|
restDaoStub.get.yields({
|
||||||
restDaoStub.get.yields(42);
|
code: 400
|
||||||
|
|
||||||
pubkeyDao.getByUserId('userId', function(err, key) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(key).to.not.exist;
|
|
||||||
expect(restDaoStub.get.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should react to 404', function(done) {
|
pubkeyDao.verify('id', function(err) {
|
||||||
restDaoStub.get.yields({
|
expect(err).to.not.exist;
|
||||||
code: 404
|
done();
|
||||||
});
|
|
||||||
|
|
||||||
pubkeyDao.getByUserId('userId', function(err, key) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(key).to.not.exist;
|
|
||||||
expect(restDaoStub.get.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should return empty array', function(done) {
|
|
||||||
restDaoStub.get.yields(null, []);
|
|
||||||
|
|
||||||
pubkeyDao.getByUserId('userId', function(err, key) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(key).to.not.exist;
|
|
||||||
expect(restDaoStub.get.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
restDaoStub.get.yields(null, [{
|
|
||||||
_id: '12345',
|
|
||||||
publicKey: 'asdf'
|
|
||||||
}]);
|
|
||||||
|
|
||||||
pubkeyDao.getByUserId('userId', function(err, key) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(key).to.exist;
|
|
||||||
expect(key._id).to.exist;
|
|
||||||
expect(key.publicKey).to.exist;
|
|
||||||
expect(restDaoStub.get.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('put', function() {
|
it('should work', function(done) {
|
||||||
it('should fail', function(done) {
|
var uuid = 'c621e328-8548-40a1-8309-adf1955e98a9';
|
||||||
restDaoStub.put.yields();
|
restDaoStub.get.yields(null);
|
||||||
|
|
||||||
pubkeyDao.put({
|
pubkeyDao.verify(uuid, function(err) {
|
||||||
_id: '12345',
|
expect(err).to.not.exist;
|
||||||
publicKey: 'asdf'
|
expect(restDaoStub.get.calledWith(sinon.match(function(arg) {
|
||||||
}, function(err) {
|
return arg.uri === '/verify/' + uuid && arg.type === 'text';
|
||||||
expect(err).to.not.exist;
|
}))).to.be.true;
|
||||||
expect(restDaoStub.put.calledOnce).to.be.true;
|
done();
|
||||||
done();
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('get by userId', function() {
|
||||||
|
it('should fail', function(done) {
|
||||||
|
restDaoStub.get.yields(42);
|
||||||
|
|
||||||
|
pubkeyDao.getByUserId('userId', function(err, key) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(key).to.not.exist;
|
||||||
|
expect(restDaoStub.get.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('remove', function() {
|
it('should react to 404', function(done) {
|
||||||
it('should fail', function(done) {
|
restDaoStub.get.yields({
|
||||||
restDaoStub.remove.yields();
|
code: 404
|
||||||
|
});
|
||||||
|
|
||||||
pubkeyDao.remove('12345', function(err) {
|
pubkeyDao.getByUserId('userId', function(err, key) {
|
||||||
expect(err).to.not.exist;
|
expect(err).to.not.exist;
|
||||||
expect(restDaoStub.remove.calledOnce).to.be.true;
|
expect(key).to.not.exist;
|
||||||
done();
|
expect(restDaoStub.get.calledOnce).to.be.true;
|
||||||
});
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should return empty array', function(done) {
|
||||||
|
restDaoStub.get.yields(null, []);
|
||||||
|
|
||||||
|
pubkeyDao.getByUserId('userId', function(err, key) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(key).to.not.exist;
|
||||||
|
expect(restDaoStub.get.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
restDaoStub.get.yields(null, [{
|
||||||
|
_id: '12345',
|
||||||
|
publicKey: 'asdf'
|
||||||
|
}]);
|
||||||
|
|
||||||
|
pubkeyDao.getByUserId('userId', function(err, key) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(key).to.exist;
|
||||||
|
expect(key._id).to.exist;
|
||||||
|
expect(key.publicKey).to.exist;
|
||||||
|
expect(restDaoStub.get.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('put', function() {
|
||||||
|
it('should fail', function(done) {
|
||||||
|
restDaoStub.put.yields();
|
||||||
|
|
||||||
|
pubkeyDao.put({
|
||||||
|
_id: '12345',
|
||||||
|
publicKey: 'asdf'
|
||||||
|
}, function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(restDaoStub.put.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('remove', function() {
|
||||||
|
it('should fail', function(done) {
|
||||||
|
restDaoStub.remove.yields();
|
||||||
|
|
||||||
|
pubkeyDao.remove('12345', function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(restDaoStub.remove.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
});
|
});
|
@ -1,197 +1,193 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
KeychainDAO = require('../../src/js/dao/keychain-dao'),
|
||||||
mocks = require('angularMocks'),
|
InvitationDAO = require('../../src/js/dao/invitation-dao'),
|
||||||
KeychainDAO = require('js/dao/keychain-dao'),
|
PGP = require('../../src/js/crypto/pgp'),
|
||||||
InvitationDAO = require('js/dao/invitation-dao'),
|
ReadCtrl = require('../../src/js/controller/read'),
|
||||||
PGP = require('js/crypto/pgp'),
|
OutboxBO = require('../../src/js/bo/outbox'),
|
||||||
ReadCtrl = require('js/controller/read'),
|
appController = require('../../src/js/app-controller');
|
||||||
OutboxBO = require('js/bo/outbox'),
|
|
||||||
appController = require('js/app-controller');
|
|
||||||
|
|
||||||
describe('Read Controller unit test', function() {
|
describe('Read Controller unit test', function() {
|
||||||
var scope, ctrl,
|
var scope, ctrl,
|
||||||
origKeychain, keychainMock,
|
origKeychain, keychainMock,
|
||||||
origInvitation, invitationMock,
|
origInvitation, invitationMock,
|
||||||
origCrypto, cryptoMock,
|
origCrypto, cryptoMock,
|
||||||
origOutbox, outboxMock,
|
origOutbox, outboxMock,
|
||||||
origEmailDao;
|
origEmailDao;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
origKeychain = appController._keychain;
|
origKeychain = appController._keychain;
|
||||||
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
||||||
|
|
||||||
origInvitation = appController._invitationDao;
|
origInvitation = appController._invitationDao;
|
||||||
appController._invitationDao = invitationMock = sinon.createStubInstance(InvitationDAO);
|
appController._invitationDao = invitationMock = sinon.createStubInstance(InvitationDAO);
|
||||||
|
|
||||||
origCrypto = appController._pgp;
|
origCrypto = appController._pgp;
|
||||||
appController._pgp = cryptoMock = sinon.createStubInstance(PGP);
|
appController._pgp = cryptoMock = sinon.createStubInstance(PGP);
|
||||||
|
|
||||||
origOutbox = appController._outboxBo;
|
origOutbox = appController._outboxBo;
|
||||||
appController._outboxBo = outboxMock = sinon.createStubInstance(OutboxBO);
|
appController._outboxBo = outboxMock = sinon.createStubInstance(OutboxBO);
|
||||||
|
|
||||||
origEmailDao = appController._emailDao;
|
origEmailDao = appController._emailDao;
|
||||||
appController._emailDao = {
|
appController._emailDao = {
|
||||||
_account: 'sender@example.com'
|
_account: 'sender@example.com'
|
||||||
|
};
|
||||||
|
|
||||||
|
angular.module('readtest', []);
|
||||||
|
mocks.module('readtest');
|
||||||
|
mocks.inject(function($rootScope, $controller) {
|
||||||
|
scope = $rootScope.$new();
|
||||||
|
scope.state = {};
|
||||||
|
ctrl = $controller(ReadCtrl, {
|
||||||
|
$scope: scope
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
appController._keychain = origKeychain;
|
||||||
|
appController._invitationDao = origInvitation;
|
||||||
|
appController._pgp = origCrypto;
|
||||||
|
appController._outboxBo = origOutbox;
|
||||||
|
appController._emailDao = origEmailDao;
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('scope variables', function() {
|
||||||
|
it('should be set correctly', function() {
|
||||||
|
expect(scope.state.read).to.exist;
|
||||||
|
expect(scope.state.read.open).to.be.false;
|
||||||
|
expect(scope.state.read.toggle).to.exist;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('open/close read view', function() {
|
||||||
|
it('should open/close', function() {
|
||||||
|
expect(scope.state.read.open).to.be.false;
|
||||||
|
scope.state.read.toggle(true);
|
||||||
|
expect(scope.state.read.open).to.be.true;
|
||||||
|
scope.state.read.toggle(false);
|
||||||
|
expect(scope.state.read.open).to.be.false;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('getKeyId', function() {
|
||||||
|
var address = 'asfd@asdf.com';
|
||||||
|
|
||||||
|
it('should show searching on error', function() {
|
||||||
|
expect(scope.keyId).to.equal('No key found.');
|
||||||
|
keychainMock.getReceiverPublicKey.yields(42);
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.equal(42);
|
||||||
|
expect(scope.keyId).to.equal('Searching...');
|
||||||
};
|
};
|
||||||
|
|
||||||
angular.module('readtest', []);
|
scope.getKeyId(address);
|
||||||
mocks.module('readtest');
|
|
||||||
mocks.inject(function($rootScope, $controller) {
|
|
||||||
scope = $rootScope.$new();
|
|
||||||
scope.state = {};
|
|
||||||
ctrl = $controller(ReadCtrl, {
|
|
||||||
$scope: scope
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
it('should allow invitation on empty key', function() {
|
||||||
appController._keychain = origKeychain;
|
keychainMock.getReceiverPublicKey.yields();
|
||||||
appController._invitationDao = origInvitation;
|
|
||||||
appController._pgp = origCrypto;
|
scope.onError = function(err) {
|
||||||
appController._outboxBo = origOutbox;
|
expect(err).not.exist;
|
||||||
appController._emailDao = origEmailDao;
|
expect(scope.keyId).to.equal('User has no key. Click to invite.');
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.getKeyId(address);
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('scope variables', function() {
|
it('should show searching on error', function() {
|
||||||
it('should be set correctly', function() {
|
keychainMock.getReceiverPublicKey.yields(null, {
|
||||||
expect(scope.state.read).to.exist;
|
publicKey: 'PUBLIC KEY'
|
||||||
expect(scope.state.read.open).to.be.false;
|
|
||||||
expect(scope.state.read.toggle).to.exist;
|
|
||||||
});
|
});
|
||||||
|
|
||||||
|
cryptoMock.getFingerprint.returns('XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX');
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(scope.keyId).to.equal('PGP key: XXXXXXXX');
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.getKeyId(address);
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('open/close read view', function() {
|
|
||||||
it('should open/close', function() {
|
|
||||||
expect(scope.state.read.open).to.be.false;
|
|
||||||
scope.state.read.toggle(true);
|
|
||||||
expect(scope.state.read.open).to.be.true;
|
|
||||||
scope.state.read.toggle(false);
|
|
||||||
expect(scope.state.read.open).to.be.false;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('getKeyId', function() {
|
|
||||||
var address = 'asfd@asdf.com';
|
|
||||||
|
|
||||||
it('should show searching on error', function() {
|
|
||||||
expect(scope.keyId).to.equal('No key found.');
|
|
||||||
keychainMock.getReceiverPublicKey.yields(42);
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.equal(42);
|
|
||||||
expect(scope.keyId).to.equal('Searching...');
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.getKeyId(address);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should allow invitation on empty key', function() {
|
|
||||||
keychainMock.getReceiverPublicKey.yields();
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).not.exist;
|
|
||||||
expect(scope.keyId).to.equal('User has no key. Click to invite.');
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.getKeyId(address);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should show searching on error', function() {
|
|
||||||
keychainMock.getReceiverPublicKey.yields(null, {
|
|
||||||
publicKey: 'PUBLIC KEY'
|
|
||||||
});
|
|
||||||
|
|
||||||
cryptoMock.getFingerprint.returns('XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX');
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(scope.keyId).to.equal('PGP key: XXXXXXXX');
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.getKeyId(address);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('invite', function() {
|
|
||||||
it('not allow invitation for secure users', function() {
|
|
||||||
expect(scope.keyId).to.equal('No key found.');
|
|
||||||
|
|
||||||
scope.invite({
|
|
||||||
secure: true,
|
|
||||||
address: 'asdf@asdf.de'
|
|
||||||
});
|
|
||||||
|
|
||||||
expect(scope.keyId).to.equal('No key found.');
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should show error on invitation dao invite error', function() {
|
|
||||||
invitationMock.invite.yields(42);
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.equal(42);
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.invite({
|
|
||||||
address: 'asdf@asdf.de'
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should show error on outbox put error', function() {
|
|
||||||
invitationMock.invite.yields();
|
|
||||||
outboxMock.put.yields(42);
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.equal(42);
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.invite({
|
|
||||||
address: 'asdf@asdf.de'
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function() {
|
|
||||||
invitationMock.invite.yields();
|
|
||||||
outboxMock.put.yields();
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.invite({
|
|
||||||
address: 'asdf@asdf.de'
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('parseConversation', function() {
|
|
||||||
it.skip('should work', function() {
|
|
||||||
var body = 'foo\n' +
|
|
||||||
'\n' +
|
|
||||||
'> bar\n' +
|
|
||||||
'>\n' +
|
|
||||||
'> foofoo\n' +
|
|
||||||
'>> foofoobar\n' +
|
|
||||||
'\ncomment\n' +
|
|
||||||
'>> barbar';
|
|
||||||
|
|
||||||
var nodes = scope.parseConversation({
|
|
||||||
body: body
|
|
||||||
});
|
|
||||||
expect(nodes).to.exist;
|
|
||||||
|
|
||||||
var expectedJson = '{"children":["foo\\n",{"children":["bar\\n\\nfoofoo",{"children":["foofoobar"]}]},"\\ncomment",{"children":[{"children":["barbar"]}]}]}';
|
|
||||||
var json = JSON.stringify(nodes);
|
|
||||||
expect(json).to.equal(expectedJson);
|
|
||||||
|
|
||||||
var expectedHtml = '<div class="view-read-body"><div class="line"><span>foo</span><br></div><div class="line empty-line"><span></span><br></div><div class="prev-message"><div class="line"><span>bar</span><br></div><div class="line empty-line"><span></span><br></div><div class="line"><span>foofoo</span><br></div></div><div class="prev-message"><div class="prev-message"><div class="line"><span>foofoobar</span><br></div></div></div><div class="line empty-line"><span></span><br></div><div class="line"><span>comment</span><br></div><div class="prev-message"><div class="prev-message"><div class="line"><span>barbar</span><br></div></div></div></div>';
|
|
||||||
var html = scope.renderNodes(nodes);
|
|
||||||
expect(html).to.equal(expectedHtml);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe('invite', function() {
|
||||||
|
it('not allow invitation for secure users', function() {
|
||||||
|
expect(scope.keyId).to.equal('No key found.');
|
||||||
|
|
||||||
|
scope.invite({
|
||||||
|
secure: true,
|
||||||
|
address: 'asdf@asdf.de'
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(scope.keyId).to.equal('No key found.');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should show error on invitation dao invite error', function() {
|
||||||
|
invitationMock.invite.yields(42);
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.equal(42);
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.invite({
|
||||||
|
address: 'asdf@asdf.de'
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should show error on outbox put error', function() {
|
||||||
|
invitationMock.invite.yields();
|
||||||
|
outboxMock.put.yields(42);
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.equal(42);
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.invite({
|
||||||
|
address: 'asdf@asdf.de'
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function() {
|
||||||
|
invitationMock.invite.yields();
|
||||||
|
outboxMock.put.yields();
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.invite({
|
||||||
|
address: 'asdf@asdf.de'
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('parseConversation', function() {
|
||||||
|
it.skip('should work', function() {
|
||||||
|
var body = 'foo\n' +
|
||||||
|
'\n' +
|
||||||
|
'> bar\n' +
|
||||||
|
'>\n' +
|
||||||
|
'> foofoo\n' +
|
||||||
|
'>> foofoobar\n' +
|
||||||
|
'\ncomment\n' +
|
||||||
|
'>> barbar';
|
||||||
|
|
||||||
|
var nodes = scope.parseConversation({
|
||||||
|
body: body
|
||||||
|
});
|
||||||
|
expect(nodes).to.exist;
|
||||||
|
|
||||||
|
var expectedJson = '{"children":["foo\\n",{"children":["bar\\n\\nfoofoo",{"children":["foofoobar"]}]},"\\ncomment",{"children":[{"children":["barbar"]}]}]}';
|
||||||
|
var json = JSON.stringify(nodes);
|
||||||
|
expect(json).to.equal(expectedJson);
|
||||||
|
|
||||||
|
var expectedHtml = '<div class="view-read-body"><div class="line"><span>foo</span><br></div><div class="line empty-line"><span></span><br></div><div class="prev-message"><div class="line"><span>bar</span><br></div><div class="line empty-line"><span></span><br></div><div class="line"><span>foofoo</span><br></div></div><div class="prev-message"><div class="prev-message"><div class="line"><span>foofoobar</span><br></div></div></div><div class="line empty-line"><span></span><br></div><div class="line"><span>comment</span><br></div><div class="prev-message"><div class="prev-message"><div class="line"><span>barbar</span><br></div></div></div></div>';
|
||||||
|
var html = scope.renderNodes(nodes);
|
||||||
|
expect(html).to.equal(expectedHtml);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
});
|
});
|
@ -1,225 +1,221 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var RestDAO = require('js/dao/rest-dao'),
|
var RestDAO = require('../../src/js/dao/rest-dao');
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
describe('Rest DAO unit tests', function() {
|
describe('Rest DAO unit tests', function() {
|
||||||
|
|
||||||
var restDao, xhrMock, requests;
|
var restDao, xhrMock, requests;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
|
restDao = new RestDAO();
|
||||||
|
xhrMock = sinon.useFakeXMLHttpRequest();
|
||||||
|
requests = [];
|
||||||
|
|
||||||
|
xhrMock.onCreate = function(xhr) {
|
||||||
|
requests.push(xhr);
|
||||||
|
};
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
xhrMock.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('contructor', function() {
|
||||||
|
it('should set default base uri', function() {
|
||||||
restDao = new RestDAO();
|
restDao = new RestDAO();
|
||||||
xhrMock = sinon.useFakeXMLHttpRequest();
|
expect(restDao).to.exist;
|
||||||
requests = [];
|
expect(restDao._baseUri).to.exist;
|
||||||
|
|
||||||
xhrMock.onCreate = function(xhr) {
|
|
||||||
requests.push(xhr);
|
|
||||||
};
|
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
it('should accept default base uri', function() {
|
||||||
xhrMock.restore();
|
var baseUri = 'http://custom.com';
|
||||||
});
|
|
||||||
|
|
||||||
describe('contructor', function() {
|
restDao = new RestDAO(baseUri);
|
||||||
it('should set default base uri', function() {
|
expect(restDao).to.exist;
|
||||||
restDao = new RestDAO();
|
expect(restDao._baseUri).to.equal(baseUri);
|
||||||
expect(restDao).to.exist;
|
});
|
||||||
expect(restDao._baseUri).to.exist;
|
});
|
||||||
|
|
||||||
|
describe('get', function() {
|
||||||
|
it('should work with json as default type', function() {
|
||||||
|
restDao.get({
|
||||||
|
uri: '/asdf'
|
||||||
|
}, function(err, data, status) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(data.foo).to.equal('bar');
|
||||||
|
var req = requests[0];
|
||||||
|
expect(req.requestHeaders.Accept).to.equal('application/json');
|
||||||
|
expect(status).to.equal(200);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should accept default base uri', function() {
|
expect(requests.length).to.equal(1);
|
||||||
var baseUri = 'http://custom.com';
|
requests[0].respond(200, {
|
||||||
|
"Content-Type": "application/json"
|
||||||
|
}, '{"foo": "bar"}');
|
||||||
|
});
|
||||||
|
|
||||||
restDao = new RestDAO(baseUri);
|
it('should work with jsonz', function() {
|
||||||
expect(restDao).to.exist;
|
restDao.get({
|
||||||
expect(restDao._baseUri).to.equal(baseUri);
|
uri: '/asdf',
|
||||||
|
type: 'json'
|
||||||
|
}, function(err, data, status) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(data.foo).to.equal('bar');
|
||||||
|
var req = requests[0];
|
||||||
|
expect(req.requestHeaders.Accept).to.equal('application/json');
|
||||||
|
expect(status).to.equal(200);
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(requests.length).to.equal(1);
|
||||||
|
requests[0].respond(200, {
|
||||||
|
"Content-Type": "application/json"
|
||||||
|
}, '{"foo": "bar"}');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work with plain text', function() {
|
||||||
|
restDao.get({
|
||||||
|
uri: '/asdf',
|
||||||
|
type: 'text'
|
||||||
|
}, function(err, data, status) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(data).to.equal('foobar!');
|
||||||
|
var req = requests[0];
|
||||||
|
expect(req.requestHeaders.Accept).to.equal('text/plain');
|
||||||
|
expect(status).to.equal(200);
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(requests.length).to.equal(1);
|
||||||
|
requests[0].respond(200, {
|
||||||
|
"Content-Type": "text/plain"
|
||||||
|
}, 'foobar!');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work with xml', function() {
|
||||||
|
restDao.get({
|
||||||
|
uri: '/asdf',
|
||||||
|
type: 'xml'
|
||||||
|
}, function(err, data, status) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(data).to.equal('<foo>bar</foo>');
|
||||||
|
var req = requests[0];
|
||||||
|
expect(req.requestHeaders.Accept).to.equal('application/xml');
|
||||||
|
expect(status).to.equal(200);
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(requests.length).to.equal(1);
|
||||||
|
requests[0].respond(200, {
|
||||||
|
"Content-Type": "application/xml"
|
||||||
|
}, '<foo>bar</foo>');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail for missing uri parameter', function() {
|
||||||
|
restDao.get({}, function(err, data) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(err.code).to.equal(400);
|
||||||
|
expect(data).to.not.exist;
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('get', function() {
|
it('should fail for unhandled data type', function() {
|
||||||
it('should work with json as default type', function() {
|
restDao.get({
|
||||||
restDao.get({
|
uri: '/asdf',
|
||||||
uri: '/asdf'
|
type: 'snafu'
|
||||||
}, function(err, data, status) {
|
}, function(err, data) {
|
||||||
expect(err).to.not.exist;
|
expect(err).to.exist;
|
||||||
expect(data.foo).to.equal('bar');
|
expect(err.code).to.equal(400);
|
||||||
var req = requests[0];
|
expect(data).to.not.exist;
|
||||||
expect(req.requestHeaders.Accept).to.equal('application/json');
|
|
||||||
expect(status).to.equal(200);
|
|
||||||
});
|
|
||||||
|
|
||||||
expect(requests.length).to.equal(1);
|
|
||||||
requests[0].respond(200, {
|
|
||||||
"Content-Type": "application/json"
|
|
||||||
}, '{"foo": "bar"}');
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work with jsonz', function() {
|
|
||||||
restDao.get({
|
|
||||||
uri: '/asdf',
|
|
||||||
type: 'json'
|
|
||||||
}, function(err, data, status) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(data.foo).to.equal('bar');
|
|
||||||
var req = requests[0];
|
|
||||||
expect(req.requestHeaders.Accept).to.equal('application/json');
|
|
||||||
expect(status).to.equal(200);
|
|
||||||
});
|
|
||||||
|
|
||||||
expect(requests.length).to.equal(1);
|
|
||||||
requests[0].respond(200, {
|
|
||||||
"Content-Type": "application/json"
|
|
||||||
}, '{"foo": "bar"}');
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work with plain text', function() {
|
|
||||||
restDao.get({
|
|
||||||
uri: '/asdf',
|
|
||||||
type: 'text'
|
|
||||||
}, function(err, data, status) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(data).to.equal('foobar!');
|
|
||||||
var req = requests[0];
|
|
||||||
expect(req.requestHeaders.Accept).to.equal('text/plain');
|
|
||||||
expect(status).to.equal(200);
|
|
||||||
});
|
|
||||||
|
|
||||||
expect(requests.length).to.equal(1);
|
|
||||||
requests[0].respond(200, {
|
|
||||||
"Content-Type": "text/plain"
|
|
||||||
}, 'foobar!');
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work with xml', function() {
|
|
||||||
restDao.get({
|
|
||||||
uri: '/asdf',
|
|
||||||
type: 'xml'
|
|
||||||
}, function(err, data, status) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
expect(data).to.equal('<foo>bar</foo>');
|
|
||||||
var req = requests[0];
|
|
||||||
expect(req.requestHeaders.Accept).to.equal('application/xml');
|
|
||||||
expect(status).to.equal(200);
|
|
||||||
});
|
|
||||||
|
|
||||||
expect(requests.length).to.equal(1);
|
|
||||||
requests[0].respond(200, {
|
|
||||||
"Content-Type": "application/xml"
|
|
||||||
}, '<foo>bar</foo>');
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail for missing uri parameter', function() {
|
|
||||||
restDao.get({}, function(err, data) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(err.code).to.equal(400);
|
|
||||||
expect(data).to.not.exist;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail for unhandled data type', function() {
|
|
||||||
restDao.get({
|
|
||||||
uri: '/asdf',
|
|
||||||
type: 'snafu'
|
|
||||||
}, function(err, data) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(err.code).to.equal(400);
|
|
||||||
expect(data).to.not.exist;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail for server error', function() {
|
|
||||||
restDao.get({
|
|
||||||
uri: '/asdf'
|
|
||||||
}, function(err, data) {
|
|
||||||
expect(err).to.exist;
|
|
||||||
expect(err.code).to.equal(500);
|
|
||||||
expect(data).to.not.exist;
|
|
||||||
});
|
|
||||||
|
|
||||||
expect(requests.length).to.equal(1);
|
|
||||||
requests[0].respond(500, {
|
|
||||||
"Content-Type": "text/plain"
|
|
||||||
}, 'Internal error');
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('post', function() {
|
it('should fail for server error', function() {
|
||||||
it('should fail', function() {
|
restDao.get({
|
||||||
restDao.post('/asdf', {}, function(err) {
|
uri: '/asdf'
|
||||||
expect(err).to.exist;
|
}, function(err, data) {
|
||||||
expect(err.code).to.equal(500);
|
expect(err).to.exist;
|
||||||
});
|
expect(err.code).to.equal(500);
|
||||||
|
expect(data).to.not.exist;
|
||||||
expect(requests.length).to.equal(1);
|
|
||||||
requests[0].respond(500, {
|
|
||||||
"Content-Type": "text/plain"
|
|
||||||
}, 'Internal error');
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should work', function() {
|
expect(requests.length).to.equal(1);
|
||||||
restDao.post('/asdf', {}, function(err, res, status) {
|
requests[0].respond(500, {
|
||||||
expect(err).to.not.exist;
|
"Content-Type": "text/plain"
|
||||||
expect(res).to.equal('');
|
}, 'Internal error');
|
||||||
expect(status).to.equal(201);
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
expect(requests.length).to.equal(1);
|
describe('post', function() {
|
||||||
requests[0].respond(201);
|
it('should fail', function() {
|
||||||
|
restDao.post('/asdf', {}, function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(err.code).to.equal(500);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
expect(requests.length).to.equal(1);
|
||||||
|
requests[0].respond(500, {
|
||||||
|
"Content-Type": "text/plain"
|
||||||
|
}, 'Internal error');
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('put', function() {
|
it('should work', function() {
|
||||||
it('should fail', function() {
|
restDao.post('/asdf', {}, function(err, res, status) {
|
||||||
restDao.put('/asdf', {}, function(err) {
|
expect(err).to.not.exist;
|
||||||
expect(err).to.exist;
|
expect(res).to.equal('');
|
||||||
expect(err.code).to.equal(500);
|
expect(status).to.equal(201);
|
||||||
});
|
|
||||||
|
|
||||||
expect(requests.length).to.equal(1);
|
|
||||||
requests[0].respond(500, {
|
|
||||||
"Content-Type": "text/plain"
|
|
||||||
}, 'Internal error');
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should work', function() {
|
expect(requests.length).to.equal(1);
|
||||||
restDao.put('/asdf', {}, function(err, res, status) {
|
requests[0].respond(201);
|
||||||
expect(err).to.not.exist;
|
});
|
||||||
expect(res).to.equal('');
|
});
|
||||||
expect(status).to.equal(201);
|
|
||||||
});
|
|
||||||
|
|
||||||
expect(requests.length).to.equal(1);
|
describe('put', function() {
|
||||||
requests[0].respond(201);
|
it('should fail', function() {
|
||||||
|
restDao.put('/asdf', {}, function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(err.code).to.equal(500);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
expect(requests.length).to.equal(1);
|
||||||
|
requests[0].respond(500, {
|
||||||
|
"Content-Type": "text/plain"
|
||||||
|
}, 'Internal error');
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('remove', function() {
|
it('should work', function() {
|
||||||
it('should fail', function() {
|
restDao.put('/asdf', {}, function(err, res, status) {
|
||||||
restDao.remove('/asdf', function(err) {
|
expect(err).to.not.exist;
|
||||||
expect(err).to.exist;
|
expect(res).to.equal('');
|
||||||
expect(err.code).to.equal(500);
|
expect(status).to.equal(201);
|
||||||
});
|
|
||||||
|
|
||||||
expect(requests.length).to.equal(1);
|
|
||||||
requests[0].respond(500, {
|
|
||||||
"Content-Type": "text/plain"
|
|
||||||
}, 'Internal error');
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('should work', function() {
|
expect(requests.length).to.equal(1);
|
||||||
restDao.remove('/asdf', function(err, res, status) {
|
requests[0].respond(201);
|
||||||
expect(err).to.not.exist;
|
});
|
||||||
expect(res).to.equal('');
|
});
|
||||||
expect(status).to.equal(200);
|
|
||||||
});
|
|
||||||
|
|
||||||
expect(requests.length).to.equal(1);
|
describe('remove', function() {
|
||||||
requests[0].respond(200);
|
it('should fail', function() {
|
||||||
|
restDao.remove('/asdf', function(err) {
|
||||||
|
expect(err).to.exist;
|
||||||
|
expect(err.code).to.equal(500);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
expect(requests.length).to.equal(1);
|
||||||
|
requests[0].respond(500, {
|
||||||
|
"Content-Type": "text/plain"
|
||||||
|
}, 'Internal error');
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should work', function() {
|
||||||
|
restDao.remove('/asdf', function(err, res, status) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
expect(res).to.equal('');
|
||||||
|
expect(status).to.equal(200);
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(requests.length).to.equal(1);
|
||||||
|
requests[0].respond(200);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
});
|
});
|
@ -1,126 +1,122 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
SetPassphraseCtrl = require('../../src/js/controller/set-passphrase'),
|
||||||
mocks = require('angularMocks'),
|
PGP = require('../../src/js/crypto/pgp'),
|
||||||
SetPassphraseCtrl = require('js/controller/set-passphrase'),
|
appController = require('../../src/js/app-controller'),
|
||||||
PGP = require('js/crypto/pgp'),
|
KeychainDAO = require('../../src/js/dao/keychain-dao');
|
||||||
appController = require('js/app-controller'),
|
|
||||||
KeychainDAO = require('js/dao/keychain-dao');
|
|
||||||
|
|
||||||
describe('Set Passphrase Controller unit test', function() {
|
describe('Set Passphrase Controller unit test', function() {
|
||||||
var scope, setPassphraseCtrl,
|
var scope, setPassphraseCtrl,
|
||||||
dummyFingerprint, expectedFingerprint,
|
dummyFingerprint, expectedFingerprint,
|
||||||
dummyKeyId, expectedKeyId,
|
dummyKeyId, expectedKeyId,
|
||||||
emailAddress, keySize, cryptoMock, keychainMock;
|
emailAddress, keySize, cryptoMock, keychainMock;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
appController._pgp = cryptoMock = sinon.createStubInstance(PGP);
|
appController._pgp = cryptoMock = sinon.createStubInstance(PGP);
|
||||||
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
appController._keychain = keychainMock = sinon.createStubInstance(KeychainDAO);
|
||||||
|
|
||||||
dummyFingerprint = '3A2D39B4E1404190B8B949DE7D7E99036E712926';
|
dummyFingerprint = '3A2D39B4E1404190B8B949DE7D7E99036E712926';
|
||||||
expectedFingerprint = '3A2D 39B4 E140 4190 B8B9 49DE 7D7E 9903 6E71 2926';
|
expectedFingerprint = '3A2D 39B4 E140 4190 B8B9 49DE 7D7E 9903 6E71 2926';
|
||||||
dummyKeyId = '9FEB47936E712926';
|
dummyKeyId = '9FEB47936E712926';
|
||||||
expectedKeyId = '6E712926';
|
expectedKeyId = '6E712926';
|
||||||
cryptoMock.getFingerprint.returns(dummyFingerprint);
|
cryptoMock.getFingerprint.returns(dummyFingerprint);
|
||||||
cryptoMock.getKeyId.returns(dummyKeyId);
|
cryptoMock.getKeyId.returns(dummyKeyId);
|
||||||
emailAddress = 'fred@foo.com';
|
emailAddress = 'fred@foo.com';
|
||||||
keySize = 1234;
|
keySize = 1234;
|
||||||
|
|
||||||
cryptoMock.getKeyParams.returns({
|
cryptoMock.getKeyParams.returns({
|
||||||
|
_id: dummyKeyId,
|
||||||
|
fingerprint: dummyFingerprint,
|
||||||
|
userId: emailAddress,
|
||||||
|
userIds: [],
|
||||||
|
bitSize: keySize
|
||||||
|
});
|
||||||
|
|
||||||
|
angular.module('setpassphrasetest', []);
|
||||||
|
mocks.module('setpassphrasetest');
|
||||||
|
mocks.inject(function($rootScope, $controller) {
|
||||||
|
scope = $rootScope.$new();
|
||||||
|
scope.state = {};
|
||||||
|
setPassphraseCtrl = $controller(SetPassphraseCtrl, {
|
||||||
|
$scope: scope
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {});
|
||||||
|
|
||||||
|
describe('setPassphrase', function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
scope.oldPassphrase = 'old';
|
||||||
|
scope.newPassphrase = 'new';
|
||||||
|
|
||||||
|
keychainMock.lookupPrivateKey.withArgs(dummyKeyId).yields(null, {
|
||||||
|
encryptedKey: 'encrypted'
|
||||||
|
});
|
||||||
|
|
||||||
|
cryptoMock.changePassphrase.withArgs({
|
||||||
|
privateKeyArmored: 'encrypted',
|
||||||
|
oldPassphrase: 'old',
|
||||||
|
newPassphrase: 'new'
|
||||||
|
}).yields(null, 'newArmoredKey');
|
||||||
|
|
||||||
|
keychainMock.saveLocalPrivateKey.withArgs({
|
||||||
_id: dummyKeyId,
|
_id: dummyKeyId,
|
||||||
fingerprint: dummyFingerprint,
|
|
||||||
userId: emailAddress,
|
userId: emailAddress,
|
||||||
userIds: [],
|
userIds: [],
|
||||||
bitSize: keySize
|
encryptedKey: 'newArmoredKey'
|
||||||
});
|
}).yields();
|
||||||
|
|
||||||
angular.module('setpassphrasetest', []);
|
scope.onError = function(err) {
|
||||||
mocks.module('setpassphrasetest');
|
expect(err.title).to.equal('Success');
|
||||||
mocks.inject(function($rootScope, $controller) {
|
done();
|
||||||
scope = $rootScope.$new();
|
};
|
||||||
scope.state = {};
|
|
||||||
setPassphraseCtrl = $controller(SetPassphraseCtrl, {
|
scope.setPassphrase();
|
||||||
$scope: scope
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function() {});
|
|
||||||
|
|
||||||
describe('setPassphrase', function() {
|
|
||||||
it('should work', function(done) {
|
|
||||||
scope.oldPassphrase = 'old';
|
|
||||||
scope.newPassphrase = 'new';
|
|
||||||
|
|
||||||
keychainMock.lookupPrivateKey.withArgs(dummyKeyId).yields(null, {
|
|
||||||
encryptedKey: 'encrypted'
|
|
||||||
});
|
|
||||||
|
|
||||||
cryptoMock.changePassphrase.withArgs({
|
|
||||||
privateKeyArmored: 'encrypted',
|
|
||||||
oldPassphrase: 'old',
|
|
||||||
newPassphrase: 'new'
|
|
||||||
}).yields(null, 'newArmoredKey');
|
|
||||||
|
|
||||||
keychainMock.saveLocalPrivateKey.withArgs({
|
|
||||||
_id: dummyKeyId,
|
|
||||||
userId: emailAddress,
|
|
||||||
userIds: [],
|
|
||||||
encryptedKey: 'newArmoredKey'
|
|
||||||
}).yields();
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err.title).to.equal('Success');
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.setPassphrase();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('check passphrase quality', function() {
|
|
||||||
it('should be too short', function() {
|
|
||||||
scope.newPassphrase = '&§DG36';
|
|
||||||
scope.checkPassphraseQuality();
|
|
||||||
|
|
||||||
expect(scope.passphraseMsg).to.equal('Very weak');
|
|
||||||
expect(scope.passphraseRating).to.equal(0);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should be very weak', function() {
|
|
||||||
scope.newPassphrase = 'aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa';
|
|
||||||
scope.checkPassphraseQuality();
|
|
||||||
|
|
||||||
expect(scope.passphraseMsg).to.equal('Very weak');
|
|
||||||
expect(scope.passphraseRating).to.equal(0);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should be weak', function() {
|
|
||||||
scope.newPassphrase = 'asdfasdfasdfasdfasdfasdfasdfasdfasdfasdfasdf';
|
|
||||||
scope.checkPassphraseQuality();
|
|
||||||
|
|
||||||
expect(scope.passphraseMsg).to.equal('Weak');
|
|
||||||
expect(scope.passphraseRating).to.equal(1);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should be good', function() {
|
|
||||||
scope.newPassphrase = 'asdfasdfasdfasdfasdfasdfasdfasdfasdfasdfasdf5';
|
|
||||||
scope.checkPassphraseQuality();
|
|
||||||
|
|
||||||
expect(scope.passphraseMsg).to.equal('Good');
|
|
||||||
expect(scope.passphraseRating).to.equal(2);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should be strong', function() {
|
|
||||||
scope.newPassphrase = '&§DG36abcd';
|
|
||||||
scope.checkPassphraseQuality();
|
|
||||||
|
|
||||||
expect(scope.passphraseMsg).to.equal('Strong');
|
|
||||||
expect(scope.passphraseRating).to.equal(3);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe('check passphrase quality', function() {
|
||||||
|
it('should be too short', function() {
|
||||||
|
scope.newPassphrase = '&§DG36';
|
||||||
|
scope.checkPassphraseQuality();
|
||||||
|
|
||||||
|
expect(scope.passphraseMsg).to.equal('Very weak');
|
||||||
|
expect(scope.passphraseRating).to.equal(0);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should be very weak', function() {
|
||||||
|
scope.newPassphrase = 'aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa';
|
||||||
|
scope.checkPassphraseQuality();
|
||||||
|
|
||||||
|
expect(scope.passphraseMsg).to.equal('Very weak');
|
||||||
|
expect(scope.passphraseRating).to.equal(0);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should be weak', function() {
|
||||||
|
scope.newPassphrase = 'asdfasdfasdfasdfasdfasdfasdfasdfasdfasdfasdf';
|
||||||
|
scope.checkPassphraseQuality();
|
||||||
|
|
||||||
|
expect(scope.passphraseMsg).to.equal('Weak');
|
||||||
|
expect(scope.passphraseRating).to.equal(1);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should be good', function() {
|
||||||
|
scope.newPassphrase = 'asdfasdfasdfasdfasdfasdfasdfasdfasdfasdfasdf5';
|
||||||
|
scope.checkPassphraseQuality();
|
||||||
|
|
||||||
|
expect(scope.passphraseMsg).to.equal('Good');
|
||||||
|
expect(scope.passphraseRating).to.equal(2);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should be strong', function() {
|
||||||
|
scope.newPassphrase = '&§DG36abcd';
|
||||||
|
scope.checkPassphraseQuality();
|
||||||
|
|
||||||
|
expect(scope.passphraseMsg).to.equal('Strong');
|
||||||
|
expect(scope.passphraseRating).to.equal(3);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
});
|
});
|
@ -1,472 +1,469 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var DeviceStorageDAO = require('js/dao/devicestorage-dao'),
|
var DeviceStorageDAO = require('../../src/js/dao/devicestorage-dao'),
|
||||||
Auth = require('js/bo/auth'),
|
Auth = require('../../src/js/bo/auth'),
|
||||||
cfg = require('js/app-config').config,
|
cfg = require('../../src/js/app-config').config,
|
||||||
UpdateHandler = require('js/util/update/update-handler'),
|
UpdateHandler = require('../../src/js/util/update/update-handler'),
|
||||||
config = require('js/app-config').config,
|
config = require('../../src/js/app-config').config;
|
||||||
expect = chai.expect;
|
|
||||||
|
|
||||||
describe('UpdateHandler', function() {
|
describe('UpdateHandler', function() {
|
||||||
var updateHandler, appConfigStorageStub, authStub, userStorageStub, origDbVersion;
|
var updateHandler, appConfigStorageStub, authStub, userStorageStub, origDbVersion;
|
||||||
|
|
||||||
chai.Assertion.includeStack = true;
|
chai.Assertion.includeStack = true;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
origDbVersion = cfg.dbVersion;
|
origDbVersion = cfg.dbVersion;
|
||||||
appConfigStorageStub = sinon.createStubInstance(DeviceStorageDAO);
|
appConfigStorageStub = sinon.createStubInstance(DeviceStorageDAO);
|
||||||
userStorageStub = sinon.createStubInstance(DeviceStorageDAO);
|
userStorageStub = sinon.createStubInstance(DeviceStorageDAO);
|
||||||
authStub = sinon.createStubInstance(Auth);
|
authStub = sinon.createStubInstance(Auth);
|
||||||
updateHandler = new UpdateHandler(appConfigStorageStub, userStorageStub, authStub);
|
updateHandler = new UpdateHandler(appConfigStorageStub, userStorageStub, authStub);
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
cfg.dbVersion = origDbVersion;
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('#constructor', function() {
|
||||||
|
it('should create instance', function() {
|
||||||
|
expect(updateHandler).to.exist;
|
||||||
|
expect(updateHandler._appConfigStorage).to.equal(appConfigStorageStub);
|
||||||
|
expect(updateHandler._userStorage).to.equal(userStorageStub);
|
||||||
|
|
||||||
|
// the update handler must contain as many db update sripts as there are database versions
|
||||||
|
expect(updateHandler._updateScripts.length).to.equal(cfg.dbVersion);
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
describe('#update', function() {
|
||||||
cfg.dbVersion = origDbVersion;
|
var versionDbType = 'dbVersion';
|
||||||
});
|
|
||||||
|
|
||||||
describe('#constructor', function() {
|
it('should not update when up to date', function(done) {
|
||||||
it('should create instance', function() {
|
cfg.dbVersion = 10; // app requires database version 10
|
||||||
expect(updateHandler).to.exist;
|
appConfigStorageStub.listItems.withArgs(versionDbType).yieldsAsync(null, ['10']); // database version is 10
|
||||||
expect(updateHandler._appConfigStorage).to.equal(appConfigStorageStub);
|
|
||||||
expect(updateHandler._userStorage).to.equal(userStorageStub);
|
|
||||||
|
|
||||||
// the update handler must contain as many db update sripts as there are database versions
|
updateHandler.update(function(error) {
|
||||||
expect(updateHandler._updateScripts.length).to.equal(cfg.dbVersion);
|
expect(error).to.not.exist;
|
||||||
|
expect(appConfigStorageStub.listItems.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('#update', function() {
|
describe('dummy updates for v2 to v4', function() {
|
||||||
var versionDbType = 'dbVersion';
|
var updateCounter;
|
||||||
|
|
||||||
it('should not update when up to date', function(done) {
|
beforeEach(function() {
|
||||||
cfg.dbVersion = 10; // app requires database version 10
|
updateCounter = 0;
|
||||||
appConfigStorageStub.listItems.withArgs(versionDbType).yieldsAsync(null, ['10']); // database version is 10
|
appConfigStorageStub.listItems.withArgs(versionDbType).yieldsAsync(null, ['2']); // database version is 0
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
expect(appConfigStorageStub.listItems.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
cfg.dbVersion = 4; // app requires database version 4
|
||||||
|
|
||||||
|
// a simple dummy update to executed that only increments the update counter
|
||||||
|
function dummyUpdate(options, callback) {
|
||||||
|
updateCounter++;
|
||||||
|
callback();
|
||||||
|
}
|
||||||
|
|
||||||
|
// inject the dummy updates instead of live ones
|
||||||
|
updateHandler._updateScripts = [dummyUpdate, dummyUpdate, dummyUpdate, dummyUpdate];
|
||||||
|
|
||||||
|
// execute test
|
||||||
updateHandler.update(function(error) {
|
updateHandler.update(function(error) {
|
||||||
expect(error).to.not.exist;
|
expect(error).to.not.exist;
|
||||||
expect(appConfigStorageStub.listItems.calledOnce).to.be.true;
|
expect(updateCounter).to.equal(2);
|
||||||
|
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('dummy updates for v2 to v4', function() {
|
it('should fail while updating to v3', function(done) {
|
||||||
var updateCounter;
|
cfg.dbVersion = 4; // app requires database version 4
|
||||||
|
|
||||||
beforeEach(function() {
|
function dummyUpdate(options, callback) {
|
||||||
updateCounter = 0;
|
updateCounter++;
|
||||||
appConfigStorageStub.listItems.withArgs(versionDbType).yieldsAsync(null, ['2']); // database version is 0
|
callback();
|
||||||
});
|
}
|
||||||
|
|
||||||
afterEach(function() {
|
function failingUpdate(options, callback) {
|
||||||
expect(appConfigStorageStub.listItems.calledOnce).to.be.true;
|
callback({});
|
||||||
});
|
}
|
||||||
|
|
||||||
|
// inject the dummy updates instead of live ones
|
||||||
|
updateHandler._updateScripts = [dummyUpdate, dummyUpdate, failingUpdate, dummyUpdate];
|
||||||
|
|
||||||
it('should work', function(done) {
|
// execute test
|
||||||
cfg.dbVersion = 4; // app requires database version 4
|
updateHandler.update(function(error) {
|
||||||
|
expect(error).to.exist;
|
||||||
|
expect(updateCounter).to.equal(0);
|
||||||
|
|
||||||
// a simple dummy update to executed that only increments the update counter
|
done();
|
||||||
function dummyUpdate(options, callback) {
|
|
||||||
updateCounter++;
|
|
||||||
callback();
|
|
||||||
}
|
|
||||||
|
|
||||||
// inject the dummy updates instead of live ones
|
|
||||||
updateHandler._updateScripts = [dummyUpdate, dummyUpdate, dummyUpdate, dummyUpdate];
|
|
||||||
|
|
||||||
// execute test
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.not.exist;
|
|
||||||
expect(updateCounter).to.equal(2);
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail while updating to v3', function(done) {
|
|
||||||
cfg.dbVersion = 4; // app requires database version 4
|
|
||||||
|
|
||||||
function dummyUpdate(options, callback) {
|
|
||||||
updateCounter++;
|
|
||||||
callback();
|
|
||||||
}
|
|
||||||
|
|
||||||
function failingUpdate(options, callback) {
|
|
||||||
callback({});
|
|
||||||
}
|
|
||||||
|
|
||||||
// inject the dummy updates instead of live ones
|
|
||||||
updateHandler._updateScripts = [dummyUpdate, dummyUpdate, failingUpdate, dummyUpdate];
|
|
||||||
|
|
||||||
// execute test
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(updateCounter).to.equal(0);
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('v0 -> v1', function() {
|
|
||||||
var emailDbType = 'email_';
|
|
||||||
|
|
||||||
beforeEach(function() {
|
|
||||||
cfg.dbVersion = 1; // app requires database version 1
|
|
||||||
appConfigStorageStub.listItems.withArgs(versionDbType).yieldsAsync(); // database version is 0
|
|
||||||
});
|
|
||||||
|
|
||||||
afterEach(function() {
|
|
||||||
// database version is only queried for version checking prior to the update script
|
|
||||||
// so no need to check this in case-specific tests
|
|
||||||
expect(appConfigStorageStub.listItems.calledOnce).to.be.true;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
userStorageStub.removeList.withArgs(emailDbType).yieldsAsync();
|
|
||||||
appConfigStorageStub.storeList.withArgs([1], versionDbType).yieldsAsync();
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.not.exist;
|
|
||||||
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
|
||||||
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail when persisting database version fails', function(done) {
|
|
||||||
userStorageStub.removeList.yieldsAsync();
|
|
||||||
appConfigStorageStub.storeList.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
|
||||||
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail when wiping emails from database fails', function(done) {
|
|
||||||
userStorageStub.removeList.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
|
||||||
expect(appConfigStorageStub.storeList.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('v1 -> v2', function() {
|
});
|
||||||
var emailDbType = 'email_';
|
|
||||||
|
|
||||||
beforeEach(function() {
|
describe('v0 -> v1', function() {
|
||||||
cfg.dbVersion = 2; // app requires database version 2
|
var emailDbType = 'email_';
|
||||||
appConfigStorageStub.listItems.withArgs(versionDbType).yieldsAsync(null, [1]); // database version is 0
|
|
||||||
});
|
|
||||||
|
|
||||||
afterEach(function() {
|
beforeEach(function() {
|
||||||
// database version is only queried for version checking prior to the update script
|
cfg.dbVersion = 1; // app requires database version 1
|
||||||
// so no need to check this in case-specific tests
|
appConfigStorageStub.listItems.withArgs(versionDbType).yieldsAsync(); // database version is 0
|
||||||
expect(appConfigStorageStub.listItems.calledOnce).to.be.true;
|
});
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
afterEach(function() {
|
||||||
userStorageStub.removeList.withArgs(emailDbType).yieldsAsync();
|
// database version is only queried for version checking prior to the update script
|
||||||
appConfigStorageStub.storeList.withArgs([2], versionDbType).yieldsAsync();
|
// so no need to check this in case-specific tests
|
||||||
|
expect(appConfigStorageStub.listItems.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
it('should work', function(done) {
|
||||||
expect(error).to.not.exist;
|
userStorageStub.removeList.withArgs(emailDbType).yieldsAsync();
|
||||||
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
appConfigStorageStub.storeList.withArgs([1], versionDbType).yieldsAsync();
|
||||||
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
updateHandler.update(function(error) {
|
||||||
});
|
expect(error).to.not.exist;
|
||||||
});
|
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
||||||
|
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
|
||||||
it('should fail when persisting database version fails', function(done) {
|
done();
|
||||||
userStorageStub.removeList.yieldsAsync();
|
|
||||||
appConfigStorageStub.storeList.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
|
||||||
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail when wiping emails from database fails', function(done) {
|
|
||||||
userStorageStub.removeList.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
|
||||||
expect(appConfigStorageStub.storeList.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('v2 -> v3', function() {
|
it('should fail when persisting database version fails', function(done) {
|
||||||
var emailDbType = 'email_';
|
userStorageStub.removeList.yieldsAsync();
|
||||||
|
appConfigStorageStub.storeList.yieldsAsync(new Error());
|
||||||
|
|
||||||
beforeEach(function() {
|
updateHandler.update(function(error) {
|
||||||
cfg.dbVersion = 3; // app requires database version 2
|
expect(error).to.exist;
|
||||||
appConfigStorageStub.listItems.withArgs(versionDbType).yieldsAsync(null, [2]); // database version is 0
|
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
||||||
});
|
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
|
||||||
afterEach(function() {
|
done();
|
||||||
// database version is only queried for version checking prior to the update script
|
|
||||||
// so no need to check this in case-specific tests
|
|
||||||
expect(appConfigStorageStub.listItems.calledOnce).to.be.true;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work', function(done) {
|
|
||||||
userStorageStub.removeList.withArgs(emailDbType).yieldsAsync();
|
|
||||||
appConfigStorageStub.storeList.withArgs([3], versionDbType).yieldsAsync();
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.not.exist;
|
|
||||||
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
|
||||||
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail when persisting database version fails', function(done) {
|
|
||||||
userStorageStub.removeList.yieldsAsync();
|
|
||||||
appConfigStorageStub.storeList.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
|
||||||
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail when wiping emails from database fails', function(done) {
|
|
||||||
userStorageStub.removeList.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
|
||||||
expect(appConfigStorageStub.storeList.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
describe('v3 -> v4', function() {
|
|
||||||
var EMAIL_ADDR_DB_KEY = 'emailaddress';
|
|
||||||
var USERNAME_DB_KEY = 'username';
|
|
||||||
var PROVIDER_DB_KEY = 'provider';
|
|
||||||
var IMAP_DB_KEY = 'imap';
|
|
||||||
var SMTP_DB_KEY = 'smtp';
|
|
||||||
var REALNAME_DB_KEY = 'realname';
|
|
||||||
var emailaddress = 'bla@blubb.io';
|
|
||||||
|
|
||||||
var imap = config.gmail.imap,
|
|
||||||
smtp = config.gmail.smtp;
|
|
||||||
|
|
||||||
beforeEach(function() {
|
|
||||||
cfg.dbVersion = 4; // app requires database version 4
|
|
||||||
appConfigStorageStub.listItems.withArgs(versionDbType).yieldsAsync(null, [3]); // database version is 3
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should add gmail as mail service provider with email address and no provider present in db', function(done) {
|
|
||||||
appConfigStorageStub.listItems.withArgs(EMAIL_ADDR_DB_KEY).yieldsAsync(null, [emailaddress]);
|
|
||||||
appConfigStorageStub.listItems.withArgs(PROVIDER_DB_KEY).yieldsAsync(null, []);
|
|
||||||
appConfigStorageStub.storeList.withArgs([4], versionDbType).yieldsAsync();
|
|
||||||
appConfigStorageStub.storeList.withArgs(['gmail'], PROVIDER_DB_KEY).yieldsAsync();
|
|
||||||
appConfigStorageStub.storeList.withArgs([emailaddress], USERNAME_DB_KEY).yieldsAsync();
|
|
||||||
appConfigStorageStub.storeList.withArgs([imap], IMAP_DB_KEY).yieldsAsync();
|
|
||||||
appConfigStorageStub.storeList.withArgs([smtp], SMTP_DB_KEY).yieldsAsync();
|
|
||||||
appConfigStorageStub.storeList.withArgs([''], REALNAME_DB_KEY).yieldsAsync();
|
|
||||||
authStub._loadCredentials.yieldsAsync();
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.not.exist;
|
|
||||||
expect(appConfigStorageStub.storeList.callCount).to.equal(6);
|
|
||||||
expect(appConfigStorageStub.listItems.calledThrice).to.be.true;
|
|
||||||
expect(authStub._loadCredentials.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not add a provider when no email adress is in db', function(done) {
|
|
||||||
appConfigStorageStub.listItems.withArgs(EMAIL_ADDR_DB_KEY).yieldsAsync(null, []);
|
|
||||||
appConfigStorageStub.listItems.withArgs(PROVIDER_DB_KEY).yieldsAsync(null, []);
|
|
||||||
appConfigStorageStub.storeList.withArgs([4], versionDbType).yieldsAsync();
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.not.exist;
|
|
||||||
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
expect(appConfigStorageStub.listItems.calledThrice).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail when appConfigStore write fails', function(done) {
|
|
||||||
appConfigStorageStub.listItems.yieldsAsync(null, []);
|
|
||||||
appConfigStorageStub.storeList.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(appConfigStorageStub.listItems.calledThrice).to.be.true;
|
|
||||||
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should fail when appConfigStore read fails', function(done) {
|
|
||||||
appConfigStorageStub.listItems.withArgs(EMAIL_ADDR_DB_KEY).yieldsAsync(new Error());
|
|
||||||
appConfigStorageStub.storeList.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.exist;
|
|
||||||
expect(appConfigStorageStub.listItems.calledTwice).to.be.true;
|
|
||||||
expect(appConfigStorageStub.storeList.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('v4 -> v5', function() {
|
it('should fail when wiping emails from database fails', function(done) {
|
||||||
var FOLDER_TYPE_INBOX = 'Inbox';
|
userStorageStub.removeList.yieldsAsync(new Error());
|
||||||
var FOLDER_TYPE_SENT = 'Sent';
|
|
||||||
var FOLDER_TYPE_DRAFTS = 'Drafts';
|
|
||||||
var FOLDER_TYPE_TRASH = 'Trash';
|
|
||||||
|
|
||||||
var FOLDER_DB_TYPE = 'folders';
|
updateHandler.update(function(error) {
|
||||||
var VERSION_DB_TYPE = 'dbVersion';
|
expect(error).to.exist;
|
||||||
|
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
||||||
|
expect(appConfigStorageStub.storeList.called).to.be.false;
|
||||||
|
|
||||||
var POST_UPDATE_DB_VERSION = 5;
|
done();
|
||||||
|
|
||||||
beforeEach(function() {
|
|
||||||
cfg.dbVersion = 5; // app requires database version 4
|
|
||||||
appConfigStorageStub.listItems.withArgs(VERSION_DB_TYPE).yieldsAsync(null, [4]); // database version is 4
|
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
describe('v1 -> v2', function() {
|
||||||
// database version is only queried for version checking prior to the update script
|
var emailDbType = 'email_';
|
||||||
// so no need to check this in case-specific tests
|
|
||||||
expect(appConfigStorageStub.listItems.calledOnce).to.be.true;
|
beforeEach(function() {
|
||||||
|
cfg.dbVersion = 2; // app requires database version 2
|
||||||
|
appConfigStorageStub.listItems.withArgs(versionDbType).yieldsAsync(null, [1]); // database version is 0
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
// database version is only queried for version checking prior to the update script
|
||||||
|
// so no need to check this in case-specific tests
|
||||||
|
expect(appConfigStorageStub.listItems.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
userStorageStub.removeList.withArgs(emailDbType).yieldsAsync();
|
||||||
|
appConfigStorageStub.storeList.withArgs([2], versionDbType).yieldsAsync();
|
||||||
|
|
||||||
|
updateHandler.update(function(error) {
|
||||||
|
expect(error).to.not.exist;
|
||||||
|
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
||||||
|
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should work', function(done) {
|
it('should fail when persisting database version fails', function(done) {
|
||||||
userStorageStub.listItems.withArgs(FOLDER_DB_TYPE).yieldsAsync(null, [
|
userStorageStub.removeList.yieldsAsync();
|
||||||
[{
|
appConfigStorageStub.storeList.yieldsAsync(new Error());
|
||||||
name: 'inbox1',
|
|
||||||
type: FOLDER_TYPE_INBOX
|
|
||||||
}, {
|
|
||||||
name: 'inbox2',
|
|
||||||
type: FOLDER_TYPE_INBOX
|
|
||||||
}, {
|
|
||||||
name: 'sent1',
|
|
||||||
type: FOLDER_TYPE_SENT
|
|
||||||
}, {
|
|
||||||
name: 'sent2',
|
|
||||||
type: FOLDER_TYPE_SENT
|
|
||||||
}, {
|
|
||||||
name: 'drafts1',
|
|
||||||
type: FOLDER_TYPE_DRAFTS
|
|
||||||
}, {
|
|
||||||
name: 'drafts2',
|
|
||||||
type: FOLDER_TYPE_DRAFTS
|
|
||||||
}, {
|
|
||||||
name: 'trash1',
|
|
||||||
type: FOLDER_TYPE_TRASH
|
|
||||||
}, {
|
|
||||||
name: 'trash2',
|
|
||||||
type: FOLDER_TYPE_TRASH
|
|
||||||
}]
|
|
||||||
]);
|
|
||||||
|
|
||||||
userStorageStub.storeList.withArgs([
|
updateHandler.update(function(error) {
|
||||||
[{
|
expect(error).to.exist;
|
||||||
name: 'inbox1',
|
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
||||||
type: FOLDER_TYPE_INBOX
|
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
||||||
}, {
|
|
||||||
name: 'sent1',
|
|
||||||
type: FOLDER_TYPE_SENT
|
|
||||||
}, {
|
|
||||||
name: 'drafts1',
|
|
||||||
type: FOLDER_TYPE_DRAFTS
|
|
||||||
}, {
|
|
||||||
name: 'trash1',
|
|
||||||
type: FOLDER_TYPE_TRASH
|
|
||||||
}]
|
|
||||||
], FOLDER_DB_TYPE).yieldsAsync();
|
|
||||||
|
|
||||||
appConfigStorageStub.storeList.withArgs([POST_UPDATE_DB_VERSION], VERSION_DB_TYPE).yieldsAsync();
|
done();
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
|
||||||
expect(error).to.not.exist;
|
|
||||||
expect(userStorageStub.listItems.calledOnce).to.be.true;
|
|
||||||
expect(userStorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should fail when persisting database version fails', function(done) {
|
it('should fail when wiping emails from database fails', function(done) {
|
||||||
userStorageStub.listItems.yieldsAsync(null, []);
|
userStorageStub.removeList.yieldsAsync(new Error());
|
||||||
userStorageStub.storeList.yieldsAsync();
|
|
||||||
appConfigStorageStub.storeList.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
updateHandler.update(function(error) {
|
||||||
expect(error).to.exist;
|
expect(error).to.exist;
|
||||||
expect(userStorageStub.listItems.calledOnce).to.be.true;
|
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
||||||
expect(userStorageStub.storeList.calledOnce).to.be.true;
|
expect(appConfigStorageStub.storeList.called).to.be.false;
|
||||||
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
done();
|
done();
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should fail when persisting folders fails', function(done) {
|
describe('v2 -> v3', function() {
|
||||||
userStorageStub.listItems.yieldsAsync(null, []);
|
var emailDbType = 'email_';
|
||||||
userStorageStub.storeList.yieldsAsync(new Error());
|
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
beforeEach(function() {
|
||||||
expect(error).to.exist;
|
cfg.dbVersion = 3; // app requires database version 2
|
||||||
expect(userStorageStub.listItems.calledOnce).to.be.true;
|
appConfigStorageStub.listItems.withArgs(versionDbType).yieldsAsync(null, [2]); // database version is 0
|
||||||
expect(userStorageStub.storeList.calledOnce).to.be.true;
|
});
|
||||||
expect(appConfigStorageStub.storeList.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
afterEach(function() {
|
||||||
});
|
// database version is only queried for version checking prior to the update script
|
||||||
|
// so no need to check this in case-specific tests
|
||||||
|
expect(appConfigStorageStub.listItems.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
userStorageStub.removeList.withArgs(emailDbType).yieldsAsync();
|
||||||
|
appConfigStorageStub.storeList.withArgs([3], versionDbType).yieldsAsync();
|
||||||
|
|
||||||
|
updateHandler.update(function(error) {
|
||||||
|
expect(error).to.not.exist;
|
||||||
|
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
||||||
|
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('should fail when listing folders fails', function(done) {
|
it('should fail when persisting database version fails', function(done) {
|
||||||
userStorageStub.listItems.yieldsAsync(new Error());
|
userStorageStub.removeList.yieldsAsync();
|
||||||
|
appConfigStorageStub.storeList.yieldsAsync(new Error());
|
||||||
|
|
||||||
updateHandler.update(function(error) {
|
updateHandler.update(function(error) {
|
||||||
expect(error).to.exist;
|
expect(error).to.exist;
|
||||||
expect(userStorageStub.listItems.calledOnce).to.be.true;
|
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
||||||
expect(userStorageStub.storeList.called).to.be.false;
|
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
||||||
expect(appConfigStorageStub.storeList.called).to.be.false;
|
|
||||||
|
|
||||||
done();
|
done();
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail when wiping emails from database fails', function(done) {
|
||||||
|
userStorageStub.removeList.yieldsAsync(new Error());
|
||||||
|
|
||||||
|
updateHandler.update(function(error) {
|
||||||
|
expect(error).to.exist;
|
||||||
|
expect(userStorageStub.removeList.calledOnce).to.be.true;
|
||||||
|
expect(appConfigStorageStub.storeList.called).to.be.false;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
describe('v3 -> v4', function() {
|
||||||
|
var EMAIL_ADDR_DB_KEY = 'emailaddress';
|
||||||
|
var USERNAME_DB_KEY = 'username';
|
||||||
|
var PROVIDER_DB_KEY = 'provider';
|
||||||
|
var IMAP_DB_KEY = 'imap';
|
||||||
|
var SMTP_DB_KEY = 'smtp';
|
||||||
|
var REALNAME_DB_KEY = 'realname';
|
||||||
|
var emailaddress = 'bla@blubb.io';
|
||||||
|
|
||||||
|
var imap = config.gmail.imap,
|
||||||
|
smtp = config.gmail.smtp;
|
||||||
|
|
||||||
|
beforeEach(function() {
|
||||||
|
cfg.dbVersion = 4; // app requires database version 4
|
||||||
|
appConfigStorageStub.listItems.withArgs(versionDbType).yieldsAsync(null, [3]); // database version is 3
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should add gmail as mail service provider with email address and no provider present in db', function(done) {
|
||||||
|
appConfigStorageStub.listItems.withArgs(EMAIL_ADDR_DB_KEY).yieldsAsync(null, [emailaddress]);
|
||||||
|
appConfigStorageStub.listItems.withArgs(PROVIDER_DB_KEY).yieldsAsync(null, []);
|
||||||
|
appConfigStorageStub.storeList.withArgs([4], versionDbType).yieldsAsync();
|
||||||
|
appConfigStorageStub.storeList.withArgs(['gmail'], PROVIDER_DB_KEY).yieldsAsync();
|
||||||
|
appConfigStorageStub.storeList.withArgs([emailaddress], USERNAME_DB_KEY).yieldsAsync();
|
||||||
|
appConfigStorageStub.storeList.withArgs([imap], IMAP_DB_KEY).yieldsAsync();
|
||||||
|
appConfigStorageStub.storeList.withArgs([smtp], SMTP_DB_KEY).yieldsAsync();
|
||||||
|
appConfigStorageStub.storeList.withArgs([''], REALNAME_DB_KEY).yieldsAsync();
|
||||||
|
authStub._loadCredentials.yieldsAsync();
|
||||||
|
|
||||||
|
updateHandler.update(function(error) {
|
||||||
|
expect(error).to.not.exist;
|
||||||
|
expect(appConfigStorageStub.storeList.callCount).to.equal(6);
|
||||||
|
expect(appConfigStorageStub.listItems.calledThrice).to.be.true;
|
||||||
|
expect(authStub._loadCredentials.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not add a provider when no email adress is in db', function(done) {
|
||||||
|
appConfigStorageStub.listItems.withArgs(EMAIL_ADDR_DB_KEY).yieldsAsync(null, []);
|
||||||
|
appConfigStorageStub.listItems.withArgs(PROVIDER_DB_KEY).yieldsAsync(null, []);
|
||||||
|
appConfigStorageStub.storeList.withArgs([4], versionDbType).yieldsAsync();
|
||||||
|
|
||||||
|
updateHandler.update(function(error) {
|
||||||
|
expect(error).to.not.exist;
|
||||||
|
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
expect(appConfigStorageStub.listItems.calledThrice).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail when appConfigStore write fails', function(done) {
|
||||||
|
appConfigStorageStub.listItems.yieldsAsync(null, []);
|
||||||
|
appConfigStorageStub.storeList.yieldsAsync(new Error());
|
||||||
|
|
||||||
|
updateHandler.update(function(error) {
|
||||||
|
expect(error).to.exist;
|
||||||
|
expect(appConfigStorageStub.listItems.calledThrice).to.be.true;
|
||||||
|
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail when appConfigStore read fails', function(done) {
|
||||||
|
appConfigStorageStub.listItems.withArgs(EMAIL_ADDR_DB_KEY).yieldsAsync(new Error());
|
||||||
|
appConfigStorageStub.storeList.yieldsAsync(new Error());
|
||||||
|
|
||||||
|
updateHandler.update(function(error) {
|
||||||
|
expect(error).to.exist;
|
||||||
|
expect(appConfigStorageStub.listItems.calledTwice).to.be.true;
|
||||||
|
expect(appConfigStorageStub.storeList.called).to.be.false;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('v4 -> v5', function() {
|
||||||
|
var FOLDER_TYPE_INBOX = 'Inbox';
|
||||||
|
var FOLDER_TYPE_SENT = 'Sent';
|
||||||
|
var FOLDER_TYPE_DRAFTS = 'Drafts';
|
||||||
|
var FOLDER_TYPE_TRASH = 'Trash';
|
||||||
|
|
||||||
|
var FOLDER_DB_TYPE = 'folders';
|
||||||
|
var VERSION_DB_TYPE = 'dbVersion';
|
||||||
|
|
||||||
|
var POST_UPDATE_DB_VERSION = 5;
|
||||||
|
|
||||||
|
beforeEach(function() {
|
||||||
|
cfg.dbVersion = 5; // app requires database version 4
|
||||||
|
appConfigStorageStub.listItems.withArgs(VERSION_DB_TYPE).yieldsAsync(null, [4]); // database version is 4
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
// database version is only queried for version checking prior to the update script
|
||||||
|
// so no need to check this in case-specific tests
|
||||||
|
expect(appConfigStorageStub.listItems.calledOnce).to.be.true;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work', function(done) {
|
||||||
|
userStorageStub.listItems.withArgs(FOLDER_DB_TYPE).yieldsAsync(null, [
|
||||||
|
[{
|
||||||
|
name: 'inbox1',
|
||||||
|
type: FOLDER_TYPE_INBOX
|
||||||
|
}, {
|
||||||
|
name: 'inbox2',
|
||||||
|
type: FOLDER_TYPE_INBOX
|
||||||
|
}, {
|
||||||
|
name: 'sent1',
|
||||||
|
type: FOLDER_TYPE_SENT
|
||||||
|
}, {
|
||||||
|
name: 'sent2',
|
||||||
|
type: FOLDER_TYPE_SENT
|
||||||
|
}, {
|
||||||
|
name: 'drafts1',
|
||||||
|
type: FOLDER_TYPE_DRAFTS
|
||||||
|
}, {
|
||||||
|
name: 'drafts2',
|
||||||
|
type: FOLDER_TYPE_DRAFTS
|
||||||
|
}, {
|
||||||
|
name: 'trash1',
|
||||||
|
type: FOLDER_TYPE_TRASH
|
||||||
|
}, {
|
||||||
|
name: 'trash2',
|
||||||
|
type: FOLDER_TYPE_TRASH
|
||||||
|
}]
|
||||||
|
]);
|
||||||
|
|
||||||
|
userStorageStub.storeList.withArgs([
|
||||||
|
[{
|
||||||
|
name: 'inbox1',
|
||||||
|
type: FOLDER_TYPE_INBOX
|
||||||
|
}, {
|
||||||
|
name: 'sent1',
|
||||||
|
type: FOLDER_TYPE_SENT
|
||||||
|
}, {
|
||||||
|
name: 'drafts1',
|
||||||
|
type: FOLDER_TYPE_DRAFTS
|
||||||
|
}, {
|
||||||
|
name: 'trash1',
|
||||||
|
type: FOLDER_TYPE_TRASH
|
||||||
|
}]
|
||||||
|
], FOLDER_DB_TYPE).yieldsAsync();
|
||||||
|
|
||||||
|
appConfigStorageStub.storeList.withArgs([POST_UPDATE_DB_VERSION], VERSION_DB_TYPE).yieldsAsync();
|
||||||
|
|
||||||
|
updateHandler.update(function(error) {
|
||||||
|
expect(error).to.not.exist;
|
||||||
|
expect(userStorageStub.listItems.calledOnce).to.be.true;
|
||||||
|
expect(userStorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail when persisting database version fails', function(done) {
|
||||||
|
userStorageStub.listItems.yieldsAsync(null, []);
|
||||||
|
userStorageStub.storeList.yieldsAsync();
|
||||||
|
appConfigStorageStub.storeList.yieldsAsync(new Error());
|
||||||
|
|
||||||
|
updateHandler.update(function(error) {
|
||||||
|
expect(error).to.exist;
|
||||||
|
expect(userStorageStub.listItems.calledOnce).to.be.true;
|
||||||
|
expect(userStorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
expect(appConfigStorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail when persisting folders fails', function(done) {
|
||||||
|
userStorageStub.listItems.yieldsAsync(null, []);
|
||||||
|
userStorageStub.storeList.yieldsAsync(new Error());
|
||||||
|
|
||||||
|
updateHandler.update(function(error) {
|
||||||
|
expect(error).to.exist;
|
||||||
|
expect(userStorageStub.listItems.calledOnce).to.be.true;
|
||||||
|
expect(userStorageStub.storeList.calledOnce).to.be.true;
|
||||||
|
expect(appConfigStorageStub.storeList.called).to.be.false;
|
||||||
|
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should fail when listing folders fails', function(done) {
|
||||||
|
userStorageStub.listItems.yieldsAsync(new Error());
|
||||||
|
|
||||||
|
updateHandler.update(function(error) {
|
||||||
|
expect(error).to.exist;
|
||||||
|
expect(userStorageStub.listItems.calledOnce).to.be.true;
|
||||||
|
expect(userStorageStub.storeList.called).to.be.false;
|
||||||
|
expect(appConfigStorageStub.storeList.called).to.be.false;
|
||||||
|
|
||||||
|
done();
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -1,401 +1,397 @@
|
|||||||
define(function(require) {
|
'use strict';
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var expect = chai.expect,
|
var mocks = angular.mocks,
|
||||||
angular = require('angular'),
|
WriteCtrl = require('../../src/js/controller/write'),
|
||||||
mocks = require('angularMocks'),
|
EmailDAO = require('../../src/js/dao/email-dao'),
|
||||||
WriteCtrl = require('js/controller/write'),
|
OutboxBO = require('../../src/js/bo/outbox'),
|
||||||
EmailDAO = require('js/dao/email-dao'),
|
KeychainDAO = require('../../src/js/dao/keychain-dao'),
|
||||||
OutboxBO = require('js/bo/outbox'),
|
appController = require('../../src/js/app-controller');
|
||||||
KeychainDAO = require('js/dao/keychain-dao'),
|
|
||||||
appController = require('js/app-controller');
|
|
||||||
|
|
||||||
describe('Write controller unit test', function() {
|
describe('Write controller unit test', function() {
|
||||||
var ctrl, scope,
|
var ctrl, scope,
|
||||||
origEmailDao, origOutbox, origKeychain,
|
origEmailDao, origOutbox, origKeychain,
|
||||||
emailDaoMock, keychainMock, outboxMock, emailAddress, realname;
|
emailDaoMock, keychainMock, outboxMock, emailAddress, realname;
|
||||||
|
|
||||||
beforeEach(function() {
|
beforeEach(function() {
|
||||||
// the app controller is a singleton, we need to remember the
|
// the app controller is a singleton, we need to remember the
|
||||||
// outbox and email dao to restore it after the tests
|
// outbox and email dao to restore it after the tests
|
||||||
origEmailDao = appController._emailDao;
|
origEmailDao = appController._emailDao;
|
||||||
origOutbox = appController._outboxBo;
|
origOutbox = appController._outboxBo;
|
||||||
origKeychain = appController._keychain;
|
origKeychain = appController._keychain;
|
||||||
|
|
||||||
outboxMock = sinon.createStubInstance(OutboxBO);
|
outboxMock = sinon.createStubInstance(OutboxBO);
|
||||||
appController._outboxBo = outboxMock;
|
appController._outboxBo = outboxMock;
|
||||||
|
|
||||||
emailDaoMock = sinon.createStubInstance(EmailDAO);
|
emailDaoMock = sinon.createStubInstance(EmailDAO);
|
||||||
appController._emailDao = emailDaoMock;
|
appController._emailDao = emailDaoMock;
|
||||||
|
|
||||||
emailAddress = 'fred@foo.com';
|
emailAddress = 'fred@foo.com';
|
||||||
realname = 'Fred Foo';
|
realname = 'Fred Foo';
|
||||||
emailDaoMock._account = {
|
emailDaoMock._account = {
|
||||||
emailAddress: emailAddress,
|
emailAddress: emailAddress,
|
||||||
realname: realname
|
realname: realname
|
||||||
};
|
};
|
||||||
|
|
||||||
keychainMock = sinon.createStubInstance(KeychainDAO);
|
keychainMock = sinon.createStubInstance(KeychainDAO);
|
||||||
appController._keychain = keychainMock;
|
appController._keychain = keychainMock;
|
||||||
|
|
||||||
angular.module('writetest', []);
|
angular.module('writetest', []);
|
||||||
mocks.module('writetest');
|
mocks.module('writetest');
|
||||||
mocks.inject(function($rootScope, $controller) {
|
mocks.inject(function($rootScope, $controller) {
|
||||||
scope = $rootScope.$new();
|
scope = $rootScope.$new();
|
||||||
scope.state = {};
|
scope.state = {};
|
||||||
ctrl = $controller(WriteCtrl, {
|
ctrl = $controller(WriteCtrl, {
|
||||||
$scope: scope
|
$scope: scope
|
||||||
});
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
afterEach(function() {
|
afterEach(function() {
|
||||||
// restore the app controller
|
// restore the app controller
|
||||||
appController._emailDao = origEmailDao;
|
appController._emailDao = origEmailDao;
|
||||||
appController._outboxBo = origOutbox;
|
appController._outboxBo = origOutbox;
|
||||||
appController._keychain = origKeychain;
|
appController._keychain = origKeychain;
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('scope variables', function() {
|
||||||
|
it('should be set correctly', function() {
|
||||||
|
expect(scope.state.writer).to.exist;
|
||||||
|
expect(scope.state.lightbox).to.be.undefined;
|
||||||
|
expect(scope.state.writer.write).to.exist;
|
||||||
|
expect(scope.state.writer.close).to.exist;
|
||||||
|
expect(scope.verify).to.exist;
|
||||||
|
expect(scope.checkSendStatus).to.exist;
|
||||||
|
expect(scope.sendToOutbox).to.exist;
|
||||||
|
expect(scope.tagStyle).to.exist;
|
||||||
|
expect(scope.lookupAddressBook).to.exist;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('close', function() {
|
||||||
|
it('should close the writer', function() {
|
||||||
|
scope.state.lightbox = 'write';
|
||||||
|
|
||||||
|
scope.state.writer.close();
|
||||||
|
|
||||||
|
expect(scope.state.lightbox).to.be.undefined;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('write', function() {
|
||||||
|
it('should prepare write view', function() {
|
||||||
|
var verifyMock = sinon.stub(scope, 'verify');
|
||||||
|
|
||||||
|
scope.state.writer.write();
|
||||||
|
|
||||||
|
expect(scope.writerTitle).to.equal('New email');
|
||||||
|
expect(scope.to).to.deep.equal([]);
|
||||||
|
expect(scope.subject).to.equal('');
|
||||||
|
expect(scope.body).to.equal('');
|
||||||
|
expect(verifyMock.calledOnce).to.be.true;
|
||||||
|
|
||||||
|
scope.verify.restore();
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('scope variables', function() {
|
it('should prefill write view for response', function() {
|
||||||
it('should be set correctly', function() {
|
var verifyMock = sinon.stub(scope, 'verify'),
|
||||||
expect(scope.state.writer).to.exist;
|
address = 'pity@dafool',
|
||||||
expect(scope.state.lightbox).to.be.undefined;
|
subject = 'Ermahgerd!',
|
||||||
expect(scope.state.writer.write).to.exist;
|
body = 'so much body!',
|
||||||
expect(scope.state.writer.close).to.exist;
|
re = {
|
||||||
expect(scope.verify).to.exist;
|
id: 'abc',
|
||||||
expect(scope.checkSendStatus).to.exist;
|
from: [{
|
||||||
expect(scope.sendToOutbox).to.exist;
|
address: address
|
||||||
expect(scope.tagStyle).to.exist;
|
}],
|
||||||
expect(scope.lookupAddressBook).to.exist;
|
subject: subject,
|
||||||
});
|
sentDate: new Date(),
|
||||||
|
body: body,
|
||||||
|
references: ['ghi', 'def']
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.sendBtnSecure = true;
|
||||||
|
|
||||||
|
scope.state.writer.write(re);
|
||||||
|
|
||||||
|
expect(scope.writerTitle).to.equal('Reply');
|
||||||
|
expect(scope.to).to.deep.equal([{
|
||||||
|
address: address,
|
||||||
|
}]);
|
||||||
|
expect(scope.subject).to.equal('Re: ' + subject);
|
||||||
|
expect(scope.body).to.contain(body);
|
||||||
|
expect(scope.references).to.deep.equal(['ghi', 'def', 'abc']);
|
||||||
|
expect(verifyMock.called).to.be.true;
|
||||||
|
|
||||||
|
scope.verify.restore();
|
||||||
});
|
});
|
||||||
|
|
||||||
describe('close', function() {
|
it('should prefill write view for forward', function() {
|
||||||
it('should close the writer', function() {
|
var verifyMock = sinon.stub(scope, 'verify'),
|
||||||
scope.state.lightbox = 'write';
|
address = 'pity@dafool',
|
||||||
|
subject = 'Ermahgerd!',
|
||||||
scope.state.writer.close();
|
body = 'so much body!',
|
||||||
|
re = {
|
||||||
expect(scope.state.lightbox).to.be.undefined;
|
from: [{
|
||||||
});
|
address: address
|
||||||
});
|
}],
|
||||||
|
to: [{
|
||||||
describe('write', function() {
|
address: address
|
||||||
it('should prepare write view', function() {
|
}],
|
||||||
var verifyMock = sinon.stub(scope, 'verify');
|
subject: subject,
|
||||||
|
sentDate: new Date(),
|
||||||
scope.state.writer.write();
|
body: body,
|
||||||
|
attachments: [{}]
|
||||||
expect(scope.writerTitle).to.equal('New email');
|
|
||||||
expect(scope.to).to.deep.equal([]);
|
|
||||||
expect(scope.subject).to.equal('');
|
|
||||||
expect(scope.body).to.equal('');
|
|
||||||
expect(verifyMock.calledOnce).to.be.true;
|
|
||||||
|
|
||||||
scope.verify.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should prefill write view for response', function() {
|
|
||||||
var verifyMock = sinon.stub(scope, 'verify'),
|
|
||||||
address = 'pity@dafool',
|
|
||||||
subject = 'Ermahgerd!',
|
|
||||||
body = 'so much body!',
|
|
||||||
re = {
|
|
||||||
id: 'abc',
|
|
||||||
from: [{
|
|
||||||
address: address
|
|
||||||
}],
|
|
||||||
subject: subject,
|
|
||||||
sentDate: new Date(),
|
|
||||||
body: body,
|
|
||||||
references: ['ghi', 'def']
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.sendBtnSecure = true;
|
|
||||||
|
|
||||||
scope.state.writer.write(re);
|
|
||||||
|
|
||||||
expect(scope.writerTitle).to.equal('Reply');
|
|
||||||
expect(scope.to).to.deep.equal([{
|
|
||||||
address: address,
|
|
||||||
}]);
|
|
||||||
expect(scope.subject).to.equal('Re: ' + subject);
|
|
||||||
expect(scope.body).to.contain(body);
|
|
||||||
expect(scope.references).to.deep.equal(['ghi', 'def', 'abc']);
|
|
||||||
expect(verifyMock.called).to.be.true;
|
|
||||||
|
|
||||||
scope.verify.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should prefill write view for forward', function() {
|
|
||||||
var verifyMock = sinon.stub(scope, 'verify'),
|
|
||||||
address = 'pity@dafool',
|
|
||||||
subject = 'Ermahgerd!',
|
|
||||||
body = 'so much body!',
|
|
||||||
re = {
|
|
||||||
from: [{
|
|
||||||
address: address
|
|
||||||
}],
|
|
||||||
to: [{
|
|
||||||
address: address
|
|
||||||
}],
|
|
||||||
subject: subject,
|
|
||||||
sentDate: new Date(),
|
|
||||||
body: body,
|
|
||||||
attachments: [{}]
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.sendBtnSecure = false;
|
|
||||||
|
|
||||||
scope.state.writer.write(re, null, true);
|
|
||||||
|
|
||||||
expect(scope.writerTitle).to.equal('Forward');
|
|
||||||
expect(scope.to).to.deep.equal([]);
|
|
||||||
expect(scope.subject).to.equal('Fwd: ' + subject);
|
|
||||||
expect(scope.body).to.contain(body);
|
|
||||||
expect(verifyMock.called).to.be.true;
|
|
||||||
expect(scope.attachments).to.not.equal(re.attachments); // not the same reference
|
|
||||||
expect(scope.attachments).to.deep.equal(re.attachments); // but the same content
|
|
||||||
|
|
||||||
scope.verify.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('verify', function() {
|
|
||||||
var checkSendStatusMock;
|
|
||||||
|
|
||||||
beforeEach(function() {
|
|
||||||
checkSendStatusMock = sinon.stub(scope, 'checkSendStatus');
|
|
||||||
});
|
|
||||||
|
|
||||||
afterEach(function() {
|
|
||||||
scope.checkSendStatus.restore();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should do nothing if recipient is not provided', function() {
|
|
||||||
scope.verify(undefined);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not work for invalid email addresses', function() {
|
|
||||||
var recipient = {
|
|
||||||
address: ''
|
|
||||||
};
|
};
|
||||||
|
|
||||||
scope.verify(recipient);
|
scope.sendBtnSecure = false;
|
||||||
|
|
||||||
expect(recipient.key).to.be.undefined;
|
scope.state.writer.write(re, null, true);
|
||||||
expect(recipient.secure).to.be.undefined;
|
|
||||||
expect(scope.checkSendStatus.callCount).to.equal(2);
|
|
||||||
expect(keychainMock.getReceiverPublicKey.called).to.be.false;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should not work for error in keychain', function(done) {
|
expect(scope.writerTitle).to.equal('Forward');
|
||||||
var recipient = {
|
expect(scope.to).to.deep.equal([]);
|
||||||
address: 'asds@example.com'
|
expect(scope.subject).to.equal('Fwd: ' + subject);
|
||||||
};
|
expect(scope.body).to.contain(body);
|
||||||
|
expect(verifyMock.called).to.be.true;
|
||||||
|
expect(scope.attachments).to.not.equal(re.attachments); // not the same reference
|
||||||
|
expect(scope.attachments).to.deep.equal(re.attachments); // but the same content
|
||||||
|
|
||||||
keychainMock.refreshKeyForUserId.withArgs(recipient.address).yields({
|
scope.verify.restore();
|
||||||
errMsg: '404 not found yadda yadda'
|
|
||||||
});
|
|
||||||
|
|
||||||
scope.onError = function() {
|
|
||||||
expect(recipient.key).to.be.undefined;
|
|
||||||
expect(recipient.secure).to.be.false;
|
|
||||||
expect(scope.checkSendStatus.callCount).to.equal(1);
|
|
||||||
expect(keychainMock.refreshKeyForUserId.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.verify(recipient);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work for main userId', function(done) {
|
|
||||||
var recipient = {
|
|
||||||
address: 'asdf@example.com'
|
|
||||||
};
|
|
||||||
|
|
||||||
keychainMock.refreshKeyForUserId.withArgs(recipient.address).yields(null, {
|
|
||||||
userId: 'asdf@example.com'
|
|
||||||
});
|
|
||||||
|
|
||||||
scope.$digest = function() {
|
|
||||||
expect(recipient.key).to.deep.equal({
|
|
||||||
userId: 'asdf@example.com'
|
|
||||||
});
|
|
||||||
expect(recipient.secure).to.be.true;
|
|
||||||
expect(scope.checkSendStatus.callCount).to.equal(2);
|
|
||||||
expect(keychainMock.refreshKeyForUserId.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.verify(recipient);
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work for secondary userId', function(done) {
|
|
||||||
var recipient = {
|
|
||||||
address: 'asdf@example.com'
|
|
||||||
};
|
|
||||||
var key = {
|
|
||||||
userId: 'qwer@example.com',
|
|
||||||
userIds: [{
|
|
||||||
emailAddress: 'asdf@example.com'
|
|
||||||
}]
|
|
||||||
};
|
|
||||||
|
|
||||||
keychainMock.refreshKeyForUserId.withArgs(recipient.address).yields(null, key);
|
|
||||||
|
|
||||||
scope.$digest = function() {
|
|
||||||
expect(recipient.key).to.deep.equal(key);
|
|
||||||
expect(recipient.secure).to.be.true;
|
|
||||||
expect(scope.checkSendStatus.callCount).to.equal(2);
|
|
||||||
expect(keychainMock.refreshKeyForUserId.calledOnce).to.be.true;
|
|
||||||
done();
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.verify(recipient);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('checkSendStatus', function() {
|
|
||||||
beforeEach(function() {
|
|
||||||
scope.state.writer.write();
|
|
||||||
});
|
|
||||||
|
|
||||||
afterEach(function() {});
|
|
||||||
|
|
||||||
it('should not be able to send with no recipients', function() {
|
|
||||||
scope.checkSendStatus();
|
|
||||||
|
|
||||||
expect(scope.okToSend).to.be.false;
|
|
||||||
expect(scope.sendBtnText).to.be.undefined;
|
|
||||||
expect(scope.sendBtnSecure).to.be.undefined;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should be able to send plaintext', function() {
|
|
||||||
scope.to = [{
|
|
||||||
address: 'asdf@asdf.de'
|
|
||||||
}];
|
|
||||||
scope.checkSendStatus();
|
|
||||||
|
|
||||||
expect(scope.okToSend).to.be.true;
|
|
||||||
expect(scope.sendBtnText).to.equal('Send');
|
|
||||||
expect(scope.sendBtnSecure).to.be.false;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should send plaintext if one receiver is not secure', function() {
|
|
||||||
scope.to = [{
|
|
||||||
address: 'asdf@asdf.de',
|
|
||||||
secure: true
|
|
||||||
}, {
|
|
||||||
address: 'asdf@asdfg.de'
|
|
||||||
}];
|
|
||||||
scope.checkSendStatus();
|
|
||||||
|
|
||||||
expect(scope.okToSend).to.be.true;
|
|
||||||
expect(scope.sendBtnText).to.equal('Send');
|
|
||||||
expect(scope.sendBtnSecure).to.be.false;
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should be able to send securely to multiple recipients', function() {
|
|
||||||
scope.to = [{
|
|
||||||
address: 'asdf@asdf.de',
|
|
||||||
secure: true
|
|
||||||
}, {
|
|
||||||
address: 'asdf@asdfg.de',
|
|
||||||
secure: true
|
|
||||||
}];
|
|
||||||
scope.checkSendStatus();
|
|
||||||
|
|
||||||
expect(scope.okToSend).to.be.true;
|
|
||||||
expect(scope.sendBtnText).to.equal('Send securely');
|
|
||||||
expect(scope.sendBtnSecure).to.be.true;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('send to outbox', function() {
|
|
||||||
it('should work', function() {
|
|
||||||
scope.to = [{
|
|
||||||
address: 'pity@dafool'
|
|
||||||
}];
|
|
||||||
scope.cc = [];
|
|
||||||
scope.bcc = [];
|
|
||||||
scope.subject = 'Ermahgerd!';
|
|
||||||
scope.body = 'wow. much body! very text!';
|
|
||||||
scope.attachments = [];
|
|
||||||
scope.state.nav = {
|
|
||||||
currentFolder: 'currentFolder'
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.replyTo = {};
|
|
||||||
|
|
||||||
outboxMock.put.withArgs(sinon.match(function(mail) {
|
|
||||||
expect(mail.from).to.deep.equal([{
|
|
||||||
address: emailAddress,
|
|
||||||
name: realname
|
|
||||||
}]);
|
|
||||||
expect(mail.to).to.deep.equal(scope.to);
|
|
||||||
expect(mail.cc).to.deep.equal(scope.cc);
|
|
||||||
expect(mail.bcc).to.deep.equal(scope.bcc);
|
|
||||||
expect(mail.body).to.contain(scope.body);
|
|
||||||
expect(mail.subject).to.equal(scope.subject);
|
|
||||||
expect(mail.attachments).to.be.empty;
|
|
||||||
expect(mail.sentDate).to.exist;
|
|
||||||
|
|
||||||
|
|
||||||
return true;
|
|
||||||
})).yields();
|
|
||||||
emailDaoMock.setFlags.yields();
|
|
||||||
|
|
||||||
scope.onError = function(err) {
|
|
||||||
expect(err).to.not.exist;
|
|
||||||
};
|
|
||||||
|
|
||||||
scope.sendToOutbox();
|
|
||||||
|
|
||||||
expect(outboxMock.put.calledOnce).to.be.true;
|
|
||||||
expect(emailDaoMock.setFlags.calledOnce).to.be.true;
|
|
||||||
expect(scope.state.lightbox).to.be.undefined;
|
|
||||||
expect(scope.replyTo.answered).to.be.true;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
describe('lookupAddressBook', function() {
|
|
||||||
it('should work', function(done) {
|
|
||||||
keychainMock.listLocalPublicKeys.yields(null, [{
|
|
||||||
userId: 'test@asdf.com',
|
|
||||||
publicKey: 'KEY'
|
|
||||||
}]);
|
|
||||||
|
|
||||||
var result = scope.lookupAddressBook('test');
|
|
||||||
|
|
||||||
result.then(function(response) {
|
|
||||||
expect(response).to.deep.equal([{
|
|
||||||
address: 'test@asdf.com'
|
|
||||||
}]);
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
scope.$digest();
|
|
||||||
});
|
|
||||||
|
|
||||||
it('should work with cache', function(done) {
|
|
||||||
scope.addressBookCache = [{
|
|
||||||
address: 'test@asdf.com'
|
|
||||||
}, {
|
|
||||||
address: 'tes@asdf.com'
|
|
||||||
}];
|
|
||||||
|
|
||||||
var result = scope.lookupAddressBook('test');
|
|
||||||
|
|
||||||
result.then(function(response) {
|
|
||||||
expect(response).to.deep.equal([{
|
|
||||||
address: 'test@asdf.com'
|
|
||||||
}]);
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
scope.$digest();
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe('verify', function() {
|
||||||
|
var checkSendStatusMock;
|
||||||
|
|
||||||
|
beforeEach(function() {
|
||||||
|
checkSendStatusMock = sinon.stub(scope, 'checkSendStatus');
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {
|
||||||
|
scope.checkSendStatus.restore();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should do nothing if recipient is not provided', function() {
|
||||||
|
scope.verify(undefined);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not work for invalid email addresses', function() {
|
||||||
|
var recipient = {
|
||||||
|
address: ''
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.verify(recipient);
|
||||||
|
|
||||||
|
expect(recipient.key).to.be.undefined;
|
||||||
|
expect(recipient.secure).to.be.undefined;
|
||||||
|
expect(scope.checkSendStatus.callCount).to.equal(2);
|
||||||
|
expect(keychainMock.getReceiverPublicKey.called).to.be.false;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should not work for error in keychain', function(done) {
|
||||||
|
var recipient = {
|
||||||
|
address: 'asds@example.com'
|
||||||
|
};
|
||||||
|
|
||||||
|
keychainMock.refreshKeyForUserId.withArgs(recipient.address).yields({
|
||||||
|
errMsg: '404 not found yadda yadda'
|
||||||
|
});
|
||||||
|
|
||||||
|
scope.onError = function() {
|
||||||
|
expect(recipient.key).to.be.undefined;
|
||||||
|
expect(recipient.secure).to.be.false;
|
||||||
|
expect(scope.checkSendStatus.callCount).to.equal(1);
|
||||||
|
expect(keychainMock.refreshKeyForUserId.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.verify(recipient);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work for main userId', function(done) {
|
||||||
|
var recipient = {
|
||||||
|
address: 'asdf@example.com'
|
||||||
|
};
|
||||||
|
|
||||||
|
keychainMock.refreshKeyForUserId.withArgs(recipient.address).yields(null, {
|
||||||
|
userId: 'asdf@example.com'
|
||||||
|
});
|
||||||
|
|
||||||
|
scope.$digest = function() {
|
||||||
|
expect(recipient.key).to.deep.equal({
|
||||||
|
userId: 'asdf@example.com'
|
||||||
|
});
|
||||||
|
expect(recipient.secure).to.be.true;
|
||||||
|
expect(scope.checkSendStatus.callCount).to.equal(2);
|
||||||
|
expect(keychainMock.refreshKeyForUserId.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.verify(recipient);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work for secondary userId', function(done) {
|
||||||
|
var recipient = {
|
||||||
|
address: 'asdf@example.com'
|
||||||
|
};
|
||||||
|
var key = {
|
||||||
|
userId: 'qwer@example.com',
|
||||||
|
userIds: [{
|
||||||
|
emailAddress: 'asdf@example.com'
|
||||||
|
}]
|
||||||
|
};
|
||||||
|
|
||||||
|
keychainMock.refreshKeyForUserId.withArgs(recipient.address).yields(null, key);
|
||||||
|
|
||||||
|
scope.$digest = function() {
|
||||||
|
expect(recipient.key).to.deep.equal(key);
|
||||||
|
expect(recipient.secure).to.be.true;
|
||||||
|
expect(scope.checkSendStatus.callCount).to.equal(2);
|
||||||
|
expect(keychainMock.refreshKeyForUserId.calledOnce).to.be.true;
|
||||||
|
done();
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.verify(recipient);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('checkSendStatus', function() {
|
||||||
|
beforeEach(function() {
|
||||||
|
scope.state.writer.write();
|
||||||
|
});
|
||||||
|
|
||||||
|
afterEach(function() {});
|
||||||
|
|
||||||
|
it('should not be able to send with no recipients', function() {
|
||||||
|
scope.checkSendStatus();
|
||||||
|
|
||||||
|
expect(scope.okToSend).to.be.false;
|
||||||
|
expect(scope.sendBtnText).to.be.undefined;
|
||||||
|
expect(scope.sendBtnSecure).to.be.undefined;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should be able to send plaintext', function() {
|
||||||
|
scope.to = [{
|
||||||
|
address: 'asdf@asdf.de'
|
||||||
|
}];
|
||||||
|
scope.checkSendStatus();
|
||||||
|
|
||||||
|
expect(scope.okToSend).to.be.true;
|
||||||
|
expect(scope.sendBtnText).to.equal('Send');
|
||||||
|
expect(scope.sendBtnSecure).to.be.false;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should send plaintext if one receiver is not secure', function() {
|
||||||
|
scope.to = [{
|
||||||
|
address: 'asdf@asdf.de',
|
||||||
|
secure: true
|
||||||
|
}, {
|
||||||
|
address: 'asdf@asdfg.de'
|
||||||
|
}];
|
||||||
|
scope.checkSendStatus();
|
||||||
|
|
||||||
|
expect(scope.okToSend).to.be.true;
|
||||||
|
expect(scope.sendBtnText).to.equal('Send');
|
||||||
|
expect(scope.sendBtnSecure).to.be.false;
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should be able to send securely to multiple recipients', function() {
|
||||||
|
scope.to = [{
|
||||||
|
address: 'asdf@asdf.de',
|
||||||
|
secure: true
|
||||||
|
}, {
|
||||||
|
address: 'asdf@asdfg.de',
|
||||||
|
secure: true
|
||||||
|
}];
|
||||||
|
scope.checkSendStatus();
|
||||||
|
|
||||||
|
expect(scope.okToSend).to.be.true;
|
||||||
|
expect(scope.sendBtnText).to.equal('Send securely');
|
||||||
|
expect(scope.sendBtnSecure).to.be.true;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('send to outbox', function() {
|
||||||
|
it('should work', function() {
|
||||||
|
scope.to = [{
|
||||||
|
address: 'pity@dafool'
|
||||||
|
}];
|
||||||
|
scope.cc = [];
|
||||||
|
scope.bcc = [];
|
||||||
|
scope.subject = 'Ermahgerd!';
|
||||||
|
scope.body = 'wow. much body! very text!';
|
||||||
|
scope.attachments = [];
|
||||||
|
scope.state.nav = {
|
||||||
|
currentFolder: 'currentFolder'
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.replyTo = {};
|
||||||
|
|
||||||
|
outboxMock.put.withArgs(sinon.match(function(mail) {
|
||||||
|
expect(mail.from).to.deep.equal([{
|
||||||
|
address: emailAddress,
|
||||||
|
name: realname
|
||||||
|
}]);
|
||||||
|
expect(mail.to).to.deep.equal(scope.to);
|
||||||
|
expect(mail.cc).to.deep.equal(scope.cc);
|
||||||
|
expect(mail.bcc).to.deep.equal(scope.bcc);
|
||||||
|
expect(mail.body).to.contain(scope.body);
|
||||||
|
expect(mail.subject).to.equal(scope.subject);
|
||||||
|
expect(mail.attachments).to.be.empty;
|
||||||
|
expect(mail.sentDate).to.exist;
|
||||||
|
|
||||||
|
|
||||||
|
return true;
|
||||||
|
})).yields();
|
||||||
|
emailDaoMock.setFlags.yields();
|
||||||
|
|
||||||
|
scope.onError = function(err) {
|
||||||
|
expect(err).to.not.exist;
|
||||||
|
};
|
||||||
|
|
||||||
|
scope.sendToOutbox();
|
||||||
|
|
||||||
|
expect(outboxMock.put.calledOnce).to.be.true;
|
||||||
|
expect(emailDaoMock.setFlags.calledOnce).to.be.true;
|
||||||
|
expect(scope.state.lightbox).to.be.undefined;
|
||||||
|
expect(scope.replyTo.answered).to.be.true;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('lookupAddressBook', function() {
|
||||||
|
it('should work', function(done) {
|
||||||
|
keychainMock.listLocalPublicKeys.yields(null, [{
|
||||||
|
userId: 'test@asdf.com',
|
||||||
|
publicKey: 'KEY'
|
||||||
|
}]);
|
||||||
|
|
||||||
|
var result = scope.lookupAddressBook('test');
|
||||||
|
|
||||||
|
result.then(function(response) {
|
||||||
|
expect(response).to.deep.equal([{
|
||||||
|
address: 'test@asdf.com'
|
||||||
|
}]);
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
scope.$digest();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should work with cache', function(done) {
|
||||||
|
scope.addressBookCache = [{
|
||||||
|
address: 'test@asdf.com'
|
||||||
|
}, {
|
||||||
|
address: 'tes@asdf.com'
|
||||||
|
}];
|
||||||
|
|
||||||
|
var result = scope.lookupAddressBook('test');
|
||||||
|
|
||||||
|
result.then(function(response) {
|
||||||
|
expect(response).to.deep.equal([{
|
||||||
|
address: 'test@asdf.com'
|
||||||
|
}]);
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
scope.$digest();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
});
|
});
|
Loading…
Reference in New Issue
Block a user