@crawlee/core 4.0.0-beta.121 → 4.0.0-beta.122

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.
@@ -1,7 +1,7 @@
1
1
  import { inspect } from 'node:util';
2
2
  import { isAsyncIterable, isIterable } from '@crawlee/utils/internal';
3
3
  import { downloadListOfUrls } from '@crawlee/utils';
4
- import ow from 'ow';
4
+ import { z } from 'zod';
5
5
  import { LruCache } from '@apify/datastructures';
6
6
  import { tryCancel } from '@apify/timeout';
7
7
  import { Configuration } from '../configuration.js';
@@ -9,6 +9,7 @@ import { getObjectType } from '../debug.js';
9
9
  import { EventType } from '../events/event_manager.js';
10
10
  import { Request } from '../request.js';
11
11
  import { serviceLocator } from '../service_locator.js';
12
+ import { parseArgument, schemas, validators } from '../validators.js';
12
13
  import { activeStorageTransaction, rejectOperationInTransaction } from './transaction.js';
13
14
  import { drainRequestBatches } from './batched_adds.js';
14
15
  import { StorageStatsTracker } from './storage_stats.js';
@@ -20,6 +21,43 @@ import { RequestDeduplicationCache } from './request_dedup_cache.js';
20
21
  * @internal
21
22
  */
22
23
  const MAX_CACHED_REQUESTS = 2_000_000;
24
+ const iterableSchema = z.custom((value) => isIterable(value) || isAsyncIterable(value), {
25
+ error: (issue) => `Expected an iterable or async iterable, got ${getObjectType(issue.input)}`,
26
+ });
27
+ const operationOptionsSchema = z.strictObject({
28
+ forefront: z.boolean().default(false),
29
+ });
30
+ const addRequestsOptionsSchema = z.strictObject({
31
+ forefront: z.boolean().default(false),
32
+ cache: z.boolean().default(true),
33
+ });
34
+ const addRequestsBatchedOptionsSchema = z.strictObject({
35
+ forefront: z.boolean().optional(),
36
+ waitForAllRequestsToBeAdded: z.boolean().default(false),
37
+ batchSize: schemas.anyNumber.default(1000),
38
+ waitBetweenBatchesMillis: schemas.anyNumber.default(1000),
39
+ maxNewRequests: schemas.anyNumber.optional(),
40
+ });
41
+ const newRequestLikeSchema = z.looseObject({
42
+ url: z.string(),
43
+ id: z.undefined().optional(),
44
+ });
45
+ const handledRequestSchema = z.looseObject({
46
+ id: z.string(),
47
+ uniqueKey: z.string(),
48
+ handledAt: z.string().optional(),
49
+ });
50
+ const reclaimedRequestSchema = z.looseObject({
51
+ id: z.string(),
52
+ uniqueKey: z.string(),
53
+ });
54
+ const uniqueKeySchema = z.string();
55
+ const openOptionsSchema = z.strictObject({
56
+ configuration: z.instanceof(Configuration).optional(),
57
+ storageBackend: validators.storageBackend.optional(),
58
+ proxyConfiguration: validators.proxyConfiguration.optional(),
59
+ httpClient: schemas.httpClient.optional(),
60
+ });
23
61
  /**
24
62
  * Represents a queue of URLs to crawl, which is used for deep crawling of websites
25
63
  * where you start with several URLs and then recursively
@@ -140,20 +178,14 @@ export class RequestQueue {
140
178
  */
