ui-soxo-bootstrap-core 2.6.18 → 2.6.19
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
|
@@ -6,79 +6,53 @@
|
|
|
6
6
|
* Ensure to follow a minimal standard
|
|
7
7
|
*/
|
|
8
8
|
import React, { useState, useEffect, useRef } from 'react';
|
|
9
|
-
|
|
10
9
|
import PhoneInput from 'react-phone-input-2';
|
|
11
|
-
|
|
12
10
|
import 'react-phone-input-2/lib/style.css';
|
|
13
|
-
|
|
14
|
-
import PropTypes from "prop-types";
|
|
15
|
-
|
|
11
|
+
import PropTypes from 'prop-types';
|
|
16
12
|
import './phone-input.scss';
|
|
17
13
|
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
14
|
+
export default function CountryPhoneInput({
|
|
15
|
+
value,
|
|
16
|
+
onChange,
|
|
17
|
+
disabled,
|
|
18
|
+
disableCountryCode,
|
|
19
|
+
required,
|
|
20
|
+
defaultCountryCode,
|
|
21
|
+
onBlur,
|
|
22
|
+
className,
|
|
23
|
+
onKeyDown,
|
|
24
|
+
}) {
|
|
25
|
+
const inputRef = useRef();
|
|
26
|
+
const hasInitializedRef = useRef(false); // IMPORTANT
|
|
27
|
+
|
|
28
|
+
const [phone, setPhone] = useState('');
|
|
29
|
+
/**
|
|
30
|
+
* run ONLY ONCE when initial value has dial code
|
|
31
|
+
*/
|
|
25
32
|
useEffect(() => {
|
|
26
|
-
if (
|
|
27
|
-
// To prepopulate phone number ,concat dialCode and phone number
|
|
33
|
+
if (!hasInitializedRef.current && value?.code?.dialCode && value?.value) {
|
|
28
34
|
setPhone(value.code.dialCode + value.value);
|
|
29
|
-
|
|
30
|
-
// In case of update , to identify the country code that is getting selected
|
|
31
|
-
// We are setting a timeout
|
|
32
|
-
setTimeout(() => {
|
|
33
|
-
// Using the reference , we get the internal state of the library component
|
|
34
|
-
let selectedCountry = null;
|
|
35
|
-
|
|
36
|
-
let selectedCode = null;
|
|
37
|
-
|
|
38
|
-
if (
|
|
39
|
-
inputRef.current &&
|
|
40
|
-
inputRef.current.state &&
|
|
41
|
-
inputRef.current.state.selectedCountry
|
|
42
|
-
) {
|
|
43
|
-
selectedCountry = inputRef.current.state.selectedCountry;
|
|
44
|
-
|
|
45
|
-
// Once we get the selected country ,we format it to the form that is received for normal onChange
|
|
46
|
-
selectedCode = {
|
|
47
|
-
countryCode: selectedCountry.iso2,
|
|
48
|
-
dialCode: selectedCountry.dialCode,
|
|
49
|
-
name: selectedCountry.name,
|
|
50
|
-
};
|
|
51
|
-
}
|
|
52
|
-
|
|
53
|
-
// Below being the format expected , we trigger the onChange to manually update the form
|
|
54
|
-
let updatedValue = {
|
|
55
|
-
value: value.code.dialCode + value.value,
|
|
56
|
-
code: selectedCode,
|
|
57
|
-
};
|
|
58
|
-
|
|
59
|
-
onChange(updatedValue);
|
|
60
|
-
}, 0);
|
|
35
|
+
hasInitializedRef.current = true; // 👈 mark as done
|
|
61
36
|
}
|
|
62
|
-
}, []);
|
|
37
|
+
}, [value]);
|
|
63
38
|
|
|
64
39
|
/**
|
|
65
|
-
*
|
|
66
|
-
* @param {*} value
|
|
40
|
+
* handle user input
|
|
67
41
|
*/
|
|
68
|
-
function handleInput(
|
|
69
|
-
if (code
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
42
|
+
function handleInput(inputValue, code) {
|
|
43
|
+
if (!code?.dialCode) return;
|
|
44
|
+
|
|
45
|
+
const phoneNumber = inputValue.slice(code.dialCode.length);
|
|
46
|
+
|
|
47
|
+
// remove autofill class when user edits field (if you use it)
|
|
48
|
+
onChange({
|
|
49
|
+
value: phoneNumber,
|
|
75
50
|
code,
|
|
76
|
-
};
|
|
77
|
-
onChange(value);
|
|
51
|
+
});
|
|
78
52
|
}
|
|
79
53
|
|
|
80
54
|
return (
|
|
81
|
-
<div className=
|
|
55
|
+
<div className={`phone-input ${className || ''}`}>
|
|
82
56
|
<PhoneInput
|
|
83
57
|
ref={inputRef}
|
|
84
58
|
country={defaultCountryCode || 'in'}
|
|
@@ -104,4 +78,4 @@ CountryPhoneInput.propTypes = {
|
|
|
104
78
|
disableCountryCode: PropTypes.bool,
|
|
105
79
|
/** A boolean indicating whether the input is required or not. This prop is optional. */
|
|
106
80
|
required: PropTypes.bool,
|
|
107
|
-
};
|
|
81
|
+
};
|
|
@@ -12,6 +12,20 @@
|
|
|
12
12
|
// }
|
|
13
13
|
}
|
|
14
14
|
|
|
15
|
+
.autofilled-field {
|
|
16
|
+
.react-tel-input {
|
|
17
|
+
.form-control {
|
|
18
|
+
border-color: #fa8c16 !important; // AntD warning orange
|
|
19
|
+
background-color: #fff7e6;
|
|
20
|
+
box-shadow: none;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
.flag-dropdown {
|
|
24
|
+
border-color: #fa8c16 !important;
|
|
25
|
+
background-color: #fff7e6;
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
}
|
|
15
29
|
// /* For tablets and smaller screens (max-width: 1024px) */
|
|
16
30
|
// @media (max-width: 1024px) {
|
|
17
31
|
// .phone-input {
|
|
@@ -30,7 +30,7 @@ import { getAccessToken, getRefreshToken } from '../../utils/http/auth.helper';
|
|
|
30
30
|
|
|
31
31
|
import { Location } from '../../utils';
|
|
32
32
|
|
|
33
|
-
import { checkLicenseStatus, formatMobile,
|
|
33
|
+
import { checkLicenseStatus, formatMobile, safeJSON } from '../../utils/common/common.utils';
|
|
34
34
|
|
|
35
35
|
import { MailOutlined, MessageOutlined, WhatsAppOutlined } from '@ant-design/icons';
|
|
36
36
|
|
|
@@ -50,8 +50,6 @@ const tailLayout = {
|
|
|
50
50
|
|
|
51
51
|
const LICENSE_EXPIRY = '2026-12-12';
|
|
52
52
|
|
|
53
|
-
//password valdity expire
|
|
54
|
-
const PASSWORD_VALIDITY_DAYS = 90;
|
|
55
53
|
|
|
56
54
|
const headers = {
|
|
57
55
|
db_ptr: 'nuraho',
|
|
@@ -115,47 +113,32 @@ function LoginPhone({ history, appSettings }) {
|
|
|
115
113
|
*
|
|
116
114
|
* - Parses `last_password_change` from user.other_details.
|
|
117
115
|
* - Calculates expiry using PASSWORD_VALIDITY_DAYS.
|
|
118
|
-
* - Uses `checkExpiryStatus()` to determine status.
|
|
119
116
|
* - Shows Ant Design warning message if expired or within warning period.
|
|
120
117
|
* - Warning message includes navigation to `/change-password`.
|
|
121
118
|
*
|
|
122
119
|
* Requires:
|
|
123
120
|
* - PASSWORD_VALIDITY_DAYS constant
|
|
124
|
-
* - checkExpiryStatus utility
|
|
125
121
|
* - React Router history
|
|
126
122
|
* - antd message component
|
|
127
123
|
*/
|
|
128
|
-
const handlePasswordExpiryCheck = (
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
const lastPasswordChange = otherDetails?.last_password_change;
|
|
132
|
-
|
|
133
|
-
if (lastPasswordChange) {
|
|
134
|
-
const onlyDate = new Date(lastPasswordChange).toISOString().split('T')[0];
|
|
135
|
-
const passwordExpiryDate = new Date(onlyDate);
|
|
136
|
-
passwordExpiryDate.setDate(passwordExpiryDate.getDate() + PASSWORD_VALIDITY_DAYS);
|
|
137
|
-
|
|
138
|
-
const passwordStatus = checkExpiryStatus({
|
|
139
|
-
expiryDate: passwordExpiryDate,
|
|
140
|
-
warningDays: 2,
|
|
141
|
-
expiredMessage: 'Your password has expired. Please reset it.',
|
|
142
|
-
warningMessage: (d) => (
|
|
143
|
-
<span>
|
|
144
|
-
Your password will expire in {d} day(s).{' '}
|
|
145
|
-
<a
|
|
146
|
-
onClick={() => {
|
|
147
|
-
history.push('/change-password');
|
|
148
|
-
}}
|
|
149
|
-
>
|
|
150
|
-
Click here to update.
|
|
151
|
-
</a>
|
|
152
|
-
</span>
|
|
153
|
-
),
|
|
154
|
-
});
|
|
124
|
+
const handlePasswordExpiryCheck = (expiryDays) => {
|
|
125
|
+
if (expiryDays == null) return;
|
|
155
126
|
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
127
|
+
if (expiryDays <= 0) {
|
|
128
|
+
message.error('Your password has expired. Please reset it.');
|
|
129
|
+
|
|
130
|
+
setExpiredPassword(true);
|
|
131
|
+
setShowResetpassword(true);
|
|
132
|
+
|
|
133
|
+
return;
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
if (expiryDays <= 2) {
|
|
137
|
+
message.warning(
|
|
138
|
+
<span>
|
|
139
|
+
Your password will expire in {expiryDays} day(s). <a onClick={() => history.push('/change-password')}>Click here to update.</a>
|
|
140
|
+
</span>
|
|
141
|
+
);
|
|
159
142
|
}
|
|
160
143
|
};
|
|
161
144
|
|
|
@@ -196,7 +179,7 @@ function LoginPhone({ history, appSettings }) {
|
|
|
196
179
|
if (insider_token) localStorage.insider_token = insider_token;
|
|
197
180
|
|
|
198
181
|
if (result.success) {
|
|
199
|
-
handlePasswordExpiryCheck(
|
|
182
|
+
handlePasswordExpiryCheck(result.expiry_in_days);
|
|
200
183
|
|
|
201
184
|
//two_factor_authentication variable is present then proceed Two factor authentication
|
|
202
185
|
if (result.data && result.data.two_factor_authentication) {
|
|
@@ -421,7 +404,7 @@ function LoginPhone({ history, appSettings }) {
|
|
|
421
404
|
// set user info into local storage
|
|
422
405
|
localStorage.setItem('userInfo', JSON.stringify(userInfo));
|
|
423
406
|
|
|
424
|
-
handlePasswordExpiryCheck(result.
|
|
407
|
+
handlePasswordExpiryCheck(result.expiry_in_days);
|
|
425
408
|
|
|
426
409
|
setTimeout(() => history.push('/'), 500);
|
|
427
410
|
} else {
|
|
@@ -123,41 +123,6 @@ export const checkLicenseStatus = (expiryDate) => {
|
|
|
123
123
|
return { valid: true, daysLeft, message: null, level: null };
|
|
124
124
|
};
|
|
125
125
|
|
|
126
|
-
/**
|
|
127
|
-
* Checks password expiry status.
|
|
128
|
-
*
|
|
129
|
-
* @param {string|Date} expiryDate
|
|
130
|
-
* @param {number} warningDays
|
|
131
|
-
* @param {string} expiredMessage
|
|
132
|
-
* @param {(daysLeft: number) => string} warningMessage
|
|
133
|
-
*
|
|
134
|
-
* @returns {{ valid: boolean, daysLeft: number, message: string|null, level: "error"|"warning"|null }}
|
|
135
|
-
*/
|
|
136
|
-
|
|
137
|
-
export const checkExpiryStatus = ({ expiryDate, warningDays, expiredMessage, warningMessage }) => {
|
|
138
|
-
const expiry = new Date(expiryDate);
|
|
139
|
-
|
|
140
|
-
if (isNaN(expiry)) {
|
|
141
|
-
return { valid: false, daysLeft: 0, message: 'Invalid date', level: 'error' };
|
|
142
|
-
}
|
|
143
|
-
|
|
144
|
-
expiry.setHours(0, 0, 0, 0);
|
|
145
|
-
const today = new Date();
|
|
146
|
-
today.setHours(0, 0, 0, 0);
|
|
147
|
-
|
|
148
|
-
const msDiff = expiry.getTime() - today.getTime();
|
|
149
|
-
const daysLeft = Math.ceil(msDiff / (1000 * 60 * 60 * 24));
|
|
150
|
-
|
|
151
|
-
if (daysLeft < 0) {
|
|
152
|
-
return { valid: false, daysLeft, message: expiredMessage, level: 'error' };
|
|
153
|
-
}
|
|
154
|
-
|
|
155
|
-
if (daysLeft <= warningDays) {
|
|
156
|
-
return { valid: true, daysLeft, message: warningMessage(daysLeft), level: 'warning' };
|
|
157
|
-
}
|
|
158
|
-
|
|
159
|
-
return { valid: true, daysLeft, message: null, level: null };
|
|
160
|
-
};
|
|
161
126
|
|
|
162
127
|
/**
|
|
163
128
|
* Masks a mobile number by hiding all but the last `visibleDigits`.
|