Files
CodeNomad/packages/ui/src/lib/runtime-env.ts
2025-11-23 00:36:43 +00:00

87 lines
2.2 KiB
TypeScript

export type HostRuntime = "electron" | "tauri" | "web"
export type PlatformKind = "desktop" | "mobile"
export interface RuntimeEnvironment {
host: HostRuntime
platform: PlatformKind
}
declare global {
interface Window {
electronAPI?: unknown
__TAURI__?: {
invoke?: <T = unknown>(cmd: string, args?: Record<string, unknown>) => Promise<T>
event?: {
listen: (event: string, handler: (payload: { payload: unknown }) => void) => Promise<() => void>
}
dialog?: {
open?: (options: Record<string, unknown>) => Promise<string | string[] | null>
save?: (options: Record<string, unknown>) => Promise<string | null>
}
}
}
}
function detectHost(): HostRuntime {
if (typeof window === "undefined") {
return "web"
}
const win = window as Window & { electronAPI?: unknown }
if (typeof win.electronAPI !== "undefined") {
return "electron"
}
if (typeof win.__TAURI__ !== "undefined") {
return "tauri"
}
if (typeof navigator !== "undefined" && /tauri/i.test(navigator.userAgent)) {
return "tauri"
}
return "web"
}
function detectPlatform(): PlatformKind {
if (typeof navigator === "undefined") {
return "desktop"
}
const uaData = (navigator as any).userAgentData
if (uaData?.mobile) {
return "mobile"
}
const ua = navigator.userAgent.toLowerCase()
if (/android|iphone|ipad|ipod|blackberry|mini|windows phone|mobile|silk/.test(ua)) {
return "mobile"
}
return "desktop"
}
let cachedEnv: RuntimeEnvironment | null = null
export function detectRuntimeEnvironment(): RuntimeEnvironment {
if (cachedEnv) {
return cachedEnv
}
cachedEnv = {
host: detectHost(),
platform: detectPlatform(),
}
if (typeof console !== "undefined") {
const message = `[runtime] host=${cachedEnv.host} platform=${cachedEnv.platform}`
console.info(message)
}
return cachedEnv
}
export const runtimeEnv = detectRuntimeEnvironment()
export const isElectronHost = () => runtimeEnv.host === "electron"
export const isTauriHost = () => runtimeEnv.host === "tauri"
export const isWebHost = () => runtimeEnv.host === "web"
export const isMobilePlatform = () => runtimeEnv.platform === "mobile"