feat : user can login with user name..

fix: username should be one special  character and one alphabet.
This commit is contained in:
2025-10-25 18:54:14 +05:30
parent 2eec1b2e30
commit 3f1bbf1a4c
4 changed files with 54 additions and 24 deletions

View File

@@ -20,7 +20,7 @@ export default function Layout({ children }: { children: React.ReactNode }) {
{ label: "Change Login Password", href: "/settings/change_login_password" },
{ label: "Change transaction Password", href: "/settings/change_txn_password" },
{ label: "Set transaction Password", href: "/settings/set_txn_password" },
{ label: "Preferred Name", href: "/settings/user_id" },
{ label: "Preferred Name", href: "/settings/user_name" },
];
useEffect(() => {
const token = localStorage.getItem("access_token");

View File

@@ -32,13 +32,13 @@ export default function SetPreferredNameSimple() {
const icon = <IconUser size={18} stroke={1.5} />;
// 🟢 Fetch name + generate captcha on mount
// Fetch name + generate captcha on mount
useEffect(() => {
checkPreferredName();
regenerateCaptcha();
}, []);
// 🟢 OTP timer
// OTP timer
useEffect(() => {
let interval: number | undefined;
if (timerActive && countdown > 0) {
@@ -55,7 +55,7 @@ export default function SetPreferredNameSimple() {
};
}, [timerActive, countdown]);
// 🟢 API: Fetch preferred name
// API: Fetch preferred name
async function checkPreferredName() {
try {
const token = localStorage.getItem("access_token");
@@ -77,20 +77,23 @@ export default function SetPreferredNameSimple() {
}
}
// 🟢 Captcha
// Captcha
const regenerateCaptcha = async () => {
const newCaptcha = await generateCaptcha();
setCaptcha(newCaptcha);
setCaptchaInput("");
};
// 🟢 Live Validation (kept from your previous version)
function onPreferredNameChange(value: string) {
const sanitized = value.replace(/[^A-Za-z0-9@_]/g, "").slice(0, 11);
setPreferredName(sanitized);
if (sanitized.length > 0 && (sanitized.length < 5 || sanitized.length > 11)) {
setPreferredNameError("Preferred Name must be 511 characters.");
} else if (!/[A-Za-z]/.test(sanitized)) {
setPreferredNameError("Preferred Name must contain at least one letter.");
} else if (!/[@_]/.test(sanitized)) {
setPreferredNameError("Preferred Name must contain at least one special character (@ or _).");
} else {
setPreferredNameError(null);
}
@@ -107,7 +110,7 @@ export default function SetPreferredNameSimple() {
}
}
// 🟢 OTP
// OTP
async function handleSendOtp() {
try {
await sendOtp({ type: "USERNAME_UPDATED" });
@@ -147,7 +150,7 @@ export default function SetPreferredNameSimple() {
}
}
// 🟢 Update Preferred Name API
// Update Preferred Name API
async function handleUpdatePreferredName() {
const token = localStorage.getItem("access_token");
if (!token) {
@@ -199,7 +202,7 @@ export default function SetPreferredNameSimple() {
regenerateCaptcha();
};
// 🟢 Main Submit
// Main Submit
const handleSubmit = async () => {
if (step === "form") {
if (!preferredName || !confirmName || !captchaInput) {
@@ -210,6 +213,14 @@ export default function SetPreferredNameSimple() {
});
return;
}
if(preferredName !== confirmName){
notifications.show({
title: "Mismatch Input",
message: "Preferred name and Confirm preferred name not same.",
color: "red",
});
return;
}
if (preferredNameError || confirmNameError) {
notifications.show({
@@ -286,7 +297,11 @@ export default function SetPreferredNameSimple() {
mb="xs"
rightSection={icon}
readOnly={step !== "form"}
onCopy={(e) => e.preventDefault()}
onPaste={(e) => e.preventDefault()}
onCut={(e) => e.preventDefault()}
error={confirmNameError || undefined}
/>
</Group>
@@ -396,6 +411,10 @@ export default function SetPreferredNameSimple() {
<List.Item>
You can change your username a maximum of 5 times.
</List.Item>
<List.Item>
Preferred Name must contain at least one alphabet and one special character (@ or _).
</List.Item>
</List>
</Paper>

View File

@@ -14,8 +14,8 @@ interface SendOtpPayload {
}
function getStoredMobileNumber(): string {
// const mobileNumber = localStorage.getItem('remitter_mobile_no');
const mobileNumber = "6297421727";
const mobileNumber = localStorage.getItem('remitter_mobile_no');
// const mobileNumber = "7890544527";
if (!mobileNumber) throw new Error('Mobile number not found.');
return mobileNumber;
}

View File

@@ -45,8 +45,8 @@ export default function Login() {
}
try {
// await sendOtp({ type: 'LOGIN_OTP', username: CIF, mobileNumber: mobile });
await sendOtp({ type: 'LOGIN_OTP', username: CIF, mobileNumber: "6297421727" });
await sendOtp({ type: 'LOGIN_OTP', username: CIF, mobileNumber: mobile });
// await sendOtp({ type: 'LOGIN_OTP', username: CIF, mobileNumber: "7890544527" });
notifications.show({
color: 'orange',
title: 'OTP Required',
@@ -67,8 +67,8 @@ export default function Login() {
async function handleVerifyOtp(mobile?: string) {
try {
if (mobile) {
// await verifyLoginOtp(otp, mobile);
await verifyLoginOtp(otp, '6297421727');
await verifyLoginOtp(otp, mobile);
// await verifyLoginOtp(otp, '7890544527');
return true;
}
}
@@ -124,14 +124,15 @@ export default function Login() {
try {
// --- Validation (before any API call) ---
if (!otpRequired && !otpVerified) {
const onlyDigit = /^\d{11}$/;
// const onlyDigit = /^\d{11}$/;
const onlyDigit = /^[A-Za-z0-9@_]{5,11}$/;
if (!onlyDigit.test(CIF)) {
notifications.show({
withBorder: true,
color: "red",
title: "Invalid UserId",
message: "UserID must be 11 digit",
message: "The User ID or Username must contain 5 to 11 alphanumeric characters.",
autoClose: 5000,
});
setIsLogging(false);
@@ -178,6 +179,7 @@ export default function Login() {
// --- LOGIN API FLOW ---
if (!otpRequired || otpVerified) {
const isNumeric = /^\d+$/.test(CIF);
const response = await fetch("api/auth/login", {
method: "POST",
headers: {
@@ -185,7 +187,8 @@ export default function Login() {
"X-Login-Type": "IB",
},
body: JSON.stringify({
customerNo: CIF,
customerNo: isNumeric ? CIF : null,
userName: isNumeric ? null : CIF,
password: psw,
otp: otp,
}),
@@ -522,14 +525,15 @@ export default function Login() {
/>
</div>
<Box w={{ base: "100%", md: "45%" }} p="lg">
<Card shadow="md" padding="xl" radius="md" style={{ maxWidth: 550, height: '70vh' }}>
<Card shadow="md" padding="xl" radius="md" style={{ maxWidth: 550, height: '70vh', justifyContent: 'space-between' }} >
<form onSubmit={handleLogin}>
<TextInput
label="User ID"
placeholder="Enter your CIF No"
label="User ID / User Name"
placeholder="Enter your CIF No / User Name"
value={CIF}
onInput={(e) => {
const input = e.currentTarget.value.replace(/\D/g, "");
// const input = e.currentTarget.value.replace(/\D/g, "");
const input = e.currentTarget.value.replace(/[^A-Za-z0-9@_]/g, "");
if (input.length <= 11) SetCIF(input);
}}
withAsterisk
@@ -609,10 +613,17 @@ export default function Login() {
)}
<Button type="submit" fullWidth mt="md" loading={isLogging} disabled={isLogging}>
<Button type="submit" fullWidth mt="sm" loading={isLogging} disabled={isLogging}>
{isLogging ? "Processing..." : buttonLabel}
</Button>
<Box mt="xs">
<Text size="sm">
<Text component="span" c="red" fw={600}>Note: </Text>
<Text component="span" c="black">
Existing users logging in to the new Internet Banking for the first time should use their CIF number to avoid login issues.
</Text>
</Text>
</Box>
</form>
</Card>
</Box>