{"record":{"id":"92c07acec8bb89ee","repo":"transloadit/uppy","slug":"unexpected-facebook-response-missing-batch-result","errorCode":null,"errorMessage":"Unexpected Facebook response: missing batch result","messagePattern":"Unexpected Facebook response: missing batch result","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/@uppy/companion/src/server/provider/facebook/index.ts","lineNumber":171,"sourceCode":"      if (secret == null) {\n        throw new Error('Facebook provider secret is not configured')\n      }\n\n      const responses = await runRequestBatch({\n        secret,\n        token,\n        requests: [\n          {\n            method: 'GET',\n            relative_url: `me?${new URLSearchParams({ fields: 'email' }).toString()}`,\n          },\n          { method: 'GET', relative_url: `${path}?${new URLSearchParams(qs)}` },\n        ],\n      })\n      const response1 = responses[0]\n      const response2 = responses[1]\n      if (!response1 || !response2) {\n        throw new Error('Unexpected Facebook response: missing batch result')\n      }\n\n      const { email } = response1.body as { email?: string }\n\n      const list = response2.body as FacebookListResponse\n\n      const currentQuery: Record<string, string> = {}\n      if (typeof cursor === 'string') currentQuery['cursor'] = cursor\n      return adaptData(list, email, directory, currentQuery)\n    })\n  }\n\n  override async download({\n    companion,\n    id,\n    providerUserSession: { accessToken: token },\n  }: {\n    companion: CompanionLike","sourceCodeStart":153,"sourceCodeEnd":189,"githubUrl":"https://github.com/transloadit/uppy/blob/5d4dedd02a1ac0ae022c75c54aca76558f88e256/packages/@uppy/companion/src/server/provider/facebook/index.ts#L153-L189","documentation":"The Facebook provider's list() uses a two-request batch (user profile for email + paginated content list) and requires both results to exist. If either responses[0] or responses[1] is missing, this error is thrown before parsing.","triggerScenarios":"Browsing Facebook in the Dashboard (list or listWithPagination) when the Graph API batch endpoint returns fewer than two results — typically because one sub-request errored, permissions were revoked, or the token expired.","commonSituations":"Token invalidated by password change or app removal, missing Graph API permissions for the user-profile sub-request, or Facebook returning per-item errors inside the batch array.","solutions":["Have the user reconnect Facebook to mint a fresh token","Verify the app's granted permissions include what the profile + photos list calls need","Check Companion logs for provider.facebook.list.error context around the failure","Retry after reconnecting; transient Graph API errors are also possible"],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":null,"typeGuard":"function isCompleteBatch(responses: unknown[]): responses is [{ body: unknown }, { body: unknown }] {\n  return responses.length >= 2 && Boolean(responses[0]) && Boolean(responses[1])\n}","tryCatchPattern":"try {\n  const { items, username } = await facebookProvider.list({ token, directory, companion })\n} catch (err) {\n  if (err instanceof Error && err.message.includes('missing batch result')) {\n    return promptReconnect('Facebook session expired — please reconnect.')\n  }\n  throw err\n}","preventionTips":["Surface provider re-auth prompts when listing fails","Track token age and proactively refresh Facebook sessions","Handle partial Graph API batch failures in your own batch calls if you build custom providers"],"tags":["companion","facebook","graph-api","batch-request"],"backgroundTag":"api-response-schema-mismatch","analyzedSha":"5d4dedd02a1ac0ae022c75c54aca76558f88e256","analyzedAt":"2026-08-28T12:18:41.267Z","schemaVersion":2},"datasetVersion":"2026-08-28T16:17:29.566Z"}