{"record":{"id":"cdcb3ddaaad8ee49","repo":"cjpais/Handy","slug":"failed-to-initialize","errorCode":null,"errorMessage":"Failed to initialize:","messagePattern":"Failed to initialize:","errorType":"console","errorClass":null,"httpStatus":null,"severity":"warning","filePath":"src/App.tsx","lineNumber":69,"sourceCode":"\n  useEffect(() => {\n    checkOnboardingStatus();\n  }, []);\n\n  // Initialize RTL direction when language changes\n  useEffect(() => {\n    initializeRTL(i18n.language);\n  }, [i18n.language]);\n\n  // Initialize Enigo, shortcuts, and refresh audio devices when main app loads\n  useEffect(() => {\n    if (onboardingStep === \"done\" && !hasCompletedPostOnboardingInit.current) {\n      hasCompletedPostOnboardingInit.current = true;\n      Promise.all([\n        commands.initializeEnigo(),\n        commands.initializeShortcuts(),\n      ]).catch((e) => {\n        console.warn(\"Failed to initialize:\", e);\n      });\n      refreshAudioDevices();\n      refreshOutputDevices();\n    }\n  }, [onboardingStep, refreshAudioDevices, refreshOutputDevices]);\n\n  // Handle keyboard shortcuts for debug mode toggle\n  useEffect(() => {\n    const handleKeyDown = (event: KeyboardEvent) => {\n      // Check for Ctrl+Shift+D (Windows/Linux) or Cmd+Shift+D (macOS)\n      const isDebugShortcut =\n        event.shiftKey &&\n        event.key.toLowerCase() === \"d\" &&\n        (event.ctrlKey || event.metaKey);\n\n      if (isDebugShortcut) {\n        event.preventDefault();\n        const currentDebugMode = settings?.debug_mode ?? false;","sourceCodeStart":51,"sourceCodeEnd":87,"githubUrl":"https://github.com/cjpais/Handy/blob/c89b7bf38974ad317177389f5bfe28236f0d64e3/src/App.tsx#L51-L87","documentation":"Once onboarding is done, App.tsx fires two backend commands — initializeEnigo (Enigo, the input simulator Handy uses to paste transcriptions into other apps) and initializeShortcuts (global hotkeys via rdev) — and refreshes audio device lists. This catch logs when either init command rejects. The app keeps running, but text pasting and global shortcuts are dead until something re-initializes them, which is the functional symptom to look for.","triggerScenarios":"Enigo init failing on Linux without X11/Wayland support or missing input libraries (headless, container, minimal session); rdev's global grab failing when another instance or security tool holds it; invoking after backend teardown; macOS where the accessibility grant was revoked between onboarding and this call.","commonSituations":"Linux systems missing libx11/libxdo/evdev access; VMs and CI without an input subsystem; conflicts with other global-shortcut apps; Wayland sessions with restricted key grabbing.","solutions":["Inspect which of the two commands failed from the logged error; they have different remedies","On Linux, run inside a real desktop session and install the X11/evdev dev libraries Handy's BUILD.md calls for","On macOS, re-check System Settings > Privacy > Accessibility if shortcuts specifically fail","Add a retry or user-visible 'shortcuts unavailable — click to re-init' path, since currently a failed init leaves the app degraded with only a console warning"],"exampleFix":"// before\nPromise.all([commands.initializeEnigo(), commands.initializeShortcuts()]).catch((e) => {\n  console.warn(\"Failed to initialize:\", e);\n});\n\n// after\nPromise.all([commands.initializeEnigo(), commands.initializeShortcuts()]).catch(\n  async (e) => {\n    console.warn(\"Failed to initialize, retrying once:\", e);\n    await new Promise((r) => setTimeout(r, 1500));\n    try {\n      await Promise.all([commands.initializeEnigo(), commands.initializeShortcuts()]);\n    } catch (retryErr) {\n      console.error(\"Initialization failed after retry — paste/shortcuts disabled:\", retryErr);\n      toast.warn(t(\"errors.initFailed\"));\n    }\n  },\n);","handlingStrategy":"retry","validationCode":null,"typeGuard":null,"tryCatchPattern":"try {\n  await Promise.all([commands.initializeEnigo(), commands.initializeShortcuts()]);\n} catch (e) {\n  console.warn(\"Failed to initialize:\", e);\n  await retryOnce(1500); // then surface a UI hint if it still fails\n}","preventionTips":["On Linux, verify X11/evdev libraries and a real session exist before expecting Enigo/rdev to init","Surface init failure in the UI — a console-only warning leaves paste/shortcuts silently broken","Check macOS accessibility is actually granted when shortcuts fail despite onboarding saying otherwise"],"tags":["tauri","enigo","global-shortcuts","initialization","linux"],"backgroundTag":"global-shortcut-initialization-failed","analyzedSha":"c89b7bf38974ad317177389f5bfe28236f0d64e3","analyzedAt":"2026-08-17T10:29:55.597Z","contentChangedAt":"2026-08-17T10:29:55.597Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}