diff --git a/src/reset-password/ResetPasswordPage.jsx b/src/reset-password/ResetPasswordPage.jsx
index 54629fe9..511b4e5a 100644
--- a/src/reset-password/ResetPasswordPage.jsx
+++ b/src/reset-password/ResetPasswordPage.jsx
@@ -4,6 +4,7 @@ import { connect } from 'react-redux';
import { Button, Input, ValidationFormGroup } from '@edx/paragon';
import { injectIntl, intlShape } from '@edx/frontend-platform/i18n';
+import { getQueryParameters } from '@edx/frontend-platform';
import messages from './messages';
import { resetPassword, validateToken } from './data/actions';
import { resetPasswordResultSelector } from './data/selectors';
@@ -16,6 +17,7 @@ import Spinner from './Spinner';
const ResetPasswordPage = (props) => {
const { intl } = props;
+ const params = getQueryParameters();
const [newPasswordInput, setNewPasswordValue] = useState('');
const [confirmPasswordInput, setConfirmPasswordValue] = useState('');
@@ -55,7 +57,7 @@ const ResetPasswordPage = (props) => {
new_password1: newPasswordInput,
new_password2: confirmPasswordInput,
};
- props.resetPassword(formPayload, props.token);
+ props.resetPassword(formPayload, props.token, params);
}
};
diff --git a/src/reset-password/data/actions.js b/src/reset-password/data/actions.js
index 7e8eb146..88b3b71a 100644
--- a/src/reset-password/data/actions.js
+++ b/src/reset-password/data/actions.js
@@ -24,9 +24,9 @@ export const validateTokenFailure = (tokenStatus) => ({
});
// Reset Password
-export const resetPassword = (formPayload, token) => ({
+export const resetPassword = (formPayload, token, params) => ({
type: RESET_PASSWORD.BASE,
- payload: { formPayload, token },
+ payload: { formPayload, token, params },
});
export const resetPasswordBegin = () => ({
diff --git a/src/reset-password/data/sagas.js b/src/reset-password/data/sagas.js
index 849f7200..3768cdb5 100644
--- a/src/reset-password/data/sagas.js
+++ b/src/reset-password/data/sagas.js
@@ -34,7 +34,7 @@ export function* handleValidateToken(action) {
export function* handleResetPassword(action) {
try {
yield put(resetPasswordBegin());
- const data = yield call(resetPassword, action.payload.formPayload, action.payload.token);
+ const data = yield call(resetPassword, action.payload.formPayload, action.payload.token, action.payload.params);
const resetStatus = data.reset_status;
const resetErrors = data.err_msg;
diff --git a/src/reset-password/data/service.js b/src/reset-password/data/service.js
index 8682c728..cc7f3274 100644
--- a/src/reset-password/data/service.js
+++ b/src/reset-password/data/service.js
@@ -22,15 +22,17 @@ export async function validateToken(token) {
}
// eslint-disable-next-line import/prefer-default-export
-export async function resetPassword(payload, token) {
+export async function resetPassword(payload, token, queryParams) {
const requestConfig = {
headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
isPublic: true,
};
+ let path = `password/reset/${token}/?track=pwreset`;
+ path += queryParams.is_account_recovery ? '&is_account_recovery=true' : '';
const { data } = await getAuthenticatedHttpClient()
.post(
- `${getConfig().LMS_BASE_URL}/password/reset/${token}/?track=pwreset`,
+ `${getConfig().LMS_BASE_URL}/${path}`,
formurlencoded(payload),
requestConfig,
)
diff --git a/src/reset-password/data/tests/sagas.test.js b/src/reset-password/data/tests/sagas.test.js
new file mode 100644
index 00000000..9541d8f6
--- /dev/null
+++ b/src/reset-password/data/tests/sagas.test.js
@@ -0,0 +1,59 @@
+import { runSaga } from 'redux-saga';
+
+import {
+ resetPasswordBegin,
+ resetPasswordSuccess,
+ resetPasswordFailure,
+} from '../actions';
+import { handleResetPassword } from '../sagas';
+import * as api from '../service';
+
+describe('handleResetPassword', () => {
+ const params = {
+ payload: {
+ formPayload: {
+ new_password1: 'new_password1',
+ new_password2: 'new_password1',
+ },
+ token: 'token',
+ params: {},
+ },
+ };
+
+ const responseData = {
+ reset_status: true,
+ err_msg: '',
+ };
+
+ it('should call service and dispatch success action', async () => {
+ const resetPassword = jest.spyOn(api, 'resetPassword')
+ .mockImplementation(() => Promise.resolve(responseData));
+
+ const dispatched = [];
+ await runSaga(
+ { dispatch: (action) => dispatched.push(action) },
+ handleResetPassword,
+ params,
+ );
+
+ expect(resetPassword).toHaveBeenCalledTimes(1);
+ expect(dispatched).toEqual([resetPasswordBegin(), resetPasswordSuccess(true)]);
+ resetPassword.mockClear();
+ });
+
+ it('should call service and dispatch error action', async () => {
+ const resetPassword = jest.spyOn(api, 'resetPassword')
+ .mockImplementation(() => Promise.reject());
+
+ const dispatched = [];
+ await runSaga(
+ { dispatch: (action) => dispatched.push(action) },
+ handleResetPassword,
+ params,
+ );
+
+ expect(resetPassword).toHaveBeenCalledTimes(1);
+ expect(dispatched).toEqual([resetPasswordBegin(), resetPasswordFailure()]);
+ resetPassword.mockClear();
+ });
+});
diff --git a/src/reset-password/tests/ResetPasswordPage.test.jsx b/src/reset-password/tests/ResetPasswordPage.test.jsx
index 901d9679..f6bb7b24 100644
--- a/src/reset-password/tests/ResetPasswordPage.test.jsx
+++ b/src/reset-password/tests/ResetPasswordPage.test.jsx
@@ -1,11 +1,12 @@
import React from 'react';
-import { mount } from 'enzyme';
import { Provider } from 'react-redux';
import { act } from 'react-dom/test-utils';
import renderer from 'react-test-renderer';
import configureStore from 'redux-mock-store';
+import { mount } from 'enzyme';
import { IntlProvider, injectIntl } from '@edx/frontend-platform/i18n';
import * as auth from '@edx/frontend-platform/auth';
+import { resetPassword } from '../data/actions';
import ResetPasswordPage from '../ResetPasswordPage';
@@ -15,6 +16,7 @@ jest.mock('@edx/frontend-platform/auth');
const IntlResetPasswordPage = injectIntl(ResetPasswordPage);
const mockStore = configureStore();
+
describe('ResetPasswordPage', () => {
let props = {};
let store = {};
@@ -36,6 +38,10 @@ describe('ResetPasswordPage', () => {
};
});
+ afterEach(() => {
+ jest.clearAllMocks();
+ });
+
it('should match reset password default section snapshot', () => {
props = {
...props,
@@ -106,4 +112,46 @@ describe('ResetPasswordPage', () => {
resetPasswordPage.update();
expect(resetPasswordPage.find('#reset-password-input-invalid-feedback').text()).toEqual(validationMessage);
});
+
+ it('with valid inputs resetPassword action is dispatch', () => {
+ const newPassword = 'test-password1';
+ store = mockStore({
+ ...store,
+ });
+
+ props = {
+ ...props,
+ token_status: 'valid',
+ token: 'token',
+ };
+
+ const formPayload = {
+ new_password1: newPassword,
+ new_password2: newPassword,
+ };
+
+ store.dispatch = jest.fn(store.dispatch);
+ const resetPage = mount(reduxWrapper(