diff --git a/web/client/components/security/forms/PasswordReset.jsx b/web/client/components/security/forms/PasswordReset.jsx
index 14335817d6..0563cf47ed 100644
--- a/web/client/components/security/forms/PasswordReset.jsx
+++ b/web/client/components/security/forms/PasswordReset.jsx
@@ -22,7 +22,9 @@ const PasswordReset = React.createClass({
// I18N
newPasswordText: React.PropTypes.node,
- passwordCheckText: React.PropTypes.node
+ passwordCheckText: React.PropTypes.node,
+ changed: React.PropTypes.bool,
+ error: React.PropTypes.object
},
contextTypes: {
messages: React.PropTypes.object
@@ -69,6 +71,15 @@ const PasswordReset = React.createClass({
}
return null;
},
+ renderStatus() {
+ if (this.props.changed) {
+ return ;
+ }
+ if (this.props.error) {
+ return ;
+ }
+ return null;
+ },
render() {
return (
);
},
isValid(password, passwordcheck) {
diff --git a/web/client/components/security/forms/__tests__/PasswordReset-test.jsx b/web/client/components/security/forms/__tests__/PasswordReset-test.jsx
index 738b2b5fd8..b23f8bf370 100644
--- a/web/client/components/security/forms/__tests__/PasswordReset-test.jsx
+++ b/web/client/components/security/forms/__tests__/PasswordReset-test.jsx
@@ -30,6 +30,20 @@ describe("Test the password reset form component", () => {
expect(cmp).toExist();
});
+ it('alert for success', () => {
+ const cmp = ReactDOM.render(, document.getElementById("container"));
+ expect(cmp).toExist();
+ let alert = ReactDOM.findDOMNode(ReactTestUtils.scryRenderedDOMComponentsWithClass(cmp, "alert-success")[0]);
+ expect(alert).toExist();
+ });
+
+ it('alert for error', () => {
+ const cmp = ReactDOM.render(, document.getElementById("container"));
+ expect(cmp).toExist();
+ let alert = ReactDOM.findDOMNode(ReactTestUtils.scryRenderedDOMComponentsWithClass(cmp, "alert-danger")[0]);
+ expect(alert).toExist();
+ });
+
it('test component validity', () => {
const cmp = ReactDOM.render(, document.getElementById("container"));
expect(cmp).toExist();
diff --git a/web/client/components/security/modals/PasswordResetModal.jsx b/web/client/components/security/modals/PasswordResetModal.jsx
index 01478268a7..3977210891 100644
--- a/web/client/components/security/modals/PasswordResetModal.jsx
+++ b/web/client/components/security/modals/PasswordResetModal.jsx
@@ -32,7 +32,9 @@ const PasswordResetModal = React.createClass({
closeGlyph: React.PropTypes.string,
style: React.PropTypes.object,
buttonSize: React.PropTypes.string,
- includeCloseButton: React.PropTypes.bool
+ includeCloseButton: React.PropTypes.bool,
+ changed: React.PropTypes.bool,
+ error: React.PropTypes.object
},
getDefaultProps() {
return {
@@ -92,6 +94,7 @@ const PasswordResetModal = React.createClass({
},
getBody() {
return ( {
this.setState({passwordValid: valid, password});
}} />);
diff --git a/web/client/plugins/login/index.js b/web/client/plugins/login/index.js
index 94d85bc743..cfdf16cf4a 100644
--- a/web/client/plugins/login/index.js
+++ b/web/client/plugins/login/index.js
@@ -36,7 +36,9 @@ const UserDetails = connect((state) => ({
const PasswordReset = connect((state) => ({
user: state.security && state.security.user,
- show: state.controls.ResetPassword && state.controls.ResetPassword.enabled
+ show: state.controls.ResetPassword && state.controls.ResetPassword.enabled,
+ changed: state.security && state.security.passwordChanged && true || false,
+ error: state.security && state.security.passwordError
}), {
onPasswordChange: (user, pass) => { return geoStoreChangePassword(user, pass); },
onClose: setControlProperty.bind(null, "ResetPassword", "enabled", false, false)
diff --git a/web/client/reducers/__tests__/security-test.js b/web/client/reducers/__tests__/security-test.js
index 9c673cf950..52a004a0cd 100644
--- a/web/client/reducers/__tests__/security-test.js
+++ b/web/client/reducers/__tests__/security-test.js
@@ -7,7 +7,7 @@
*/
var expect = require('expect');
var security = require('../security');
-var {LOGIN_SUCCESS, LOGIN_FAIL, RESET_ERROR, LOGOUT} = require('../../actions/security');
+var {LOGIN_SUCCESS, LOGIN_FAIL, RESET_ERROR, LOGOUT, CHANGE_PASSWORD_SUCCESS, CHANGE_PASSWORD_FAIL} = require('../../actions/security');
var {USERMANAGER_UPDATE_USER} = require('../../actions/users');
describe('Test the security reducer', () => {
@@ -87,4 +87,20 @@ describe('Test the security reducer', () => {
expect(state).toExist();
expect(state.user.name).toBe("user");
});
+
+ it('change password success', () => {
+ let state = security({user: testUser.User}, {type: CHANGE_PASSWORD_SUCCESS, user: {
+ id: 6,
+ password: "newpassword"
+ }});
+ expect(state).toExist();
+ expect(state.user.password).toBe("newpassword");
+ expect(state.passwordChanged).toBe(true);
+ });
+
+ it('change password fail', () => {
+ let state = security({user: testUser.User}, {type: CHANGE_PASSWORD_FAIL, error: {message: 'error'}});
+ expect(state).toExist();
+ expect(state.passwordError).toExist();
+ });
});
diff --git a/web/client/reducers/security.js b/web/client/reducers/security.js
index 9045ac2961..2597d31ecd 100644
--- a/web/client/reducers/security.js
+++ b/web/client/reducers/security.js
@@ -6,7 +6,8 @@
* LICENSE file in the root directory of this source tree.
*/
-const { LOGIN_SUCCESS, LOGIN_FAIL, LOGOUT, CHANGE_PASSWORD_SUCCESS, RESET_ERROR } = require('../actions/security');
+const { LOGIN_SUCCESS, LOGIN_FAIL, LOGOUT, CHANGE_PASSWORD_SUCCESS, CHANGE_PASSWORD_FAIL, RESET_ERROR } = require('../actions/security');
+const { SET_CONTROL_PROPERTY } = require('../actions/controls');
const { USERMANAGER_UPDATE_USER } = require('../actions/users');
const SecurityUtils = require('../utils/SecurityUtils');
@@ -23,6 +24,14 @@ function security(state = {user: null, errorCause: null}, action) {
});
}
return state;
+ case SET_CONTROL_PROPERTY:
+ if (action.control === 'ResetPassword' && action.property === 'enabled') {
+ return assign({}, state, {
+ passwordChanged: false,
+ passwordError: null
+ });
+ }
+ return state;
case LOGIN_SUCCESS:
const userAttributes = SecurityUtils.getUserAttributes(action.userDetails.User);
const userUuid = head(userAttributes.filter(attribute => attribute.name.toLowerCase() === 'uuid'));
@@ -50,7 +59,14 @@ function security(state = {user: null, errorCause: null}, action) {
case CHANGE_PASSWORD_SUCCESS:
return assign({}, state, {
user: assign({}, state.user, assign({}, action.user, {date: new Date().getUTCMilliseconds()})),
- authHeader: action.authHeader
+ authHeader: action.authHeader,
+ passwordChanged: true,
+ passwordError: null
+ });
+ case CHANGE_PASSWORD_FAIL:
+ return assign({}, state, {
+ passwordError: action.error,
+ passwordChanged: false
});
default:
return state;
diff --git a/web/client/translations/data.de-DE b/web/client/translations/data.de-DE
index a0b8d1ca7a..7eff6553a5 100644
--- a/web/client/translations/data.de-DE
+++ b/web/client/translations/data.de-DE
@@ -483,6 +483,8 @@
"passwordCheckFail": "Passwörter sind nicht identisch!",
"username": "Benutzername",
"password": "Passwort",
+ "passwordChanged": "Passwort geändert",
+ "passwordError": "Fehler beim Ändern des Passworts",
"signIn":"Anmelden",
"loginFail":"Anmeldung gescheitert",
"loginFailedStatusMessages": {
diff --git a/web/client/translations/data.en-US b/web/client/translations/data.en-US
index 334ff92a7a..86fca979ba 100644
--- a/web/client/translations/data.en-US
+++ b/web/client/translations/data.en-US
@@ -483,6 +483,8 @@
"passwordCheckFail": "Passwords do not match!",
"username": "Username",
"password": "Password",
+ "passwordChanged": "Password changed",
+ "passwordError": "Error changing password",
"signIn":"Sign-in",
"loginFail":"Login Fail",
"loginFailedStatusMessages": {
diff --git a/web/client/translations/data.fr-FR b/web/client/translations/data.fr-FR
index 0f9a53b6cc..60807514d6 100644
--- a/web/client/translations/data.fr-FR
+++ b/web/client/translations/data.fr-FR
@@ -485,6 +485,8 @@
"passwordCheckFail": "Les deux mots de passe ne correspondent pas!",
"username": "Nom d'utilisateur",
"password": "Mot de passe",
+ "passwordChanged": "Mot de passe changé",
+ "passwordError": "Erreur de changement de mot de passe",
"signIn":"S'authentifier",
"loginFail":"Erreur d'authentification",
"loginFailedStatusMessages": {
diff --git a/web/client/translations/data.it-IT b/web/client/translations/data.it-IT
index 22af284f36..0e481f1f5c 100644
--- a/web/client/translations/data.it-IT
+++ b/web/client/translations/data.it-IT
@@ -483,6 +483,8 @@
"passwordCheckFail": "Le due password non corrispondono",
"username": "Username",
"password": "Password",
+ "passwordChanged": "La password è stata cambiata",
+ "passwordError": "Errore nel cambio della password",
"signIn":"Accedi",
"loginFail":"Login Fallito",
"loginFailedStatusMessages": {