feat(session): support account delete with session token (#275), r=@philbooth

This commit is contained in:
Vijay Budhram 2018-04-25 09:56:29 -04:00 коммит произвёл GitHub
Родитель 13b889e14a
Коммит 687ae96ce1
Не найден ключ, соответствующий данной подписи
Идентификатор ключа GPG: 4AEE18F83AFDEB23
7 изменённых файлов: 102 добавлений и 16 удалений

1
.gitignore поставляемый
Просмотреть файл

@ -2,5 +2,6 @@
/build
/components
/docs
/fxa-auth-server
sauce_connect.log*
.DS_Store

Просмотреть файл

@ -785,9 +785,10 @@ define([
* @param {Object} [options={}] Options
* @param {Boolean} [options.skipCaseError]
* If `true`, the request will skip the incorrect case error
* @param {String} sessionToken User session token
* @return {Promise} A promise that will be fulfilled with JSON `xhr.responseText` of the request
*/
FxAccountClient.prototype.accountDestroy = function(email, password, options) {
FxAccountClient.prototype.accountDestroy = function (email, password, options, sessionToken) {
var self = this;
options = options || {};
@ -796,26 +797,33 @@ define([
required(email, 'email');
required(password, 'password');
return credentials.setup(email, password);
var defers = [credentials.setup(email, password)];
if (sessionToken) {
defers.push(hawkCredentials(sessionToken, 'sessionToken', HKDF_SIZE));
}
return Promise.all(defers);
})
.then(
function (result) {
function (results) {
var auth = results[0];
var creds = results[1];
var data = {
email: result.emailUTF8,
authPW: sjcl.codec.hex.fromBits(result.authPW)
email: auth.emailUTF8,
authPW: sjcl.codec.hex.fromBits(auth.authPW)
};
return self.request.send('/account/destroy', 'POST', null, data)
return self.request.send('/account/destroy', 'POST', creds, data)
.then(
function(response) {
function (response) {
return response;
},
function(error) {
function (error) {
// if incorrect email case error
if (error && error.email && error.errno === ERRORS.INCORRECT_EMAIL_CASE && !options.skipCaseError) {
options.skipCaseError = true;
return self.accountDestroy(error.email, password, options);
return self.accountDestroy(error.email, password, options, sessionToken);
} else {
throw error;
}

Просмотреть файл

@ -55,6 +55,83 @@ define([
);
});
test('#destroy with sessionToken', function () {
var email;
var password;
return accountHelper.newVerifiedAccount()
.then(function (account) {
email = account.input.email;
password = account.input.password;
return respond(client.accountDestroy(email, password, {}, account.signIn.sessionToken), RequestMocks.accountDestroy);
})
.then(
function (res) {
assert.ok(res, 'got response');
return respond(client.signIn(email, password), ErrorMocks.accountDoesNotExist);
}
).then(
function () {
assert.fail();
},
function (error) {
assert.equal(error.errno, 102, 'Account is gone');
assert.equal(error.code, 400, 'Correct status code');
}
);
});
test('#destroy with sessionToken, incorrect case', function () {
var account;
return accountHelper.newVerifiedAccount()
.then(function (acc) {
account = acc;
var incorrectCaseEmail = account.input.email.charAt(0).toUpperCase() + account.input.email.slice(1);
return respond(client.accountDestroy(incorrectCaseEmail, account.input.password, {}, account.signIn.sessionToken), RequestMocks.accountDestroy);
})
.then(
function (res) {
assert.ok(res);
return respond(client.signIn(account.input.email, account.input.password, {}, account.signIn.sessionToken), ErrorMocks.accountDoesNotExist);
}
).then(
function () {
assert.fail();
},
function (error) {
assert.ok(error);
assert.equal(error.errno, 102);
assert.equal(error.code, 400, 'Correct status code');
}
);
});
test('#destroy with sessionToken, incorrect case with skipCaseError', function () {
var account;
return accountHelper.newVerifiedAccount()
.then(function (acc) {
account = acc;
var incorrectCaseEmail = account.input.email.charAt(0).toUpperCase() + account.input.email.slice(1);
return respond(client.accountDestroy(incorrectCaseEmail, account.input.password, {skipCaseError: true}, account.signIn.sessionToken), ErrorMocks.incorrectEmailCase);
})
.then(
function () {
assert.fail();
},
function (res) {
assert.equal(res.code, 400);
assert.equal(res.errno, 120);
}
);
});
test('#keys', function () {
return accountHelper.newVerifiedAccount()
.then(function (account) {
@ -183,7 +260,7 @@ define([
var account;
var opts = {
service: 'sync',
redirectTo: 'https://sync.firefox.com/after_reset',
redirectTo: 'https://sync.127.0.0.1/after_reset',
resume: 'resumejwt'
};

Просмотреть файл

@ -54,7 +54,7 @@ define([
var user;
var opts = {
service: 'sync',
redirectTo: 'https://sync.firefox.com/after_reset',
redirectTo: 'https://sync.127.0.0.1/after_reset',
resume: 'resumejwt',
type: 'upgradeSession'
};

Просмотреть файл

@ -297,7 +297,7 @@ define([
},
originalLoginEmail: email.toUpperCase(),
reason: 'password_change',
redirectTo: 'http://example.io',
redirectTo: 'http://127.0.0.1',
resume: 'RESUME_TOKEN',
service: 'sync',
verificationMethod: 'email-2fa'

Просмотреть файл

@ -94,7 +94,7 @@ define([
metricsContext: {
context: 'fx_desktop_v2'
},
redirectTo: 'http://sync.firefox.com/after_reset',
redirectTo: 'http://sync.127.0.0.1/after_reset',
service: 'sync'
};
@ -129,7 +129,7 @@ define([
metricsContext: {
context: 'fx_desktop_v2'
},
redirectTo: 'http://sync.firefox.com/after_reset',
redirectTo: 'http://sync.127.0.0.1/after_reset',
resume: 'resumejwt',
service: 'sync'
};

Просмотреть файл

@ -89,7 +89,7 @@ define([
var password = 'iliketurtles';
var opts = {
service: 'sync',
redirectTo: 'https://sync.firefox.com/after_reset',
redirectTo: 'https://sync.127.0.0.1/after_reset',
resume: 'resumejwt'
};
@ -153,7 +153,7 @@ define([
var email = user + '@restmail.net';
var password = 'iliketurtles';
var opts = {
redirectTo: 'http://sync.firefox.com/after_reset'
redirectTo: 'http://sync.127.0.0.1/after_reset'
};
return respond(client.signUp(email, password, opts), RequestMocks.signUp)