{"record":{"id":"95edca51e34b05af","repo":"tinyhumansai/openhuman","slug":"model-testing-is-only-available-in-the-desktop-app","errorCode":null,"errorMessage":"Model testing is only available in the desktop app.","messagePattern":"Model testing is only available in the desktop app\\.","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"app/src/services/api/aiSettingsApi.ts","lineNumber":810,"sourceCode":"/** Fetch BYO provider auth failures recorded this process, keyed by slug. */\nexport async function loadProviderAuthErrors(): Promise<ProviderAuthError[]> {\n  if (!isTauri()) {\n    return [];\n  }\n  const res = await callCoreRpc<{ result: { errors: ProviderAuthError[] } }>({\n    method: 'openhuman.inference_provider_auth_errors',\n    params: {},\n  });\n  return res?.result?.errors ?? [];\n}\n\nexport async function testProviderModel(\n  workload: WorkloadId,\n  provider: string,\n  prompt = 'Hello world'\n): Promise<ProviderModelTestResult> {\n  if (!isTauri()) {\n    throw new Error('Model testing is only available in the desktop app.');\n  }\n  const res = await callCoreRpc<{ result: ProviderModelTestResult }>({\n    method: 'openhuman.inference_test_provider_model',\n    params: { workload, provider, prompt },\n    timeoutMs: PROVIDER_MODEL_TEST_TIMEOUT_MS,\n  });\n  if (!res?.result) {\n    throw new Error(\n      `Model test RPC returned no result for ${workload} via ${provider} (openhuman.inference_test_provider_model).`\n    );\n  }\n  return res.result;\n}\n\n// ─── Local provider façade (Ollama install / detect / model manage) ───────\n\n/** Snapshot of the Ollama daemon + installed-model state for the AI panel. */\nexport interface LocalProviderSnapshot {","sourceCodeStart":792,"sourceCodeEnd":828,"githubUrl":"https://github.com/tinyhumansai/openhuman/blob/a221052e0df5b1f7598fceba7329fd1af95d6699/app/src/services/api/aiSettingsApi.ts#L792-L828","documentation":"testProviderModel performs an inference test through the core RPC openhuman.inference_test_provider_model, which only exists when running inside the Tauri desktop shell. The isTauri() check fails (e.g. plain browser/Vite dev server without the Tauri host) and the call is refused before any RPC attempt.","triggerScenarios":"Opening the UI with `pnpm dev` (browser tab only) and clicking 'Test model' in the AI settings panel; running the frontend in a non-Tauri web deployment; unit/component tests executing the function in a plain JS DOM.","commonSituations":"Developers prototyping in the browser instead of `pnpm dev:app`; a web build of screens that were written for desktop; E2E harnesses that don't boot the Tauri host.","solutions":["Run the full desktop app (`pnpm dev:app`) when testing model connectivity","Hide or disable the 'Test model' button when !isTauri(), offering a desktop-only tooltip","In browser-only builds, replace the test with a hint to open the desktop app"],"exampleFix":"// before\n<button onClick={() => testProviderModel(workload, provider)}>Test model</button>\n\n// after\n{isTauri()\n  ? <button onClick={() => testProviderModel(workload, provider)}>Test model</button>\n  : <span className=\"hint\">Model testing is available in the desktop app.</span>}","handlingStrategy":"type-guard","validationCode":"import { isTauri } from '@/utils/tauri';\nconst canTestModels = isTauri();\n// gate the UI before any call:\nif (canTestModels) { const r = await testProviderModel(workload, provider); }","typeGuard":"const isDesktopHost = (): boolean => isTauri(); // use wherever the test button renders","tryCatchPattern":"try { await testProviderModel(workload, provider); }\ncatch (e) { if (String(e.message).includes('desktop app')) showDesktopOnlyNotice(); else throw e; }","preventionTips":["Use `pnpm dev:app` (full Tauri host) when touching inference/model settings","Conditionally render desktop-only capabilities via isTauri() instead of catching","Mark such functions in code review as desktop-only API surface"],"tags":["environment","tauri","ai-settings","feature-availability"],"backgroundTag":null,"analyzedSha":"a221052e0df5b1f7598fceba7329fd1af95d6699","analyzedAt":"2026-08-16T12:47:06.542Z","schemaVersion":2},"datasetVersion":"2026-08-16T13:17:31.715Z"}