This is an automated email from the ASF dual-hosted git repository.

mehul pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/ranger.git

commit 50a56de798b968d6e1e05b71c2f356502f5abaee
Author: Mugdha Varadkar <mug...@apache.org>
AuthorDate: Wed Aug 16 00:10:23 2023 +0530

    RANGER-4374: Getting page not found when wrong password is send in 'Old 
Password'
    
    Signed-off-by: Mehul Parikh <me...@apache.org>
---
 .../react-webapp/src/components/Editable.jsx       |  7 --
 .../webapp/react-webapp/src/utils/XAMessages.js    |  8 +--
 .../main/webapp/react-webapp/src/utils/XAUtils.js  |  2 +-
 .../main/webapp/react-webapp/src/utils/appState.js |  3 +
 .../main/webapp/react-webapp/src/utils/fetchAPI.js |  6 +-
 .../src/views/AuditEvent/AccessLogDetail.jsx       | 10 +--
 .../src/views/AuditEvent/AccessLogsTable.jsx       |  8 ++-
 .../src/views/AuditEvent/AdminLogs/PolicyLogs.jsx  |  8 +--
 .../src/views/AuditEvent/AdminLogs/UserLogs.jsx    |  6 +-
 .../src/views/Encryption/KeyManager.jsx            | 13 ++--
 .../src/views/SecurityZone/SecurityZoneForm.jsx    |  4 +-
 .../src/views/ServiceManager/ServiceDefinition.jsx | 20 +++---
 .../views/ServiceManager/ServiceViewDetails.jsx    | 12 ++--
 .../react-webapp/src/views/SideBar/SideBarBody.jsx |  1 +
 .../users_details/EditUserView.jsx                 | 51 +++++++++-----
 .../users_details/UserFormComp.jsx                 | 10 ++-
 .../users_details/UserListing.jsx                  |  2 +-
 .../webapp/react-webapp/src/views/UserProfile.jsx  | 78 +++++++++++++++++++---
 18 files changed, 171 insertions(+), 78 deletions(-)

