@browserless.io/browserless 2.7.1 → 2.9.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.
Files changed (138) hide show
  1. package/CHANGELOG.md +19 -1
  2. package/README.md +41 -3
  3. package/assets/debugger.png +0 -0
  4. package/bin/browserless.js +8 -4
  5. package/bin/scaffold/README.md +6 -4
  6. package/bin/scaffold/src/hello-world.http.ts +7 -1
  7. package/build/browserless.d.ts +8 -5
  8. package/build/browserless.js +23 -22
  9. package/build/browsers/chrome.cdp.d.ts +2 -2
  10. package/build/browsers/chrome.cdp.js +2 -2
  11. package/build/browsers/chrome.playwright.d.ts +2 -2
  12. package/build/browsers/chrome.playwright.js +2 -2
  13. package/build/browsers/chromium.cdp.d.ts +4 -4
  14. package/build/browsers/chromium.cdp.js +49 -32
  15. package/build/browsers/chromium.playwright.d.ts +4 -4
  16. package/build/browsers/chromium.playwright.js +14 -13
  17. package/build/browsers/firefox.playwright.d.ts +4 -4
  18. package/build/browsers/firefox.playwright.js +14 -13
  19. package/build/browsers/index.d.ts +24 -8
  20. package/build/browsers/index.js +20 -15
  21. package/build/browsers/webkit.playwright.d.ts +4 -4
  22. package/build/browsers/webkit.playwright.js +14 -13
  23. package/build/config.d.ts +3 -0
  24. package/build/config.js +3 -0
  25. package/build/exports.d.ts +1 -0
  26. package/build/exports.js +1 -0
  27. package/build/file-system.d.ts +2 -3
  28. package/build/file-system.js +2 -2
  29. package/build/index.js +7 -7
  30. package/build/limiter.d.ts +2 -3
  31. package/build/limiter.js +11 -11
  32. package/build/logger.d.ts +19 -0
  33. package/build/logger.js +43 -0
  34. package/build/monitoring.d.ts +2 -3
  35. package/build/monitoring.js +4 -4
  36. package/build/router.d.ts +4 -5
  37. package/build/router.js +31 -28
  38. package/build/routes/chrome/http/content.post.body.json +8 -8
  39. package/build/routes/chrome/http/pdf.post.body.json +9 -9
  40. package/build/routes/chrome/http/scrape.post.body.json +8 -8
  41. package/build/routes/chrome/http/screenshot.post.body.json +8 -8
  42. package/build/routes/chromium/http/content.post.body.json +8 -8
  43. package/build/routes/chromium/http/pdf.post.body.json +9 -9
  44. package/build/routes/chromium/http/scrape.post.body.json +8 -8
  45. package/build/routes/chromium/http/screenshot.post.body.json +8 -8
  46. package/build/routes/firefox/ws/playwright.d.ts +2 -2
  47. package/build/routes/firefox/ws/playwright.js +1 -1
  48. package/build/routes/management/http/static.get.d.ts +2 -2
  49. package/build/routes/management/http/static.get.js +8 -10
  50. package/build/routes/management/tests/management.spec.js +9 -0
  51. package/build/routes/webkit/ws/playwright.d.ts +2 -2
  52. package/build/routes/webkit/ws/playwright.js +1 -1
  53. package/build/sdk-utils.js +23 -10
  54. package/build/server.d.ts +4 -5
  55. package/build/server.js +38 -33
  56. package/build/shared/browser.ws.d.ts +2 -2
  57. package/build/shared/browser.ws.js +1 -1
  58. package/build/shared/chromium.playwright.ws.d.ts +2 -2
  59. package/build/shared/chromium.playwright.ws.js +1 -1
  60. package/build/shared/chromium.ws.d.ts +2 -2
  61. package/build/shared/chromium.ws.js +1 -1
  62. package/build/shared/content.http.d.ts +2 -2
  63. package/build/shared/content.http.js +4 -1
  64. package/build/shared/download.http.d.ts +2 -2
  65. package/build/shared/download.http.js +11 -12
  66. package/build/shared/function.http.d.ts +2 -2
  67. package/build/shared/function.http.js +4 -5
  68. package/build/shared/json-protocol.http.d.ts +3 -3
  69. package/build/shared/json-protocol.http.js +2 -2
  70. package/build/shared/json-version.http.d.ts +3 -3
  71. package/build/shared/json-version.http.js +2 -2
  72. package/build/shared/page.ws.d.ts +2 -2
  73. package/build/shared/page.ws.js +1 -1
  74. package/build/shared/pdf.http.d.ts +2 -2
  75. package/build/shared/pdf.http.js +6 -4
  76. package/build/shared/performance.http.d.ts +2 -2
  77. package/build/shared/performance.http.js +2 -1
  78. package/build/shared/scrape.http.d.ts +2 -2
  79. package/build/shared/scrape.http.js +4 -1
  80. package/build/shared/screenshot.http.d.ts +2 -2
  81. package/build/shared/screenshot.http.js +4 -1
  82. package/build/shared/utils/function/handler.d.ts +2 -3
  83. package/build/shared/utils/function/handler.js +8 -8
  84. package/build/shared/utils/performance/child.js +4 -4
  85. package/build/shared/utils/performance/main.d.ts +1 -1
  86. package/build/shared/utils/performance/main.js +5 -7
  87. package/build/shared/utils/performance/types.d.ts +2 -1
  88. package/build/types.d.ts +6 -15
  89. package/build/types.js +1 -10
  90. package/build/utils.d.ts +1 -1
  91. package/build/utils.js +6 -2
  92. package/package.json +18 -15
  93. package/scripts/install-debugger.js +55 -15
  94. package/src/browserless.ts +29 -21
  95. package/src/browsers/chrome.cdp.ts +2 -5
  96. package/src/browsers/chrome.playwright.ts +2 -5
  97. package/src/browsers/chromium.cdp.ts +84 -35
  98. package/src/browsers/chromium.playwright.ts +26 -13
  99. package/src/browsers/firefox.playwright.ts +28 -13
  100. package/src/browsers/index.ts +24 -16
  101. package/src/browsers/webkit.playwright.ts +28 -13
  102. package/src/config.ts +4 -0
  103. package/src/exports.ts +1 -0
  104. package/src/file-system.ts +2 -7
  105. package/src/index.ts +7 -7
  106. package/src/limiter.ts +13 -11
  107. package/src/logger.ts +52 -0
  108. package/src/monitoring.ts +6 -8
  109. package/src/router.ts +29 -27
  110. package/src/routes/firefox/ws/playwright.ts +2 -0
  111. package/src/routes/management/http/static.get.ts +13 -10
  112. package/src/routes/management/tests/management.spec.ts +15 -0
  113. package/src/routes/webkit/ws/playwright.ts +2 -0
  114. package/src/sdk-utils.ts +20 -2
  115. package/src/server.ts +47 -32
  116. package/src/shared/browser.ws.ts +2 -0
  117. package/src/shared/chromium.playwright.ws.ts +2 -0
  118. package/src/shared/chromium.ws.ts +2 -0
  119. package/src/shared/content.http.ts +6 -0
  120. package/src/shared/download.http.ts +14 -11
  121. package/src/shared/function.http.ts +5 -4
  122. package/src/shared/json-protocol.http.ts +8 -3
  123. package/src/shared/json-version.http.ts +8 -4
  124. package/src/shared/page.ws.ts +2 -0
  125. package/src/shared/pdf.http.ts +7 -3
  126. package/src/shared/performance.http.ts +3 -0
  127. package/src/shared/scrape.http.ts +6 -0
  128. package/src/shared/screenshot.http.ts +5 -0
  129. package/src/shared/utils/function/handler.ts +9 -13
  130. package/src/shared/utils/performance/child.ts +4 -4
  131. package/src/shared/utils/performance/main.ts +5 -6
  132. package/src/shared/utils/performance/types.ts +2 -1
  133. package/src/types.ts +5 -9
  134. package/src/utils.ts +7 -2
  135. package/static/docs/swagger.json +11 -11
  136. package/static/docs/swagger.min.json +10 -10
  137. package/static/function/client.js +1656 -2916
  138. package/static/function/index.html +1656 -2916
