@crawlee/browser 3.17.1-beta.8 → 3.17.1-beta.80

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/index.mjs CHANGED
@@ -50,6 +50,7 @@ export const RequestQueue = mod.RequestQueue;
50
50
  export const RequestQueueV1 = mod.RequestQueueV1;
51
51
  export const RequestQueueV2 = mod.RequestQueueV2;
52
52
  export const RequestState = mod.RequestState;
53
+ export const RequestValidationError = mod.RequestValidationError;
53
54
  export const RetryRequestError = mod.RetryRequestError;
54
55
  export const Router = mod.Router;
55
56
  export const STATE_PERSISTENCE_KEY = mod.STATE_PERSISTENCE_KEY;
@@ -79,6 +80,7 @@ export const createDeserialize = mod.createDeserialize;
79
80
  export const createEventLoopLoadSignal = mod.createEventLoopLoadSignal;
80
81
  export const createRequestOptions = mod.createRequestOptions;
81
82
  export const createRequests = mod.createRequests;
83
+ export const defaultRoute = mod.defaultRoute;
82
84
  export const deserializeArray = mod.deserializeArray;
83
85
  export const enqueueLinks = mod.enqueueLinks;
84
86
  export const evaluateLoadSignalSample = mod.evaluateLoadSignalSample;
@@ -100,5 +102,6 @@ export const tryAbsoluteURL = mod.tryAbsoluteURL;
100
102
  export const updateEnqueueLinksPatternCache = mod.updateEnqueueLinksPatternCache;
101
103
  export const useState = mod.useState;
102
104
  export const validateGlobPattern = mod.validateGlobPattern;
105
+ export const validateUserData = mod.validateUserData;
103
106
  export const validators = mod.validators;
104
107
  export const withCheckedStorageAccess = mod.withCheckedStorageAccess;
@@ -331,6 +331,11 @@ export declare abstract class BrowserCrawler<InternalBrowserPoolOptions extends
331
331
  protected _cleanupContext(crawlingContext: Context): Promise<void>;
332
332
  private containsSelectors;
333
333
  protected isRequestBlocked(crawlingContext: Context): Promise<string | false>;
334
+ /**
335
+ * `BrowserCrawler` hands `BasicCrawler` a wrapper that opens a page before delegating, and keeps the user's
336
+ * own handler in `userProvidedRequestHandler` — so resolve router-aware metadata against that instead.
337
+ */
338
+ protected get userRequestHandler(): RequestHandler<Context>;
334
339
  /**
335
340
  * Wrapper around requestHandler that opens and closes pages etc.
336
341
  */
@@ -9,6 +9,7 @@ const browser_pool_1 = require("@crawlee/browser-pool");
9
9
  const utils_1 = require("@crawlee/utils");
10
10
  const ow_1 = tslib_1.__importDefault(require("ow"));
11
11
  const timeout_1 = require("@apify/timeout");
12
+ const PAGE_CLOSE_TIMEOUT_MILLIS = 5000;
12
13
  /**
13
14
  * Provides a simple framework for parallel crawling of web pages
14
15
  * using headless browsers with [Puppeteer](https://github.com/puppeteer/puppeteer)
@@ -185,7 +186,8 @@ class BrowserCrawler extends basic_1.BasicCrawler {
185
186
  const { page } = crawlingContext;
186
187
  // Page creation may be aborted
187
188
  if (page) {
188
- await page.close().catch((error) => this.log.debug('Error while closing page', { error }));
189
+ // Puppeteer 25+ can hang `page.close()` indefinitely when the page's navigation was aborted, don't let it block the crawler.
190
+ await (0, timeout_1.addTimeoutToPromise)(async () => page.close(), PAGE_CLOSE_TIMEOUT_MILLIS, `page.close() timed out after ${PAGE_CLOSE_TIMEOUT_MILLIS / 1000} seconds`).catch((error) => this.log.debug('Error while closing page', { error }));
189
191
  }
190
192
  }
191
193
  async containsSelectors(page, selectors) {
@@ -220,6 +222,13 @@ class BrowserCrawler extends basic_1.BasicCrawler {
220
222
  return `Received blocked status code: ${blockedStatusCode}`;
221
223
  return false;
222
224
  }
225
+ /**
226
+ * `BrowserCrawler` hands `BasicCrawler` a wrapper that opens a page before delegating, and keeps the user's
227
+ * own handler in `userProvidedRequestHandler` — so resolve router-aware metadata against that instead.
228
+ */
229
+ get userRequestHandler() {
230
+ return this.userProvidedRequestHandler;
231
+ }
223
232
  /**
224
233
  * Wrapper around requestHandler that opens and closes pages etc.
225
234
  */
