import Cookies from "js-cookie"; import { toast } from "sonner"; import { AuthCookies, ProfileData, LoginFormData, NavigationConfig } from "@/types/auth"; import { getCookiesDecrypt, setCookiesEncrypt } from "@/lib/utils"; // Navigation configuration based on user roles export const NAVIGATION_CONFIG: NavigationConfig[] = [ { roleId: 2, path: "/in/dashboard/executive", label: "Executive Dashboard" }, { roleId: 3, path: "/in/dashboard", label: "Dashboard" }, { roleId: 4, path: "/in/dashboard", label: "Dashboard" }, { roleId: 9, path: "/in/supervisor/ticketing", label: "Ticketing" }, { roleId: 10, path: "/in/dashboard", label: "Dashboard" }, { roleId: 11, path: "/in/dashboard", label: "Dashboard" }, { roleId: 12, path: "/in/dashboard", label: "Dashboard" }, { roleId: 13, path: "/in/dashboard", label: "Dashboard" }, { roleId: 14, path: "/in/dashboard", label: "Dashboard" }, { roleId: 15, path: "/in/dashboard", label: "Dashboard" }, { roleId: 18, path: "/in/dashboard/executive-data", label: "Executive Data Dashboard" }, { roleId: 19, path: "/in/dashboard", label: "Dashboard" }, ]; // Cookie management utilities export const setAuthCookies = (accessToken: string, refreshToken: string): void => { const dateTime = new Date(); const newTime = dateTime.getTime() + 10 * 60 * 1000; // 10 minutes Cookies.set("access_token", accessToken, { expires: 1 }); Cookies.set("refresh_token", refreshToken, { expires: 1 }); Cookies.set("time_refresh", new Date(newTime).toISOString(), { expires: 1 }); Cookies.set("is_first_login", String(true), { secure: true, sameSite: "strict" }); }; export const setProfileCookies = (profile: ProfileData): void => { Cookies.set("home_path", profile.homePath || "", { expires: 1 }); Cookies.set("profile_picture", profile.profilePictureUrl || "", { expires: 1 }); Cookies.set("state", profile.userLevel?.name || "", { expires: 1 }); Cookies.set("state-prov", profile.userLevel?.province?.provName || "", { expires: 1 }); setCookiesEncrypt("uie", profile.id, { expires: 1 }); setCookiesEncrypt("urie", profile.roleId.toString(), { expires: 1 }); setCookiesEncrypt("urne", profile.role?.name || "", { expires: 1 }); setCookiesEncrypt("ulie", profile.userLevel?.id.toString() || "", { expires: 1 }); setCookiesEncrypt("uplie", profile.userLevel?.parentLevelId?.toString() || "", { expires: 1 }); setCookiesEncrypt("ulne", profile.userLevel?.levelNumber.toString() || "", { expires: 1 }); setCookiesEncrypt("ufne", profile.fullname, { expires: 1 }); setCookiesEncrypt("ulnae", profile.userLevel?.name || "", { expires: 1 }); setCookiesEncrypt("uinse", profile.instituteId || "", { expires: 1 }); Cookies.set("status", "login", { expires: 1 }); }; export const clearAllCookies = (): void => { Object.keys(Cookies.get()).forEach((cookieName) => { Cookies.remove(cookieName); }); }; export const getAuthCookies = (): Partial => { return { access_token: Cookies.get("access_token"), refresh_token: Cookies.get("refresh_token"), time_refresh: Cookies.get("time_refresh"), is_first_login: Cookies.get("is_first_login"), home_path: Cookies.get("home_path"), profile_picture: Cookies.get("profile_picture"), state: Cookies.get("state"), "state-prov": Cookies.get("state-prov"), uie: getCookiesDecrypt("uie"), urie: getCookiesDecrypt("urie"), urne: getCookiesDecrypt("urne"), ulie: getCookiesDecrypt("ulie"), uplie: getCookiesDecrypt("uplie"), ulne: getCookiesDecrypt("ulne"), ufne: getCookiesDecrypt("ufne"), ulnae: getCookiesDecrypt("ulnae"), uinse: getCookiesDecrypt("uinse"), status: Cookies.get("status"), }; }; // User validation utilities export const isUserEligible = (profile: ProfileData): boolean => { return !( profile.isInternational || !profile.isActive || profile.isDelete ); }; export const isProtectedRole = (roleId: number): boolean => { const protectedRoles = [2, 3, 4, 9, 10, 11, 12, 18, 19]; return protectedRoles.includes(roleId); }; export const isSpecialLevel = (userLevelId: number, parentLevelId?: number): boolean => { return userLevelId === 794 || parentLevelId === 771; }; // Navigation utilities export const getNavigationPath = (roleId: number, userLevelId?: number, parentLevelId?: number): string => { const config = NAVIGATION_CONFIG.find(nav => nav.roleId === roleId); console.log("Navigation Config : ", config); if (config) { // Special handling for role 2 with specific level conditions if (roleId === 2 && userLevelId && parentLevelId && isSpecialLevel(userLevelId, parentLevelId)) { return "/in/dashboard"; } return config.path; } return "/"; // Default fallback }; // Error handling utilities export const handleAuthError = (error: any, defaultMessage: string = "Authentication failed"): string => { if (typeof error === "string") { return error; } if (error?.message) { return error.message; } if (error?.response?.data?.message) { return error.response.data.message; } return defaultMessage; }; export const showAuthError = (error: any, defaultMessage: string = "Authentication failed"): void => { const message = handleAuthError(error, defaultMessage); toast.error(message); }; export const showAuthSuccess = (message: string): void => { toast.success(message); }; // Form validation utilities export const validateEmail = (email: string): boolean => { const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/; return emailRegex.test(email); }; export const validatePassword = (password: string): { isValid: boolean; errors: string[] } => { const errors: string[] = []; if (password.length < 6) { errors.push("Password must be at least 6 characters long"); } if (password.length > 100) { errors.push("Password must be less than 100 characters"); } return { isValid: errors.length === 0, errors }; }; // Loading state utilities export const createLoadingState = () => { let isLoading = false; return { get: () => isLoading, set: (loading: boolean) => { isLoading = loading; }, withLoading: async (fn: () => Promise): Promise => { isLoading = true; try { return await fn(); } finally { isLoading = false; } } }; }; // Constants export const AUTH_CONSTANTS = { CLIENT_ID: "mediahub-app", GRANT_TYPE: "password", TOKEN_REFRESH_INTERVAL: 10 * 60 * 1000, // 10 minutes MAX_LOGIN_ATTEMPTS: 3, LOCKOUT_DURATION: 15 * 60 * 1000, // 15 minutes } as const; // Rate limiting utilities export class LoginRateLimiter { private attempts: Map = new Map(); canAttempt(username: string): boolean { const userAttempts = this.attempts.get(username); if (!userAttempts) { return true; } const timeSinceLastAttempt = Date.now() - userAttempts.lastAttempt; if (timeSinceLastAttempt > AUTH_CONSTANTS.LOCKOUT_DURATION) { this.attempts.delete(username); return true; } return userAttempts.count < AUTH_CONSTANTS.MAX_LOGIN_ATTEMPTS; } recordAttempt(username: string): void { const userAttempts = this.attempts.get(username); if (userAttempts) { userAttempts.count++; userAttempts.lastAttempt = Date.now(); } else { this.attempts.set(username, { count: 1, lastAttempt: Date.now() }); } } resetAttempts(username: string): void { this.attempts.delete(username); } getRemainingTime(username: string): number { const userAttempts = this.attempts.get(username); if (!userAttempts) { return 0; } const timeSinceLastAttempt = Date.now() - userAttempts.lastAttempt; return Math.max(0, AUTH_CONSTANTS.LOCKOUT_DURATION - timeSinceLastAttempt); } } // Global rate limiter instance export const loginRateLimiter = new LoginRateLimiter();