@@ -1,5 +1,6 @@
1
1
  import * as path from 'path';
2
2
  import {
3
+ Logger as BlessLogger,
3
4
  BrowserHTTPRoute,
4
5
  BrowserManager,
5
6
  BrowserWebsocketRoute,
@@ -22,7 +23,6 @@ import {
22
23
  WebSocketRoute,
23
24
  WebkitPlaywright,
24
25
  availableBrowsers,
25
- createLogger,
26
26
  getRouteFiles,
27
27
  makeExternalURL,
28
28
  printLogo,
@@ -45,12 +45,13 @@ type routeInstances =
45
45
  | BrowserWebsocketRoute;
46
46
 
47
47
  export class Browserless extends EventEmitter {
48
- protected debug: debug.Debugger = createLogger('index');
48
+ protected logger: BlessLogger;
49
49
  protected browserManager: BrowserManager;
50
50
  protected config: Config;
51
51
  protected fileSystem: FileSystem;
52
52
  protected hooks: Hooks;
53
53
  protected limiter: Limiter;
54
+ protected Logger: typeof BlessLogger;
54
55
  protected metrics: Metrics;
55
56
  protected monitoring: Monitoring;
56
57
  protected router: Router;
@@ -71,12 +72,14 @@ export class Browserless extends EventEmitter {
71
72
  fileSystem,
72
73
  hooks,
73
74
  limiter,
75
+ Logger: LoggerOverride,
74
76
  metrics,
75
77
  monitoring,
76
78
  router,
77
79
  token,
78
80
  webhooks,
79
81
  }: {
82
+ Logger?: Browserless['Logger'];
80
83
  browserManager?: Browserless['browserManager'];
81
84
  config?: Browserless['config'];
82
85
  fileSystem?: Browserless['fileSystem'];
@@ -89,6 +92,8 @@ export class Browserless extends EventEmitter {
89
92
  webhooks?: Browserless['webhooks'];
90
93
  } = {}) {
91
94
  super();
95
+ this.Logger = LoggerOverride ?? BlessLogger;
96
+ this.logger = new this.Logger('index');
92
97
  this.config = config || new Config();
93
98
  this.metrics = metrics || new Metrics();
94
99
  this.token = token || new Token(this.config);
@@ -108,7 +113,8 @@ export class Browserless extends EventEmitter {
108
113
  this.hooks,
109
114
  );
110
115
  this.router =
111
- router || new Router(this.config, this.browserManager, this.limiter);
116
+ router ||
117
+ new Router(this.config, this.browserManager, this.limiter, this.Logger);
112
118
  }
113
119
 
114
120
  protected saveMetrics = async (): Promise<void> => {
@@ -123,7 +129,7 @@ export class Browserless extends EventEmitter {
123
129
 
124
130
  this.metrics.reset();
125
131
 
126
- this.debug(
132
+ this.logger.info(
127
133
  `Current period usage: ${JSON.stringify({
128
134
  date: aggregatedStats.date,
129
135
  error: aggregatedStats.error,
@@ -140,7 +146,7 @@ export class Browserless extends EventEmitter {
140
146
  );
141
147
 
142
148
  if (metricsPath) {
143
- this.debug(`Saving metrics to "${metricsPath}"`);
149
+ this.logger.info(`Saving metrics to "${metricsPath}"`);
144
150
  this.fileSystem.append(
145
151
  metricsPath,
146
152
  JSON.stringify(aggregatedStats),
@@ -164,7 +170,7 @@ export class Browserless extends EventEmitter {
164
170
  );
165
171
  };
166
172
 
167
- private routeIsDisabled(route: routeInstances) {
173
+ protected routeIsDisabled(route: routeInstances) {
168
174
  return this.disabledRouteNames.some((name) => name === route.name);
169
175
  }
170
176
 
@@ -224,18 +230,24 @@ export class Browserless extends EventEmitter {
224
230
  const [[internalHttpRouteFiles, internalWsRouteFiles], installedBrowsers] =
225
231
  await Promise.all([getRouteFiles(this.config), availableBrowsers]);
226
232
 
233
+ const hasDebugger = await this.config.hasDebugger();
234
+ const debuggerURL =
235
+ hasDebugger &&
236
+ makeExternalURL(
237
+ this.config.getExternalAddress(),
238
+ `/debugger/?token=${this.config.getToken()}`,
239
+ );
227
240
  const docsLink = makeExternalURL(this.config.getExternalAddress(), '/docs');
228
241
 
229
- this.debug(printLogo(docsLink));
230
- this.debug(`Running as user "${userInfo().username}"`);
231
- this.debug('Starting import of HTTP Routes');
242
+ this.logger.info(printLogo(docsLink, debuggerURL));
243
+ this.logger.info(`Running as user "${userInfo().username}"`);
244
+ this.logger.info('Starting import of HTTP Routes');
232
245
 
233
246
  for (const httpRoute of [
234
247
  ...this.httpRouteFiles,
235
248
  ...internalHttpRouteFiles,
236
249
  ]) {
237
250
  if (httpRoute.endsWith('js')) {
238
- const { name } = path.parse(httpRoute);
239
251
  const [bodySchema, querySchema] = await Promise.all(
240
252
  routeSchemas.map(async (schemaType) => {
241
253
  const schemaPath = path.parse(httpRoute);
@@ -249,7 +261,6 @@ export class Browserless extends EventEmitter {
249
261
  const routeImport = `${
250
262
  this.config.getIsWin() ? 'file:///' : ''
251
263
  }${httpRoute}`;
252
- const logger = createLogger(`http:${name}`);
253
264
  const {
254
265
  default: Route,
255
266
  }: { default: Implements<HTTPRoute> | Implements<BrowserHTTPRoute> } =
@@ -258,7 +269,6 @@ export class Browserless extends EventEmitter {
258
269
  this.browserManager,
259
270
  this.config,
260
271
  this.fileSystem,
261
- logger,
262
272
  this.metrics,
263
273
  this.monitoring,
264
274
  this.staticSDKDir,
@@ -271,7 +281,6 @@ export class Browserless extends EventEmitter {
271
281
  route.metrics = () => this.metrics;
272
282
  route.monitoring = () => this.monitoring;
273
283
  route.fileSystem = () => this.fileSystem;
274
- route.debug = () => logger;
275
284
  route.staticSDKDir = () => this.staticSDKDir;
276
285
 
277
286
  httpRoutes.push(route);
@@ -279,13 +288,12 @@ export class Browserless extends EventEmitter {
279
288
  }
280
289
  }
281
290
 
282
- this.debug('Starting import of WebSocket Routes');
291
+ this.logger.info('Starting import of WebSocket Routes');
283
292
  for (const wsRoute of [
284
293
  ...this.webSocketRouteFiles,
285
294
  ...internalWsRouteFiles,
286
295
  ]) {
287
296
  if (wsRoute.endsWith('js')) {
288
- const { name } = path.parse(wsRoute);
289
297
  const [, querySchema] = await Promise.all(
290
298
  routeSchemas.map(async (schemaType) => {
291
299
  const schemaPath = path.parse(wsRoute);
@@ -299,7 +307,6 @@ export class Browserless extends EventEmitter {
299
307
  const wsImport = `${
300
308
  this.config.getIsWin() ? 'file:///' : ''
301
309
  }${wsRoute}`;
302
- const logger = createLogger(`ws:${name}`);
303
310
  const {
304
311
  default: Route,
305
312
  }: {
@@ -311,7 +318,6 @@ export class Browserless extends EventEmitter {
311
318
  this.browserManager,
312
319
  this.config,
313
320
  this.fileSystem,
314
- logger,
315
321
  this.metrics,
316
322
  this.monitoring,
317
323
  this.staticSDKDir,
@@ -323,7 +329,6 @@ export class Browserless extends EventEmitter {
323
329
  route.metrics = () => this.metrics;
324
330
  route.monitoring = () => this.monitoring;
325
331
  route.fileSystem = () => this.fileSystem;
326
- route.debug = () => logger;
327
332
  route.staticSDKDir = () => this.staticSDKDir;
328
333
 
329
334
  wsRoutes.push(route);
@@ -351,7 +356,7 @@ export class Browserless extends EventEmitter {
351
356
  .map((r) => r.name);
352
357
 
353
358
  if (duplicateNamedRoutes.length) {
354
- this.debug(
359
+ this.logger.warn(
355
360
  `Found duplicate routing names. Route names must be unique:`,
356
361
  duplicateNamedRoutes,
357
362
  );
@@ -360,7 +365,9 @@ export class Browserless extends EventEmitter {
360
365
  httpRoutes.forEach((r) => this.router.registerHTTPRoute(r));
361
366
  wsRoutes.forEach((r) => this.router.registerWebSocketRoute(r));
362
367
 
363
- this.debug(`Imported and validated all route files, starting up server.`);
368
+ this.logger.info(
369
+ `Imported and validated all route files, starting up server.`,
370
+ );
364
371
 
365
372
  this.server = new HTTPServer(
366
373
  this.config,
@@ -368,10 +375,11 @@ export class Browserless extends EventEmitter {
368
375
  this.token,
369
376
  this.router,
370
377
  this.hooks,
378
+ this.Logger,
371
379
  );
372
380
 
373
381
  await this.server.start();
374
- this.debug(`Starting metrics collection.`);
382
+ this.logger.info(`Starting metrics collection.`);
375
383
  this.metricsSaveIntervalID = setInterval(
376
384
  () => this.saveMetrics(),
377
385
  this.metricsSaveInterval,
@@ -1,10 +1,7 @@
1
- import {
2
- chromeExecutablePath,
3
- createLogger,
4
- } from '@browserless.io/browserless';
1
+ import { Logger, chromeExecutablePath } from '@browserless.io/browserless';
5
2
  import { ChromiumCDP } from './chromium.cdp.js';
6
3
 
7
4
  export class ChromeCDP extends ChromiumCDP {
8
5
  protected executablePath = chromeExecutablePath();
9
- protected debug = createLogger('browsers:chrome:cdp');
6
+ protected logger = new Logger('browsers:chrome:cdp');
10
7
  }
@@ -1,10 +1,7 @@
1
- import {
2
- chromeExecutablePath,
3
- createLogger,
4
- } from '@browserless.io/browserless';
1
+ import { Logger, chromeExecutablePath } from '@browserless.io/browserless';
5
2
  import { ChromiumPlaywright } from './chromium.playwright.js';
6
3
 
7
4
  export class ChromePlaywright extends ChromiumPlaywright {
8
5
  protected executablePath = chromeExecutablePath();
9
- protected debug = createLogger('browsers:chrome:playwright');
6
+ protected logger = new Logger('browsers:chrome:playwright');
10
7
  }
@@ -2,9 +2,9 @@ import {
2
2
  BLESS_PAGE_IDENTIFIER,
3
3
  CDPLaunchOptions,
4
4
  Config,
5
+ Logger,
5
6
  Request,
6
7
  ServerError,
7
- createLogger,
8
8
  noop,
9
9
  once,
10
10
  } from '@browserless.io/browserless';
@@ -29,7 +29,7 @@ export class ChromiumCDP extends EventEmitter {
29
29
  protected browser: Browser | null = null;
30
30
  protected browserWSEndpoint: string | null = null;
31
31
  protected port?: number;
32
- protected debug = createLogger('browsers:chromium:cdp');
32
+ protected logger: Logger;
33
33
  protected proxy = httpProxy.createProxyServer();
34
34
  protected executablePath = playwright.chromium.executablePath();
35
35
 
@@ -37,9 +37,11 @@ export class ChromiumCDP extends EventEmitter {
37
37
  blockAds,
38
38
  config,
39
39
  userDataDir,
40
+ logger,
40
41
  }: {
41
42
  blockAds: boolean;
42
43
  config: Config;
44
+ logger: Logger;
43
45
  userDataDir: ChromiumCDP['userDataDir'];
44
46
  }) {
45
47
  super();
@@ -47,7 +49,9 @@ export class ChromiumCDP extends EventEmitter {
47
49
  this.userDataDir = userDataDir;
48
50
  this.config = config;
49
51
  this.blockAds = blockAds;
50
- this.debug(`Starting new browser instance`);
52
+ this.logger = logger;
53
+
54
+ this.logger.info(`Starting new ${this.constructor.name} instance`);
51
55
  }
52
56
 
53
57
  protected cleanListeners() {
@@ -63,31 +67,62 @@ export class ChromiumCDP extends EventEmitter {
63
67
  protected onTargetCreated = async (target: Target) => {
64
68
  if (target.type() === 'page') {
65
69
  const page = await target.page().catch((e) => {
66
- this.debug(`Error in new page ${e}`);
70
+ this.logger.error(`Error in ${this.constructor.name} new page ${e}`);
67
71
  return null;
68
72
  });
69
73
 
70
74
  if (page) {
71
- if (!this.config.getAllowFileProtocol()) {
72
- this.debug(`Setting up file:// protocol request rejection`);
73
- page.on('request', async (request) => {
74
- if (request.url().startsWith('file://')) {
75
- this.debug(`File protocol request found in request, terminating`);
76
- page.close().catch(noop);
77
- this.close();
78
- }
79
- });
80
-
81
- page.on('response', async (response) => {
82
- if (response.url().startsWith('file://')) {
83
- this.debug(
84
- `File protocol request found in response, terminating`,
85
- );
86
- page.close().catch(noop);
87
- this.close();
88
- }
89
- });
90
- }
75
+ this.logger.trace(`Setting up file:// protocol request rejection`);
76
+
77
+ page.on('error', (err) => {
78
+ this.logger.error(err);
79
+ });
80
+
81
+ page.on('pageerror', (err) => {
82
+ this.logger.warn(err);
83
+ });
84
+
85
+ page.on('framenavigated', (frame) => {
86
+ this.logger.trace(`Navigation to ${frame.url()}`);
87
+ });
88
+
89
+ page.on('console', (message) => {
90
+ this.logger.trace(`${message.type()}: ${message.text()}`);
91
+ });
92
+
93
+ page.on('requestfailed', (req) => {
94
+ this.logger.warn(`"${req.failure()?.errorText}": ${req.url()}`);
95
+ });
96
+
97
+ page.on('request', async (request) => {
98
+ this.logger.trace(`${request.method()}: ${request.url()}`);
99
+ if (
100
+ !this.config.getAllowFileProtocol() &&
101
+ request.url().startsWith('file://')
102
+ ) {
103
+ this.logger.error(
104
+ `File protocol request found in request to ${this.constructor.name}, terminating`,
105
+ );
106
+ page.close().catch(noop);
107
+ this.close();
108
+ }
109
+ });
110
+
111
+ page.on('response', async (response) => {
112
+ this.logger.trace(`${response.status()}: ${response.url()}`);
113
+
114
+ if (
115
+ !this.config.getAllowFileProtocol() &&
116
+ response.url().startsWith('file://')
117
+ ) {
118
+ this.logger.error(
119
+ `File protocol request found in response to ${this.constructor.name}, terminating`,
120
+ );
121
+ page.close().catch(noop);
122
+ this.close();
123
+ }
124
+ });
125
+
91
126
  this.emit('newPage', page);
92
127
  }
93
128
  }
@@ -97,7 +132,9 @@ export class ChromiumCDP extends EventEmitter {
97
132
 
98
133
  public newPage = async (): Promise<Page> => {
99
134
  if (!this.browser) {
100
- throw new ServerError(`Browser hasn't been launched yet!`);
135
+ throw new ServerError(
136
+ `${this.constructor.name} hasn't been launched yet!`,
137
+ );
101
138
  }
102
139
 
103
140
  return this.browser.newPage();
@@ -105,7 +142,9 @@ export class ChromiumCDP extends EventEmitter {
105
142
 
106
143
  public close = async (): Promise<void> => {
107
144
  if (this.browser) {
108
- this.debug(`Closing browser process and all listeners`);
145
+ this.logger.info(
146
+ `Closing ${this.constructor.name} process and all listeners`,
147
+ );
109
148
  this.emit('close');
110
149
  this.cleanListeners();
111
150
  this.browser.removeAllListeners();
@@ -122,7 +161,7 @@ export class ChromiumCDP extends EventEmitter {
122
161
 
123
162
  public launch = async (options: CDPLaunchOptions = {}): Promise<Browser> => {
124
163
  this.port = await getPort();
125
- this.debug(`Got open port ${this.port}`);
164
+ this.logger.info(`${this.constructor.name} got open port ${this.port}`);
126
165
  const __dirname = path.dirname(fileURLToPath(import.meta.url));
127
166
  const finalOptions = {
128
167
  ...options,
@@ -157,13 +196,17 @@ export class ChromiumCDP extends EventEmitter {
157
196
  ? puppeteerStealth.launch.bind(puppeteerStealth)
158
197
  : puppeteer.launch.bind(puppeteer);
159
198
 
160
- this.debug(finalOptions, `Launching CDP Handler`);
161
- // @ts-ignore mis-matched types from stealth...
199
+ this.logger.info(
200
+ finalOptions,
201
+ `Launching ${this.constructor.name} Handler`,
202
+ );
162
203
  this.browser = (await launch(finalOptions)) as Browser;
163
204
  this.browser.on('targetcreated', this.onTargetCreated);
164
205
  this.running = true;
165
206
  this.browserWSEndpoint = this.browser.wsEndpoint();
166
- this.debug(`Browser is running on ${this.browserWSEndpoint}`);
207
+ this.logger.info(
208
+ `${this.constructor.name} is running on ${this.browserWSEndpoint}`,
209
+ );
167
210
 
168
211
  return this.browser;
169
212
  };
@@ -199,7 +242,9 @@ export class ChromiumCDP extends EventEmitter {
199
242
  );
200
243
  }
201
244
  socket.once('close', resolve);
202
- this.debug(`Proxying ${req.parsed.href}`);
245
+ this.logger.info(
246
+ `Proxying ${req.parsed.href} to ${this.constructor.name}`,
247
+ );
203
248
 
204
249
  const shouldMakePage = req.parsed.pathname.includes(
205
250
  BLESS_PAGE_IDENTIFIER,
@@ -223,7 +268,9 @@ export class ChromiumCDP extends EventEmitter {
223
268
  target,
224
269
  },
225
270
  (error) => {
226
- this.debug(`Error proxying session: ${error}`);
271
+ this.logger.error(
272
+ `Error proxying session to ${this.constructor.name}: ${error}`,
273
+ );
227
274
  this.close();
228
275
  return reject(error);
229
276
  },
@@ -253,8 +300,8 @@ export class ChromiumCDP extends EventEmitter {
253
300
  this.browser?.process()?.once('close', close);
254
301
  socket.once('close', close);
255
302
 
256
- this.debug(
257
- `Proxying ${req.parsed.href} to browser ${this.browserWSEndpoint}`,
303
+ this.logger.info(
304
+ `Proxying ${req.parsed.href} to ${this.constructor.name} ${this.browserWSEndpoint}`,
258
305
  );
259
306
 
260
307
  req.url = '';
@@ -271,7 +318,9 @@ export class ChromiumCDP extends EventEmitter {
271
318
  target: this.browserWSEndpoint,
272
319
  },
273
320
  (error) => {
274
- this.debug(`Error proxying session: ${error}`);
321
+ this.logger.error(
322
+ `Error proxying session to ${this.constructor.name}: ${error}`,
323
+ );
275
324
  this.close();
276
325
  return reject(error);
277
326
  },
@@ -1,9 +1,9 @@
1
1
  import {
2
2
  BrowserServerOptions,
3
3
  Config,
4
+ Logger,
4
5
  Request,
5
6
  ServerError,
6
- createLogger,
7
7
  } from '@browserless.io/browserless';
8
8
  import playwright, { Page } from 'playwright-core';
9
9
  import { Duplex } from 'stream';
@@ -15,25 +15,28 @@ export class ChromiumPlaywright extends EventEmitter {
15
15
  protected config: Config;
16
16
  protected userDataDir: string | null;
17
17
  protected running = false;
18
+ protected logger: Logger;
18
19
  protected proxy = httpProxy.createProxyServer();
19
20
  protected browser: playwright.BrowserServer | null = null;
20
21
  protected browserWSEndpoint: string | null = null;
21
- protected debug = createLogger('browsers:chromium:playwright');
22
22
  protected executablePath = playwright.chromium.executablePath();
23
23
 
24
24
  constructor({
25
25
  config,
26
26
  userDataDir,
27
+ logger,
27
28
  }: {
28
29
  config: Config;
30
+ logger: Logger;
29
31
  userDataDir: ChromiumPlaywright['userDataDir'];
30
32
  }) {
31
33
  super();
32
34
 
33
35
  this.userDataDir = userDataDir;
34
36
  this.config = config;
37
+ this.logger = logger;
35
38
 
36
- this.debug(`Starting new browser instance`);
39
+ this.logger.info(`Starting new ${this.constructor.name} instance`);
37
40
  }
38
41
 
39
42
  protected cleanListeners() {
@@ -44,7 +47,9 @@ export class ChromiumPlaywright extends EventEmitter {
44
47
 
45
48
  public close = async (): Promise<void> => {
46
49
  if (this.browser) {
47
- this.debug(`Closing browser process and all listeners`);
50
+ this.logger.info(
51
+ `Closing ${this.constructor.name} process and all listeners`,
52
+ );
48
53
  this.emit('close');
49
54
  this.cleanListeners();
50
55
  this.browser.close();
@@ -57,18 +62,22 @@ export class ChromiumPlaywright extends EventEmitter {
57
62
  public pages = async (): Promise<[]> => [];
58
63
 
59
64
  public getPageId = (): string => {
60
- throw new ServerError(`#getPageId is not yet supported with this browser.`);
65
+ throw new ServerError(
66
+ `#getPageId is not yet supported with ${this.constructor.name}.`,
67
+ );
61
68
  };
62
69
 
63
70
  public makeLiveURL = (): void => {
64
71
  throw new ServerError(
65
- `Live URLs are not yet supported with this browser. In the future this will be at "${this.config.getExternalAddress()}"`,
72
+ `Live URLs are not yet supported with ${this.constructor.name}. In the future this will be at "${this.config.getExternalAddress()}"`,
66
73
  );
67
74
  };
68
75
 
69
76
  public newPage = async (): Promise<Page> => {
70
77
  if (!this.browser || !this.browserWSEndpoint) {
71
- throw new ServerError(`Browser hasn't been launched yet!`);
78
+ throw new ServerError(
79
+ `${this.constructor.name} hasn't been launched yet!`,
80
+ );
72
81
  }
73
82
  const browser = await playwright.chromium.connect(this.browserWSEndpoint);
74
83
  return await browser.newPage();
@@ -77,7 +86,7 @@ export class ChromiumPlaywright extends EventEmitter {
77
86
  public launch = async (
78
87
  options: BrowserServerOptions = {},
79
88
  ): Promise<playwright.BrowserServer> => {
80
- this.debug(`Launching Playwright Handler`);
89
+ this.logger.info(`Launching ${this.constructor.name} Handler`);
81
90
 
82
91
  this.browser = await playwright.chromium.launchServer({
83
92
  ...options,
@@ -91,7 +100,9 @@ export class ChromiumPlaywright extends EventEmitter {
91
100
 
92
101
  const browserWSEndpoint = this.browser.wsEndpoint();
93
102
 
94
- this.debug(`Browser is running on ${browserWSEndpoint}`);
103
+ this.logger.info(
104
+ `${this.constructor.name} is running on ${browserWSEndpoint}`,
105
+ );
95
106
  this.running = true;
96
107
  this.browserWSEndpoint = browserWSEndpoint;
97
108
 
@@ -118,7 +129,7 @@ export class ChromiumPlaywright extends EventEmitter {
118
129
  };
119
130
 
120
131
  public proxyPageWebSocket = async () => {
121
- console.warn(`Not yet implemented`);
132
+ this.logger.warn(`${this.constructor.name} Not yet implemented`);
122
133
  };
123
134
 
124
135
  public proxyWebSocket = async (
@@ -134,8 +145,8 @@ export class ChromiumPlaywright extends EventEmitter {
134
145
  }
135
146
  socket.once('close', resolve);
136
147
 
137
- this.debug(
138
- `Proxying ${req.parsed.href} to browser ${this.browserWSEndpoint}`,
148
+ this.logger.info(
149
+ `Proxying ${req.parsed.href} to ${this.constructor.name} ${this.browserWSEndpoint}`,
139
150
  );
140
151
 
141
152
  // Delete headers known to cause issues
@@ -152,7 +163,9 @@ export class ChromiumPlaywright extends EventEmitter {
152
163
  target: this.browserWSEndpoint,
153
164
  },
154
165
  (error) => {
155
- this.debug(`Error proxying session: ${error}`);
166
+ this.logger.error(
167
+ `Error proxying session to ${this.constructor.name}: ${error}`,
168
+ );
156
169
  this.close();
157
170
  return reject(error);
158
171
  },