diff --git 
a/security-admin/src/main/webapp/react-webapp/src/components/Editable.jsx 
b/security-admin/src/main/webapp/react-webapp/src/components/Editable.jsx
index 34eb8c5fa..75f7fcff1 100644
--- a/security-admin/src/main/webapp/react-webapp/src/components/Editable.jsx
+++ b/security-admin/src/main/webapp/react-webapp/src/components/Editable.jsx
@@ -727,13 +727,6 @@ const Editable = (props) => {
           <RadioBtnComp value={value} options={options} valRef={selectValRef} 
/>
         ) : type === TYPE_INPUT ? (
           <InputboxComp value={value} valRef={selectValRef} />
-        ) : type === TYPE_SELECT ? (
-          <CreatableSelectNew
-            value={value}
-            valRef={selectValRef}
-            conditionDefVal={props.conditionDefVal}
-            selectProps={props.selectProps}
-          />
         ) : type === TYPE_CUSTOM ? (
           <CustomCondition
             value={value}
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/utils/XAMessages.js 
b/security-admin/src/main/webapp/react-webapp/src/utils/XAMessages.js
index 82eb8fe18..aae75199b 100644
--- a/security-admin/src/main/webapp/react-webapp/src/utils/XAMessages.js
+++ b/security-admin/src/main/webapp/react-webapp/src/utils/XAMessages.js
@@ -25,7 +25,7 @@ export const RegexMessage = {
       "Please avoid these characters (&, <, >, ', \", `) for policy name.",
     userNameValidationMsg: (
       <>
-        <p className="pd-10" style={{ fontSize: "small" }}>
+        <p className="pd-10 mb-0" style={{ fontSize: "small" }}>
           1. User name should be start with alphabet / numeric / underscore /
           non-us characters.
           <br />
@@ -39,7 +39,7 @@ export const RegexMessage = {
       "Password should be minimum 8 characters ,atleast one uppercase letter, 
one lowercase letter and one numeric. For FIPS environment password should be 
minimum 14 characters with atleast one uppercase letter, one special 
characters, one lowercase letter and one numeric.",
     emailvalidationinfomessage: (
       <>
-        <p className="pd-10" style={{ fontSize: "small" }}>
+        <p className="pd-10 mb-0" style={{ fontSize: "small" }}>
           1. Email address should be start with alphabet / numeric / underscore
           / non-us characters.
           <br /> 2. Allowed special character <b>.-@</b> .
@@ -55,7 +55,7 @@ export const RegexMessage = {
                       2. Dragging bottom-right corner of javascript condition 
editor(Textarea) can resizable",
     firstNameValidationMsg: (
       <>
-        <p className="pd-10" style={{ fontSize: "small" }}>
+        <p className="pd-10 mb-0" style={{ fontSize: "small" }}>
           1. First name should be start with alphabet / numeric / underscore /
           non-us characters.
           <br />
@@ -67,7 +67,7 @@ export const RegexMessage = {
     ),
     lastNameValidationMsg: (
       <>
-        <p className="pd-10" style={{ fontSize: "small" }}>
+        <p className="pd-10 mb-0" style={{ fontSize: "small" }}>
           1. Last name should be start with alphabet / numeric / underscore /
           non-us characters.
           <br />
diff --git a/security-admin/src/main/webapp/react-webapp/src/utils/XAUtils.js 
b/security-admin/src/main/webapp/react-webapp/src/utils/XAUtils.js
index 7edee019e..20dece45f 100644
--- a/security-admin/src/main/webapp/react-webapp/src/utils/XAUtils.js
+++ b/security-admin/src/main/webapp/react-webapp/src/utils/XAUtils.js
@@ -18,7 +18,7 @@
  */
 
 import React, { useState } from "react";
-import { getUserProfile, setUserProfile } from "Utils/appState";
+import { getUserProfile } from "Utils/appState";
 import { UserRoles, PathAssociateWithModule, QueryParams } from 
"Utils/XAEnums";
 import {
   filter,
diff --git a/security-admin/src/main/webapp/react-webapp/src/utils/appState.js 
b/security-admin/src/main/webapp/react-webapp/src/utils/appState.js
index 6267de2b4..938cf9b2d 100644
--- a/security-admin/src/main/webapp/react-webapp/src/utils/appState.js
+++ b/security-admin/src/main/webapp/react-webapp/src/utils/appState.js
@@ -19,6 +19,7 @@
 
 const appState = {};
 const serviceDefData = {};
+
 function getUserProfile() {
   return appState.userProfile;
 }
@@ -26,9 +27,11 @@ function getUserProfile() {
 function setUserProfile(profile = null) {
   appState.userProfile = profile;
 }
+
 function getServiceDef() {
   return serviceDefData;
 }
+
 function setServiceDef(serviceDef, tagServiceDef, allServiceDefs) {
   serviceDefData.serviceDefs = serviceDef;
   serviceDefData.tagServiceDefs = tagServiceDef;
diff --git a/security-admin/src/main/webapp/react-webapp/src/utils/fetchAPI.js 
b/security-admin/src/main/webapp/react-webapp/src/utils/fetchAPI.js
index ef32634bb..135182b40 100644
--- a/security-admin/src/main/webapp/react-webapp/src/utils/fetchAPI.js
+++ b/security-admin/src/main/webapp/react-webapp/src/utils/fetchAPI.js
@@ -17,7 +17,6 @@
  * under the License.
  */
 import axios from "axios";
-import ErrorPage from "../views/ErrorPage";
 import {
   RANGER_REST_CSRF_ENABLED,
   RANGER_REST_CSRF_CUSTOM_HEADER,
@@ -55,6 +54,7 @@ async function fetchApi(axiosConfig = {}, otherConf = {}) {
   const config = {
     ...axiosConfig
   };
+
   if (otherConf && otherConf.cancelRequest) {
     /*
       Below code add "source" attribute in second argument which is use to 
cancel request.
@@ -77,6 +77,7 @@ async function fetchApi(axiosConfig = {}, otherConf = {}) {
     config.cancelToken = source.token;
     otherConf.source = source;
   }
+
   try {
     const resp = await axios(config);
     return resp;
@@ -88,6 +89,9 @@ async function fetchApi(axiosConfig = {}, otherConf = {}) {
         window.location.replace("login.jsp?sessionTimeout=true");
       }
     }
+    if (config.skipNavigate !== undefined && config.skipNavigate) {
+      throw error;
+    }
     if (
       error?.response?.status === 400 &&
       (error?.response?.data?.messageList?.[0]?.name == "DATA_NOT_FOUND" ||
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AccessLogDetail.jsx
 
b/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AccessLogDetail.jsx
index af64aa877..dc75efe50 100644
--- 
a/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AccessLogDetail.jsx
+++ 
b/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AccessLogDetail.jsx
@@ -36,6 +36,7 @@ function AccessLogDetail(props) {
     fetchServiceDefs();
     fetchAcessLogs();
   }, []);
+
   const fetchServiceDefs = async () => {
     let serviceDefsResp = [];
     try {
@@ -51,9 +52,10 @@ function AccessLogDetail(props) {
     setServiceDefs(serviceDefsResp.data.serviceDefs);
     setLoader(false);
   };
+
   const fetchAcessLogs = async () => {
-    let accessResp;
-    let accessData;
+    let accessResp = {};
+    let accessData = {};
 
     try {
       accessResp = await fetchApi({
@@ -66,7 +68,7 @@ function AccessLogDetail(props) {
       console.error(
         `Error occurred while fetching Access or CSRF headers! ${error}`
       );
-      toast.error(error.response.data.msgDesc);
+      toast.error(error?.response?.data?.msgDesc);
     }
     if (!isEmpty(accessResp)) {
       accessResp.data.vXAccessAudits.map((obj) => {
@@ -91,7 +93,7 @@ function AccessLogDetail(props) {
           <div className="wrap">
             <AccessLogsTable data={access}></AccessLogsTable>
           </div>
-          {access.policyId != -1 && (
+          {access?.policyId !== undefined && access?.policyId > 0 && (
             <>
               <h5 className="heading-without-wrap">Policy Details</h5>
               <div className="wrap">
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AccessLogsTable.jsx
 
b/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AccessLogsTable.jsx
index cf92a9a99..e4c814dca 100644
--- 
a/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AccessLogsTable.jsx
+++ 
b/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AccessLogsTable.jsx
@@ -173,7 +173,13 @@ export const AccessLogsTable = ({ data = {} }) => {
         </tr>
         <tr>
           <td>Result</td>
-          <td>{accessResult == 1 ? "Allowed" : "Denied"}</td>
+          <td>
+            {accessResult !== undefined
+              ? accessResult == 1
+                ? "Allowed"
+                : "Denied"
+              : "--"}
+          </td>
         </tr>
         <tr>
           <td className="text-nowrap">Access Enforcer</td>
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AdminLogs/PolicyLogs.jsx
 
b/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AdminLogs/PolicyLogs.jsx
index 92a1aac47..2ea9816ef 100644
--- 
a/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AdminLogs/PolicyLogs.jsx
+++ 
b/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AdminLogs/PolicyLogs.jsx
@@ -241,7 +241,7 @@ export const PolicyLogs = ({ data, reportdata }) => {
     return obj.attributeName == "Policy Resources" && obj.action == "update";
   });
 
-  /*UPDATESS*/
+  /* UPDATES */
 
   const policyDetailsUpdate = (details, resources) => {
     let tablerow = [];
@@ -1743,7 +1743,7 @@ export const PolicyLogs = ({ data, reportdata }) => {
 
     let keynew = {};
     resources.map((obj) => {
-      keynew = !isEmpty(ovj.previousValue) && JSON.parse(obj.previousValue);
+      keynew = !isEmpty(obj.previousValue) && JSON.parse(obj.previousValue);
     });
 
     Object.keys(keynew).map((key, index) => {
@@ -3041,8 +3041,8 @@ export const PolicyLogs = ({ data, reportdata }) => {
                               <td className="table-warning policyitem-field">
                                 <i>{`Users`}</i>
                                 {`: ${
-                                  !isEmpty(policy.suers)
-                                    ? policy.suers.join(", ")
+                                  !isEmpty(policy.users)
+                                    ? policy.users.join(", ")
                                     : "<empty>"
                                 } `}
                               </td>
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AdminLogs/UserLogs.jsx
 
b/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AdminLogs/UserLogs.jsx
index 0a94a3b85..a856187af 100644
--- 
a/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AdminLogs/UserLogs.jsx
+++ 
b/security-admin/src/main/webapp/react-webapp/src/views/AuditEvent/AdminLogs/UserLogs.jsx
@@ -243,15 +243,15 @@ export const UserLogs = ({ data, reportdata }) => {
       if (val == "ROLE_USER") {
         val = UserRoles.ROLE_USER.label;
       }
-      if (val == "ROLE_USER") {
-        val = UserRoles.ROLE_USER.label;
-      }
       if (val == "ROLE_SYS_ADMIN") {
         val = UserRoles.ROLE_SYS_ADMIN.label;
       }
       if (val == "ROLE_KEY_ADMIN") {
         val = UserRoles.ROLE_KEY_ADMIN.label;
       }
+      if (val == "ROLE_ADMIN_AUDITOR") {
+        val = UserRoles.ROLE_ADMIN_AUDITOR.label;
+      }
       if (val == "ROLE_KEY_ADMIN_AUDITOR") {
         val = UserRoles.ROLE_KEY_ADMIN_AUDITOR.label;
       }
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/views/Encryption/KeyManager.jsx
 
b/security-admin/src/main/webapp/react-webapp/src/views/Encryption/KeyManager.jsx
index d4f4a24b6..fa5f975b7 100644
--- 
a/security-admin/src/main/webapp/react-webapp/src/views/Encryption/KeyManager.jsx
+++ 
b/security-admin/src/main/webapp/react-webapp/src/views/Encryption/KeyManager.jsx
@@ -31,7 +31,6 @@ import { fetchApi } from "Utils/fetchAPI";
 import dateFormat from "dateformat";
 import moment from "moment-timezone";
 import { find, sortBy, isUndefined, isEmpty } from "lodash";
-import { commonBreadcrumb } from "../../utils/XAUtils";
 import StructuredFilter from 
"../../components/structured-filter/react-typeahead/tokenizer";
 import AsyncSelect from "react-select/async";
 import { isKeyAdmin, parseSearchFilter } from "../../utils/XAUtils";
@@ -60,7 +59,7 @@ function init(props) {
     updatetable: moment.now(),
     currentPageIndex: 0,
     currentPageSize: 25,
-    resetPage: { page: null }
+    resetPage: { page: 0 }
   };
 }
 
@@ -166,7 +165,8 @@ const KeyManager = (props) => {
     currentPageIndex,
     currentPageSize,
     pagecount,
-    updatetable
+    updatetable,
+    resetPage
   } = keyState;
 
   useEffect(() => {
@@ -331,9 +331,8 @@ const KeyManager = (props) => {
       setBlockUI(false);
       toast.success(`Success! Key deleted successfully`);
       if (keydata.length == 1 && currentPageIndex > 1) {
-        let page = currentPageIndex - currentPageIndex;
         if (typeof resetPage?.page === "function") {
-          resetPage.page(page);
+          resetPage.page(0);
         }
       } else {
         dispatch({
@@ -344,7 +343,7 @@ const KeyManager = (props) => {
     } catch (error) {
       setBlockUI(false);
       let errorMsg = "";
-      if (error.response.data.msgDesc) {
+      if (error?.response?.data?.msgDesc) {
         errorMsg = toast.error("Error! " + error.response.data.msgDesc + "\n");
       } else {
         errorMsg = `Error occurred during deleting Key` + "\n";
@@ -410,7 +409,7 @@ const KeyManager = (props) => {
       });
       dispatch({
         type: "SET_RESET_PAGE",
-        resetPage: gotoPage
+        resetPage: { page: gotoPage }
       });
       dispatch({
         type: "SET_LOADER",
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/views/SecurityZone/SecurityZoneForm.jsx
 
b/security-admin/src/main/webapp/react-webapp/src/views/SecurityZone/SecurityZoneForm.jsx
index ea76fa823..c506ee0f8 100644
--- 
a/security-admin/src/main/webapp/react-webapp/src/views/SecurityZone/SecurityZoneForm.jsx
+++ 
b/security-admin/src/main/webapp/react-webapp/src/views/SecurityZone/SecurityZoneForm.jsx
@@ -205,7 +205,9 @@ const SecurityZoneForm = (props) => {
         console.error(
           `Error occurred while fetching Zone or CSRF headers! ${error}`
         );
-        toast.error(error.response.data.msgDesc);
+        if (error?.response?.data?.msgDesc) {
+          toast.error(error.response.data.msgDesc);
+        }
       }
       setZone(zoneResp?.data);
     }
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/views/ServiceManager/ServiceDefinition.jsx
 
b/security-admin/src/main/webapp/react-webapp/src/views/ServiceManager/ServiceDefinition.jsx
index af1903ec7..696c25c8c 100644
--- 
a/security-admin/src/main/webapp/react-webapp/src/views/ServiceManager/ServiceDefinition.jsx
+++ 
b/security-admin/src/main/webapp/react-webapp/src/views/ServiceManager/ServiceDefinition.jsx
@@ -476,15 +476,17 @@ class ServiceDefinition extends Component {
                                 <p className="form-header">
                                   Config Properties :
                                 </p>
-                                <Table bordered size="sm">
-                                  <tbody className="service-config">
-                                    {s?.configs &&
-                                      this.getServiceConfigs(
-                                        this.state.serviceDef,
-                                        s.configs
-                                      )}
-                                  </tbody>
-                                </Table>
+                                <div className="table-responsive">
+                                  <Table bordered size="sm">
+                                    <tbody className="service-config">
+                                      {s?.configs &&
+                                        this.getServiceConfigs(
+                                          this.state.serviceDef,
+                                          s.configs
+                                        )}
+                                    </tbody>
+                                  </Table>
+                                </div>
                                 <p className="form-header">Audit Filter :</p>
                                 <div className="table-responsive">
                                   <Table
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/views/ServiceManager/ServiceViewDetails.jsx
 
b/security-admin/src/main/webapp/react-webapp/src/views/ServiceManager/ServiceViewDetails.jsx
index c774504ec..52279345f 100644
--- 
a/security-admin/src/main/webapp/react-webapp/src/views/ServiceManager/ServiceViewDetails.jsx
+++ 
b/security-admin/src/main/webapp/react-webapp/src/views/ServiceManager/ServiceViewDetails.jsx
@@ -281,11 +281,13 @@ export const ServiceViewDetails = (props) => {
           </tbody>
         </Table>
         <p className="form-header">Config Properties :</p>
-        <Table bordered size="sm">
-          <tbody className="service-config">
-            {getServiceConfigs(serviceDefData, serviceData.configs)}
-          </tbody>
-        </Table>
+        <div className="table-responsive">
+          <Table bordered size="sm">
+            <tbody className="service-config">
+              {getServiceConfigs(serviceDefData, serviceData.configs)}
+            </tbody>
+          </Table>
+        </div>
         <p className="form-header">Audit Filter :</p>
         <div className="table-responsive">
           <Table bordered size="sm" className="table-audit-filter-ready-only">
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/views/SideBar/SideBarBody.jsx 
b/security-admin/src/main/webapp/react-webapp/src/views/SideBar/SideBarBody.jsx
index 4d8494fc4..aa4a2d890 100644
--- 
a/security-admin/src/main/webapp/react-webapp/src/views/SideBar/SideBarBody.jsx
+++ 
b/security-admin/src/main/webapp/react-webapp/src/views/SideBar/SideBarBody.jsx
@@ -45,6 +45,7 @@ import {
 import { getServiceDef } from "../../utils/appState";
 import ResourceTagContent from "./ResourceTagContent";
 import { Button } from "react-bootstrap";
+import { toast } from "react-toastify";
 
 function reducer(state, action) {
   switch (action.type) {
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/views/UserGroupRoleListing/users_details/EditUserView.jsx
 
b/security-admin/src/main/webapp/react-webapp/src/views/UserGroupRoleListing/users_details/EditUserView.jsx
index 73585458a..44468cda6 100644
--- 
a/security-admin/src/main/webapp/react-webapp/src/views/UserGroupRoleListing/users_details/EditUserView.jsx
+++ 
b/security-admin/src/main/webapp/react-webapp/src/views/UserGroupRoleListing/users_details/EditUserView.jsx
@@ -17,18 +17,18 @@
  * under the License.
  */
 
-import React, { useState, useEffect, useReducer } from "react";
+import React, { useEffect, useReducer } from "react";
 import { Tab, Button, Nav, Row, Col } from "react-bootstrap";
 import { Form, Field } from "react-final-form";
-import { getUserProfile, setUserProfile } from "Utils/appState";
+import { getUserProfile } from "Utils/appState";
 import UserFormComp from 
"Views/UserGroupRoleListing/users_details/UserFormComp";
 import { Loader, scrollToError } from "Components/CommonComponents";
 import { fetchApi } from "Utils/fetchAPI";
 import { UserTypes, RegexValidation } from "Utils/XAEnums";
 import { toast } from "react-toastify";
-import withRouter from "Hooks/withRouter";
 import { useParams, useLocation, useNavigate } from "react-router-dom";
-import { commonBreadcrumb } from "../../../utils/XAUtils";
+import { has } from "lodash";
+import { commonBreadcrumb, InfoIcon } from "../../../utils/XAUtils";
 
 const initialState = {
   userInfo: {},
@@ -89,16 +89,6 @@ function AddUserView(props) {
     });
   };
 
-  const Error = ({ name }) => (
-    <Field name={name}>
-      {({ meta: { error, touched } }) => {
-        return error && touched ? (
-          <div className="col-sm-2">{error}</div>
-        ) : null;
-      }}
-    </Field>
-  );
-
   const validateForm = (values) => {
     const errors = {};
     if (!values.newPassword) {
@@ -110,7 +100,10 @@ function AddUserView(props) {
     }
     if (!values.reEnterPassword) {
       errors.reEnterPassword = "Required";
-    } else if (values.newPassword !== values.reEnterPassword) {
+    } else if (
+      has(values, "newPassword") &&
+      values.newPassword !== values.reEnterPassword
+    ) {
       errors.reEnterPassword = "Password must be match with new password";
     }
     return errors;
@@ -132,7 +125,8 @@ function AddUserView(props) {
       toast.success("User password change successfully!!");
       navigate("/users/usertab");
     } catch (error) {
-      console.error(`Error occurred while updating user password! ${error}`);
+      toast.error("Error occured while updating user details!");
+      console.error(`Error occurred while updating user details! ${error}`);
     }
   };
 
@@ -187,7 +181,6 @@ function AddUserView(props) {
             <Tab.Content>
               <Tab.Pane eventKey="edit-password">
                 <>
-                  <h4 className="wrap-header bold">User Password Change</h4>
                   <Form
                     onSubmit={handleSubmit}
                     validate={validateForm}
@@ -241,6 +234,18 @@ function AddUserView(props) {
                                     }
                                     data-cy="newPassword"
                                   />
+                                  <InfoIcon
+                                    css="info-user-role-grp-icon"
+                                    position="right"
+                                    message={
+                                      <p
+                                        className="pd-10 mb-0"
+                                        style={{ fontSize: "small" }}
+                                      >
+                                        {RegexValidation.PASSWORD.message}
+                                      </p>
+                                    }
+                                  />
                                   {meta.error && meta.touched && (
                                     <span className="invalid-field">
                                       {meta.error}
@@ -277,6 +282,18 @@ function AddUserView(props) {
                                     }
                                     data-cy="reEnterPassword"
                                   />
+                                  <InfoIcon
+                                    css="info-user-role-grp-icon"
+                                    position="right"
+                                    message={
+                                      <p
+                                        className="pd-10 mb-0"
+                                        style={{ fontSize: "small" }}
+                                      >
+                                        {RegexValidation.PASSWORD.message}
+                                      </p>
+                                    }
+                                  />
                                   {meta.error && meta.touched && (
                                     <span className="invalid-field">
                                       {meta.error}
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/views/UserGroupRoleListing/users_details/UserFormComp.jsx
 
b/security-admin/src/main/webapp/react-webapp/src/views/UserGroupRoleListing/users_details/UserFormComp.jsx
index 1b32993b7..23bc1b169 100644
--- 
a/security-admin/src/main/webapp/react-webapp/src/views/UserGroupRoleListing/users_details/UserFormComp.jsx
+++ 
b/security-admin/src/main/webapp/react-webapp/src/views/UserGroupRoleListing/users_details/UserFormComp.jsx
@@ -469,7 +469,10 @@ function UserFormComp(props) {
                           css="info-user-role-grp-icon"
                           position="right"
                           message={
-                            <p className="pd-10" style={{ fontSize: "small" }}>
+                            <p
+                              className="pd-10 mb-0"
+                              style={{ fontSize: "small" }}
+                            >
                               {
                                 RegexMessage.MESSAGE
                                   .passwordvalidationinfomessage
@@ -518,7 +521,10 @@ function UserFormComp(props) {
                           css="info-user-role-grp-icon"
                           position="right"
                           message={
-                            <p className="pd-10" style={{ fontSize: "small" }}>
+                            <p
+                              className="pd-10 mb-0"
+                              style={{ fontSize: "small" }}
+                            >
                               {
                                 RegexMessage.MESSAGE
                                   .passwordvalidationinfomessage
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/views/UserGroupRoleListing/users_details/UserListing.jsx
 
b/security-admin/src/main/webapp/react-webapp/src/views/UserGroupRoleListing/users_details/UserListing.jsx
index c3150fd65..1890168e5 100644
--- 
a/security-admin/src/main/webapp/react-webapp/src/views/UserGroupRoleListing/users_details/UserListing.jsx
+++ 
b/security-admin/src/main/webapp/react-webapp/src/views/UserGroupRoleListing/users_details/UserListing.jsx
@@ -279,7 +279,7 @@ function Users() {
           setBlockUI(false);
         } catch (error) {
           setBlockUI(false);
-          if (error.response.data.msgDesc) {
+          if (error?.response?.data?.msgDesc) {
             errorMsg += error.response.data.msgDesc + "\n";
           } else {
             errorMsg +=
diff --git 
a/security-admin/src/main/webapp/react-webapp/src/views/UserProfile.jsx 
b/security-admin/src/main/webapp/react-webapp/src/views/UserProfile.jsx
index 452fe931e..64c695b33 100644
--- a/security-admin/src/main/webapp/react-webapp/src/views/UserProfile.jsx
+++ b/security-admin/src/main/webapp/react-webapp/src/views/UserProfile.jsx
@@ -30,6 +30,7 @@ import { has, isEmpty, isUndefined } from "lodash";
 import { RegexMessage } from "../utils/XAMessages";
 import { fetchApi } from "Utils/fetchAPI";
 import CustomBreadcrumb from "./CustomBreadcrumb";
+
 class UserProfile extends Component {
   constructor(props) {
     super(props);
@@ -37,6 +38,7 @@ class UserProfile extends Component {
       blockUI: false
     };
   }
+
   updateUserInfo = async (values) => {
     const userProps = getUserProfile();
 
@@ -83,7 +85,8 @@ class UserProfile extends Component {
       const passwdResp = await fetchApi({
         url: "users/" + userProps.id + "/passwordchange",
         method: "post",
-        data: jsonData
+        data: jsonData,
+        skipNavigate: true
       });
       this.setState({ blockUI: false });
       toast.success("Successfully updated user password");
@@ -91,11 +94,11 @@ class UserProfile extends Component {
     } catch (error) {
       this.setState({ blockUI: false });
       if (
-        (has(error?.response, "data.msgDesc") &&
-          error?.response?.data?.msgDesc == "serverMsg.userMgrOldPassword") ||
-        "serverMsg.userMgrNewPassword"
+        has(error?.response, "data.msgDesc") &&
+        (error?.response?.data?.msgDesc == "serverMsg.userMgrOldPassword" ||
+          error?.response?.data?.msgDesc == "serverMsg.userMgrNewPassword")
       ) {
-        toast.error("You can not use old password.");
+        toast.error("Error occured while updating user password!");
       }
       console.error(`Error occurred while updating user password! ${error}`);
     }
@@ -103,12 +106,14 @@ class UserProfile extends Component {
 
   validatePasswordForm = (values) => {
     const errors = {};
+
     if (!values.oldPassword) {
       errors.oldPassword = "Required";
     }
     if (!values.newPassword) {
       errors.newPassword = "Required";
     }
+
     if (
       values &&
       has(values, "newPassword") &&
@@ -116,19 +121,53 @@ class UserProfile extends Component {
     ) {
       errors.newPassword = RegexValidation.PASSWORD.message;
     }
+
     if (!values.reEnterPassword) {
       errors.reEnterPassword = "Required";
-    } else if (values.newPassword !== values.reEnterPassword) {
-      errors.reEnterPassword = "Must match";
+    } else if (
+      has(values, "newPassword") &&
+      values.newPassword !== values.reEnterPassword
+    ) {
+      errors.reEnterPassword =
+        "Re-enter New Password must match with New Password";
     }
+
+    if (values && has(values, "oldPassword") && has(values, "newPassword")) {
+      if (values.oldPassword === values.newPassword) {
+        errors.newPassword = "New Password cannot be same as Old Password";
+      }
+    }
+
     return errors;
   };
 
   validateUserForm = (values) => {
     const errors = {};
+
     if (!values.firstName) {
       errors.firstName = "Required";
     }
+
+    if (
+      values &&
+      has(values, "firstName") &&
+      !RegexValidation.NAME_VALIDATION.regexExpressionForFirstAndLastName.test(
+        values.firstName
+      )
+    ) {
+      errors.firstName = RegexMessage.MESSAGE.firstNameValidationMsg;
+    }
+
+    if (
+      values &&
+      has(values, "lastName") &&
+      !RegexValidation.NAME_VALIDATION.regexExpressionForFirstAndLastName.test(
+        values.lastName
+      )
+    ) {
+      errors.lastName = RegexMessage.MESSAGE.lastNameValidationMsg;
+    }
+
     if (
       (!isEmpty(values.emailAddress) || !isUndefined(values.emailAddress)) &&
       !RegexValidation.EMAIL_VALIDATION.regexExpressionForEmail.test(
@@ -266,7 +305,11 @@ class UserProfile extends Component {
                                       ? "isError"
                                       : "lastName"
                                   }
-                                  className="form-control"
+                                  className={
+                                    meta.error && meta.touched
+                                      ? "form-control border-danger"
+                                      : "form-control"
+                                  }
                                   disabled={
                                     userProps.userSource ==
                                     UserTypes.USER_INTERNAL.value
@@ -282,6 +325,11 @@ class UserProfile extends Component {
                                     RegexMessage.MESSAGE.lastNameValidationMsg
                                   }
                                 />
+                                {meta.error && meta.touched && (
+                                  <span className="invalid-field">
+                                    {meta.error}
+                                  </span>
+                                )}
                               </Col>
                             </Row>
                           )}
@@ -318,6 +366,14 @@ class UserProfile extends Component {
                                   }
                                   data-cy="emailAddress"
                                 />
+                                <InfoIcon
+                                  css="info-user-role-grp-icon"
+                                  position="right"
+                                  message={
+                                    RegexMessage.MESSAGE
+                                      .emailvalidationinfomessage
+                                  }
+                                />
                                 {meta.error && meta.touched && (
                                   <span className="invalid-field">
                                     {meta.error}
@@ -455,7 +511,7 @@ class UserProfile extends Component {
                                   position="right"
                                   message={
                                     <p
-                                      className="pd-10"
+                                      className="pd-10 mb-0"
                                       style={{ fontSize: "small" }}
                                     >
                                       {RegexValidation.PASSWORD.message}
@@ -503,7 +559,7 @@ class UserProfile extends Component {
                                   position="right"
                                   message={
                                     <p
-                                      className="pd-10"
+                                      className="pd-10 mb-0"
                                       style={{ fontSize: "small" }}
                                     >
                                       {RegexValidation.PASSWORD.message}
@@ -551,7 +607,7 @@ class UserProfile extends Component {
                                   position="right"
                                   message={
                                     <p
-                                      className="pd-10"
+                                      className="pd-10 mb-0"
                                       style={{ fontSize: "small" }}
                                     >
                                       {RegexValidation.PASSWORD.message}

Reply via email to