Enhance input validation and error handling in authStore
- Added robust validation for `user` object fields to ensure non-empty strings. - Improved `calculateExpiry` with value range checks and warnings for invalid `expiresIn`. - Incorporated try-catch in `initializeAuth` to log errors and prevent app crashes during auth initialization.
This commit is contained in:
@@ -50,8 +50,15 @@ function isValidToken(token: string): boolean {
|
|||||||
* @returns Unix timestamp
|
* @returns Unix timestamp
|
||||||
*/
|
*/
|
||||||
function calculateExpiry(expiresIn?: number): number {
|
function calculateExpiry(expiresIn?: number): number {
|
||||||
// Default to 15 minutes if not provided
|
// Default to 15 minutes if not provided or invalid
|
||||||
const seconds = expiresIn || 900;
|
let seconds = expiresIn || 900;
|
||||||
|
|
||||||
|
// Validate positive number and prevent overflow
|
||||||
|
if (seconds <= 0 || seconds > 31536000) { // Max 1 year
|
||||||
|
console.warn(`Invalid expiresIn value: ${expiresIn}, using default 900s`);
|
||||||
|
seconds = 900;
|
||||||
|
}
|
||||||
|
|
||||||
return Date.now() + seconds * 1000;
|
return Date.now() + seconds * 1000;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -67,8 +74,10 @@ export const useAuthStore = create<AuthState>((set, get) => ({
|
|||||||
// Set complete auth state (user + tokens)
|
// Set complete auth state (user + tokens)
|
||||||
setAuth: async (user, accessToken, refreshToken, expiresIn) => {
|
setAuth: async (user, accessToken, refreshToken, expiresIn) => {
|
||||||
// Validate inputs
|
// Validate inputs
|
||||||
if (!user || !user.id || !user.email) {
|
if (!user || !user.id || !user.email ||
|
||||||
throw new Error('Invalid user object');
|
typeof user.id !== 'string' || typeof user.email !== 'string' ||
|
||||||
|
user.id.trim() === '' || user.email.trim() === '') {
|
||||||
|
throw new Error('Invalid user object: id and email must be non-empty strings');
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!isValidToken(accessToken) || !isValidToken(refreshToken)) {
|
if (!isValidToken(accessToken) || !isValidToken(refreshToken)) {
|
||||||
@@ -116,8 +125,10 @@ export const useAuthStore = create<AuthState>((set, get) => ({
|
|||||||
|
|
||||||
// Update user only
|
// Update user only
|
||||||
setUser: (user) => {
|
setUser: (user) => {
|
||||||
if (!user || !user.id || !user.email) {
|
if (!user || !user.id || !user.email ||
|
||||||
throw new Error('Invalid user object');
|
typeof user.id !== 'string' || typeof user.email !== 'string' ||
|
||||||
|
user.id.trim() === '' || user.email.trim() === '') {
|
||||||
|
throw new Error('Invalid user object: id and email must be non-empty strings');
|
||||||
}
|
}
|
||||||
|
|
||||||
set({ user });
|
set({ user });
|
||||||
@@ -178,7 +189,13 @@ export const useAuthStore = create<AuthState>((set, get) => ({
|
|||||||
/**
|
/**
|
||||||
* Initialize auth store from storage
|
* Initialize auth store from storage
|
||||||
* Call this on app startup
|
* Call this on app startup
|
||||||
|
* Errors are logged but don't throw to prevent app crashes
|
||||||
*/
|
*/
|
||||||
export async function initializeAuth(): Promise<void> {
|
export async function initializeAuth(): Promise<void> {
|
||||||
|
try {
|
||||||
await useAuthStore.getState().loadAuthFromStorage();
|
await useAuthStore.getState().loadAuthFromStorage();
|
||||||
|
} catch (error) {
|
||||||
|
// Log error but don't throw - app should continue even if auth init fails
|
||||||
|
console.error('Failed to initialize auth:', error);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user