UNPKG

besper-frontend-site-dev-0935

Version:

Professional B-esper Frontend Site - Site-wide integration toolkit for full website bot deployment

125 lines (108 loc) 3.15 kB
// General helper utility functions export function generateId(prefix: string = 'besper'): string { return `${prefix}-${Math.random().toString(36).substr(2, 9)}`; } export function sleep(ms: number): Promise<void> { return new Promise(resolve => setTimeout(resolve, ms)); } export function deepClone<T>(obj: T): T { if (obj === null || typeof obj !== 'object') return obj; if (obj instanceof Date) return new Date(obj.getTime()) as unknown as T; if (obj instanceof Array) return obj.map(item => deepClone(item)) as unknown as T; if (typeof obj === 'object') { const clonedObj = {} as T; for (const key in obj) { if (obj.hasOwnProperty(key)) { clonedObj[key] = deepClone(obj[key]); } } return clonedObj; } return obj; } export function mergeDeep<T extends Record<string, any>>( target: T, source: Partial<T> ): T { const result = { ...target }; for (const key in source) { if (source.hasOwnProperty(key)) { const sourceValue = source[key]; const targetValue = result[key]; if (isObject(sourceValue) && isObject(targetValue)) { result[key] = mergeDeep(targetValue, sourceValue); } else { result[key] = sourceValue as T[Extract<keyof T, string>]; } } } return result; } function isObject(item: any): item is Record<string, any> { return item && typeof item === 'object' && !Array.isArray(item); } export function pick<T, K extends keyof T>(obj: T, keys: K[]): Pick<T, K> { const result = {} as Pick<T, K>; keys.forEach(key => { if (key in obj) { result[key] = obj[key]; } }); return result; } export function omit<T, K extends keyof T>(obj: T, keys: K[]): Omit<T, K> { const result = { ...obj }; keys.forEach(key => { delete result[key]; }); return result; } export function isEmpty(value: any): boolean { if (value == null) return true; if (Array.isArray(value) || typeof value === 'string') return value.length === 0; if (typeof value === 'object') return Object.keys(value).length === 0; return false; } export function retry<T>( fn: () => Promise<T>, maxAttempts: number = 3, delay: number = 1000 ): Promise<T> { return new Promise((resolve, reject) => { let attempts = 0; const attempt = async () => { try { const result = await fn(); resolve(result); } catch (error) { attempts++; if (attempts >= maxAttempts) { reject(error); } else { setTimeout(attempt, delay * attempts); } } }; attempt(); }); } export function createUrlWithParams( baseUrl: string, params: Record<string, string | number | boolean> ): string { const url = new URL(baseUrl); Object.entries(params).forEach(([key, value]) => { url.searchParams.set(key, String(value)); }); return url.toString(); } export function parseQueryString(queryString: string): Record<string, string> { const params = new URLSearchParams(queryString); const result: Record<string, string> = {}; params.forEach((value, key) => { result[key] = value; }); return result; }