claritykit-svelte
Version:
A comprehensive Svelte component library focused on accessibility, ADHD-optimized design, developer experience, and full SSR compatibility
108 lines (107 loc) • 3.57 kB
JavaScript
/**
* Environment detection utilities for SSR compatibility
* Provides reliable browser/server environment detection and safe API access
*/
/**
* Detects if code is running in a browser environment
* Checks for both window and document to ensure full browser context
*/
export const isBrowser = typeof window !== 'undefined' && typeof document !== 'undefined';
/**
* Detects if code is running in a server environment
* Inverse of isBrowser for clearer semantic meaning
*/
export const isServer = !isBrowser;
/**
* Safely executes a callback that requires DOM access
* @param callback - Function that accesses DOM APIs
* @param fallback - Value to return if DOM is not available
* @returns Result of callback or fallback value
*/
export function safelyAccessDOM(callback, fallback) {
if (isBrowser) {
try {
return callback();
}
catch (error) {
console.warn('DOM access failed:', error);
return fallback;
}
}
return fallback;
}
/**
* Safely executes a callback that requires window object
* @param callback - Function that accesses window APIs
* @param fallback - Value to return if window is not available
* @returns Result of callback or fallback value
*/
export function safelyAccessWindow(callback, fallback) {
if (isBrowser && typeof window !== 'undefined') {
try {
return callback();
}
catch (error) {
console.warn('Window access failed:', error);
return fallback;
}
}
return fallback;
}
/**
* Safely executes a callback that requires localStorage
* @param callback - Function that accesses localStorage
* @param fallback - Value to return if localStorage is not available
* @returns Result of callback or fallback value
*/
export function safelyAccessStorage(callback, fallback) {
if (isBrowser && typeof localStorage !== 'undefined') {
try {
return callback();
}
catch (error) {
// localStorage might be disabled or throw in private browsing
console.warn('Storage access failed:', error);
return fallback;
}
}
return fallback;
}
/**
* Returns a promise that resolves when DOM is ready
* Useful for components that need to wait for client-side hydration
*/
export function waitForDOM() {
if (isServer) {
return Promise.resolve();
}
if (document.readyState === 'loading') {
return new Promise((resolve) => {
document.addEventListener('DOMContentLoaded', () => resolve(), { once: true });
});
}
return Promise.resolve();
}
/**
* Checks if the current environment supports a specific API
* @param apiName - Name of the API to check (e.g., 'IntersectionObserver', 'ResizeObserver')
* @returns True if API is available, false otherwise
*/
export function supportsAPI(apiName) {
return safelyAccessWindow(() => apiName in window, false) || false;
}
/**
* Gets comprehensive environment information
* @returns Object containing environment details
*/
export function getEnvironmentInfo() {
return {
isBrowser,
isServer,
userAgent: safelyAccessWindow(() => navigator.userAgent),
supportsIntersectionObserver: supportsAPI('IntersectionObserver'),
supportsResizeObserver: supportsAPI('ResizeObserver'),
supportsMatchMedia: safelyAccessWindow(() => 'matchMedia' in window, false) || false,
supportsLocalStorage: safelyAccessStorage(() => true, false) || false,
};
}