@mendable/firecrawl-js 4.38.0 → 4.40.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 +53 -2
- package/dist/{chunk-KSTNOGOD.js → chunk-OJ4YJQ4J.js} +1 -1
- package/dist/index.cjs +204 -17
- package/dist/index.d.cts +289 -7
- package/dist/index.d.ts +289 -7
- package/dist/index.js +203 -17
- package/dist/{package-OS7RONXY.js → package-F6O7J2XI.js} +1 -1
- package/package.json +1 -1
- package/pnpm-workspace.yaml +3 -2
- package/src/__tests__/e2e/v2/batch.test.ts +13 -11
- package/src/__tests__/e2e/v2/crawl.test.ts +24 -20
- package/src/__tests__/e2e/v2/extract.test.ts +32 -7
- package/src/__tests__/e2e/v2/map.test.ts +4 -3
- package/src/__tests__/e2e/v2/parse.test.ts +4 -3
- package/src/__tests__/e2e/v2/scrape.test.ts +10 -9
- package/src/__tests__/e2e/v2/search.test.ts +9 -8
- package/src/__tests__/e2e/v2/usage.test.ts +6 -5
- package/src/__tests__/e2e/v2/utils/rateLimit.ts +257 -0
- package/src/__tests__/e2e/v2/watcher.test.ts +4 -3
- package/src/__tests__/unit/v2/agent-effort-trace.unit.test.ts +1 -1
- package/src/__tests__/unit/v2/agent-thread.unit.test.ts +164 -0
- package/src/__tests__/unit/v2/e2eRateLimitRetry.test.ts +501 -0
- package/src/__tests__/unit/v2/extract.unit.test.ts +1 -1
- package/src/__tests__/unit/v2/scrapeAutoResume.test.ts +1 -1
- package/src/__tests__/unit/v2/search-country.unit.test.ts +32 -0
- package/src/__tests__/unit/v2/search-data-property.test.ts +1 -0
- package/src/__tests__/unit/v2/threat-protection.unit.test.ts +18 -1
- package/src/__tests__/unit/v2/tools.unit.test.ts +240 -0
- package/src/__tests__/unit/v2/v1-aliases.test.ts +1 -0
- package/src/v2/client.ts +52 -4
- package/src/v2/methods/agent.ts +23 -1
- package/src/v2/methods/research.ts +14 -8
- package/src/v2/methods/scrape.ts +3 -1
- package/src/v2/methods/search.ts +8 -1
- package/src/v2/methods/tools.ts +137 -0
- package/src/v2/types.ts +307 -35
- package/src/v2/utils/errorHandler.ts +19 -3
package/README.md
CHANGED
|
@@ -261,8 +261,13 @@ const related = await app.research.similarPapers('pmid:<id>', {
|
|
|
261
261
|
});
|
|
262
262
|
```
|
|
263
263
|
|
|
264
|
-
|
|
265
|
-
|
|
264
|
+
> **`app.research.searchGithub` is deprecated.** The research index GitHub
|
|
265
|
+
> endpoint stops responding after 2026-11-03. Use `app.developerSearch`
|
|
266
|
+
> instead: it searches GitHub issues, pull requests and readmes plus curated
|
|
267
|
+
> documentation sources, returns matched passages, and adds filters for repo,
|
|
268
|
+
> language, license and stars. It does not carry over the `scores` breakdown
|
|
269
|
+
> or the `resultType: "web"` fallback results. See
|
|
270
|
+
> [the developer index docs](https://docs.firecrawl.dev/features/developer).
|
|
266
271
|
|
|
267
272
|
### Scrape-bound interactive browsing (v2)
|
|
268
273
|
|
|
@@ -381,3 +386,49 @@ The Firecrawl Node SDK is licensed under the MIT License. This means you are fre
|
|
|
381
386
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
|
382
387
|
|
|
383
388
|
Please note that while this SDK is MIT licensed, it is part of a larger project which may be under different licensing terms. Always refer to the license information in the root directory of the main project for overall licensing details.
|
|
389
|
+
|
|
390
|
+
### Alexandria
|
|
391
|
+
|
|
392
|
+
With a matching API deployment, Search returns complete tool contracts in `tools`.
|
|
393
|
+
`domainTools: true` adds domain matches to that same array. Find Tools walks the catalogue
|
|
394
|
+
without executing the tools it returns.
|
|
395
|
+
|
|
396
|
+
```ts
|
|
397
|
+
const results = await firecrawl.search("podcast conversations about AI agents", {
|
|
398
|
+
sources: ["web", "alexandria"],
|
|
399
|
+
domainTools: true,
|
|
400
|
+
limit: 2,
|
|
401
|
+
});
|
|
402
|
+
console.log(results.tools?.[0].options);
|
|
403
|
+
|
|
404
|
+
const catalogue = await firecrawl.findTools({ providers: ["particle"], limit: 2 });
|
|
405
|
+
const next = catalogue.items[0]?.next;
|
|
406
|
+
if (next) console.log(await firecrawl.scrape({ alexandria: next }));
|
|
407
|
+
```
|
|
408
|
+
|
|
409
|
+
Execute a selected contract with `scrape({ alexandria, requestId })`, where `alexandria`
|
|
410
|
+
is one `{ provider, capability, options }` call or an array of up to ten calls:
|
|
411
|
+
|
|
412
|
+
```ts
|
|
413
|
+
const requestId = crypto.randomUUID();
|
|
414
|
+
const result = await firecrawl.scrape({
|
|
415
|
+
alexandria: {
|
|
416
|
+
provider: "particle",
|
|
417
|
+
capability: "podcasts/episodes/search",
|
|
418
|
+
options: { semantic_search: "AI agents" },
|
|
419
|
+
},
|
|
420
|
+
requestId,
|
|
421
|
+
});
|
|
422
|
+
for (const item of result.alexandria) {
|
|
423
|
+
if (item.error) console.error(item.error.code, item.error.message);
|
|
424
|
+
else console.log(item.data);
|
|
425
|
+
}
|
|
426
|
+
```
|
|
427
|
+
|
|
428
|
+
Check each returned `alexandria` item's `error` before using its `data`. The result and
|
|
429
|
+
execution errors expose `requestId`; reuse it with the identical payload for a retry.
|
|
430
|
+
Automatic retries retain the same ID. Find Tools costs zero credits; provider execution
|
|
431
|
+
uses its published price. A provider whose data terms have not been accepted rejects the
|
|
432
|
+
call with a 403 whose `SdkError` carries `code: "THIRD_PARTY_DATA_TERMS_REQUIRED"` and a
|
|
433
|
+
`requiresAction: { type: "accept_terms", terms, version, url }` pointing at the page where
|
|
434
|
+
an organization admin can accept them.
|
|
@@ -12,7 +12,7 @@ var require_package = __commonJS({
|
|
|
12
12
|
"package.json"(exports, module) {
|
|
13
13
|
module.exports = {
|
|
14
14
|
name: "@mendable/firecrawl-js",
|
|
15
|
-
version: "4.
|
|
15
|
+
version: "4.40.0",
|
|
16
16
|
description: "JavaScript SDK for the Firecrawl API: web scraping, crawling, web search, and scientific literature search over a research paper index of PubMed, bioRxiv, medRxiv and arXiv abstracts",
|
|
17
17
|
main: "dist/index.js",
|
|
18
18
|
types: "dist/index.d.ts",
|
package/dist/index.cjs
CHANGED
|
@@ -39,7 +39,7 @@ var require_package = __commonJS({
|
|
|
39
39
|
"package.json"(exports2, module2) {
|
|
40
40
|
module2.exports = {
|
|
41
41
|
name: "@mendable/firecrawl-js",
|
|
42
|
-
version: "4.
|
|
42
|
+
version: "4.40.0",
|
|
43
43
|
description: "JavaScript SDK for the Firecrawl API: web scraping, crawling, web search, and scientific literature search over a research paper index of PubMed, bioRxiv, medRxiv and arXiv abstracts",
|
|
44
44
|
main: "dist/index.js",
|
|
45
45
|
types: "dist/index.d.ts",
|
|
@@ -129,7 +129,8 @@ __export(index_exports, {
|
|
|
129
129
|
ResearchClient: () => ResearchClient,
|
|
130
130
|
SdkError: () => SdkError,
|
|
131
131
|
Watcher: () => Watcher,
|
|
132
|
-
default: () => index_default
|
|
132
|
+
default: () => index_default,
|
|
133
|
+
parseRequiresAction: () => parseRequiresAction
|
|
133
134
|
});
|
|
134
135
|
module.exports = __toCommonJS(index_exports);
|
|
135
136
|
|
|
@@ -269,18 +270,35 @@ var HttpClient = class {
|
|
|
269
270
|
};
|
|
270
271
|
|
|
271
272
|
// src/v2/types.ts
|
|
273
|
+
function parseRequiresAction(value) {
|
|
274
|
+
if (!value || typeof value !== "object") return void 0;
|
|
275
|
+
const record = value;
|
|
276
|
+
if (typeof record.type !== "string") return void 0;
|
|
277
|
+
const action = { type: record.type };
|
|
278
|
+
if (typeof record.terms === "string") action.terms = record.terms;
|
|
279
|
+
if (typeof record.version === "string") action.version = record.version;
|
|
280
|
+
if (typeof record.url === "string") action.url = record.url;
|
|
281
|
+
return action;
|
|
282
|
+
}
|
|
272
283
|
var SdkError = class extends Error {
|
|
284
|
+
requestId;
|
|
273
285
|
status;
|
|
274
286
|
code;
|
|
275
287
|
details;
|
|
276
288
|
jobId;
|
|
277
|
-
|
|
289
|
+
/** Present on exchange-mediated scrape failures that already captured credits. */
|
|
290
|
+
chargeId;
|
|
291
|
+
/** Present when the API needs an out-of-band step first, such as accepting provider terms. */
|
|
292
|
+
requiresAction;
|
|
293
|
+
constructor(message, status, code, details, jobId, chargeId, requiresAction) {
|
|
278
294
|
super(message);
|
|
279
295
|
this.name = "FirecrawlSdkError";
|
|
280
296
|
this.status = status;
|
|
281
297
|
this.code = code;
|
|
282
298
|
this.details = details;
|
|
283
299
|
this.jobId = jobId;
|
|
300
|
+
this.chargeId = chargeId;
|
|
301
|
+
this.requiresAction = requiresAction;
|
|
284
302
|
}
|
|
285
303
|
};
|
|
286
304
|
var JobTimeoutError = class extends SdkError {
|
|
@@ -532,14 +550,30 @@ function throwForBadResponse(resp, action) {
|
|
|
532
550
|
const status = resp.status;
|
|
533
551
|
const body = resp.data || {};
|
|
534
552
|
const msg = body?.error || body?.message || `Request failed (${status}) while trying to ${action}`;
|
|
535
|
-
throw new SdkError(
|
|
553
|
+
throw new SdkError(
|
|
554
|
+
msg,
|
|
555
|
+
status,
|
|
556
|
+
body?.code,
|
|
557
|
+
body?.details,
|
|
558
|
+
void 0,
|
|
559
|
+
body?.chargeId,
|
|
560
|
+
parseRequiresAction(body?.requiresAction)
|
|
561
|
+
);
|
|
536
562
|
}
|
|
537
563
|
function normalizeAxiosError(err, action) {
|
|
538
564
|
const status = err.response?.status;
|
|
539
565
|
const body = err.response?.data;
|
|
540
566
|
const message = body?.error || err.message || `Request failed${status ? ` (${status})` : ""} while trying to ${action}`;
|
|
541
567
|
const code = body?.code || err.code;
|
|
542
|
-
throw new SdkError(
|
|
568
|
+
throw new SdkError(
|
|
569
|
+
message,
|
|
570
|
+
status,
|
|
571
|
+
code,
|
|
572
|
+
body?.details ?? body,
|
|
573
|
+
void 0,
|
|
574
|
+
body?.chargeId,
|
|
575
|
+
parseRequiresAction(body?.requiresAction)
|
|
576
|
+
);
|
|
543
577
|
}
|
|
544
578
|
function isRetryableError(err) {
|
|
545
579
|
if (err instanceof JobTimeoutError) {
|
|
@@ -585,9 +619,10 @@ async function scrape(http, url, options, deps = {}) {
|
|
|
585
619
|
throw new Error("URL cannot be empty");
|
|
586
620
|
}
|
|
587
621
|
if (options) ensureValidScrapeOptions(options);
|
|
588
|
-
const { autoResume, ...requestOptions } = options ?? {};
|
|
622
|
+
const { autoResume, domainTools, ...requestOptions } = options ?? {};
|
|
589
623
|
const payload = { url: url.trim() };
|
|
590
624
|
Object.assign(payload, requestOptions);
|
|
625
|
+
if (domainTools) payload.domainTools = domainTools;
|
|
591
626
|
const requestTimeout = autoResume === false ? typeof options?.timeout === "number" ? { timeoutMs: options.timeout + 5e3 } : {} : {
|
|
592
627
|
timeoutMs: Math.max(
|
|
593
628
|
typeof options?.timeout === "number" ? options.timeout : 3e5,
|
|
@@ -744,6 +779,7 @@ function prepareSearchPayload(req) {
|
|
|
744
779
|
const payload = {
|
|
745
780
|
query: req.query
|
|
746
781
|
};
|
|
782
|
+
if (req.domainTools != null) payload.domainTools = req.domainTools;
|
|
747
783
|
if (req.sources) payload.sources = req.sources;
|
|
748
784
|
if (req.categories) payload.categories = req.categories;
|
|
749
785
|
if (req.includeDomains) payload.includeDomains = req.includeDomains;
|
|
@@ -751,6 +787,7 @@ function prepareSearchPayload(req) {
|
|
|
751
787
|
if (req.limit != null) payload.limit = req.limit;
|
|
752
788
|
if (req.tbs != null) payload.tbs = req.tbs;
|
|
753
789
|
if (req.location != null) payload.location = req.location;
|
|
790
|
+
if (req.country != null) payload.country = req.country;
|
|
754
791
|
if (req.ignoreInvalidURLs != null)
|
|
755
792
|
payload.ignoreInvalidURLs = req.ignoreInvalidURLs;
|
|
756
793
|
if (req.timeout != null) payload.timeout = req.timeout;
|
|
@@ -795,10 +832,12 @@ async function search(http, request) {
|
|
|
795
832
|
}
|
|
796
833
|
const data = res.data.data || {};
|
|
797
834
|
const out = {};
|
|
835
|
+
if (res.data.warning) out.warning = res.data.warning;
|
|
798
836
|
if (data.web) out.web = transformArray(data.web);
|
|
799
837
|
if (data.news) out.news = transformArray(data.news);
|
|
800
838
|
if (data.images)
|
|
801
839
|
out.images = transformArray(data.images);
|
|
840
|
+
if (data.tools) out.tools = data.tools;
|
|
802
841
|
Object.defineProperty(out, "data", {
|
|
803
842
|
get() {
|
|
804
843
|
const parts = [];
|
|
@@ -806,7 +845,9 @@ async function search(http, request) {
|
|
|
806
845
|
if (out.news?.length) parts.push(`.news (${out.news.length} results)`);
|
|
807
846
|
if (out.images?.length)
|
|
808
847
|
parts.push(`.images (${out.images.length} results)`);
|
|
809
|
-
|
|
848
|
+
if (out.tools?.length)
|
|
849
|
+
parts.push(`.tools (${out.tools.length} results)`);
|
|
850
|
+
const available = parts.length ? parts.join(", ") : ".web, .news, .images, or .tools";
|
|
810
851
|
throw new Error(
|
|
811
852
|
`SearchData has no '.data'. Results are grouped by source: ${available}`
|
|
812
853
|
);
|
|
@@ -821,6 +862,101 @@ async function search(http, request) {
|
|
|
821
862
|
}
|
|
822
863
|
}
|
|
823
864
|
|
|
865
|
+
// src/v2/methods/tools.ts
|
|
866
|
+
var ALEXANDRIA_MAX_CALLS = 10;
|
|
867
|
+
function prepareAlexandriaPayload(calls, opts) {
|
|
868
|
+
if (!Array.isArray(calls) || calls.length === 0) {
|
|
869
|
+
throw new Error("alexandria requires at least one call");
|
|
870
|
+
}
|
|
871
|
+
if (calls.length > ALEXANDRIA_MAX_CALLS) {
|
|
872
|
+
throw new Error(`alexandria accepts at most ${ALEXANDRIA_MAX_CALLS} calls`);
|
|
873
|
+
}
|
|
874
|
+
const alexandria = calls.map((call, index) => {
|
|
875
|
+
if (!call || typeof call.provider !== "string" || !call.provider.trim()) {
|
|
876
|
+
throw new Error(`alexandria[${index}].provider cannot be empty`);
|
|
877
|
+
}
|
|
878
|
+
if (typeof call.capability !== "string" || !call.capability.trim()) {
|
|
879
|
+
throw new Error(`alexandria[${index}].capability cannot be empty`);
|
|
880
|
+
}
|
|
881
|
+
if (Object.keys(call).some(
|
|
882
|
+
(key) => !["provider", "capability", "options"].includes(key)
|
|
883
|
+
))
|
|
884
|
+
throw new Error("Unknown alexandria call option");
|
|
885
|
+
const item = {
|
|
886
|
+
provider: call.provider.trim(),
|
|
887
|
+
capability: call.capability.trim()
|
|
888
|
+
};
|
|
889
|
+
if (call.options != null) {
|
|
890
|
+
if (typeof call.options !== "object" || Array.isArray(call.options)) {
|
|
891
|
+
throw new Error(`alexandria[${index}].options must be an object`);
|
|
892
|
+
}
|
|
893
|
+
item.options = call.options;
|
|
894
|
+
}
|
|
895
|
+
return item;
|
|
896
|
+
});
|
|
897
|
+
if (opts.timeout != null && (!Number.isInteger(opts.timeout) || opts.timeout <= 0)) {
|
|
898
|
+
throw new Error("timeout must be a positive integer");
|
|
899
|
+
}
|
|
900
|
+
const payload = { alexandria };
|
|
901
|
+
if (opts.timeout != null) payload.timeout = opts.timeout;
|
|
902
|
+
if (opts.integration && opts.integration.trim())
|
|
903
|
+
payload.integration = opts.integration.trim();
|
|
904
|
+
if (opts.origin) payload.origin = opts.origin;
|
|
905
|
+
return payload;
|
|
906
|
+
}
|
|
907
|
+
async function scrapeAlexandria(http, calls, opts = {}) {
|
|
908
|
+
const payload = prepareAlexandriaPayload(calls, opts);
|
|
909
|
+
const requestId = opts.requestId ?? crypto.randomUUID();
|
|
910
|
+
if (!/^[A-Za-z0-9._:-]{1,128}$/.test(requestId))
|
|
911
|
+
throw new Error("Invalid requestId");
|
|
912
|
+
try {
|
|
913
|
+
const res = await http.post("/v2/scrape", payload, {
|
|
914
|
+
headers: { "x-request-id": requestId },
|
|
915
|
+
// Allow response delivery after the API's capped execution deadline.
|
|
916
|
+
timeoutMs: Math.min(opts.timeout ?? 5e4, 5e4) + 3e4
|
|
917
|
+
});
|
|
918
|
+
if (res.status !== 200 || !res.data?.success) {
|
|
919
|
+
throwForBadResponse(res, "alexandria");
|
|
920
|
+
}
|
|
921
|
+
const data = res.data.data;
|
|
922
|
+
if (!data || !Array.isArray(data.alexandria) || typeof data.creditsCost !== "number" || !Number.isInteger(data.creditsCost) || data.creditsCost < 0) {
|
|
923
|
+
throw new SdkError("Invalid alexandria response");
|
|
924
|
+
}
|
|
925
|
+
return {
|
|
926
|
+
scrapeId: res.data.scrape_id ?? "",
|
|
927
|
+
requestId,
|
|
928
|
+
alexandria: data.alexandria,
|
|
929
|
+
creditsCost: data.creditsCost
|
|
930
|
+
};
|
|
931
|
+
} catch (err) {
|
|
932
|
+
try {
|
|
933
|
+
if (err?.isAxiosError) normalizeAxiosError(err, "alexandria");
|
|
934
|
+
throw err;
|
|
935
|
+
} catch (error) {
|
|
936
|
+
if (error && typeof error === "object")
|
|
937
|
+
Object.assign(error, { requestId });
|
|
938
|
+
throw error;
|
|
939
|
+
}
|
|
940
|
+
}
|
|
941
|
+
}
|
|
942
|
+
async function findTools(http, options = {}) {
|
|
943
|
+
const result = await scrapeAlexandria(http, [
|
|
944
|
+
{
|
|
945
|
+
provider: "firecrawl",
|
|
946
|
+
capability: "find-tools",
|
|
947
|
+
options: { ...options }
|
|
948
|
+
}
|
|
949
|
+
]);
|
|
950
|
+
const item = result.alexandria[0];
|
|
951
|
+
if (!item) throw new SdkError("Missing Find Tools result");
|
|
952
|
+
if (item.error)
|
|
953
|
+
throw Object.assign(
|
|
954
|
+
new SdkError(item.error.message, item.error.status, item.error.code),
|
|
955
|
+
{ requestId: result.requestId }
|
|
956
|
+
);
|
|
957
|
+
return item.data;
|
|
958
|
+
}
|
|
959
|
+
|
|
824
960
|
// src/v2/methods/developer.ts
|
|
825
961
|
var ENDPOINT = "/v2/search/developer";
|
|
826
962
|
async function developerSearch(http, query, options = {}) {
|
|
@@ -1371,6 +1507,9 @@ function prepareAgentPayload(args) {
|
|
|
1371
1507
|
body.threatProtection = args.threatProtection;
|
|
1372
1508
|
if (args.auditMetadata != null)
|
|
1373
1509
|
body.auditMetadata = args.auditMetadata;
|
|
1510
|
+
if (args.threadId != null) body.threadId = args.threadId;
|
|
1511
|
+
if (args.mode != null) body.mode = args.mode;
|
|
1512
|
+
if (args.exchange != null) body.exchange = args.exchange;
|
|
1374
1513
|
return body;
|
|
1375
1514
|
}
|
|
1376
1515
|
async function startAgent(http, args) {
|
|
@@ -1441,6 +1580,17 @@ async function getAgentSnapshot(http, jobId, snapshotId) {
|
|
|
1441
1580
|
throw err;
|
|
1442
1581
|
}
|
|
1443
1582
|
}
|
|
1583
|
+
async function getAgentThread(http, threadId, options) {
|
|
1584
|
+
try {
|
|
1585
|
+
const query = options?.includeData ? "?includeData=true" : "";
|
|
1586
|
+
const res = await http.get(`/v2/agent/threads/${threadId}${query}`);
|
|
1587
|
+
if (res.status !== 200) throwForBadResponse(res, "agent thread");
|
|
1588
|
+
return res.data;
|
|
1589
|
+
} catch (err) {
|
|
1590
|
+
if (err?.isAxiosError) return normalizeAxiosError(err, "agent thread");
|
|
1591
|
+
throw err;
|
|
1592
|
+
}
|
|
1593
|
+
}
|
|
1444
1594
|
async function cancelAgent(http, jobId) {
|
|
1445
1595
|
try {
|
|
1446
1596
|
const res = await http.delete(`/v2/agent/${jobId}`);
|
|
@@ -1681,9 +1831,7 @@ var ResearchClient = class {
|
|
|
1681
1831
|
appendParam(params, "query", options.query);
|
|
1682
1832
|
appendParam(params, "k", options.k);
|
|
1683
1833
|
try {
|
|
1684
|
-
const res = await this.http.get(
|
|
1685
|
-
withQuery(`${BASE}/papers/${encodeURIComponent(id)}`, params)
|
|
1686
|
-
);
|
|
1834
|
+
const res = await this.http.get(withQuery(`${BASE}/papers/${encodeURIComponent(id)}`, params));
|
|
1687
1835
|
if (res.status !== 200) throwForBadResponse(res, "get paper");
|
|
1688
1836
|
return res.data;
|
|
1689
1837
|
} catch (err) {
|
|
@@ -1709,10 +1857,7 @@ var ResearchClient = class {
|
|
|
1709
1857
|
appendParam(params, "anchor", options.anchor);
|
|
1710
1858
|
try {
|
|
1711
1859
|
const res = await this.http.get(
|
|
1712
|
-
withQuery(
|
|
1713
|
-
`${BASE}/papers/${encodeURIComponent(id)}/similar`,
|
|
1714
|
-
params
|
|
1715
|
-
)
|
|
1860
|
+
withQuery(`${BASE}/papers/${encodeURIComponent(id)}/similar`, params)
|
|
1716
1861
|
);
|
|
1717
1862
|
if (res.status !== 200) throwForBadResponse(res, "find similar papers");
|
|
1718
1863
|
return res.data;
|
|
@@ -1721,7 +1866,16 @@ var ResearchClient = class {
|
|
|
1721
1866
|
}
|
|
1722
1867
|
}
|
|
1723
1868
|
/**
|
|
1724
|
-
* Search GitHub issue/PR history and repository
|
|
1869
|
+
* Search the research index GitHub slice: issue/PR history and repository
|
|
1870
|
+
* readmes.
|
|
1871
|
+
*
|
|
1872
|
+
* @deprecated Use `developerSearch()` on the client instead. This
|
|
1873
|
+
* endpoint stops responding after 2026-11-03. The developer index searches
|
|
1874
|
+
* GitHub issues, pull requests and readmes plus curated documentation
|
|
1875
|
+
* sources, returns matched passages, and adds filters for repo, language,
|
|
1876
|
+
* license and stars. It does not carry over the `scores` breakdown or the
|
|
1877
|
+
* `resultType: "web"` fallback results. See
|
|
1878
|
+
* https://docs.firecrawl.dev/features/developer.
|
|
1725
1879
|
* @param query Search query.
|
|
1726
1880
|
* @param options Optional `k`.
|
|
1727
1881
|
*/
|
|
@@ -2130,7 +2284,28 @@ var FirecrawlClient = class {
|
|
|
2130
2284
|
});
|
|
2131
2285
|
}
|
|
2132
2286
|
async scrape(url, options) {
|
|
2133
|
-
return scrape(this.http, url, options);
|
|
2287
|
+
if (typeof url === "string") return scrape(this.http, url, options);
|
|
2288
|
+
if (!url || options !== void 0 || Object.keys(url).some(
|
|
2289
|
+
(key) => ![
|
|
2290
|
+
"alexandria",
|
|
2291
|
+
"requestId",
|
|
2292
|
+
"timeout",
|
|
2293
|
+
"integration",
|
|
2294
|
+
"origin"
|
|
2295
|
+
].includes(key)
|
|
2296
|
+
)) {
|
|
2297
|
+
throw new Error("Provide an alexandria request without URL scrape options");
|
|
2298
|
+
}
|
|
2299
|
+
const { alexandria, ...opts } = url;
|
|
2300
|
+
return scrapeAlexandria(
|
|
2301
|
+
this.http,
|
|
2302
|
+
Array.isArray(alexandria) ? alexandria : [alexandria],
|
|
2303
|
+
opts
|
|
2304
|
+
);
|
|
2305
|
+
}
|
|
2306
|
+
/** Explore the catalogue without executing the tools it returns. */
|
|
2307
|
+
async findTools(options) {
|
|
2308
|
+
return findTools(this.http, options);
|
|
2134
2309
|
}
|
|
2135
2310
|
/**
|
|
2136
2311
|
* Interact with the browser session associated with a scrape job.
|
|
@@ -2210,6 +2385,9 @@ var FirecrawlClient = class {
|
|
|
2210
2385
|
* Access the v2 research endpoints — Firecrawl's **research paper index**
|
|
2211
2386
|
* (~43M paper abstracts) plus GitHub history/readmes.
|
|
2212
2387
|
*
|
|
2388
|
+
* `research.searchGithub()` is deprecated and stops responding after
|
|
2389
|
+
* 2026-11-03. Use `developerSearch()` instead.
|
|
2390
|
+
*
|
|
2213
2391
|
* The paper corpus is roughly 90% biomedical and life sciences — PubMed,
|
|
2214
2392
|
* bioRxiv and medRxiv — with arXiv covering physics, mathematics and
|
|
2215
2393
|
* computer science.
|
|
@@ -2469,6 +2647,14 @@ var FirecrawlClient = class {
|
|
|
2469
2647
|
async getAgentSnapshot(jobId, snapshotId) {
|
|
2470
2648
|
return getAgentSnapshot(this.http, jobId, snapshotId);
|
|
2471
2649
|
}
|
|
2650
|
+
/**
|
|
2651
|
+
* Get a thread and its runs, oldest turn first.
|
|
2652
|
+
* @param threadId Thread id, as returned by startAgent or getAgentStatus.
|
|
2653
|
+
* @param options.includeData Inline each succeeded run's data.
|
|
2654
|
+
*/
|
|
2655
|
+
async getAgentThread(threadId, options) {
|
|
2656
|
+
return getAgentThread(this.http, threadId, options);
|
|
2657
|
+
}
|
|
2472
2658
|
// Browser
|
|
2473
2659
|
/**
|
|
2474
2660
|
* Create a new browser session.
|
|
@@ -4011,5 +4197,6 @@ var index_default = Firecrawl;
|
|
|
4011
4197
|
JobTimeoutError,
|
|
4012
4198
|
ResearchClient,
|
|
4013
4199
|
SdkError,
|
|
4014
|
-
Watcher
|
|
4200
|
+
Watcher,
|
|
4201
|
+
parseRequiresAction
|
|
4015
4202
|
});
|