From 6481a5a56bfb5c1ce06e1c9dafbc19f54fc2d293 Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Wed, 30 Jan 2019 18:46:08 +0200 Subject: [PATCH 01/20] adapted public api route for use with ajax --- src/Routers/PublicAPIRouter.js | 41 +++++++++++++++++++++++++++++++++- 1 file changed, 40 insertions(+), 1 deletion(-) diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 15d636c5e2..e403249047 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -159,7 +159,30 @@ export class PublicAPIRouter extends PromiseRouter { const { username, token, new_password } = req.body; - if (!username || !token || !new_password) { + if (!username) { + if(req.xhr) + throw new Parse.Error( + Parse.Error.USERNAME_MISSING, + 'Missing username' + ); + return this.invalidLink(req); + } + + if (!token) { + if(req.xhr) + throw new Parse.Error( + Parse.Error.OTHER_CAUSE, + 'Missing token' + ); + return this.invalidLink(req); + } + + if (!new_password) { + if(req.xhr) + throw new Parse.Error( + Parse.Error.PASSWORD_MISSING, + 'Missing password' + ); return this.invalidLink(req); } @@ -168,6 +191,14 @@ export class PublicAPIRouter extends PromiseRouter { .then( () => { const params = qs.stringify({ username: username }); + + if (req.xhr) { + return Promise.resolve({ + status: 200, + response: 'Password successfully reset' + }); + } + return Promise.resolve({ status: 302, location: `${config.passwordResetSuccessURL}?${params}`, @@ -181,6 +212,14 @@ export class PublicAPIRouter extends PromiseRouter { error: err, app: config.appName, }); + + if (req.xhr) { + throw new Parse.Error( + Parse.Error.OTHER_CAUSE, + 'Server failed to reset password with provided data' + ) + } + return Promise.resolve({ status: 302, location: `${config.choosePasswordURL}?${params}`, From 2d50f2056ea5ebc37d6c570fc4d0c0ccb88293ec Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Wed, 30 Jan 2019 19:31:41 +0200 Subject: [PATCH 02/20] Elegant error handling --- src/Routers/PublicAPIRouter.js | 40 +++++++++++++++------------------- 1 file changed, 18 insertions(+), 22 deletions(-) diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index e403249047..92d21aca46 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -159,31 +159,27 @@ export class PublicAPIRouter extends PromiseRouter { const { username, token, new_password } = req.body; + let error; if (!username) { - if(req.xhr) - throw new Parse.Error( - Parse.Error.USERNAME_MISSING, - 'Missing username' - ); - return this.invalidLink(req); - } - - if (!token) { - if(req.xhr) - throw new Parse.Error( - Parse.Error.OTHER_CAUSE, - 'Missing token' - ); - return this.invalidLink(req); + error = new Parse.Error( + Parse.Error.USERNAME_MISSING, + 'Missing username' + ); + } else if (!token) { + error = new Parse.Error( + Parse.Error.OTHER_CAUSE, + 'Missing token' + ); + } else if (!new_password) { + error = new Parse.Error( + Parse.Error.PASSWORD_MISSING, + 'Missing password' + ); } - if (!new_password) { - if(req.xhr) - throw new Parse.Error( - Parse.Error.PASSWORD_MISSING, - 'Missing password' - ); - return this.invalidLink(req); + if (error) { + if (req.xhr) { throw error } + return this.invalidLink(error); } return config.userController From b0e8f3d4508b010341fb63ad81f88b3e124b1539 Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Thu, 31 Jan 2019 12:02:40 +0200 Subject: [PATCH 03/20] Fixed error return --- src/Routers/PublicAPIRouter.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 92d21aca46..19b97a5360 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -179,7 +179,7 @@ export class PublicAPIRouter extends PromiseRouter { if (error) { if (req.xhr) { throw error } - return this.invalidLink(error); + return this.invalidLink(req); } return config.userController From d2f3101887c62e7e2cc302cfaa8cfa2a071cd832 Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Tue, 5 Feb 2019 12:19:19 +0200 Subject: [PATCH 04/20] Public API error flow redone, tests --- spec/PublicAPI.spec.js | 21 ++++++++ src/Routers/PublicAPIRouter.js | 91 ++++++++++++++++++---------------- 2 files changed, 70 insertions(+), 42 deletions(-) diff --git a/spec/PublicAPI.spec.js b/spec/PublicAPI.spec.js index 1c04294880..374a9a8fc3 100644 --- a/spec/PublicAPI.spec.js +++ b/spec/PublicAPI.spec.js @@ -7,6 +7,27 @@ const request = function(url, callback) { }; describe('public API', () => { + it('should return ajax response on ajax request', done => { + reconfigureServer({ + publicServerURL: 'http://localhost:8378/1', + }).then(() => { + return req({ + method: 'POST', + url: 'http://localhost:8378/1/apps/test/request_password_reset', + body: `new_password=user1&token=43634643&username=`, + headers: { + 'Content-Type': 'application/x-www-form-urlencoded', + 'X-Requested-With': 'XMLHttpRequest' + }, + followRedirects: false, + }) + }).catch(error => { + expect(error.status).not.toBe(302); + expect(error.text).toEqual('{"code":200,"error":"Missing username"}'); + done() + }) + }); + it('should get invalid_link.html', done => { request( 'http://localhost:8378/1/apps/invalid_link.html', diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 19b97a5360..a13441e64a 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -152,76 +152,83 @@ export class PublicAPIRouter extends PromiseRouter { if (!config) { this.invalidRequest(); } - if (!config.publicServerURL) { return this.missingPublicServerURL(); } - const { username, token, new_password } = req.body; + const { + username, + token, + new_password + } = req.body; + + if ((!username || !token || !new_password) && req.xhr === false) { + return this.invalidLink(req); + } - let error; if (!username) { - error = new Parse.Error( + throw new Parse.Error( Parse.Error.USERNAME_MISSING, 'Missing username' ); - } else if (!token) { - error = new Parse.Error( + } + + if (!token) { + throw new Parse.Error( Parse.Error.OTHER_CAUSE, 'Missing token' ); - } else if (!new_password) { - error = new Parse.Error( + } + + if (!new_password) { + throw new Parse.Error( Parse.Error.PASSWORD_MISSING, 'Missing password' ); } - if (error) { - if (req.xhr) { throw error } - return this.invalidLink(req); - } - return config.userController .updatePassword(username, token, new_password) .then( () => { - const params = qs.stringify({ username: username }); - - if (req.xhr) { - return Promise.resolve({ - status: 200, - response: 'Password successfully reset' - }); - } - return Promise.resolve({ - status: 302, - location: `${config.passwordResetSuccessURL}?${params}`, + success: true }); - }, - err => { - const params = qs.stringify({ - username: username, - token: token, - id: config.applicationId, - error: err, - app: config.appName, + + }, err => { + return Promise.resolve({ + success: false, + err }); + }) + .then(result => { + const params = _querystring.default.stringify({ + username: username, + token: token, + id: config.applicationId, + error: result.err, + app: config.appName + }); - if (req.xhr) { - throw new Parse.Error( - Parse.Error.OTHER_CAUSE, - 'Server failed to reset password with provided data' - ) + if (req.xhr) { + if (result.success) { + return Promise.resolve({ + status: 200, + response: 'Password successfully reset' + }) } - return Promise.resolve({ - status: 302, - location: `${config.choosePasswordURL}?${params}`, - }); + throw new Parse.Error( + Parse.Error.OTHER_CAUSE, + result.err + ) } - ); + + return Promise.resolve({ + status: 302, + location: `${result.success ? config.passwordResetSuccessURL : config.choosePasswordURL}?${params}`, + }); + }); } invalidLink(req) { From 8e0e258301e9281606dab255f40bc3d50e7387c1 Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Tue, 5 Feb 2019 12:41:40 +0200 Subject: [PATCH 05/20] Fixed code to pre-build form --- src/Routers/PublicAPIRouter.js | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index a13441e64a..bb2937af67 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -167,22 +167,22 @@ export class PublicAPIRouter extends PromiseRouter { } if (!username) { - throw new Parse.Error( - Parse.Error.USERNAME_MISSING, + throw new Error( + Error.USERNAME_MISSING, 'Missing username' ); } if (!token) { - throw new Parse.Error( - Parse.Error.OTHER_CAUSE, + throw new Error( + Error.OTHER_CAUSE, 'Missing token' ); } if (!new_password) { - throw new Parse.Error( - Parse.Error.PASSWORD_MISSING, + throw new Error( + Error.PASSWORD_MISSING, 'Missing password' ); } @@ -202,7 +202,7 @@ export class PublicAPIRouter extends PromiseRouter { }); }) .then(result => { - const params = _querystring.default.stringify({ + const params = qs.default.stringify({ username: username, token: token, id: config.applicationId, @@ -218,8 +218,8 @@ export class PublicAPIRouter extends PromiseRouter { }) } - throw new Parse.Error( - Parse.Error.OTHER_CAUSE, + throw new Error( + Error.OTHER_CAUSE, result.err ) } From 3c914df94f8847e4b1d02b6ca2c4d8034defaaab Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Tue, 5 Feb 2019 14:37:24 +0200 Subject: [PATCH 06/20] Public API change password return params --- src/Routers/PublicAPIRouter.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index bb2937af67..7aa55b78d2 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -226,7 +226,8 @@ export class PublicAPIRouter extends PromiseRouter { return Promise.resolve({ status: 302, - location: `${result.success ? config.passwordResetSuccessURL : config.choosePasswordURL}?${params}`, + location: `${result.success ? `${config.passwordResetSuccessURL}?username=${username}` : + `${config.choosePasswordURL}?${params}` }`, }); }); } From 3a7e0f741b7bc879ab265b1bffa61080aa02d252 Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Tue, 5 Feb 2019 16:11:20 +0200 Subject: [PATCH 07/20] Reverted errors in resetPassword --- src/Routers/PublicAPIRouter.js | 51 +++++++++++++--------------------- 1 file changed, 20 insertions(+), 31 deletions(-) diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 7aa55b78d2..39af0ab7b5 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -4,6 +4,7 @@ import express from 'express'; import path from 'path'; import fs from 'fs'; import qs from 'querystring'; +import { Parse } from 'parse/node'; const public_html = path.resolve(__dirname, '../../public_html'); const views = path.resolve(__dirname, '../../views'); @@ -156,35 +157,22 @@ export class PublicAPIRouter extends PromiseRouter { return this.missingPublicServerURL(); } - const { - username, - token, - new_password - } = req.body; + const { username, token, new_password } = req.body; if ((!username || !token || !new_password) && req.xhr === false) { return this.invalidLink(req); } if (!username) { - throw new Error( - Error.USERNAME_MISSING, - 'Missing username' - ); + throw new Parse.Error(Parse.Error.USERNAME_MISSING, 'Missing username'); } if (!token) { - throw new Error( - Error.OTHER_CAUSE, - 'Missing token' - ); + throw new Parse.Error(Parse.Error.OTHER_CAUSE, 'Missing token'); } if (!new_password) { - throw new Error( - Error.PASSWORD_MISSING, - 'Missing password' - ); + throw new Parse.Error(Parse.Error.PASSWORD_MISSING, 'Missing password'); } return config.userController @@ -192,42 +180,43 @@ export class PublicAPIRouter extends PromiseRouter { .then( () => { return Promise.resolve({ - success: true + success: true, }); - - }, err => { + }, + err => { return Promise.resolve({ success: false, - err + err, }); - }) + } + ) .then(result => { const params = qs.default.stringify({ username: username, token: token, id: config.applicationId, error: result.err, - app: config.appName + app: config.appName, }); if (req.xhr) { if (result.success) { return Promise.resolve({ status: 200, - response: 'Password successfully reset' - }) + response: 'Password successfully reset', + }); } - throw new Error( - Error.OTHER_CAUSE, - result.err - ) + throw new Parse.Error(Parse.Error.OTHER_CAUSE, result.err); } return Promise.resolve({ status: 302, - location: `${result.success ? `${config.passwordResetSuccessURL}?username=${username}` : - `${config.choosePasswordURL}?${params}` }`, + location: `${ + result.success + ? `${config.passwordResetSuccessURL}?username=${username}` + : `${config.choosePasswordURL}?${params}` + }`, }); }); } From a9828cc514d64c563b2c5436138ddd9fc1c20b2b Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Tue, 5 Feb 2019 17:21:37 +0200 Subject: [PATCH 08/20] Fixed querystring call --- src/Routers/PublicAPIRouter.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 39af0ab7b5..2edde2ba81 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -191,7 +191,7 @@ export class PublicAPIRouter extends PromiseRouter { } ) .then(result => { - const params = qs.default.stringify({ + const params = qs.stringify({ username: username, token: token, id: config.applicationId, From 062471fd4b9a5d7b8d33e9dbbceefdd3d387d0b3 Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Wed, 6 Feb 2019 12:15:54 +0200 Subject: [PATCH 09/20] Success test on ajax password reset --- spec/ValidationAndPasswordsReset.spec.js | 82 ++++++++++++++++++++++++ 1 file changed, 82 insertions(+) diff --git a/spec/ValidationAndPasswordsReset.spec.js b/spec/ValidationAndPasswordsReset.spec.js index a5e024168a..84842c924b 100644 --- a/spec/ValidationAndPasswordsReset.spec.js +++ b/spec/ValidationAndPasswordsReset.spec.js @@ -910,6 +910,88 @@ describe('Custom Pages, Email Verification, Password Reset', () => { }); }); + it('should programmatically reset password on ajax request', done => { + const user = new Parse.User(); + const emailAdapter = { + sendVerificationEmail: () => Promise.resolve(), + sendPasswordResetEmail: options => { + request({ + url: options.link, + followRedirects: false, + }).then(response => { + expect(response.status).toEqual(302); + const re = /http:\/\/localhost:8378\/1\/apps\/choose_password\?token=([a-zA-Z0-9]+)\&id=test\&username=zxcv/; + const match = response.text.match(re); + if (!match) { + fail('should have a token'); + done(); + return; + } + const token = match[1]; + + request({ + url: 'http://localhost:8378/1/apps/test/request_password_reset', + method: 'POST', + body: { new_password: 'hello', token, username: 'zxcv' }, + headers: { + 'Content-Type': 'application/x-www-form-urlencoded', + 'X-Requested-With': 'XMLHttpRequest', + }, + followRedirects: false, + }).then(response => { + console.log('REQUEST RESPONSE'); + expect(response.status).toEqual(200); + expect(response.text).toEqual('"Password successfully reset"'); + + Parse.User.logIn('zxcv', 'hello').then( + function() { + const config = Config.get('test'); + config.database.adapter + .find( + '_User', + { fields: {} }, + { username: 'zxcv' }, + { limit: 1 } + ) + .then(results => { + // _perishable_token should be unset after reset password + expect(results.length).toEqual(1); + expect(results[0]['_perishable_token']).toEqual(undefined); + done(); + }); + }, + err => { + jfail(err); + fail('should login with new password'); + done(); + } + ); + }); + }); + }, + sendMail: () => {}, + }; + reconfigureServer({ + appName: 'emailing app', + verifyUserEmails: true, + emailAdapter: emailAdapter, + publicServerURL: 'http://localhost:8378/1', + }).then(() => { + user.setPassword('asdf'); + user.setUsername('zxcv'); + user.set('email', 'user@parse.com'); + user.signUp().then(() => { + Parse.User.requestPasswordReset('user@parse.com', { + error: err => { + jfail(err); + fail('Should not fail'); + done(); + }, + }); + }); + }); + }); + it('deletes password reset token on email address change', done => { reconfigureServer({ appName: 'coolapp', From b5436fd9bcc8de09a57c8e25d4de48eaff2b5e82 Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Wed, 6 Feb 2019 13:52:03 +0200 Subject: [PATCH 10/20] Added few more routes to tests for coverage --- spec/PublicAPI.spec.js | 78 ++++++++++++++++++++++++++++++++++-------- 1 file changed, 64 insertions(+), 14 deletions(-) diff --git a/spec/PublicAPI.spec.js b/spec/PublicAPI.spec.js index 374a9a8fc3..e260b64cc2 100644 --- a/spec/PublicAPI.spec.js +++ b/spec/PublicAPI.spec.js @@ -10,22 +10,72 @@ describe('public API', () => { it('should return ajax response on ajax request', done => { reconfigureServer({ publicServerURL: 'http://localhost:8378/1', - }).then(() => { - return req({ - method: 'POST', - url: 'http://localhost:8378/1/apps/test/request_password_reset', - body: `new_password=user1&token=43634643&username=`, - headers: { - 'Content-Type': 'application/x-www-form-urlencoded', - 'X-Requested-With': 'XMLHttpRequest' - }, - followRedirects: false, + }) + .then(() => { + return req({ + method: 'POST', + url: 'http://localhost:8378/1/apps/test/request_password_reset', + body: `new_password=user1&token=43634643&username=`, + headers: { + 'Content-Type': 'application/x-www-form-urlencoded', + 'X-Requested-With': 'XMLHttpRequest', + }, + followRedirects: false, + }); + }) + .catch(error => { + expect(error.status).not.toBe(302); + expect(error.text).toEqual('{"code":200,"error":"Missing username"}'); + done(); + }); + }); + + it('should return missing token error on ajax request without token provided', done => { + reconfigureServer({ + publicServerURL: 'http://localhost:8378/1', + }) + .then(() => { + return req({ + method: 'POST', + url: 'http://localhost:8378/1/apps/test/request_password_reset', + body: `new_password=user1&token=&username=Johnny`, + headers: { + 'Content-Type': 'application/x-www-form-urlencoded', + 'X-Requested-With': 'XMLHttpRequest', + }, + followRedirects: false, + }); }) - }).catch(error => { - expect(error.status).not.toBe(302); - expect(error.text).toEqual('{"code":200,"error":"Missing username"}'); - done() + .catch(error => { + console.log('ERROR IN TEST: ', error); + expect(error.status).not.toBe(302); + expect(error.text).toEqual('{"code":-1,"error":"Missing token"}'); + done(); + }); + }); + + it('should return missing password error on ajax request without password provided', done => { + reconfigureServer({ + publicServerURL: 'http://localhost:8378/1', }) + .then(() => { + return req({ + method: 'POST', + url: 'http://localhost:8378/1/apps/test/request_password_reset', + body: `new_password=&token=132414&username=Johnny`, + headers: { + 'Content-Type': 'application/x-www-form-urlencoded', + 'X-Requested-With': 'XMLHttpRequest', + }, + followRedirects: false, + }); + }) + .catch(error => { + console.log('ERROR IN TEST: ', error); + expect(error.status).not.toBe(302); + expect(error.text).toEqual('{"code":201,"error":"Missing password"}'); + done(); + }); }); it('should get invalid_link.html', done => { From afdcb4f8c45a0947c71e1e5fb7f69a8dd1043a54 Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Wed, 6 Feb 2019 17:25:05 +0200 Subject: [PATCH 11/20] More tests and redone error return slightly --- spec/PasswordPolicy.spec.js | 91 ++++++++++++++++++++++++ spec/ValidationAndPasswordsReset.spec.js | 25 +++++++ src/Routers/PublicAPIRouter.js | 10 ++- 3 files changed, 125 insertions(+), 1 deletion(-) diff --git a/spec/PasswordPolicy.spec.js b/spec/PasswordPolicy.spec.js index 0f3ed1dad1..df32a34424 100644 --- a/spec/PasswordPolicy.spec.js +++ b/spec/PasswordPolicy.spec.js @@ -909,6 +909,97 @@ describe('Password Policy: ', () => { }); }); + it('Should return error when password violates Password Policy and reset through ajax', done => { + const user = new Parse.User(); + const emailAdapter = { + sendVerificationEmail: () => Promise.resolve(), + sendPasswordResetEmail: options => { + request({ + url: options.link, + followRedirects: false, + simple: false, + resolveWithFullResponse: true, + }) + .then(response => { + expect(response.status).toEqual(302); + const re = /http:\/\/localhost:8378\/1\/apps\/choose_password\?token=([a-zA-Z0-9]+)\&id=test\&username=user1/; + const match = response.text.match(re); + if (!match) { + fail('should have a token'); + done(); + return; + } + const token = match[1]; + + request({ + method: 'POST', + url: 'http://localhost:8378/1/apps/test/request_password_reset', + body: `new_password=xuser12&token=${token}&username=user1`, + headers: { + 'Content-Type': 'application/x-www-form-urlencoded', + 'X-Requested-With': 'XMLHttpRequest', + }, + followRedirects: false, + }) + .catch(error => { + expect(error.status).not.toBe(302); + expect(error.text).toEqual( + '{"code":-1,"error":"Password does not meet the Password Policy requirements."}' + ); + + Parse.User.logIn('user1', 'r@nd0m') + .then(function() { + done(); + }) + .catch(err => { + jfail(err); + fail('should login with old password'); + done(); + }); + }) + .catch(error => { + jfail(error); + fail('Failed to POST request password reset'); + done(); + }); + }) + .catch(error => { + jfail(error); + fail('Failed to get the reset link'); + done(); + }); + }, + sendMail: () => {}, + }; + reconfigureServer({ + appName: 'passwordPolicy', + verifyUserEmails: false, + emailAdapter: emailAdapter, + passwordPolicy: { + doNotAllowUsername: true, + }, + publicServerURL: 'http://localhost:8378/1', + }).then(() => { + user.setUsername('user1'); + user.setPassword('r@nd0m'); + user.set('email', 'user1@parse.com'); + user + .signUp() + .then(() => { + Parse.User.requestPasswordReset('user1@parse.com').catch(err => { + jfail(err); + fail('Reset password request should not fail'); + done(); + }); + }) + .catch(error => { + jfail(error); + fail('signUp should not fail'); + done(); + }); + }); + }); + it('should reset password even if the new password contains user name while the policy allows', done => { const user = new Parse.User(); const emailAdapter = { diff --git a/spec/ValidationAndPasswordsReset.spec.js b/spec/ValidationAndPasswordsReset.spec.js index 84842c924b..ddfb869cb2 100644 --- a/spec/ValidationAndPasswordsReset.spec.js +++ b/spec/ValidationAndPasswordsReset.spec.js @@ -992,6 +992,31 @@ describe('Custom Pages, Email Verification, Password Reset', () => { }); }); + it('should return ajax failure error on ajax request with wrong data provided', done => { + reconfigureServer({ + publicServerURL: 'http://localhost:8378/1', + }) + .then(() => { + return request({ + method: 'POST', + url: 'http://localhost:8378/1/apps/test/request_password_reset', + body: `new_password=user1&token=12345&username=Johnny`, + headers: { + 'Content-Type': 'application/x-www-form-urlencoded', + 'X-Requested-With': 'XMLHttpRequest', + }, + followRedirects: false, + }); + }) + .catch(error => { + expect(error.status).not.toBe(302); + expect(error.text).toEqual( + '{"code":-1,"error":"Failed to reset password (Username/email or token is invalid)"}' + ); + done(); + }); + }); + it('deletes password reset token on email address change', done => { reconfigureServer({ appName: 'coolapp', diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 2edde2ba81..9c2cd387d6 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -207,7 +207,15 @@ export class PublicAPIRouter extends PromiseRouter { }); } - throw new Parse.Error(Parse.Error.OTHER_CAUSE, result.err); + if ( + result.err === + 'Password does not meet the Password Policy requirements.' + ) + throw new Parse.Error(Parse.Error.OTHER_CAUSE, `${result.err}`); + throw new Parse.Error( + Parse.Error.OTHER_CAUSE, + 'Invalid token or username' + ); } return Promise.resolve({ From f51db6c879a58b6bde4a3324233b29c8e719c27d Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Wed, 6 Feb 2019 17:37:57 +0200 Subject: [PATCH 12/20] Updated error text --- src/Routers/PublicAPIRouter.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 9c2cd387d6..64920f1b45 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -214,7 +214,7 @@ export class PublicAPIRouter extends PromiseRouter { throw new Parse.Error(Parse.Error.OTHER_CAUSE, `${result.err}`); throw new Parse.Error( Parse.Error.OTHER_CAUSE, - 'Invalid token or username' + 'Failed to reset password (Username/email or token is invalid)' ); } From 0e8678366e8b1e445901e1404c9ea00ee867ebb9 Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Fri, 1 Mar 2019 12:51:40 +0200 Subject: [PATCH 13/20] Console logs removal, renamed test, added {} to if --- spec/PublicAPI.spec.js | 4 +--- spec/ValidationAndPasswordsReset.spec.js | 1 - src/Routers/PublicAPIRouter.js | 3 ++- 3 files changed, 3 insertions(+), 5 deletions(-) diff --git a/spec/PublicAPI.spec.js b/spec/PublicAPI.spec.js index e260b64cc2..1350dc060b 100644 --- a/spec/PublicAPI.spec.js +++ b/spec/PublicAPI.spec.js @@ -7,7 +7,7 @@ const request = function(url, callback) { }; describe('public API', () => { - it('should return ajax response on ajax request', done => { + it('should return missing username error on ajax request without username provided', done => { reconfigureServer({ publicServerURL: 'http://localhost:8378/1', }) @@ -47,7 +47,6 @@ describe('public API', () => { }); }) .catch(error => { - console.log('ERROR IN TEST: ', error); expect(error.status).not.toBe(302); expect(error.text).toEqual('{"code":-1,"error":"Missing token"}'); done(); @@ -71,7 +70,6 @@ describe('public API', () => { }); }) .catch(error => { - console.log('ERROR IN TEST: ', error); expect(error.status).not.toBe(302); expect(error.text).toEqual('{"code":201,"error":"Missing password"}'); done(); diff --git a/spec/ValidationAndPasswordsReset.spec.js b/spec/ValidationAndPasswordsReset.spec.js index ddfb869cb2..e3aba02774 100644 --- a/spec/ValidationAndPasswordsReset.spec.js +++ b/spec/ValidationAndPasswordsReset.spec.js @@ -939,7 +939,6 @@ describe('Custom Pages, Email Verification, Password Reset', () => { }, followRedirects: false, }).then(response => { - console.log('REQUEST RESPONSE'); expect(response.status).toEqual(200); expect(response.text).toEqual('"Password successfully reset"'); diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 64920f1b45..1a3011e2e5 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -210,8 +210,9 @@ export class PublicAPIRouter extends PromiseRouter { if ( result.err === 'Password does not meet the Password Policy requirements.' - ) + ) { throw new Parse.Error(Parse.Error.OTHER_CAUSE, `${result.err}`); + } throw new Parse.Error( Parse.Error.OTHER_CAUSE, 'Failed to reset password (Username/email or token is invalid)' From c0688b3e6ff19684b9a89758d77fb43d2a7c862a Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Fri, 1 Mar 2019 14:43:19 +0200 Subject: [PATCH 14/20] Wrong error sent --- src/Routers/PublicAPIRouter.js | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 1a3011e2e5..2be421aec4 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -212,11 +212,12 @@ export class PublicAPIRouter extends PromiseRouter { 'Password does not meet the Password Policy requirements.' ) { throw new Parse.Error(Parse.Error.OTHER_CAUSE, `${result.err}`); + } else { + throw new Parse.Error( + Parse.Error.OTHER_CAUSE, + 'Failed to reset password (Username/email or token is invalid)' + ); } - throw new Parse.Error( - Parse.Error.OTHER_CAUSE, - 'Failed to reset password (Username/email or token is invalid)' - ); } return Promise.resolve({ From 68ee2c44bf2411ca8b56b039a4d490a7e2f99ae9 Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Fri, 1 Mar 2019 15:41:07 +0200 Subject: [PATCH 15/20] Revert changes --- src/Routers/PublicAPIRouter.js | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 2be421aec4..5cc0aebe03 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -210,14 +210,13 @@ export class PublicAPIRouter extends PromiseRouter { if ( result.err === 'Password does not meet the Password Policy requirements.' - ) { + ) throw new Parse.Error(Parse.Error.OTHER_CAUSE, `${result.err}`); - } else { - throw new Parse.Error( - Parse.Error.OTHER_CAUSE, - 'Failed to reset password (Username/email or token is invalid)' - ); - } + + throw new Parse.Error( + Parse.Error.OTHER_CAUSE, + 'Failed to reset password (Username/email or token is invalid)' + ); } return Promise.resolve({ From a8cb050826a99f2ad17b0e18babb02edc0bc8a68 Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Fri, 1 Mar 2019 16:44:43 +0200 Subject: [PATCH 16/20] Revert "Revert changes" This reverts commit 68ee2c44bf2411ca8b56b039a4d490a7e2f99ae9. --- src/Routers/PublicAPIRouter.js | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 5cc0aebe03..2be421aec4 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -210,13 +210,14 @@ export class PublicAPIRouter extends PromiseRouter { if ( result.err === 'Password does not meet the Password Policy requirements.' - ) + ) { throw new Parse.Error(Parse.Error.OTHER_CAUSE, `${result.err}`); - - throw new Parse.Error( - Parse.Error.OTHER_CAUSE, - 'Failed to reset password (Username/email or token is invalid)' - ); + } else { + throw new Parse.Error( + Parse.Error.OTHER_CAUSE, + 'Failed to reset password (Username/email or token is invalid)' + ); + } } return Promise.resolve({ From 4bf3667e207f2eed37ad4fd9e4011c90ac64bf2e Mon Sep 17 00:00:00 2001 From: Vladyslav Chygrinov Date: Fri, 1 Mar 2019 16:48:27 +0200 Subject: [PATCH 17/20] real revert of {} --- src/Routers/PublicAPIRouter.js | 12 +++++------- 1 file changed, 5 insertions(+), 7 deletions(-) diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 2be421aec4..64920f1b45 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -210,14 +210,12 @@ export class PublicAPIRouter extends PromiseRouter { if ( result.err === 'Password does not meet the Password Policy requirements.' - ) { + ) throw new Parse.Error(Parse.Error.OTHER_CAUSE, `${result.err}`); - } else { - throw new Parse.Error( - Parse.Error.OTHER_CAUSE, - 'Failed to reset password (Username/email or token is invalid)' - ); - } + throw new Parse.Error( + Parse.Error.OTHER_CAUSE, + 'Failed to reset password (Username/email or token is invalid)' + ); } return Promise.resolve({ From 6f82c0b9d79a312cab3f44b03e31c65422d63bad Mon Sep 17 00:00:00 2001 From: Diamond Lewis Date: Thu, 14 Mar 2019 14:03:52 -0500 Subject: [PATCH 18/20] nits and test fix --- spec/PasswordPolicy.spec.js | 106 ++++++---------- spec/PublicAPI.spec.js | 111 +++++++++-------- spec/ValidationAndPasswordsReset.spec.js | 147 ++++++++++------------- src/Routers/PublicAPIRouter.js | 3 +- 4 files changed, 155 insertions(+), 212 deletions(-) diff --git a/spec/PasswordPolicy.spec.js b/spec/PasswordPolicy.spec.js index df32a34424..a3cf012555 100644 --- a/spec/PasswordPolicy.spec.js +++ b/spec/PasswordPolicy.spec.js @@ -909,69 +909,49 @@ describe('Password Policy: ', () => { }); }); - it('Should return error when password violates Password Policy and reset through ajax', done => { + it('Should return error when password violates Password Policy and reset through ajax', async done => { const user = new Parse.User(); const emailAdapter = { sendVerificationEmail: () => Promise.resolve(), - sendPasswordResetEmail: options => { - request({ + sendPasswordResetEmail: async options => { + const response = await request({ url: options.link, followRedirects: false, simple: false, resolveWithFullResponse: true, - }) - .then(response => { - expect(response.status).toEqual(302); - const re = /http:\/\/localhost:8378\/1\/apps\/choose_password\?token=([a-zA-Z0-9]+)\&id=test\&username=user1/; - const match = response.text.match(re); - if (!match) { - fail('should have a token'); - done(); - return; - } - const token = match[1]; - - request({ - method: 'POST', - url: 'http://localhost:8378/1/apps/test/request_password_reset', - body: `new_password=xuser12&token=${token}&username=user1`, - headers: { - 'Content-Type': 'application/x-www-form-urlencoded', - 'X-Requested-With': 'XMLHttpRequest', - }, - followRedirects: false, - }) - .catch(error => { - expect(error.status).not.toBe(302); - expect(error.text).toEqual( - '{"code":-1,"error":"Password does not meet the Password Policy requirements."}' - ); + }); + expect(response.status).toEqual(302); + const re = /http:\/\/localhost:8378\/1\/apps\/choose_password\?token=([a-zA-Z0-9]+)\&id=test\&username=user1/; + const match = response.text.match(re); + if (!match) { + fail('should have a token'); + return; + } + const token = match[1]; - Parse.User.logIn('user1', 'r@nd0m') - .then(function() { - done(); - }) - .catch(err => { - jfail(err); - fail('should login with old password'); - done(); - }); - }) - .catch(error => { - jfail(error); - fail('Failed to POST request password reset'); - done(); - }); - }) - .catch(error => { - jfail(error); - fail('Failed to get the reset link'); - done(); + try { + await request({ + method: 'POST', + url: 'http://localhost:8378/1/apps/test/request_password_reset', + body: `new_password=xuser12&token=${token}&username=user1`, + headers: { + 'Content-Type': 'application/x-www-form-urlencoded', + 'X-Requested-With': 'XMLHttpRequest', + }, + followRedirects: false, }); + } catch (error) { + expect(error.status).not.toBe(302); + expect(error.text).toEqual( + '{"code":-1,"error":"Password does not meet the Password Policy requirements."}' + ); + } + await Parse.User.logIn('user1', 'r@nd0m'); + done(); }, sendMail: () => {}, }; - reconfigureServer({ + await reconfigureServer({ appName: 'passwordPolicy', verifyUserEmails: false, emailAdapter: emailAdapter, @@ -979,25 +959,13 @@ describe('Password Policy: ', () => { doNotAllowUsername: true, }, publicServerURL: 'http://localhost:8378/1', - }).then(() => { - user.setUsername('user1'); - user.setPassword('r@nd0m'); - user.set('email', 'user1@parse.com'); - user - .signUp() - .then(() => { - Parse.User.requestPasswordReset('user1@parse.com').catch(err => { - jfail(err); - fail('Reset password request should not fail'); - done(); - }); - }) - .catch(error => { - jfail(error); - fail('signUp should not fail'); - done(); - }); }); + user.setUsername('user1'); + user.setPassword('r@nd0m'); + user.set('email', 'user1@parse.com'); + await user.signUp(); + + await Parse.User.requestPasswordReset('user1@parse.com'); }); it('should reset password even if the new password contains user name while the policy allows', done => { diff --git a/spec/PublicAPI.spec.js b/spec/PublicAPI.spec.js index 1350dc060b..22c1383d5a 100644 --- a/spec/PublicAPI.spec.js +++ b/spec/PublicAPI.spec.js @@ -7,73 +7,70 @@ const request = function(url, callback) { }; describe('public API', () => { - it('should return missing username error on ajax request without username provided', done => { - reconfigureServer({ + it('should return missing username error on ajax request without username provided', async () => { + await reconfigureServer({ publicServerURL: 'http://localhost:8378/1', - }) - .then(() => { - return req({ - method: 'POST', - url: 'http://localhost:8378/1/apps/test/request_password_reset', - body: `new_password=user1&token=43634643&username=`, - headers: { - 'Content-Type': 'application/x-www-form-urlencoded', - 'X-Requested-With': 'XMLHttpRequest', - }, - followRedirects: false, - }); - }) - .catch(error => { - expect(error.status).not.toBe(302); - expect(error.text).toEqual('{"code":200,"error":"Missing username"}'); - done(); + }); + + try { + await req({ + method: 'POST', + url: 'http://localhost:8378/1/apps/test/request_password_reset', + body: `new_password=user1&token=43634643&username=`, + headers: { + 'Content-Type': 'application/x-www-form-urlencoded', + 'X-Requested-With': 'XMLHttpRequest', + }, + followRedirects: false, }); + } catch (error) { + expect(error.status).not.toBe(302); + expect(error.text).toEqual('{"code":200,"error":"Missing username"}'); + } }); - it('should return missing token error on ajax request without token provided', done => { - reconfigureServer({ + it('should return missing token error on ajax request without token provided', async () => { + await reconfigureServer({ publicServerURL: 'http://localhost:8378/1', - }) - .then(() => { - return req({ - method: 'POST', - url: 'http://localhost:8378/1/apps/test/request_password_reset', - body: `new_password=user1&token=&username=Johnny`, - headers: { - 'Content-Type': 'application/x-www-form-urlencoded', - 'X-Requested-With': 'XMLHttpRequest', - }, - followRedirects: false, - }); - }) - .catch(error => { - expect(error.status).not.toBe(302); - expect(error.text).toEqual('{"code":-1,"error":"Missing token"}'); - done(); + }); + + try { + await req({ + method: 'POST', + url: 'http://localhost:8378/1/apps/test/request_password_reset', + body: `new_password=user1&token=&username=Johnny`, + headers: { + 'Content-Type': 'application/x-www-form-urlencoded', + 'X-Requested-With': 'XMLHttpRequest', + }, + followRedirects: false, }); + } catch (error) { + expect(error.status).not.toBe(302); + expect(error.text).toEqual('{"code":-1,"error":"Missing token"}'); + } }); - it('should return missing password error on ajax request without password provided', done => { - reconfigureServer({ + it('should return missing password error on ajax request without password provided', async () => { + await reconfigureServer({ publicServerURL: 'http://localhost:8378/1', - }) - .then(() => { - return req({ - method: 'POST', - url: 'http://localhost:8378/1/apps/test/request_password_reset', - body: `new_password=&token=132414&username=Johnny`, - headers: { - 'Content-Type': 'application/x-www-form-urlencoded', - 'X-Requested-With': 'XMLHttpRequest', - }, - followRedirects: false, - }); - }) - .catch(error => { - expect(error.status).not.toBe(302); - expect(error.text).toEqual('{"code":201,"error":"Missing password"}'); - done(); + }); + + try { + await req({ + method: 'POST', + url: 'http://localhost:8378/1/apps/test/request_password_reset', + body: `new_password=&token=132414&username=Johnny`, + headers: { + 'Content-Type': 'application/x-www-form-urlencoded', + 'X-Requested-With': 'XMLHttpRequest', + }, + followRedirects: false, }); + } catch (error) { + expect(error.status).not.toBe(302); + expect(error.text).toEqual('{"code":201,"error":"Missing password"}'); + } }); it('should get invalid_link.html', done => { diff --git a/spec/ValidationAndPasswordsReset.spec.js b/spec/ValidationAndPasswordsReset.spec.js index e3aba02774..a17df5749d 100644 --- a/spec/ValidationAndPasswordsReset.spec.js +++ b/spec/ValidationAndPasswordsReset.spec.js @@ -910,110 +910,87 @@ describe('Custom Pages, Email Verification, Password Reset', () => { }); }); - it('should programmatically reset password on ajax request', done => { + it('should programmatically reset password on ajax request', async done => { const user = new Parse.User(); const emailAdapter = { sendVerificationEmail: () => Promise.resolve(), - sendPasswordResetEmail: options => { - request({ + sendPasswordResetEmail: async options => { + const response = await request({ url: options.link, followRedirects: false, - }).then(response => { - expect(response.status).toEqual(302); - const re = /http:\/\/localhost:8378\/1\/apps\/choose_password\?token=([a-zA-Z0-9]+)\&id=test\&username=zxcv/; - const match = response.text.match(re); - if (!match) { - fail('should have a token'); - done(); - return; - } - const token = match[1]; - - request({ - url: 'http://localhost:8378/1/apps/test/request_password_reset', - method: 'POST', - body: { new_password: 'hello', token, username: 'zxcv' }, - headers: { - 'Content-Type': 'application/x-www-form-urlencoded', - 'X-Requested-With': 'XMLHttpRequest', - }, - followRedirects: false, - }).then(response => { - expect(response.status).toEqual(200); - expect(response.text).toEqual('"Password successfully reset"'); + }); + expect(response.status).toEqual(302); + const re = /http:\/\/localhost:8378\/1\/apps\/choose_password\?token=([a-zA-Z0-9]+)\&id=test\&username=zxcv/; + const match = response.text.match(re); + if (!match) { + fail('should have a token'); + return; + } + const token = match[1]; - Parse.User.logIn('zxcv', 'hello').then( - function() { - const config = Config.get('test'); - config.database.adapter - .find( - '_User', - { fields: {} }, - { username: 'zxcv' }, - { limit: 1 } - ) - .then(results => { - // _perishable_token should be unset after reset password - expect(results.length).toEqual(1); - expect(results[0]['_perishable_token']).toEqual(undefined); - done(); - }); - }, - err => { - jfail(err); - fail('should login with new password'); - done(); - } - ); - }); + const resetResponse = await request({ + url: 'http://localhost:8378/1/apps/test/request_password_reset', + method: 'POST', + body: { new_password: 'hello', token, username: 'zxcv' }, + headers: { + 'Content-Type': 'application/x-www-form-urlencoded', + 'X-Requested-With': 'XMLHttpRequest', + }, + followRedirects: false, }); + expect(resetResponse.status).toEqual(200); + expect(resetResponse.text).toEqual('"Password successfully reset"'); + + await Parse.User.logIn('zxcv', 'hello'); + const config = Config.get('test'); + const results = await config.database.adapter.find( + '_User', + { fields: {} }, + { username: 'zxcv' }, + { limit: 1 } + ); + // _perishable_token should be unset after reset password + expect(results.length).toEqual(1); + expect(results[0]['_perishable_token']).toEqual(undefined); + done(); }, sendMail: () => {}, }; - reconfigureServer({ + await reconfigureServer({ appName: 'emailing app', verifyUserEmails: true, emailAdapter: emailAdapter, publicServerURL: 'http://localhost:8378/1', - }).then(() => { - user.setPassword('asdf'); - user.setUsername('zxcv'); - user.set('email', 'user@parse.com'); - user.signUp().then(() => { - Parse.User.requestPasswordReset('user@parse.com', { - error: err => { - jfail(err); - fail('Should not fail'); - done(); - }, - }); - }); }); + user.setPassword('asdf'); + user.setUsername('zxcv'); + user.set('email', 'user@parse.com'); + await user.signUp(); + await Parse.User.requestPasswordReset('user@parse.com'); }); - it('should return ajax failure error on ajax request with wrong data provided', done => { - reconfigureServer({ + it('should return ajax failure error on ajax request with wrong data provided', async () => { + await reconfigureServer({ publicServerURL: 'http://localhost:8378/1', - }) - .then(() => { - return request({ - method: 'POST', - url: 'http://localhost:8378/1/apps/test/request_password_reset', - body: `new_password=user1&token=12345&username=Johnny`, - headers: { - 'Content-Type': 'application/x-www-form-urlencoded', - 'X-Requested-With': 'XMLHttpRequest', - }, - followRedirects: false, - }); - }) - .catch(error => { - expect(error.status).not.toBe(302); - expect(error.text).toEqual( - '{"code":-1,"error":"Failed to reset password (Username/email or token is invalid)"}' - ); - done(); + }); + + try { + await request({ + method: 'POST', + url: 'http://localhost:8378/1/apps/test/request_password_reset', + body: `new_password=user1&token=12345&username=Johnny`, + headers: { + 'Content-Type': 'application/x-www-form-urlencoded', + 'X-Requested-With': 'XMLHttpRequest', + }, + followRedirects: false, }); + } catch (error) { + expect(error.status).not.toBe(302); + expect(error.text).toEqual( + '{"code":-1,"error":"Failed to reset password (Username/email or token is invalid)"}' + ); + } }); it('deletes password reset token on email address change', done => { diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 64920f1b45..1a3011e2e5 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -210,8 +210,9 @@ export class PublicAPIRouter extends PromiseRouter { if ( result.err === 'Password does not meet the Password Policy requirements.' - ) + ) { throw new Parse.Error(Parse.Error.OTHER_CAUSE, `${result.err}`); + } throw new Parse.Error( Parse.Error.OTHER_CAUSE, 'Failed to reset password (Username/email or token is invalid)' From 5342a1801461a9cfb54b90eaad18c9171cd5d11f Mon Sep 17 00:00:00 2001 From: Diamond Lewis Date: Thu, 14 Mar 2019 14:48:23 -0500 Subject: [PATCH 19/20] fix tests --- spec/PasswordPolicy.spec.js | 2 +- src/Controllers/UserController.js | 2 +- src/Routers/PublicAPIRouter.js | 16 +++++++--------- 3 files changed, 9 insertions(+), 11 deletions(-) diff --git a/spec/PasswordPolicy.spec.js b/spec/PasswordPolicy.spec.js index 5fdd10e2bb..d4562003b0 100644 --- a/spec/PasswordPolicy.spec.js +++ b/spec/PasswordPolicy.spec.js @@ -947,7 +947,7 @@ describe('Password Policy: ', () => { } catch (error) { expect(error.status).not.toBe(302); expect(error.text).toEqual( - '{"code":-1,"error":"Password does not meet the Password Policy requirements."}' + '{"code":-1,"error":"Password cannot contain your username."}' ); } await Parse.User.logIn('user1', 'r@nd0m'); diff --git a/src/Controllers/UserController.js b/src/Controllers/UserController.js index 6b9587182c..1842b60341 100644 --- a/src/Controllers/UserController.js +++ b/src/Controllers/UserController.js @@ -246,7 +246,7 @@ export class UserController extends AdaptableController { return this.checkResetTokenValidity(username, token) .then(user => updateUserPassword(user.objectId, password, this.config)) .catch(error => { - if (error.message) { + if (error && error.message) { // in case of Parse.Error, fail with the error message only return Promise.reject(error.message); } else { diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 1a3011e2e5..1b63f1ba2f 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -153,6 +153,7 @@ export class PublicAPIRouter extends PromiseRouter { if (!config) { this.invalidRequest(); } + if (!config.publicServerURL) { return this.missingPublicServerURL(); } @@ -206,17 +207,14 @@ export class PublicAPIRouter extends PromiseRouter { response: 'Password successfully reset', }); } - - if ( - result.err === - 'Password does not meet the Password Policy requirements.' - ) { + if (result.err) { throw new Parse.Error(Parse.Error.OTHER_CAUSE, `${result.err}`); + } else { + throw new Parse.Error( + Parse.Error.OTHER_CAUSE, + 'Failed to reset password (Username/email or token is invalid)' + ); } - throw new Parse.Error( - Parse.Error.OTHER_CAUSE, - 'Failed to reset password (Username/email or token is invalid)' - ); } return Promise.resolve({ From a8d95042e6012fe68782b409b34158777eb20f5a Mon Sep 17 00:00:00 2001 From: Diamond Lewis Date: Thu, 14 Mar 2019 15:25:12 -0500 Subject: [PATCH 20/20] throw proper error --- spec/ValidationAndPasswordsReset.spec.js | 2 +- src/Controllers/UserController.js | 2 +- src/Routers/PublicAPIRouter.js | 5 ----- 3 files changed, 2 insertions(+), 7 deletions(-) diff --git a/spec/ValidationAndPasswordsReset.spec.js b/spec/ValidationAndPasswordsReset.spec.js index a17df5749d..0e9db70a4f 100644 --- a/spec/ValidationAndPasswordsReset.spec.js +++ b/spec/ValidationAndPasswordsReset.spec.js @@ -988,7 +988,7 @@ describe('Custom Pages, Email Verification, Password Reset', () => { } catch (error) { expect(error.status).not.toBe(302); expect(error.text).toEqual( - '{"code":-1,"error":"Failed to reset password (Username/email or token is invalid)"}' + '{"code":-1,"error":"Failed to reset password: username / email / token is invalid"}' ); } }); diff --git a/src/Controllers/UserController.js b/src/Controllers/UserController.js index 1842b60341..2d7b444428 100644 --- a/src/Controllers/UserController.js +++ b/src/Controllers/UserController.js @@ -90,7 +90,7 @@ export class UserController extends AdaptableController { ) .then(results => { if (results.length != 1) { - throw undefined; + throw 'Failed to reset password: username / email / token is invalid'; } if ( diff --git a/src/Routers/PublicAPIRouter.js b/src/Routers/PublicAPIRouter.js index 1b63f1ba2f..efa0ea5852 100644 --- a/src/Routers/PublicAPIRouter.js +++ b/src/Routers/PublicAPIRouter.js @@ -209,11 +209,6 @@ export class PublicAPIRouter extends PromiseRouter { } if (result.err) { throw new Parse.Error(Parse.Error.OTHER_CAUSE, `${result.err}`); - } else { - throw new Parse.Error( - Parse.Error.OTHER_CAUSE, - 'Failed to reset password (Username/email or token is invalid)' - ); } }