@browserless.io/browserless 2.20.1 → 2.21.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 (137) hide show
  1. package/CHANGELOG.md +15 -1
  2. package/bin/browserless.js +2 -1
  3. package/build/browserless.js +3 -2
  4. package/build/browsers/index.d.ts +3 -2
  5. package/build/browsers/index.js +3 -1
  6. package/build/router.js +7 -3
  7. package/build/routes/chrome/http/content.post.body.json +8 -8
  8. package/build/routes/chrome/http/pdf.post.body.json +8 -8
  9. package/build/routes/chrome/http/scrape.post.body.json +8 -8
  10. package/build/routes/chrome/http/screenshot.post.body.json +8 -8
  11. package/build/routes/chrome/tests/pdf.spec.js +24 -12
  12. package/build/routes/chromium/http/content.post.body.json +8 -8
  13. package/build/routes/chromium/http/pdf.post.body.json +8 -8
  14. package/build/routes/chromium/http/scrape.post.body.json +8 -8
  15. package/build/routes/chromium/http/screenshot.post.body.json +8 -8
  16. package/build/routes/chromium/tests/pdf.spec.js +24 -12
  17. package/build/shared/pdf.http.js +10 -5
  18. package/extensions/ublock/_locales/ar/messages.json +5 -1
  19. package/extensions/ublock/_locales/az/messages.json +4 -0
  20. package/extensions/ublock/_locales/be/messages.json +4 -0
  21. package/extensions/ublock/_locales/bg/messages.json +4 -0
  22. package/extensions/ublock/_locales/bn/messages.json +4 -0
  23. package/extensions/ublock/_locales/br_FR/messages.json +9 -5
  24. package/extensions/ublock/_locales/bs/messages.json +4 -0
  25. package/extensions/ublock/_locales/ca/messages.json +5 -1
  26. package/extensions/ublock/_locales/cs/messages.json +4 -0
  27. package/extensions/ublock/_locales/cv/messages.json +4 -0
  28. package/extensions/ublock/_locales/cy/messages.json +4 -0
  29. package/extensions/ublock/_locales/da/messages.json +4 -0
  30. package/extensions/ublock/_locales/de/messages.json +4 -0
  31. package/extensions/ublock/_locales/el/messages.json +8 -4
  32. package/extensions/ublock/_locales/en/messages.json +4 -0
  33. package/extensions/ublock/_locales/en_GB/messages.json +4 -0
  34. package/extensions/ublock/_locales/eo/messages.json +9 -5
  35. package/extensions/ublock/_locales/es/messages.json +4 -0
  36. package/extensions/ublock/_locales/et/messages.json +4 -0
  37. package/extensions/ublock/_locales/eu/messages.json +4 -0
  38. package/extensions/ublock/_locales/fa/messages.json +4 -0
  39. package/extensions/ublock/_locales/fi/messages.json +6 -2
  40. package/extensions/ublock/_locales/fil/messages.json +4 -0
  41. package/extensions/ublock/_locales/fr/messages.json +4 -0
  42. package/extensions/ublock/_locales/fy/messages.json +4 -0
  43. package/extensions/ublock/_locales/gl/messages.json +12 -8
  44. package/extensions/ublock/_locales/gu/messages.json +4 -0
  45. package/extensions/ublock/_locales/he/messages.json +4 -0
  46. package/extensions/ublock/_locales/hi/messages.json +4 -0
  47. package/extensions/ublock/_locales/hr/messages.json +4 -0
  48. package/extensions/ublock/_locales/hu/messages.json +68 -64
  49. package/extensions/ublock/_locales/hy/messages.json +4 -0
  50. package/extensions/ublock/_locales/id/messages.json +6 -2
  51. package/extensions/ublock/_locales/it/messages.json +4 -0
  52. package/extensions/ublock/_locales/ja/messages.json +4 -0
  53. package/extensions/ublock/_locales/ka/messages.json +4 -0
  54. package/extensions/ublock/_locales/kk/messages.json +4 -0
  55. package/extensions/ublock/_locales/kn/messages.json +4 -0
  56. package/extensions/ublock/_locales/ko/messages.json +4 -0
  57. package/extensions/ublock/_locales/lt/messages.json +4 -0
  58. package/extensions/ublock/_locales/lv/messages.json +4 -0
  59. package/extensions/ublock/_locales/mk/messages.json +4 -0
  60. package/extensions/ublock/_locales/ml/messages.json +4 -0
  61. package/extensions/ublock/_locales/mr/messages.json +4 -0
  62. package/extensions/ublock/_locales/ms/messages.json +4 -0
  63. package/extensions/ublock/_locales/nb/messages.json +4 -0
  64. package/extensions/ublock/_locales/nl/messages.json +4 -0
  65. package/extensions/ublock/_locales/no/messages.json +4 -0
  66. package/extensions/ublock/_locales/oc/messages.json +4 -0
  67. package/extensions/ublock/_locales/pa/messages.json +8 -4
  68. package/extensions/ublock/_locales/pl/messages.json +4 -0
  69. package/extensions/ublock/_locales/pt_BR/messages.json +4 -0
  70. package/extensions/ublock/_locales/pt_PT/messages.json +4 -0
  71. package/extensions/ublock/_locales/ro/messages.json +4 -0
  72. package/extensions/ublock/_locales/ru/messages.json +4 -0
  73. package/extensions/ublock/_locales/si/messages.json +4 -0
  74. package/extensions/ublock/_locales/sk/messages.json +4 -0
  75. package/extensions/ublock/_locales/sl/messages.json +4 -0
  76. package/extensions/ublock/_locales/so/messages.json +4 -0
  77. package/extensions/ublock/_locales/sq/messages.json +4 -0
  78. package/extensions/ublock/_locales/sr/messages.json +6 -2
  79. package/extensions/ublock/_locales/sv/messages.json +4 -0
  80. package/extensions/ublock/_locales/sw/messages.json +4 -0
  81. package/extensions/ublock/_locales/ta/messages.json +4 -0
  82. package/extensions/ublock/_locales/te/messages.json +4 -0
  83. package/extensions/ublock/_locales/th/messages.json +4 -0
  84. package/extensions/ublock/_locales/tr/messages.json +4 -0
  85. package/extensions/ublock/_locales/uk/messages.json +4 -0
  86. package/extensions/ublock/_locales/ur/messages.json +4 -0
  87. package/extensions/ublock/_locales/vi/messages.json +4 -0
  88. package/extensions/ublock/_locales/zh_CN/messages.json +4 -0
  89. package/extensions/ublock/_locales/zh_TW/messages.json +5 -1
  90. package/extensions/ublock/assets/assets.json +8 -6
  91. package/extensions/ublock/assets/resources/scriptlets.js +455 -301
  92. package/extensions/ublock/assets/thirdparties/easylist/easylist.txt +4441 -6643
  93. package/extensions/ublock/assets/thirdparties/easylist/easyprivacy.txt +401 -307
  94. package/extensions/ublock/assets/thirdparties/pgl.yoyo.org/as/serverlist +34 -29
  95. package/extensions/ublock/assets/thirdparties/publicsuffix.org/list/effective_tld_names.dat +682 -709
  96. package/extensions/ublock/assets/thirdparties/urlhaus-filter/urlhaus-filter-online.txt +2439 -1999
  97. package/extensions/ublock/assets/ublock/badlists.txt +7 -0
  98. package/extensions/ublock/assets/ublock/badware.min.txt +992 -552
  99. package/extensions/ublock/assets/ublock/filters.min.txt +1253 -864
  100. package/extensions/ublock/assets/ublock/privacy.min.txt +58 -31
  101. package/extensions/ublock/assets/ublock/quick-fixes.min.txt +118 -126
  102. package/extensions/ublock/assets/ublock/unbreak.min.txt +129 -109
  103. package/extensions/ublock/js/background.js +4 -3
  104. package/extensions/ublock/js/benchmarks.js +29 -29
  105. package/extensions/ublock/js/codemirror/ubo-static-filtering.js +1 -0
  106. package/extensions/ublock/js/contextmenu.js +20 -21
  107. package/extensions/ublock/js/devtools.js +137 -3
  108. package/extensions/ublock/js/filtering-context.js +98 -43
  109. package/extensions/ublock/js/logger-ui.js +1 -1
  110. package/extensions/ublock/js/messaging.js +57 -135
  111. package/extensions/ublock/js/pagestore.js +44 -31
  112. package/extensions/ublock/js/redirect-resources.js +14 -4
  113. package/extensions/ublock/js/scriptlet-filtering.js +4 -1
  114. package/extensions/ublock/js/static-filtering-parser.js +107 -37
  115. package/extensions/ublock/js/static-net-filtering.js +514 -250
  116. package/extensions/ublock/js/storage.js +2 -1
  117. package/extensions/ublock/js/traffic.js +8 -4
  118. package/extensions/ublock/js/vapi-background.js +1 -0
  119. package/extensions/ublock/js/vapi-common.js +1 -0
  120. package/extensions/ublock/logger-ui.html +2 -3
  121. package/extensions/ublock/manifest.json +2 -2
  122. package/extensions/ublock/support.html +1 -0
  123. package/extensions/ublock/web_accessible_resources/noop-vast2.xml +1 -0
  124. package/extensions/ublock/web_accessible_resources/noop-vast3.xml +1 -0
  125. package/extensions/ublock/web_accessible_resources/noop-vast4.xml +1 -0
  126. package/package.json +17 -17
  127. package/src/browserless.ts +3 -2
  128. package/src/browsers/index.ts +2 -0
  129. package/src/router.ts +10 -2
  130. package/src/routes/chrome/tests/pdf.spec.ts +24 -12
  131. package/src/routes/chromium/tests/pdf.spec.ts +24 -12
  132. package/src/shared/pdf.http.ts +10 -6
  133. package/static/docs/swagger.json +10 -10
  134. package/static/docs/swagger.min.json +9 -9
  135. package/static/function/client.js +9 -9
  136. package/static/function/index.html +9 -9
  137. /package/extensions/ublock/web_accessible_resources/{noop-vmap1.0.xml → noop-vmap1.xml} +0 -0
