{"record":{"id":"0d94e5313f12ab3e","repo":"mastra-ai/mastra","slug":"no-links-received-from-firecrawl-api","errorCode":null,"errorMessage":"No links received from Firecrawl API","messagePattern":"No links received from Firecrawl API","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"warning","filePath":"packages/mcp/src/__fixtures__/fire-crawl-complex-schema.ts","lineNumber":701,"sourceCode":"            content: [{ type: 'text', text: trimResponseText(errorMessage) }],\n            isError: true,\n          };\n        }\n      }\n\n      case 'firecrawl_map': {\n        if (!isMapOptions(args)) {\n          throw new Error('Invalid arguments for firecrawl_map');\n        }\n        const { url, ...options } = args;\n        const response = await client.mapUrl(url, {\n          ...options,\n        });\n        if ('error' in response) {\n          throw new Error(response.error);\n        }\n        if (!response.links) {\n          throw new Error('No links received from Firecrawl API');\n        }\n        return {\n          content: [{ type: 'text', text: trimResponseText(response.links.join('\\n')) }],\n          isError: false,\n        };\n      }\n\n      case 'firecrawl_crawl': {\n        if (!isCrawlOptions(args)) {\n          throw new Error('Invalid arguments for firecrawl_crawl');\n        }\n        const { url, ...options } = args;\n        const response = await withRetry(async () => client.asyncCrawlUrl(url, { ...options }), 'crawl operation');\n\n        if (!response.success) {\n          throw new Error(response.error);\n        }\n","sourceCodeStart":683,"sourceCodeEnd":719,"githubUrl":"https://github.com/mastra-ai/mastra/blob/75dd419e613fe9c39f846ffc500716141b74fda6/packages/mcp/src/__fixtures__/fire-crawl-complex-schema.ts#L683-L719","documentation":"After a successful map call, the executor checks `response.links`; if it is absent/falsy it throws this error because the tool has nothing to return. Firecrawl normally always returns links, so this indicates an unexpected response shape.","triggerScenarios":"mapUrl succeeding (no `error` field) but returning a body without `links` — unexpected API version change, empty/edge-case responses for tiny or unusual sites, truncated responses.","commonSituations":"Using an SDK version mismatched with the current Firecrawl API response schema, mapping a site that yields zero discoverable links, proxying through a custom endpoint returning a modified payload.","solutions":["Check the firecrawl-js SDK version matches the live API schema and upgrade if stale.","Handle empty-link results gracefully in the caller instead of treating them as fatal.","Retry the map operation; transient truncation may explain the missing field."],"exampleFix":"null","handlingStrategy":"fallback","validationCode":"const res = await client.mapUrl(url, options);\nif (!('links' in res) || !Array.isArray(res.links)) {\n  // treat as empty result or retry rather than crashing\n}","typeGuard":"function hasLinks(r: unknown): r is { links: string[] } {\n  return typeof r === 'object' && r !== null && 'links' in r && Array.isArray((r as any).links);\n}","tryCatchPattern":"try {\n  const res = await client.mapUrl(url, options);\n  const links = Array.isArray(res.links) ? res.links : []; // fallback to empty\n} catch (e) {\n  // degrade gracefully: return empty link list with a warning\n}","preventionTips":["Pin and regularly upgrade firecrawl-js so response schemas stay in sync with the API.","Treat missing links as an empty result when the domain is tiny or unusual.","Add a schema assertion on the parsed response before consuming it."],"tags":["api-response","schema-mismatch","empty-result"],"backgroundTag":"unexpected-api-response-shape","analyzedSha":"75dd419e613fe9c39f846ffc500716141b74fda6","analyzedAt":"2026-08-30T00:15:31.844Z","schemaVersion":2},"datasetVersion":"2026-08-30T08:17:16.595Z"}