141
179
  async addRequest(requestLike, options = {}) {
142
180
  const transaction = activeStorageTransaction();
143
- ow(requestLike, ow.object);
144
- ow(options, ow.object.exactShape({
145
- forefront: ow.optional.boolean,
146
- }));
147
- const { forefront = false } = options;
181
+ parseArgument(requestLike, schemas.anyObject);
182
+ const { forefront } = parseArgument(options, operationOptionsSchema);
148
183
  if ('requestsFromUrl' in requestLike) {
149
184
  const requests = await this.fetchRequestsFromUrl(requestLike);
150
185
  const processedRequests = await this.addFetchedRequests(requestLike, requests, options);
151
186
  return { ...processedRequests[0], forefront };
152
187
  }
153
- ow(requestLike, ow.object.partialShape({
154
- url: ow.string,
155
- id: ow.undefined,
156
- }));
188
+ parseArgument(requestLike, newRequestLikeSchema);
157
189
  const request = requestLike instanceof Request ? requestLike : new Request(requestLike);
158
190
  if (transaction?.policy.requestQueue === 'deferred') {
159
191
  return this.addRequestDeferred(transaction, request, forefront);
@@ -346,14 +378,8 @@ export class RequestQueue {
346
378
  */
347
379
  async addRequests(requestsLike, options = {}) {
348
380
  const transaction = activeStorageTransaction();
349
- ow(requestsLike, ow.object
350
- .is((value) => isIterable(value) || isAsyncIterable(value))
351
- .message((value) => `Expected an iterable or async iterable, got ${getObjectType(value)}`));
352
- ow(options, ow.object.exactShape({
353
- forefront: ow.optional.boolean,
354
- cache: ow.optional.boolean,
355
- }));
356
- const { forefront = false, cache = true } = options;
381
+ parseArgument(requestsLike, iterableSchema);
382
+ const { forefront, cache } = parseArgument(options, addRequestsOptionsSchema);
357
383
  const uniqueKeyToCacheKey = new Map();
358
384
  const getCachedRequestId = (uniqueKey) => {
359
385
  const cached = uniqueKeyToCacheKey.get(uniqueKey);
@@ -439,16 +465,8 @@ export class RequestQueue {
439
465
  * @param options Options for the request queue
440
466
  */
441
467
  async addRequestsBatched(requests, options = {}) {
442
- ow(requests, ow.object
443
- .is((value) => isIterable(value) || isAsyncIterable(value))
444
- .message((value) => `Expected an iterable or async iterable, got ${getObjectType(value)}`));
445
- ow(options, ow.object.exactShape({
446
- forefront: ow.optional.boolean,
447
- waitForAllRequestsToBeAdded: ow.optional.boolean,
448
- batchSize: ow.optional.number,
449
- waitBetweenBatchesMillis: ow.optional.number,
450
- maxNewRequests: ow.optional.number,
451
- }));
468
+ parseArgument(requests, iterableSchema);
469
+ const { forefront, waitForAllRequestsToBeAdded, batchSize, waitBetweenBatchesMillis, maxNewRequests } = parseArgument(options, addRequestsBatchedOptionsSchema);
452
470
  const addRequest = this.addRequest.bind(this);
453
471
  async function* generateRequests() {
454
472
  for await (const opts of requests) {
@@ -467,7 +485,7 @@ export class RequestQueue {
467
485
  }
468
486
  if (opts && typeof opts === 'object' && 'requestsFromUrl' in opts) {
469
487
  // Handle URL lists right away
470
- await addRequest(opts, { forefront: options.forefront });
488
+ await addRequest(opts, { forefront });
471
489
  }
472
490
  else {
473
491
  // Yield valid requests
@@ -477,10 +495,10 @@ export class RequestQueue {
477
495
  }
478
496
  return drainRequestBatches({
479
497
  items: generateRequests(),
480
- batchSize: options.batchSize ?? 1000,
481
- waitBetweenBatchesMillis: options.waitBetweenBatchesMillis ?? 1000,
482
- waitForAllRequestsToBeAdded: options.waitForAllRequestsToBeAdded ?? false,
483
- maxNewRequests: options.maxNewRequests,
498
+ batchSize,
499
+ waitBetweenBatchesMillis,
500
+ waitForAllRequestsToBeAdded,
501
+ maxNewRequests,
484
502
  /**
485
503
  * Requests the backend reports as unprocessed are warned about and skipped rather than retried:
486
504
  * `unprocessedRequests` is what remains after the backend's own transient-error handling - a
@@ -489,7 +507,7 @@ export class RequestQueue {
489
507
  */
490
508
  processChunk: async (chunk, isInitial) => {
491
509
  const { processedRequests, unprocessedRequests } = await this.addRequests(chunk, {
492
- forefront: options.forefront,
510
+ forefront,
493
511
  cache: isInitial,
494
512
  });
495
513
  if (unprocessedRequests.length > 0) {
@@ -514,7 +532,7 @@ export class RequestQueue {
514
532
  */
515
533
  async getRequest(uniqueKey) {
516
534
  const transaction = activeStorageTransaction();
517
- ow(uniqueKey, ow.string);
535
+ parseArgument(uniqueKey, uniqueKeySchema);
518
536
  // Requests buffered by the active transaction (under the `deferred` write policy) are visible to it.
519
537
  const buffered = transaction && this.bufferedRequests(transaction).get(uniqueKey);
520
538
  if (buffered) {
@@ -561,11 +579,7 @@ export class RequestQueue {
561
579
  */
562
580
  async markRequestAsHandled(request) {
563
581
  rejectOperationInTransaction('RequestQueue.markRequestAsHandled()', 'it is part of the crawler request-processing bookkeeping, which a transaction must not affect.');
564
- ow(request, ow.object.partialShape({
565
- id: ow.string,
566
- uniqueKey: ow.string,
567
- handledAt: ow.optional.string,
568
- }));
582
+ parseArgument(request, handledRequestSchema);
569
583
  const forefront = this.requestCache.get(getRequestId(request.uniqueKey))?.forefront ?? false;
570
584
  const handledAt = request.handledAt ?? new Date().toISOString();
571
585
  this.#statsTracker.add('writeCount');
@@ -594,16 +608,12 @@ export class RequestQueue {
594
608
  */
595
609
  async reclaimRequest(request, options = {}) {
596
610
  rejectOperationInTransaction('RequestQueue.reclaimRequest()', 'it is part of the crawler request-processing bookkeeping, which a transaction must not affect.');
597
- ow(request, ow.object.partialShape({
598
- id: ow.string,
599
- uniqueKey: ow.string,
600
- }));
601
- ow(options, ow.object.exactShape({
602
- forefront: ow.optional.boolean,
603
- }));
604
- const { forefront = false } = options;
611
+ parseArgument(request, reclaimedRequestSchema);
612
+ const { forefront } = parseArgument(options, operationOptionsSchema);
605
613
  this.#statsTracker.add('writeCount');
606
- const processedRequest = await this.backend.reclaimRequest(request, { forefront });
614
+ const processedRequest = await this.backend.reclaimRequest(request, {
615
+ forefront,
616
+ });
607
617
  // The request was not in progress — nothing to reclaim.
608
618
  if (!processedRequest) {
609
619
  return null;
@@ -837,14 +847,9 @@ export class RequestQueue {
837
847
  */
838
848
  static async open(identifier, options = {}) {
839
849
  tryCancel();
840
- ow(options, ow.object.exactShape({
841
- configuration: ow.optional.object.instanceOf(Configuration),
842
- storageBackend: ow.optional.object,
843
- proxyConfiguration: ow.optional.object,
844
- httpClient: ow.optional.object,
845
- }));
846
- const storageBackend = options.storageBackend ?? serviceLocator.getStorageBackend();
847
- const configuration = options.configuration ?? serviceLocator.getConfiguration();
850
+ const parsedOptions = parseArgument(options, openOptionsSchema);
851
+ const storageBackend = parsedOptions.storageBackend ?? serviceLocator.getStorageBackend();
852
+ const configuration = parsedOptions.configuration ?? serviceLocator.getConfiguration();
848
853
  await purgeDefaultStorages({ onlyPurgeOnce: true, storageBackend, configuration });
849
854
  const resolved = await resolveStorageIdentifier(identifier, storageBackend, 'RequestQueue');
850
855
  const queue = await serviceLocator
@@ -854,8 +859,8 @@ export class RequestQueue {
854
859
  backendOpener: () => storageBackend.createRequestQueueBackend(resolved),
855
860
  backendCacheKey: storageBackend.getStorageBackendCacheKey?.() ?? storageBackend.constructor.name,
856
861
  });
857
- queue.#proxyConfiguration = options.proxyConfiguration;
858
- queue.#httpClient = options.httpClient;
862
+ queue.#proxyConfiguration = parsedOptions.proxyConfiguration;
863
+ queue.#httpClient = parsedOptions.httpClient;
859
864
  return queue;
860
865
  }
861
866
  }
@@ -1,4 +1,4 @@
1
- import type { BaseHttpClient } from '@crawlee/types';
1
+ import type { BaseHttpClient } from '@crawlee/http-client';
2
2
  import { type ParseSitemapOptions } from '@crawlee/utils';
3
3
  import type { UrlPatternInput } from '../enqueue_links/shared.js';
4
4
  import { Request } from '../request.js';
@@ -1,13 +1,27 @@
1
1
  import { Transform } from 'node:stream';
2
2
  import { parseSitemap } from '@crawlee/utils';
3
3
  import { minimatch } from 'minimatch';
4
- import ow from 'ow';
5
- import { constructUrlPatternObjects } from '../enqueue_links/shared.js';
4
+ import { z } from 'zod';
5
+ import { constructUrlPatternObjects, urlPatternSchema } from '../enqueue_links/shared.js';
6
6
  import { EventType } from '../events/event_manager.js';
7
7
  import { Request } from '../request.js';
8
8
  import { serviceLocator } from '../service_locator.js';
9
+ import { parseArgument, schemas } from '../validators.js';
9
10
  import { KeyValueStore } from './key_value_store.js';
10
11
  import { purgeDefaultStorages } from './utils.js';
12
+ const sitemapRequestLoaderOptionsSchema = z.strictObject({
13
+ sitemapUrls: schemas.arrayOf(z.string(), 'strings'),
14
+ proxyUrl: z.string().optional(),
15
+ persistStateKey: z.string().optional(),
16
+ signal: z.unknown().optional(),
17
+ timeoutMillis: schemas.anyNumber.optional(),
18
+ maxBufferSize: schemas.anyNumber.default(200),
19
+ parseSitemapOptions: z.looseObject({}).optional(),
20
+ include: schemas.arrayOf(urlPatternSchema, 'URL patterns').optional(),
21
+ exclude: schemas.arrayOf(urlPatternSchema, 'URL patterns').optional(),
22
+ persistenceOptions: z.looseObject({}).optional(),
23
+ httpClient: schemas.httpClient.optional(),
24
+ });
11
25
  /** @internal */
12
26
  const STATE_PERSISTENCE_KEY = 'SITEMAP_REQUEST_LOADER_STATE';
13
27
  /**
@@ -80,21 +94,7 @@ export class SitemapRequestLoader {
80
94
  #persistenceOptions;
81
95
  /** @internal */
82
96
  constructor(options) {
83
- const urlPatternValidator = ow.any(ow.string, ow.regExp, ow.object.hasKeys('glob'), ow.object.hasKeys('regexp'));
84
- ow(options, ow.object.exactShape({
85
- sitemapUrls: ow.array.ofType(ow.string),
86
- proxyUrl: ow.optional.string,
87
- persistStateKey: ow.optional.string,
88
- signal: ow.optional.any(),
89
- timeoutMillis: ow.optional.number,
90
- maxBufferSize: ow.optional.number,
91
- parseSitemapOptions: ow.optional.object,
92
- include: ow.optional.array.ofType(urlPatternValidator),
93
- exclude: ow.optional.array.ofType(urlPatternValidator),
94
- persistenceOptions: ow.optional.object,
95
- httpClient: ow.optional.object,
96
- }));
97
- const { include, exclude } = options;
97
+ const { include, exclude, persistStateKey, persistenceOptions, proxyUrl, maxBufferSize, sitemapUrls } = parseArgument(options, sitemapRequestLoaderOptionsSchema, 'SitemapRequestLoaderOptions');
98
98
  this.#log = serviceLocator.getLogger().child({ prefix: 'SitemapRequestLoader' });
99
99
  if (exclude?.length) {
100
100
  this.#urlExcludePatternObjects.push(...constructUrlPatternObjects(exclude));
@@ -102,11 +102,11 @@ export class SitemapRequestLoader {
102
102
  if (include?.length) {
103
103
  this.#urlPatternObjects.push(...constructUrlPatternObjects(include));
104
104
  }
105
- this.#persistStateKey = options.persistStateKey;
106
- this.#persistenceOptions = { enable: true, ...options.persistenceOptions };
107
- this.#proxyUrl = options.proxyUrl;
108
- this.#urlQueueStream = this.createNewStream(options.maxBufferSize ?? 200);
109
- this.#sitemapParsingProgress.pendingSitemapUrls = new Set(options.sitemapUrls);
105
+ this.#persistStateKey = persistStateKey;
106
+ this.#persistenceOptions = { enable: true, ...persistenceOptions };
107
+ this.#proxyUrl = proxyUrl;
108
+ this.#urlQueueStream = this.createNewStream(maxBufferSize);
109
+ this.#sitemapParsingProgress.pendingSitemapUrls = new Set(sitemapUrls);
110
110
  this.#events = serviceLocator.getEventManager();
111
111
  this.persistState = this.persistState.bind(this);
112
112
  }
@@ -1,11 +1,20 @@
1
1
  import { URL } from 'node:url';
2
- import ow from 'ow';
2
+ import { z } from 'zod';
3
3
  import { PersistentRateLimitError } from '../errors.js';
4
4
  import { asyncifyIterable } from '../iterables.js';
5
5
  import { serviceLocator } from '../service_locator.js';
6
6
  import { normalizeHostname } from '../url.js';
7
+ import { parseArgument, schemas } from '../validators.js';
7
8
  import { drainRequestBatches } from './batched_adds.js';
8
9
  import { RequestQueue } from './request_queue.js';
10
+ const throttlingRequestManagerOptionsSchema = z.strictObject({
11
+ inner: schemas.anyObject,
12
+ domains: schemas.arrayOf(z.string().nonempty(), 'non-empty strings'),
13
+ requestManagerOpener: schemas.anyFunction.optional(),
14
+ baseDelaySecs: schemas.anyNumber.refine((value) => value > 0, 'Expected a number greater than 0').optional(),
15
+ maxDelaySecs: schemas.anyNumber.refine((value) => value > 0, 'Expected a number greater than 0').optional(),
16
+ maxDomainStallSecs: schemas.anyNumber.refine((value) => value > 0, 'Expected a number greater than 0').optional(),
17
+ });
9
18
  /** Whether `manager` can pace requests per domain. */
10
19
  export function supportsDomainThrottling(manager) {
11
20
  const candidate = manager;
@@ -75,14 +84,7 @@ export class ThrottlingRequestManager {
75
84
  }
76
85
  constructor(options, config = serviceLocator.getConfiguration()) {
77
86
  this.config = config;
78
- ow(options, ow.object.exactShape({
79
- inner: ow.object,
80
- domains: ow.array.ofType(ow.string.nonEmpty),
81
- requestManagerOpener: ow.optional.function,
82
- baseDelaySecs: ow.optional.number.positive,
83
- maxDelaySecs: ow.optional.number.positive,
84
- maxDomainStallSecs: ow.optional.number.positive,
85
- }));
87
+ parseArgument(options, throttlingRequestManagerOptionsSchema, 'ThrottlingRequestManagerOptions');
86
88
  this.inner = options.inner;
87
89
  this.requestManagerOpener =
88
90
  options.requestManagerOpener ??
@@ -1,4 +1,5 @@
1
- import type { BaseHttpClient, Dictionary, StorageBackend } from '@crawlee/types';
1
+ import type { BaseHttpClient } from '@crawlee/http-client';
2
+ import type { Dictionary, StorageBackend } from '@crawlee/types';
2
3
  import { Configuration } from '../configuration.js';
3
4
  import type { IProxyConfiguration } from '../proxy_configuration.js';
4
5
  /**
package/validators.d.ts CHANGED
@@ -1,28 +1,25 @@
1
- import type { Dictionary } from '@crawlee/types';
1
+ export { ArgumentValidationError, parseArgument } from '@crawlee/utils';
2
+ export { schemas } from '@crawlee/utils/internal';
2
3
  /** @internal */
3
4
  export declare const validators: {
4
- browserPage: (value: Dictionary) => {
5
- validator: boolean;
6
- message: (label: string) => string;
7
- };
8
- proxyConfiguration: (value: Dictionary) => {
9
- validator: boolean;
10
- message: (label: string) => string;
11
- };
12
- requestList: (value: Dictionary) => {
13
- validator: boolean;
14
- message: (label: string) => string;
15
- };
16
- requestQueue: (value: Dictionary) => {
17
- validator: boolean;
18
- message: (label: string) => string;
19
- };
20
- browserPool: (value: Dictionary) => {
21
- validator: boolean;
22
- message: (label: string) => string;
23
- };
24
- sessionPool: (value: Dictionary) => {
25
- validator: boolean;
26
- message: (label: string) => string;
27
- };
5
+ // @ts-ignore optional peer dependency or compatibility with es2022
6
+ browserPage: import("zod").ZodType<import("@crawlee/types").Dictionary, unknown, import("zod/v4/core").$ZodTypeInternals<import("@crawlee/types").Dictionary, unknown>>;
7
+ // @ts-ignore optional peer dependency or compatibility with es2022
8
+ proxyConfiguration: import("zod").ZodType<import("@crawlee/types").Dictionary, unknown, import("zod/v4/core").$ZodTypeInternals<import("@crawlee/types").Dictionary, unknown>>;
9
+ // @ts-ignore optional peer dependency or compatibility with es2022
10
+ requestList: import("zod").ZodType<import("@crawlee/types").Dictionary, unknown, import("zod/v4/core").$ZodTypeInternals<import("@crawlee/types").Dictionary, unknown>>;
11
+ // @ts-ignore optional peer dependency or compatibility with es2022
12
+ requestQueue: import("zod").ZodType<import("@crawlee/types").Dictionary, unknown, import("zod/v4/core").$ZodTypeInternals<import("@crawlee/types").Dictionary, unknown>>;
13
+ // @ts-ignore optional peer dependency or compatibility with es2022
14
+ browserPool: import("zod").ZodType<import("@crawlee/types").Dictionary, unknown, import("zod/v4/core").$ZodTypeInternals<import("@crawlee/types").Dictionary, unknown>>;
15
+ // @ts-ignore optional peer dependency or compatibility with es2022
16
+ sessionPool: import("zod").ZodType<import("@crawlee/types").Dictionary, unknown, import("zod/v4/core").$ZodTypeInternals<import("@crawlee/types").Dictionary, unknown>>;
17
+ // @ts-ignore optional peer dependency or compatibility with es2022
18
+ requestManager: import("zod").ZodType<import("@crawlee/types").Dictionary, unknown, import("zod/v4/core").$ZodTypeInternals<import("@crawlee/types").Dictionary, unknown>>;
19
+ // @ts-ignore optional peer dependency or compatibility with es2022
20
+ storageBackend: import("zod").ZodType<import("@crawlee/types").Dictionary, unknown, import("zod/v4/core").$ZodTypeInternals<import("@crawlee/types").Dictionary, unknown>>;
21
+ // @ts-ignore optional peer dependency or compatibility with es2022
22
+ logger: import("zod").ZodType<import("@crawlee/types").Dictionary, unknown, import("zod/v4/core").$ZodTypeInternals<import("@crawlee/types").Dictionary, unknown>>;
23
+ // @ts-ignore optional peer dependency or compatibility with es2022
24
+ httpClient: import("zod").ZodCustom<import("@crawlee/http-client").BaseHttpClient, import("@crawlee/http-client").BaseHttpClient>;
28
25
  };
package/validators.js CHANGED
@@ -1,29 +1,17 @@
1
- import ow from 'ow';
1
+ import { schemas } from '@crawlee/utils/internal';
2
+ export { ArgumentValidationError, parseArgument } from '@crawlee/utils';
3
+ export { schemas } from '@crawlee/utils/internal';
2
4
  /** @internal */
3
5
  export const validators = {
4
6
  // Naming it browser page for future proofing with Playwright
5
- browserPage: (value) => ({
6
- validator: ow.isValid(value, ow.object.hasKeys('goto', 'evaluate', '$', 'on')),
7
- message: (label) => `Expected argument '${label}' to be a Puppeteer Page, got something else.`,
8
- }),
9
- proxyConfiguration: (value) => ({
10
- validator: ow.isValid(value, ow.object.hasKeys('newProxyInfo')),
11
- message: (label) => `Expected argument '${label}' to implement the IProxyConfiguration interface (missing 'newProxyInfo'), got something else.`,
12
- }),
13
- requestList: (value) => ({
14
- validator: ow.isValid(value, ow.object.hasKeys('fetchNextRequest', 'persistState')),
15
- message: (label) => `Expected argument '${label}' to be a RequestList, got something else.`,
16
- }),
17
- requestQueue: (value) => ({
18
- validator: ow.isValid(value, ow.object.hasKeys('fetchNextRequest', 'addRequest')),
19
- message: (label) => `Expected argument '${label}' to be a RequestQueue, got something else.`,
20
- }),
21
- browserPool: (value) => ({
22
- validator: ow.isValid(value, ow.object.hasKeys('newPage', 'closePage', 'extractPageState', 'injectPageState')),
23
- message: (label) => `Expected argument '${label}' to implement the IBrowserPool interface (missing one of 'newPage', 'closePage', 'extractPageState', 'injectPageState'), got something else.`,
24
- }),
25
- sessionPool: (value) => ({
26
- validator: ow.isValid(value, ow.object.hasKeys('getSession')),
27
- message: (label) => `Expected argument '${label}' to implement the ISessionPool interface (missing 'getSession'), got something else.`,
28
- }),
7
+ browserPage: schemas.objectWithKeys(['goto', 'evaluate', '$', 'on'], 'Expected a Puppeteer Page, got something else.'),
8
+ proxyConfiguration: schemas.objectWithKeys(['newProxyInfo'], "Expected an object implementing the IProxyConfiguration interface (missing 'newProxyInfo'), got something else."),
9
+ requestList: schemas.objectWithKeys(['fetchNextRequest', 'persistState'], 'Expected a RequestList, got something else.'),
10
+ requestQueue: schemas.objectWithKeys(['fetchNextRequest', 'addRequest'], 'Expected a RequestQueue, got something else.'),
11
+ browserPool: schemas.objectWithKeys(['newPage', 'closePage', 'extractPageState', 'injectPageState'], "Expected an object implementing the IBrowserPool interface (missing one of 'newPage', 'closePage', 'extractPageState', 'injectPageState'), got something else."),
12
+ sessionPool: schemas.objectWithKeys(['getSession'], "Expected an object implementing the ISessionPool interface (missing 'getSession'), got something else."),
13
+ requestManager: schemas.objectWithKeys(['fetchNextRequest', 'addRequest', 'addRequestsBatched'], "Expected an object implementing the IRequestManager interface (missing one of 'fetchNextRequest', 'addRequest', 'addRequestsBatched'), got something else."),
14
+ storageBackend: schemas.objectWithKeys(['createDatasetBackend', 'createKeyValueStoreBackend', 'createRequestQueueBackend'], "Expected an object implementing the StorageBackend interface (missing one of 'createDatasetBackend', 'createKeyValueStoreBackend', 'createRequestQueueBackend'), got something else."),
15
+ logger: schemas.logger,
16
+ httpClient: schemas.httpClient,
29
17
  };