@@ -311,7 +320,9 @@ class BrowserCrawler extends basic_1.BasicCrawler {
311
320
  const contextEnqueueLinks = crawlingContext.enqueueLinks;
312
321
  crawlingContext.enqueueLinks = async (enqueueOptions) => {
313
322
  return browserCrawlerEnqueueLinks({
314
- options: { ...enqueueOptions, limit: this.calculateEnqueuedRequestLimit(enqueueOptions?.limit) },
323
+ // `contextEnqueueLinks` clamps `limit` by the remaining `maxRequestsPerCrawl` budget itself;
324
+ // pre-clamping it here would make the crawler log the internal limit as a user-provided one
325
+ options: enqueueOptions,
315
326
  page,
316
327
  requestQueue: await this.getRequestQueue(),
317
328
  robotsTxtFile: await this.getRobotsTxtFileForUrl(crawlingContext.request.url),
@@ -475,8 +486,8 @@ async function browserCrawlerEnqueueLinks(options) {
475
486
  if (containsEnqueueLinks(options)) {
476
487
  return options.enqueueLinks({
477
488
  urls,
478
- baseUrl,
479
489
  ...enqueueLinksOptions,
490
+ baseUrl,
480
491
  });
481
492
  }
482
493
  return (0, basic_1.enqueueLinks)({
@@ -484,8 +495,8 @@ async function browserCrawlerEnqueueLinks(options) {
484
495
  robotsTxtFile: options.robotsTxtFile,
485
496
  onSkippedRequest: options.onSkippedRequest,
486
497
  urls,
487
- baseUrl,
488
498
  ...enqueueLinksOptions,
499
+ baseUrl,
489
500
  });
490
501
  }
491
502
  /**
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@crawlee/browser",
3
- "version": "3.17.1-beta.8",
3
+ "version": "3.17.1-beta.80",
4
4
  "description": "The scalable web crawling and scraping library for JavaScript/Node.js. Enables development of data extraction and web automation jobs (not only) with headless Chrome and Puppeteer.",
5
5
  "engines": {
6
6
  "node": ">=16.0.0"
@@ -53,11 +53,11 @@
53
53
  "access": "public"
54
54
  },
55
55
  "dependencies": {
56
- "@apify/timeout": "^0.3.0",
57
- "@crawlee/basic": "3.17.1-beta.8",
58
- "@crawlee/browser-pool": "3.17.1-beta.8",
59
- "@crawlee/types": "3.17.1-beta.8",
60
- "@crawlee/utils": "3.17.1-beta.8",
56
+ "@apify/timeout": "^0.4.0",
57
+ "@crawlee/basic": "3.17.1-beta.80",
58
+ "@crawlee/browser-pool": "3.17.1-beta.80",
59
+ "@crawlee/types": "3.17.1-beta.80",
60
+ "@crawlee/utils": "3.17.1-beta.80",
61
61
  "ow": "^0.28.1",
62
62
  "tslib": "^2.4.0",
63
63
  "type-fest": "^4.0.0"
@@ -81,5 +81,5 @@
81
81
  }
82
82
  }
83
83
  },
84
- "gitHead": "4f4b8c1d53b9185095ac68017aff0ef2b8182b6b"
84
+ "gitHead": "5b3c2d52f128643de6f515e87eeb531d55a187f0"
85
85
  }