firecrawl-mcp 3.25.5 → 3.26.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +78 -1
- package/dist/agent-hints.js +46 -0
- package/dist/index.js +447 -69
- package/dist/introspection-cache.js +67 -0
- package/package.json +15 -14
package/README.md
CHANGED
|
@@ -83,6 +83,9 @@ https://mcp.firecrawl.dev/v2/mcp-search
|
|
|
83
83
|
|
|
84
84
|
It exposes a fixed set of eight tools: `firecrawl_search`, `firecrawl_developer_search`, the four `firecrawl_research_*` tools, and the two Alexandria tools `firecrawl_find_tools` and `firecrawl_scrape`. Its `firecrawl_search` fetches no page content, and the surface has its own OAuth identity; the full endpoint above is unchanged. It backs a published connector listing, so its tool set is a contract rather than a profile to tune. See [docs/search-profile.md](docs/search-profile.md) for the full contract and what a change to it involves.
|
|
85
85
|
|
|
86
|
+
For packaged MCP workflows in ChatGPT, Codex, or Claude Code, see
|
|
87
|
+
[MCP plugin packages](plugins/README.md).
|
|
88
|
+
|
|
86
89
|
### Running with npx
|
|
87
90
|
|
|
88
91
|
```bash
|
|
@@ -735,6 +738,28 @@ The agent performs web searches, follows links, reads pages, and gathers data au
|
|
|
735
738
|
- `prompt`: Natural language description of the data you want (required, max 10,000 characters)
|
|
736
739
|
- `urls`: Optional array of URLs to focus the agent on specific pages
|
|
737
740
|
- `schema`: Optional JSON schema for structured output
|
|
741
|
+
- `effort`: Optional. `"low"`, `"medium"` or `"high"` reasoning budget for the agent task.
|
|
742
|
+
- `maxCredits`: Optional positive integer. Spending limit in credits for this run. The API defaults to 2,500 when omitted, and caps a free request at 2,500.
|
|
743
|
+
- `strictConstrainToURLs`: Optional boolean. If `true`, the agent only visits the URLs in `urls`.
|
|
744
|
+
- `threadId`: Optional. Continue an existing thread: the `threadId` from an earlier `firecrawl_agent` or `firecrawl_agent_status` result. Omit to start a new thread. On a follow-up, omitted `mode`, `urls`, `schema` and `exchange` settings carry over from the previous turn.
|
|
745
|
+
- `mode`: Optional. `"extract"` (default) returns the complete structured result every turn. `"chat"` lets a follow-up that asks for no new data get a short reply in `message` instead of a re-run; `exchange.requireApproval` needs it.
|
|
746
|
+
- `exchange`: Optional. Alexandria provider settings for this turn, forwarded as-is to `POST /v2/agent`:
|
|
747
|
+
- `enabled`, `toolkits` (up to 5 provider slugs), `maxCalls` (1 to 30), `requireApproval` (paid calls end the turn with a `pendingApproval`; needs `mode: "chat"` on the same call, even on a follow-up)
|
|
748
|
+
- `onTermsRequired`: what to do when an Alexandria provider the agent would use needs data terms your team has not accepted. Gated providers are never called in any mode. Omitted on a follow-up keeps the previous turn's value.
|
|
749
|
+
- `"skip"` (default): answer with accepted providers only. `exchange.skippedProviders` on the status result lists the gated providers that would have helped.
|
|
750
|
+
- `"ask"`: the same, plus a terms `pendingApproval` and `exchange.requiresAction` with the exact `terms/show` and `terms/accept` calls for each provider. Each provider's `digest` is always present and is `string | null`; when it is `null`, `terms/show` returns the current digest to send.
|
|
751
|
+
- `approve`: `{ approvalId, callIds?, always? }` answers yes to the `pendingApproval` the previous turn ended on. `callIds` and `always` apply to paid-call approvals only.
|
|
752
|
+
- `decline`: `{ approvalId }` answers no. A declined terms offer keeps those providers out of the rest of the thread.
|
|
753
|
+
- `approve` and `decline` need `threadId`, and only one of them can be sent.
|
|
754
|
+
|
|
755
|
+
**Provider terms (ask mode):** there is no auto-accept mode. When a turn ends on a terms offer, the status result carries `pendingApproval` (`kind: "terms"`) and `exchange.requiresAction` with the `approvalId` and the exact `terms/show` and `terms/accept` calls. To use the provider:
|
|
756
|
+
|
|
757
|
+
1. Show the user the terms (`terms/show` through `firecrawl_scrape` with `alexandria`).
|
|
758
|
+
2. Get the user's explicit consent to that provider's terms. A data request is not consent.
|
|
759
|
+
3. Run the `terms/accept` call through `firecrawl_scrape`.
|
|
760
|
+
4. Continue the same thread: call `firecrawl_agent` with the same `threadId` and `exchange.approve: { "approvalId": "..." }`.
|
|
761
|
+
|
|
762
|
+
If the user says no, call `firecrawl_agent` with the same `threadId` and `exchange.decline: { "approvalId": "..." }` instead.
|
|
738
763
|
|
|
739
764
|
**Prompt Example:**
|
|
740
765
|
|
|
@@ -781,9 +806,34 @@ Then poll with `firecrawl_agent_status` using the returned job ID.
|
|
|
781
806
|
}
|
|
782
807
|
```
|
|
783
808
|
|
|
809
|
+
**Usage Example (follow-up on the same thread):**
|
|
810
|
+
|
|
811
|
+
```json
|
|
812
|
+
{
|
|
813
|
+
"name": "firecrawl_agent",
|
|
814
|
+
"arguments": {
|
|
815
|
+
"prompt": "Only keep the startups based in Europe",
|
|
816
|
+
"threadId": "0199a1b2-0000-7000-8000-000000000031"
|
|
817
|
+
}
|
|
818
|
+
}
|
|
819
|
+
```
|
|
820
|
+
|
|
821
|
+
**Usage Example (continue the thread after the user accepted a provider's terms):**
|
|
822
|
+
|
|
823
|
+
```json
|
|
824
|
+
{
|
|
825
|
+
"name": "firecrawl_agent",
|
|
826
|
+
"arguments": {
|
|
827
|
+
"prompt": "I accepted the Apollo terms. Continue.",
|
|
828
|
+
"threadId": "0199a1b2-0000-7000-8000-000000000031",
|
|
829
|
+
"exchange": { "approve": { "approvalId": "0199a1b2-0000-7000-8000-000000000033" } }
|
|
830
|
+
}
|
|
831
|
+
}
|
|
832
|
+
```
|
|
833
|
+
|
|
784
834
|
**Returns:**
|
|
785
835
|
|
|
786
|
-
- Job ID for status checking
|
|
836
|
+
- Job ID for status checking, plus `threadId` and `threadTurn`. Use `firecrawl_agent_status` to poll for results.
|
|
787
837
|
|
|
788
838
|
### 9. Check Agent Status (`firecrawl_agent_status`)
|
|
789
839
|
|
|
@@ -1099,6 +1149,33 @@ Example log messages:
|
|
|
1099
1149
|
[ERROR] Rate limit exceeded
|
|
1100
1150
|
```
|
|
1101
1151
|
|
|
1152
|
+
## API response hints
|
|
1153
|
+
|
|
1154
|
+
The MCP server explicitly enables Firecrawl API response hints on its outbound
|
|
1155
|
+
requests with `X-Firecrawl-Agent-Hints: true`; the API leaves them disabled for
|
|
1156
|
+
ordinary callers. When Firecrawl returns an optional `agent_hints` array of
|
|
1157
|
+
strings, JSON tool results preserve it in their existing text and
|
|
1158
|
+
`structuredContent` alongside the tool's other structured fields. Readable
|
|
1159
|
+
Developer and Research outputs keep their existing text and show hints in a
|
|
1160
|
+
separate, labeled text block. Empty results can include hints. Error hints
|
|
1161
|
+
remain visible with `isError: true`.
|
|
1162
|
+
Responses without hints keep their existing output format. Guidance is API
|
|
1163
|
+
metadata, separate from the scraped page's content; it is not generated or
|
|
1164
|
+
executed by the MCP adapter.
|
|
1165
|
+
|
|
1166
|
+
The strings are passed through unchanged. An HTTP operation mentioned in a
|
|
1167
|
+
hint is not necessarily an MCP tool: Alexandria discovery is available through
|
|
1168
|
+
`firecrawl_find_tools`, and provider execution uses `firecrawl_scrape` with an
|
|
1169
|
+
`alexandria` body. The search-only profile exposes those paths and URL-mode
|
|
1170
|
+
Scrape, but does not expose feedback tools. Clients should use their advertised
|
|
1171
|
+
tool schemas and available capabilities. This change does not add tools,
|
|
1172
|
+
translate prose into tool calls, or submit feedback automatically.
|
|
1173
|
+
|
|
1174
|
+
The pinned `firecrawl` 4.40.0 discards outer-envelope hints in high-level
|
|
1175
|
+
Scrape and Map responses and normalized SDK errors. The adapter captures hints
|
|
1176
|
+
from the SDK HTTP response while retaining the SDK's request and retry behavior.
|
|
1177
|
+
Authentication recovery retains its existing guidance.
|
|
1178
|
+
|
|
1102
1179
|
## Error Handling
|
|
1103
1180
|
|
|
1104
1181
|
The server provides robust error handling:
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
// src/agent-hints.ts
|
|
2
|
+
var AGENT_HINTS_HEADERS = { "X-Firecrawl-Agent-Hints": "true" };
|
|
3
|
+
function readAgentHints(value) {
|
|
4
|
+
if (!value || typeof value !== "object") return void 0;
|
|
5
|
+
const hints = value.agent_hints;
|
|
6
|
+
return Array.isArray(hints) && hints.every((hint) => typeof hint === "string") ? hints : void 0;
|
|
7
|
+
}
|
|
8
|
+
function preserveAgentHints(data, envelope) {
|
|
9
|
+
const hints = readAgentHints(envelope);
|
|
10
|
+
if (!hints) return data;
|
|
11
|
+
return data && typeof data === "object" && !Array.isArray(data) ? { ...data, agent_hints: hints } : { data, agent_hints: hints };
|
|
12
|
+
}
|
|
13
|
+
function agentHintsText(hints) {
|
|
14
|
+
return `Firecrawl API agent_hints (response guidance, separate from page content):
|
|
15
|
+
${JSON.stringify(hints, null, 2)}`;
|
|
16
|
+
}
|
|
17
|
+
function withAgentHints(result, response, separateText = false) {
|
|
18
|
+
const hints = readAgentHints(response);
|
|
19
|
+
if (!hints) return result;
|
|
20
|
+
return {
|
|
21
|
+
...result,
|
|
22
|
+
content: separateText && hints.length ? [...result.content, { type: "text", text: agentHintsText(hints) }] : result.content,
|
|
23
|
+
structuredContent: { ...result.structuredContent, agent_hints: hints }
|
|
24
|
+
};
|
|
25
|
+
}
|
|
26
|
+
function readErrorAgentHints(error) {
|
|
27
|
+
const hints = readAgentHints(error);
|
|
28
|
+
if (hints) return hints;
|
|
29
|
+
if (!error || typeof error !== "object") return void 0;
|
|
30
|
+
const extras = error.extras;
|
|
31
|
+
const extrasHints = readAgentHints(extras);
|
|
32
|
+
if (extrasHints) return extrasHints;
|
|
33
|
+
const details = error.details;
|
|
34
|
+
const detailsHints = readAgentHints(details);
|
|
35
|
+
if (detailsHints) return detailsHints;
|
|
36
|
+
const response = error.response;
|
|
37
|
+
return readAgentHints(response?.data);
|
|
38
|
+
}
|
|
39
|
+
export {
|
|
40
|
+
AGENT_HINTS_HEADERS,
|
|
41
|
+
agentHintsText,
|
|
42
|
+
preserveAgentHints,
|
|
43
|
+
readAgentHints,
|
|
44
|
+
readErrorAgentHints,
|
|
45
|
+
withAgentHints
|
|
46
|
+
};
|