mirror of
https://github.com/bitwarden/browser
synced 2025-12-12 22:33:35 +00:00
195 lines
7.6 KiB
JavaScript
195 lines
7.6 KiB
JavaScript
angular
|
|
.module('bit.accounts')
|
|
|
|
.controller('accountsLoginTwoFactorController', function ($scope, $state, authService, toastr, utilsService, SweetAlert,
|
|
$analytics, i18nService, $stateParams, $filter, constantsService, $timeout, $window, cryptoService, apiService) {
|
|
$scope.i18n = i18nService;
|
|
utilsService.initListSectionItemListeners($(document), angular);
|
|
|
|
var u2f = new U2f(function (data) {
|
|
$timeout(function () {
|
|
$scope.login(data);
|
|
});
|
|
}, function (error) {
|
|
$timeout(function () {
|
|
toastr.error(error, i18nService.errorsOccurred);
|
|
});
|
|
}, function (info) {
|
|
$timeout(function () {
|
|
if (info === 'ready') {
|
|
$scope.u2fReady = true;
|
|
}
|
|
});
|
|
});
|
|
|
|
var constants = constantsService;
|
|
var email = $stateParams.email;
|
|
var masterPassword = $stateParams.masterPassword;
|
|
var providers = $stateParams.providers;
|
|
|
|
if (!email || !masterPassword || !providers) {
|
|
$state.go('login');
|
|
return;
|
|
}
|
|
|
|
$scope.providerType = $stateParams.provider || $stateParams.provider === 0 ? $stateParams.provider :
|
|
getDefaultProvider(providers);
|
|
$scope.twoFactorEmail = null;
|
|
$scope.token = null;
|
|
$scope.constantsProvider = constants.twoFactorProvider;
|
|
$scope.u2fReady = false;
|
|
$scope.remember = { checked: false };
|
|
init();
|
|
|
|
$scope.loginPromise = null;
|
|
$scope.login = function (token) {
|
|
if (!token) {
|
|
toastr.error(i18nService.verificationCodeRequired, i18nService.errorsOccurred);
|
|
return;
|
|
}
|
|
|
|
if ($scope.providerType === constants.twoFactorProvider.u2f) {
|
|
if (u2f) {
|
|
u2f.stop();
|
|
}
|
|
else {
|
|
return;
|
|
}
|
|
}
|
|
else if ($scope.providerType === constants.twoFactorProvider.email ||
|
|
$scope.providerType === constants.twoFactorProvider.authenticator) {
|
|
token = token.replace(' ', '');
|
|
}
|
|
|
|
$scope.loginPromise = authService.logIn(email, masterPassword, $scope.providerType, token, $scope.remember.checked);
|
|
$scope.loginPromise.then(function () {
|
|
$analytics.eventTrack('Logged In From Two-step');
|
|
$state.go('tabs.vault', { animation: 'in-slide-left', syncOnLoad: true });
|
|
}, function () {
|
|
u2f.start();
|
|
});
|
|
};
|
|
|
|
$scope.sendEmail = function (doToast) {
|
|
if ($scope.providerType !== constants.twoFactorProvider.email) {
|
|
return;
|
|
}
|
|
|
|
var key = cryptoService.makeKey(masterPassword, email);
|
|
cryptoService.hashPassword(masterPassword, key, function (hash) {
|
|
var request = new TwoFactorEmailRequest(email, hash);
|
|
apiService.postTwoFactorEmail(request, function () {
|
|
if (doToast) {
|
|
toastr.success('Verification email sent to ' + $scope.twoFactorEmail + '.');
|
|
}
|
|
}, function () {
|
|
toastr.error('Could not send verification email.');
|
|
});
|
|
});
|
|
};
|
|
|
|
$scope.anotherMethod = function () {
|
|
$state.go('twoFactorMethods', {
|
|
animation: 'in-slide-up',
|
|
email: email,
|
|
masterPassword: masterPassword,
|
|
providers: providers,
|
|
provider: $scope.providerType
|
|
});
|
|
};
|
|
|
|
$scope.back = function () {
|
|
$state.go('login', {
|
|
animation: 'out-slide-right'
|
|
});
|
|
};
|
|
|
|
$scope.$on('$destroy', function () {
|
|
u2f.stop();
|
|
u2f.cleanup();
|
|
u2f = null;
|
|
});
|
|
|
|
function getDefaultProvider(twoFactorProviders) {
|
|
var keys = Object.keys(twoFactorProviders);
|
|
var providerType = null;
|
|
var providerPriority = -1;
|
|
for (var i = 0; i < keys.length; i++) {
|
|
var provider = $filter('filter')(constants.twoFactorProviderInfo, { type: keys[i], active: true });
|
|
if (provider.length && provider[0].priority > providerPriority) {
|
|
if (provider[0].type == constants.twoFactorProvider.u2f &&
|
|
!utilsService.isChrome() && !utilsService.isOpera()) {
|
|
continue;
|
|
}
|
|
|
|
providerType = provider[0].type;
|
|
providerPriority = provider[0].priority;
|
|
}
|
|
}
|
|
return providerType === null ? null : parseInt(providerType);
|
|
}
|
|
|
|
function init() {
|
|
u2f.stop();
|
|
u2f.cleanup();
|
|
|
|
$timeout(function () {
|
|
$('#code').focus();
|
|
|
|
var params;
|
|
if ($scope.providerType === constants.twoFactorProvider.duo) {
|
|
params = providers[constants.twoFactorProvider.duo];
|
|
|
|
$window.Duo.init({
|
|
host: params.Host,
|
|
sig_request: params.Signature,
|
|
submit_callback: function (theForm) {
|
|
var response = $(theForm).find('input[name="sig_response"]').val();
|
|
$scope.login(response);
|
|
}
|
|
});
|
|
}
|
|
else if ($scope.providerType === constants.twoFactorProvider.u2f) {
|
|
params = providers[constants.twoFactorProvider.u2f];
|
|
var challenges = JSON.parse(params.Challenges);
|
|
|
|
u2f.init({
|
|
appId: challenges[0].appId,
|
|
challenge: challenges[0].challenge,
|
|
keys: [{
|
|
version: challenges[0].version,
|
|
keyHandle: challenges[0].keyHandle
|
|
}]
|
|
});
|
|
}
|
|
else if ($scope.providerType === constants.twoFactorProvider.email) {
|
|
params = providers[constants.twoFactorProvider.email];
|
|
$scope.twoFactorEmail = params.Email;
|
|
|
|
if (chrome.extension.getViews({ type: 'popup' }).length > 0) {
|
|
SweetAlert.swal({
|
|
title: 'Two-step Login',
|
|
text: 'Clicking outside the popup window to check your email for your verification code will ' +
|
|
'cause this popup to close. ' +
|
|
'Do you want to open this popup in a new window so that it does not close?',
|
|
showCancelButton: true,
|
|
confirmButtonText: i18nService.yes,
|
|
cancelButtonText: i18nService.no
|
|
}, function (confirmed) {
|
|
if (confirmed) {
|
|
chrome.tabs.create({ url: '/popup/index.html#!/login' });
|
|
return;
|
|
}
|
|
else if (Object.keys(providers).length > 1) {
|
|
$scope.sendEmail(false);
|
|
}
|
|
});
|
|
}
|
|
else if (Object.keys(providers).length > 1) {
|
|
$scope.sendEmail(false);
|
|
}
|
|
}
|
|
}, 500);
|
|
}
|
|
});
|