@@ -319,7 +319,8 @@ onBroadcast(msg => {
319
319
  cnameIgnoreRootDocument: µbhs.cnameIgnoreRootDocument,
320
320
  cnameMaxTTL: µbhs.cnameMaxTTL,
321
321
  cnameReplayFullURL: µbhs.cnameReplayFullURL,
322
- cnameUncloakProxied: µbhs.cnameUncloakProxied,
322
+ dnsCacheTTL: µbhs.dnsCacheTTL,
323
+ dnsResolveEnabled: µbhs.dnsResolveEnabled,
323
324
  });
324
325
  });
325
326
 
@@ -188,17 +188,20 @@ const onBeforeRootFrameRequest = function(fctxt) {
188
188
  }
189
189
 
190
190
  if ( logger.enabled ) {
191
- fctxt.setFilter(logData);
191
+ fctxt.setRealm('network').setFilter(logData);
192
192
  }
193
193
 
194
194
  // https://github.com/uBlockOrigin/uBlock-issues/issues/760
195
195
  // Redirect non-blocked request?
196
- if ( result !== 1 && trusted === false && pageStore !== null ) {
197
- pageStore.redirectNonBlockedRequest(fctxt);
196
+ if ( trusted === false && pageStore !== null ) {
197
+ if ( result !== 1 ) {
198
+ pageStore.redirectNonBlockedRequest(fctxt);
199
+ }
200
+ pageStore.skipMainDocument(fctxt);
198
201
  }
199
202
 
200
203
  if ( logger.enabled ) {
201
- fctxt.setRealm('network').toLogger();
204
+ fctxt.toLogger();
202
205
  }
203
206
 
204
207
  // Redirected
@@ -680,6 +683,7 @@ const bodyFilterer = (( ) => {
680
683
  const sessions = new Map();
681
684
  const reContentTypeCharset = /charset=['"]?([^'" ]+)/i;
682
685
  const otherValidMimes = new Set([
686
+ 'application/dash+xml',
683
687
  'application/javascript',
684
688
  'application/json',
685
689
  'application/mpegurl',
@@ -958,6 +958,7 @@ vAPI.messaging = {
958
958
 
959
959
  onPortDisconnect: function(port) {
960
960
  this.ports.delete(port.name);
961
+ void browser.runtime.lastError;
961
962
  },
962
963
 
963
964
  // https://developer.mozilla.org/en-US/docs/Mozilla/Add-ons/WebExtensions/API/runtime/Port
@@ -163,6 +163,7 @@ vAPI.webextFlavor = {
163
163
 
164
164
  // This is always true.
165
165
  soup.add('ublock').add('webext');
166
+ soup.add('ipaddress');
166
167
 
167
168
  // Whether this is a dev build.
168
169
  if ( /^\d+\.\d+\.\d+\D/.test(browser.runtime.getManifest().version) ) {
@@ -61,7 +61,7 @@
61
61
  <input type="search" placeholder="logFilterPrompt" spellcheck="false">
62
62
  <span id="filterExprButton" class="button fa-icon expanded" data-i18n-title="loggerRowFiltererBuiltinTip">angle-up</span>
63
63
  <div id="filterExprPicker">
64
- <div><span data-filtex="!" data-i18n="loggerRowFiltererBuiltinNot"></span><span data-filtex="\x1F--\x1F|\x1F<<\x1F|\x1F##" data-i18n="loggerRowFiltererBuiltinBlocked"></span><span data-filtex="\x1F\+\+\x1F|\x1F\*\*\x1F|\x1F#@#" data-i18n="loggerRowFiltererBuiltinAllowed"></span><span data-filtex="[$,](?:csp|permissions|removeparam|redirect-rule|replace|urltransform)=|\x1F\<\<\x1F" data-i18n="loggerRowFiltererBuiltinModified"></span></div>
64
+ <div><span data-filtex="!" data-i18n="loggerRowFiltererBuiltinNot"></span><span data-filtex="\x1F--\x1F|\x1F<<\x1F|\x1F##" data-i18n="loggerRowFiltererBuiltinBlocked"></span><span data-filtex="\x1F\+\+\x1F|\x1F\*\*\x1F|\x1F#@#" data-i18n="loggerRowFiltererBuiltinAllowed"></span><span data-filtex="[$,](?:csp|permissions|removeparam|redirect-rule|replace|urlskip|ur[il]transform)=|\x1F\<\<\x1F" data-i18n="loggerRowFiltererBuiltinModified"></span></div>
65
65
  <div><span data-filtex="!" data-i18n="loggerRowFiltererBuiltinNot"></span>
66
66
  <span style="flex-direction: column;">
67
67
  <div><span data-filtex="\x1F(?:css|(?:inline-)?font)\x1F">css/font</span><span data-filtex="\x1Fimage\x1F">image</span><span data-filtex="\x1Fmedia\x1F">media</span><span data-filtex="\x1F(?:inline-)?script(?:ing)?\x1F">script</span></div>
@@ -72,8 +72,7 @@
72
72
  <div><span data-filtex="!" data-i18n="loggerRowFiltererBuiltinNot"></span><span data-filtex="\x1Fget\x1F">get</span><span data-filtex="\x1Fhead\x1F">head</span><span data-filtex="\x1Fpost\x1F">post</span></div>
73
73
  <div><span data-filtex="!" data-i18n="loggerRowFiltererBuiltinNot" class="on"></span>
74
74
  <span style="flex-direction: column;">
75
- <div><span data-filtex="\bcsp=[^\x1F]+\x1F(?:--|\+\+)\x1F">csp</span><span data-filtex="\bpermissions=[^\x1F]+\x1F(?:--|\+\+)\x1F" class="on">permissions</span><span data-filtex="\bredirect-rule=[^\x1F]+\x1F(?:--|\+\+)\x1F">redirect</span></div>
76
- <div><span data-filtex="\bremoveparam=[^\x1F]+\x1F(?:--|\+\+)\x1F">removeparam</span><span data-filtex="\buritransform=[^\x1F]+\x1F(?:--|\+\+)\x1F">uritransform</span></div>
75
+ <span data-filtex="\bcsp=[^\x1F]+\x1F(?:--|\+\+)\x1F">csp</span><span data-filtex="\bpermissions=[^\x1F]+\x1F(?:--|\+\+)\x1F" class="on">permissions</span><span data-filtex="\bredirect-rule=[^\x1F]+\x1F(?:--|\+\+)\x1F">redirect</span><span data-filtex="\bremoveparam=[^\x1F]+\x1F(?:--|\+\+)\x1F">removeparam</span><span data-filtex="\breplace=[^\x1F]+\x1F(?:--|\+\+)\x1F">replace</span><span data-filtex="\burlskip=[^\x1F]+\x1F(?:--|\+\+)\x1F">urlskip</span>
77
76
  </span>
78
77
  </div>
79
78
  <div id="filterExprCnameOf" style="display:none"><span data-filtex="!" data-i18n="loggerRowFiltererBuiltinNot"></span><span data-filtex="\x1FaliasURL=.">CNAME</span></div>
@@ -89,7 +89,7 @@
89
89
  },
90
90
  "incognito": "split",
91
91
  "manifest_version": 2,
92
- "minimum_chrome_version": "73.0",
92
+ "minimum_chrome_version": "80.0",
93
93
  "name": "uBlock Origin",
94
94
  "options_ui": {
95
95
  "open_in_tab": true,
@@ -111,7 +111,7 @@
111
111
  "storage": {
112
112
  "managed_schema": "managed_storage.json"
113
113
  },
114
- "version": "1.59.0",
114
+ "version": "1.60.0",
115
115
  "web_accessible_resources": [
116
116
  "/web_accessible_resources/*"
117
117
  ]
@@ -93,6 +93,7 @@
93
93
  <option value="nuisance" data-i18n="supportS6Select1Option2"></option>
94
94
  <option value="breakage" data-i18n="supportS6Select1Option5"></option>
95
95
  <option value="privacy" data-i18n="supportS6Select1Option4"></option>
96
+ <option value="badware" data-i18n="supportS6Select1Option7"></option>
96
97
  </select>
97
98
  </p>
98
99
  <p>
@@ -0,0 +1 @@
1
+ <VAST version="2.0"></VAST>
@@ -0,0 +1 @@
1
+ <VAST version="3.0"></VAST>
@@ -0,0 +1 @@
1
+ <VAST version="4.0"></VAST>
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@browserless.io/browserless",
3
- "version": "2.20.1",
3
+ "version": "2.21.0",
4
4
  "license": "SSPL",
5
5
  "description": "The browserless platform",
6
6
  "author": "browserless.io",
@@ -57,12 +57,12 @@
57
57
  "http-proxy": "^1.18.1",
58
58
  "lighthouse": "^12.2.1",
59
59
  "micromatch": "^4.0.8",
60
- "playwright-1.41": "npm:playwright-core@1.41.2",
61
- "playwright-1.42": "npm:playwright-core@1.42.1",
62
60
  "playwright-1.43": "npm:playwright-core@1.43.1",
63
61
  "playwright-1.44": "npm:playwright-core@1.44.1",
64
- "playwright-core": "^1.47.0",
65
- "puppeteer-core": "^23.3.0",
62
+ "playwright-1.45": "npm:playwright-core@1.45.3",
63
+ "playwright-1.46": "npm:playwright-core@1.46.1",
64
+ "playwright-core": "^1.47.2",
65
+ "puppeteer-core": "^23.4.1",
66
66
  "puppeteer-extra": "^3.3.6",
67
67
  "puppeteer-extra-plugin-stealth": "^2.11.2",
68
68
  "queue": "^7.0.0",
@@ -70,41 +70,41 @@
70
70
  "tar-fs": "^3.0.6"
71
71
  },
72
72
  "optionalDependencies": {
73
- "@types/chai": "^4.3.18",
73
+ "@types/chai": "^5.0.0",
74
74
  "@types/debug": "^4.1.12",
75
75
  "@types/gradient-string": "^1.1.6",
76
76
  "@types/http-proxy": "^1.17.15",
77
77
  "@types/micromatch": "^4.0.9",
78
- "@types/mocha": "^10.0.7",
79
- "@types/node": "^22.5.4",
78
+ "@types/mocha": "^10.0.8",
79
+ "@types/node": "^22.7.3",
80
80
  "@types/sinon": "^17.0.3",
81
- "@typescript-eslint/eslint-plugin": "^8.5.0",
82
- "@typescript-eslint/parser": "^8.5.0",
81
+ "@typescript-eslint/eslint-plugin": "^8.7.0",
82
+ "@typescript-eslint/parser": "^8.7.0",
83
83
  "assert": "^2.0.0",
84
84
  "chai": "^5.1.1",
85
85
  "cross-env": "^7.0.3",
86
86
  "env-cmd": "^10.1.0",
87
- "esbuild": "^0.23.1",
87
+ "esbuild": "^0.24.0",
88
88
  "esbuild-plugin-polyfill-node": "^0.3.0",
89
- "eslint": "^9.10.0",
89
+ "eslint": "^9.11.1",
90
90
  "extract-zip": "^2.0.1",
91
91
  "gunzip-maybe": "^1.4.2",
92
92
  "marked": "^14.1.2",
93
93
  "mocha": "^10.7.3",
94
94
  "move-file": "^3.1.0",
95
95
  "prettier": "^3.3.3",
96
- "sinon": "^18.0.1",
96
+ "sinon": "^19.0.2",
97
97
  "ts-node": "^10.9.2",
98
98
  "typescript": "^5.6.2",
99
99
  "typescript-json-schema": "^0.65.1"
100
100
  },
101
101
  "playwrightVersions": {
102
102
  "default": "playwright-core",
103
- "1.45": "playwright-core",
103
+ "1.47": "playwright-core",
104
+ "1.46": "playwright-1.46",
105
+ "1.45": "playwright-1.45",
104
106
  "1.44": "playwright-1.44",
105
- "1.43": "playwright-1.43",
106
- "1.42": "playwright-1.42",
107
- "1.41": "playwright-1.41"
107
+ "1.43": "playwright-1.43"
108
108
  },
109
109
  "eslintConfig": {
110
110
  "root": true,
@@ -103,10 +103,11 @@ export class Browserless extends EventEmitter {
103
103
  this.token = token || new Token(this.config);
104
104
  this.hooks = hooks || new Hooks();
105
105
  this.webhooks = webhooks || new WebHooks(this.config);
106
- this.browserManager =
107
- browserManager || new BrowserManager(this.config, this.hooks);
108
106
  this.monitoring = monitoring || new Monitoring(this.config);
109
107
  this.fileSystem = fileSystem || new FileSystem(this.config);
108
+ this.browserManager =
109
+ browserManager ||
110
+ new BrowserManager(this.config, this.hooks, this.fileSystem);
110
111
  this.limiter =
111
112
  limiter ||
112
113
  new Limiter(
@@ -14,6 +14,7 @@ import {
14
14
  ChromiumCDP,
15
15
  ChromiumPlaywright,
16
16
  Config,
17
+ FileSystem,
17
18
  FirefoxPlaywright,
18
19
  HTTPManagementRoutes,
19
20
  Hooks,
@@ -51,6 +52,7 @@ export class BrowserManager {
51
52
  constructor(
52
53
  protected config: Config,
53
54
  protected hooks: Hooks,
55
+ protected fileSystem: FileSystem,
54
56
  ) {}
55
57
 
56
58
  protected browserIsChrome(b: BrowserInstance) {
package/src/router.ts CHANGED
@@ -70,7 +70,11 @@ export class Router extends EventEmitter {
70
70
  return Promise.resolve();
71
71
  }
72
72
  const logger = new this.logger(route.name, req);
73
- if ('browser' in route && route.browser) {
73
+ if (
74
+ Object.getPrototypeOf(route) instanceof BrowserHTTPRoute &&
75
+ 'browser' in route &&
76
+ route.browser
77
+ ) {
74
78
  const browser = await this.browserManager.getBrowserForRequest(
75
79
  req,
76
80
  route,
@@ -121,7 +125,11 @@ export class Router extends EventEmitter {
121
125
  return Promise.resolve();
122
126
  }
123
127
  const logger = new this.logger(route.name, req);
124
- if ('browser' in route && route.browser) {
128
+ if (
129
+ Object.getPrototypeOf(route) instanceof BrowserWebsocketRoute &&
130
+ 'browser' in route &&
131
+ route.browser
132
+ ) {
125
133
  const browser = await this.browserManager.getBrowserForRequest(
126
134
  req,
127
135
  route,
@@ -31,7 +31,8 @@ describe('/chrome/pdf API', function () {
31
31
  'content-type': 'application/json',
32
32
  },
33
33
  method: 'POST',
34
- }).then((res) => {
34
+ }).then(async (res) => {
35
+ await res.body?.pipeTo(new WritableStream({}));
35
36
  expect(res.headers.get('x-response-code')).to.not.be.undefined;
36
37
  expect(res.headers.get('x-response-url')).to.not.be.undefined;
37
38
  expect(res.headers.get('x-response-ip')).to.not.be.undefined;
@@ -75,7 +76,8 @@ describe('/chrome/pdf API', function () {
75
76
  'content-type': 'application/json',
76
77
  },
77
78
  method: 'POST',
78
- }).then((res) => {
79
+ }).then(async (res) => {
80
+ await res.body?.pipeTo(new WritableStream({}));
79
81
  expect(res.headers.get('content-type')).to.equal('application/pdf');
80
82
  expect(res.status).to.equal(200);
81
83
  });
@@ -99,7 +101,8 @@ describe('/chrome/pdf API', function () {
99
101
  'content-type': 'application/json',
100
102
  },
101
103
  method: 'POST',
102
- }).then((res) => {
104
+ }).then(async (res) => {
105
+ await res.body?.pipeTo(new WritableStream({}));
103
106
  expect(res.headers.get('content-type')).to.equal('application/pdf');
104
107
  expect(res.status).to.equal(200);
105
108
  });
@@ -123,7 +126,8 @@ describe('/chrome/pdf API', function () {
123
126
  'content-type': 'application/json',
124
127
  },
125
128
  method: 'POST',
126
- }).then((res) => {
129
+ }).then(async (res) => {
130
+ await res.body?.pipeTo(new WritableStream({}));
127
131
  expect(res.headers.get('content-type')).to.equal('application/pdf');
128
132
  expect(res.status).to.equal(200);
129
133
  });
@@ -150,7 +154,8 @@ describe('/chrome/pdf API', function () {
150
154
  'content-type': 'application/json',
151
155
  },
152
156
  method: 'POST',
153
- }).then((res) => {
157
+ }).then(async (res) => {
158
+ await res.body?.pipeTo(new WritableStream({}));
154
159
  expect(res.headers.get('content-type')).to.equal('application/pdf');
155
160
  expect(res.status).to.equal(200);
156
161
  });
@@ -172,7 +177,8 @@ describe('/chrome/pdf API', function () {
172
177
  'content-type': 'application/json',
173
178
  },
174
179
  method: 'POST',
175
- }).then((res) => {
180
+ }).then(async (res) => {
181
+ await res.body?.pipeTo(new WritableStream({}));
176
182
  expect(res.headers.get('content-type')).to.equal('application/pdf');
177
183
  expect(res.status).to.equal(200);
178
184
  });
@@ -255,7 +261,8 @@ describe('/chrome/pdf API', function () {
255
261
  'content-type': 'application/json',
256
262
  },
257
263
  method: 'POST',
258
- }).then((res) => {
264
+ }).then(async (res) => {
265
+ await res.body?.pipeTo(new WritableStream({}));
259
266
  expect(res.headers.get('content-type')).to.equal('application/pdf');
260
267
  expect(res.status).to.equal(200);
261
268
  });
@@ -279,7 +286,8 @@ describe('/chrome/pdf API', function () {
279
286
  'content-type': 'application/json',
280
287
  },
281
288
  method: 'POST',
282
- }).then((res) => {
289
+ }).then(async (res) => {
290
+ await res.body?.pipeTo(new WritableStream({}));
283
291
  expect(res.headers.get('content-type')).to.equal('application/pdf');
284
292
  expect(res.status).to.equal(200);
285
293
  });
@@ -300,7 +308,8 @@ describe('/chrome/pdf API', function () {
300
308
  'content-type': 'application/json',
301
309
  },
302
310
  method: 'POST',
303
- }).then((res) => {
311
+ }).then(async (res) => {
312
+ await res.body?.pipeTo(new WritableStream({}));
304
313
  expect(res.headers.get('content-type')).to.equal('application/pdf');
305
314
  expect(res.status).to.equal(200);
306
315
  });
@@ -324,7 +333,8 @@ describe('/chrome/pdf API', function () {
324
333
  'content-type': 'application/json',
325
334
  },
326
335
  method: 'POST',
327
- }).then((res) => {
336
+ }).then(async (res) => {
337
+ await res.body?.pipeTo(new WritableStream({}));
328
338
  expect(res.headers.get('content-type')).to.equal('application/pdf');
329
339
  expect(res.status).to.equal(200);
330
340
  });
@@ -350,7 +360,8 @@ describe('/chrome/pdf API', function () {
350
360
  'content-type': 'application/json',
351
361
  },
352
362
  method: 'POST',
353
- }).then((res) => {
363
+ }).then(async (res) => {
364
+ await res.body?.pipeTo(new WritableStream({}));
354
365
  expect(res.headers.get('content-type')).to.equal('application/pdf');
355
366
  expect(res.status).to.equal(200);
356
367
  });
@@ -368,7 +379,8 @@ describe('/chrome/pdf API', function () {
368
379
  'content-type': 'application/json',
369
380
  },
370
381
  method: 'POST',
371
- }).then((res) => {
382
+ }).then(async (res) => {
383
+ await res.body?.pipeTo(new WritableStream({}));
372
384
  expect(res.headers.get('x-response-code')).to.not.be.undefined;
373
385
  expect(res.headers.get('x-response-url')).to.not.be.undefined;
374
386
  expect(res.headers.get('x-response-ip')).to.not.be.undefined;
@@ -31,7 +31,8 @@ describe('/chromium/pdf API', function () {
31
31
  'content-type': 'application/json; charset=utf-8',
32
32
  },
33
33
  method: 'POST',
34
- }).then((res) => {
34
+ }).then(async (res) => {
35
+ await res.body?.pipeTo(new WritableStream({}));
35
36
  expect(res.headers.get('x-response-code')).to.not.be.undefined;
36
37
  expect(res.headers.get('x-response-url')).to.not.be.undefined;
37
38
  expect(res.headers.get('x-response-ip')).to.not.be.undefined;
@@ -75,7 +76,8 @@ describe('/chromium/pdf API', function () {
75
76
  'content-type': 'application/json',
76
77
  },
77
78
  method: 'POST',
78
- }).then((res) => {
79
+ }).then(async (res) => {
80
+ await res.body?.pipeTo(new WritableStream({}));
79
81
  expect(res.headers.get('content-type')).to.equal('application/pdf');
80
82
  expect(res.status).to.equal(200);
81
83
  });
@@ -99,7 +101,8 @@ describe('/chromium/pdf API', function () {
99
101
  'content-type': 'application/json',
100
102
  },
101
103
  method: 'POST',
102
- }).then((res) => {
104
+ }).then(async (res) => {
105
+ await res.body?.pipeTo(new WritableStream({}));
103
106
  expect(res.headers.get('content-type')).to.equal('application/pdf');
104
107
  expect(res.status).to.equal(200);
105
108
  });
@@ -123,7 +126,8 @@ describe('/chromium/pdf API', function () {
123
126
  'content-type': 'application/json',
124
127
  },
125
128
  method: 'POST',
126
- }).then((res) => {
129
+ }).then(async (res) => {
130
+ await res.body?.pipeTo(new WritableStream({}));
127
131
  expect(res.headers.get('content-type')).to.equal('application/pdf');
128
132
  expect(res.status).to.equal(200);
129
133
  });
@@ -150,7 +154,8 @@ describe('/chromium/pdf API', function () {
150
154
  'content-type': 'application/json',
151
155
  },
152
156
  method: 'POST',
153
- }).then((res) => {
157
+ }).then(async (res) => {
158
+ await res.body?.pipeTo(new WritableStream({}));
154
159
  expect(res.headers.get('content-type')).to.equal('application/pdf');
155
160
  expect(res.status).to.equal(200);
156
161
  });
@@ -172,7 +177,8 @@ describe('/chromium/pdf API', function () {
172
177
  'content-type': 'application/json',
173
178
  },
174
179
  method: 'POST',
175
- }).then((res) => {
180
+ }).then(async (res) => {
181
+ await res.body?.pipeTo(new WritableStream({}));
176
182
  expect(res.headers.get('content-type')).to.equal('application/pdf');
177
183
  expect(res.status).to.equal(200);
178
184
  });
@@ -255,7 +261,8 @@ describe('/chromium/pdf API', function () {
255
261
  'content-type': 'application/json',
256
262
  },
257
263
  method: 'POST',
258
- }).then((res) => {
264
+ }).then(async (res) => {
265
+ await res.body?.pipeTo(new WritableStream({}));
259
266
  expect(res.headers.get('content-type')).to.equal('application/pdf');
260
267
  expect(res.status).to.equal(200);
261
268
  });
@@ -279,7 +286,8 @@ describe('/chromium/pdf API', function () {
279
286
  'content-type': 'application/json',
280
287
  },
281
288
  method: 'POST',
282
- }).then((res) => {
289
+ }).then(async (res) => {
290
+ await res.body?.pipeTo(new WritableStream({}));
283
291
  expect(res.headers.get('content-type')).to.equal('application/pdf');
284
292
  expect(res.status).to.equal(200);
285
293
  });
@@ -300,7 +308,8 @@ describe('/chromium/pdf API', function () {
300
308
  'content-type': 'application/json',
301
309
  },
302
310
  method: 'POST',
303
- }).then((res) => {
311
+ }).then(async (res) => {
312
+ await res.body?.pipeTo(new WritableStream({}));
304
313
  expect(res.headers.get('content-type')).to.equal('application/pdf');
305
314
  expect(res.status).to.equal(200);
306
315
  });
@@ -324,7 +333,8 @@ describe('/chromium/pdf API', function () {
324
333
  'content-type': 'application/json',
325
334
  },
326
335
  method: 'POST',
327
- }).then((res) => {
336
+ }).then(async (res) => {
337
+ await res.body?.pipeTo(new WritableStream({}));
328
338
  expect(res.headers.get('content-type')).to.equal('application/pdf');
329
339
  expect(res.status).to.equal(200);
330
340
  });
@@ -350,7 +360,8 @@ describe('/chromium/pdf API', function () {
350
360
  'content-type': 'application/json',
351
361
  },
352
362
  method: 'POST',
353
- }).then((res) => {
363
+ }).then(async (res) => {
364
+ await res.body?.pipeTo(new WritableStream({}));
354
365
  expect(res.headers.get('content-type')).to.equal('application/pdf');
355
366
  expect(res.status).to.equal(200);
356
367
  });
@@ -368,7 +379,8 @@ describe('/chromium/pdf API', function () {
368
379
  'content-type': 'application/json',
369
380
  },
370
381
  method: 'POST',
371
- }).then((res) => {
382
+ }).then(async (res) => {
383
+ await res.body?.pipeTo(new WritableStream({}));
372
384
  expect(res.headers.get('x-response-code')).to.not.be.undefined;
373
385
  expect(res.headers.get('x-response-url')).to.not.be.undefined;
374
386
  expect(res.headers.get('x-response-ip')).to.not.be.undefined;
@@ -29,7 +29,6 @@ import {
29
29
  } from '@browserless.io/browserless';
30
30
  import { Page } from 'puppeteer-core';
31
31
  import { ServerResponse } from 'http';
32
- import { Stream } from 'stream';
33
32
 
34
33
  export interface BodySchema {
35
34
  addScriptTag?: Array<Parameters<Page['addScriptTag']>[0]>;
@@ -237,11 +236,16 @@ export default class ChromiumPDFPostRoute extends BrowserHTTPRoute {
237
236
  }
238
237
  }
239
238
 
240
- const pdfBuffer = await page.pdf(options);
241
- const readStream = new Stream.PassThrough();
242
- readStream.end(pdfBuffer);
243
-
244
- await new Promise((r) => readStream.pipe(res).once('close', r));
239
+ const pdfStream = await page.createPDFStream(options);
240
+ const writableStream = new WritableStream({
241
+ write(chunk) {
242
+ res.write(chunk);
243
+ },
244
+ close() {
245
+ res.end();
246
+ },
247
+ });
248
+ await pdfStream.pipeTo(writableStream);
245
249
 
246
250
  page.close().catch(noop);
247
251