{"record":{"id":"8683c9986fb265cb","repo":"Molunerfinn/PicGo","slug":"result-error-dynamic-message-propagated-from-rpc-8683c9","errorCode":null,"errorMessage":"result.error (dynamic message propagated from RPC failure)","messagePattern":"result\\.error \\(dynamic message propagated from RPC failure\\)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"src/renderer/queries/picgo-cloud-config-sync.ts","lineNumber":14,"sourceCode":"import { useQuery } from '@tanstack/react-query'\nimport type { IPicGoCloudConfigSyncState } from '#/types/cloudConfigSync'\nimport { cloudAdapter } from '@/adapters/cloud'\nimport { rendererQueryClient } from './query-client'\nimport { usePicGoCloudUserInfo } from './picgo-cloud'\n\nexport const PicGoCloudConfigSyncQueryKeys = {\n  state: ['picgo-cloud', 'config-sync-state'] as const\n}\n\nasync function fetchPicGoCloudConfigSyncState (): Promise<IPicGoCloudConfigSyncState> {\n  const result = await cloudAdapter.getConfigSyncState()\n  if (!result.success) {\n    throw new Error(result.error)\n  }\n  return result.data\n}\n\nexport function useCloudConfigSyncStateQuery () {\n  const { userInfo } = usePicGoCloudUserInfo()\n  return useQuery({\n    queryKey: PicGoCloudConfigSyncQueryKeys.state,\n    queryFn: fetchPicGoCloudConfigSyncState,\n    enabled: !!userInfo,\n    refetchOnWindowFocus: true\n  })\n}\n\nexport function setCloudConfigSyncStateQueryData (state: IPicGoCloudConfigSyncState) {\n  rendererQueryClient.setQueryData(PicGoCloudConfigSyncQueryKeys.state, state)\n}\n","sourceCodeStart":1,"sourceCodeEnd":32,"githubUrl":"https://github.com/Molunerfinn/PicGo/blob/07ec7068a5512344da093d49a8408fa63ba3421e/src/renderer/queries/picgo-cloud-config-sync.ts#L1-L32","documentation":"fetchPicGoCloudConfigSyncState throws Error(result.error) when the PICGO_CLOUD_CONFIG_SYNC_GET_STATE RPC via cloudAdapter.getConfigSyncState() returns success:false. The config-sync state query then enters error state with the main-process-provided message. This gate is used to keep the sync UI consistent with server state.","triggerScenarios":"The config sync state RPC fails: unauthenticated user (the query is enabled based on userInfo from usePicGoCloudUserInfo), expired token, picgo-hub connectivity failure, or handler-side exception serialized into result.error.","commonSituations":"Mounting the config sync settings panel before login completes; token expiry mid-session; transient network loss; querying while a sync run is in an inconsistent server state.","solutions":["Confirm userInfo exists — the query hook derives enabled state from usePicGoCloudUserInfo; wait for login before rendering the sync UI.","Inspect query.error.message; if auth-related, re-login and invalidate ['picgo-cloud','config-sync-state'].","For network failures, refetch after reconnect.","Guard the UI with the enabled option so the query does not run for logged-out users."],"exampleFix":"// before\nexport function useCloudConfigSyncStateQuery () {\n  const { userInfo } = usePicGoCloudUserInfo()\n  ...\n}\n// after\nexport function useCloudConfigSyncStateQuery () {\n  const { userInfo } = usePicGoCloudUserInfo()\n  return useQuery({\n    queryKey: PicGoCloudConfigSyncQueryKeys.state,\n    queryFn: fetchPicGoCloudConfigSyncState,\n    enabled: !!userInfo\n  })\n}","handlingStrategy":"validation","validationCode":"const { userInfo } = usePicGoCloudUserInfo()\nconst query = useCloudConfigSyncStateQuery()\n// Only call sync actions / trust state when:\nif (!userInfo || query.isError) return","typeGuard":"function isConfigSyncState(r: unknown): r is IPicGoCloudConfigSyncState {\n  return typeof r === 'object' && r !== null && 'phase' in r\n}","tryCatchPattern":"try {\n  const state = await cloudAdapter.getConfigSyncState()\n  if (!state.success) {\n    toast.error(resolveCloudErrorMessage(i18n.t, undefined, undefined, state.error || 'Sync state unavailable'))\n    return\n  }\n} catch (e) {\n  toast.error(e instanceof Error ? e.message : 'Sync state unavailable')\n}","preventionTips":["Set enabled: !!userInfo on the query so it never fires for anonymous users.","Disable config-sync UI controls while query.isError is true.","Re-login and invalidate the query when the error message indicates auth failure.","Treat sync state as unavailable (not as 'in sync') on error."],"tags":["rpc","react-query","config-sync","authentication"],"backgroundTag":"rpc-error-propagation","analyzedSha":"07ec7068a5512344da093d49a8408fa63ba3421e","analyzedAt":"2026-08-30T01:45:22.289Z","schemaVersion":2},"datasetVersion":"2026-08-30T03:17:51.788Z"}