firecrawl-mcp 3.23.7 → 3.23.9
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/dist/index.js +29 -5
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -18,8 +18,10 @@ var MAX_PASSAGE_CHARS = 1200;
|
|
|
18
18
|
function fmtDeveloper(results) {
|
|
19
19
|
if (!results || results.length === 0) return "(no results)";
|
|
20
20
|
return results.map((r) => {
|
|
21
|
-
const
|
|
22
|
-
const
|
|
21
|
+
const id = r.id ?? "?";
|
|
22
|
+
const kind = r.id?.split(":", 1)[0];
|
|
23
|
+
const kindLabel = kind ? ` (${kind})` : "";
|
|
24
|
+
const lines = [`## [${id}]${kindLabel} ${r.title ?? "(untitled)"}`];
|
|
23
25
|
if (r.url) lines.push(r.url);
|
|
24
26
|
const body = (r.passages ?? []).map((p) => p.text ?? "").join("\n---\n").trim();
|
|
25
27
|
lines.push(body ? body.slice(0, MAX_PASSAGE_CHARS) : "(no content)");
|
|
@@ -586,7 +588,7 @@ function fmtGithub(results) {
|
|
|
586
588
|
if (!results || results.length === 0) return "(no results)";
|
|
587
589
|
return results.map((r) => {
|
|
588
590
|
const lines = [];
|
|
589
|
-
if (r.
|
|
591
|
+
if (r.number == null && r.pageType == null) {
|
|
590
592
|
lines.push(`[${r.repo ?? "?"}] README`);
|
|
591
593
|
} else {
|
|
592
594
|
const ref = r.number != null ? `#${r.number}` : "";
|
|
@@ -1088,6 +1090,14 @@ async function authenticateRequest(request, profile) {
|
|
|
1088
1090
|
if (process.env.CLOUD_SERVICE === "true") {
|
|
1089
1091
|
if (!headerCred && !managedCred) {
|
|
1090
1092
|
if (resolved?.invalid) {
|
|
1093
|
+
if (profile.allowKeyless) {
|
|
1094
|
+
return {
|
|
1095
|
+
authType: "api-key",
|
|
1096
|
+
credentialError: "CREDENTIAL_INVALID",
|
|
1097
|
+
firecrawlApiKey: void 0,
|
|
1098
|
+
keylessClientIp: extractClientIp(request)
|
|
1099
|
+
};
|
|
1100
|
+
}
|
|
1091
1101
|
throw new InvalidFirecrawlCredentialError();
|
|
1092
1102
|
}
|
|
1093
1103
|
if (profile.allowKeyless) {
|
|
@@ -1477,7 +1487,12 @@ function recoveryPayload(code, requestId = randomUUID(), options = {}) {
|
|
|
1477
1487
|
request_id: requestId,
|
|
1478
1488
|
auth_mode: code === "CREDENTIAL_INVALID" ? "credential_error" : "keyless",
|
|
1479
1489
|
message: code === "CREDENTIAL_INVALID" ? `The supplied Firecrawl credential is invalid or revoked. ${HUMAN_CONNECTION_GUIDANCE}` : isQuotaExhausted ? `The free daily limit for this network has been reached${retryAfterSeconds ? `; try again in about ${retryAfterSeconds} seconds` : ""}. To continue now: ${HUMAN_CONNECTION_GUIDANCE}` : isToolUnavailable ? ACCOUNT_ONLY_TOOL_GUIDANCE : isKeylessAccessUnavailable ? `Anonymous keyless access is unavailable for this request. To continue: ${HUMAN_CONNECTION_GUIDANCE}` : isKeylessEligibilityUnavailable ? "The anonymous keyless eligibility check is temporarily unavailable. Retry shortly." : `This tool requires a Firecrawl account or API key. ${HUMAN_CONNECTION_GUIDANCE}`,
|
|
1480
|
-
|
|
1490
|
+
// CREDENTIAL_INVALID sessions gate every tool call (including keyless
|
|
1491
|
+
// tools) on the credentialError check before the keyless branch ever
|
|
1492
|
+
// runs, so none of KEYLESS_TOOL_NAMES are actually callable here. Listing
|
|
1493
|
+
// them as available_tools would send the agent into a retry loop against
|
|
1494
|
+
// tools that will just return this same recovery payload.
|
|
1495
|
+
...isKeylessAccessUnavailable || code === "CREDENTIAL_INVALID" ? {} : { available_tools: [...KEYLESS_TOOL_NAMES] },
|
|
1481
1496
|
docs_url: MCP_CONNECTION_GUIDE_URL,
|
|
1482
1497
|
...retryAfterSeconds ? { retry_after_seconds: retryAfterSeconds } : {},
|
|
1483
1498
|
next_actions: isKeylessEligibilityUnavailable ? [{ kind: "retry_later", after_seconds: 30 }] : isQuotaExhausted || isKeylessAccessUnavailable ? HUMAN_CONNECTION_ACTIONS : isToolUnavailable ? [
|
|
@@ -1549,7 +1564,16 @@ function guardHostedTool(tool, { logActions }) {
|
|
|
1549
1564
|
const beforeValidate = tool.beforeValidate;
|
|
1550
1565
|
return {
|
|
1551
1566
|
...tool,
|
|
1552
|
-
canList: (session) =>
|
|
1567
|
+
canList: (session) => (
|
|
1568
|
+
// A credentialError session lists the keyless tool surface (same as a
|
|
1569
|
+
// real keyless session, not the full authenticated schema) so the
|
|
1570
|
+
// client proceeds past tools/list and calling any listed tool returns
|
|
1571
|
+
// the CREDENTIAL_INVALID recovery payload (below). An empty list would
|
|
1572
|
+
// leave MCP clients that stop after tools/list unable to ever surface
|
|
1573
|
+
// the recovery guidance; the full non-keyless schema would over-disclose
|
|
1574
|
+
// to a request carrying an unrecognized or invalid credential.
|
|
1575
|
+
(session?.credentialError || isHostedKeylessSession(session) ? keylessTool : true) && (canList?.(session) ?? true)
|
|
1576
|
+
),
|
|
1553
1577
|
beforeValidate: async (args2, session) => {
|
|
1554
1578
|
const code = session?.credentialError ? "CREDENTIAL_INVALID" : isHostedKeylessSession(session) && !keylessTool ? "KEYLESS_TOOL_NOT_AVAILABLE" : void 0;
|
|
1555
1579
|
if (code) {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "firecrawl-mcp",
|
|
3
|
-
"version": "3.23.
|
|
3
|
+
"version": "3.23.9",
|
|
4
4
|
"description": "MCP server for Firecrawl — search, scrape, and interact with the web. Supports both cloud and self-hosted instances. Features include web search, scraping, page interaction, batch processing, and LLM-powered content analysis.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"mcpName": "io.github.firecrawl/firecrawl-mcp-server",
|