patchright-core 1.58.2 → 1.59.1

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 (285) hide show
  1. package/ThirdPartyNotices.txt +126 -650
  2. package/browsers.json +16 -14
  3. package/lib/bootstrap.js +77 -0
  4. package/lib/cli/browserActions.js +308 -0
  5. package/lib/cli/driver.js +3 -2
  6. package/lib/cli/installActions.js +171 -0
  7. package/lib/cli/program.js +47 -411
  8. package/lib/client/android.js +4 -4
  9. package/lib/client/api.js +3 -3
  10. package/lib/client/browser.js +8 -0
  11. package/lib/client/browserContext.js +22 -61
  12. package/lib/client/browserType.js +19 -51
  13. package/lib/client/cdpSession.js +6 -2
  14. package/lib/client/channelOwner.js +1 -1
  15. package/lib/client/clientHelper.js +2 -1
  16. package/lib/client/clock.js +0 -1
  17. package/lib/client/{webSocket.js → connect.js} +57 -7
  18. package/lib/client/connection.js +8 -4
  19. package/lib/client/consoleMessage.js +3 -0
  20. package/lib/client/debugger.js +57 -0
  21. package/lib/client/dialog.js +8 -1
  22. package/lib/client/disposable.js +76 -0
  23. package/lib/client/electron.js +1 -0
  24. package/lib/client/elementHandle.js +1 -4
  25. package/lib/client/events.js +3 -3
  26. package/lib/client/fetch.js +0 -1
  27. package/lib/client/frame.js +10 -23
  28. package/lib/client/harRouter.js +13 -1
  29. package/lib/client/jsHandle.js +4 -8
  30. package/lib/client/locator.js +13 -44
  31. package/lib/client/network.js +15 -16
  32. package/lib/client/page.js +41 -75
  33. package/lib/client/platform.js +0 -3
  34. package/lib/client/screencast.js +88 -0
  35. package/lib/client/selectors.js +3 -1
  36. package/lib/client/tracing.js +11 -5
  37. package/lib/client/video.js +13 -20
  38. package/lib/client/worker.js +6 -6
  39. package/lib/generated/bindingsControllerSource.js +1 -1
  40. package/lib/generated/clockSource.js +1 -1
  41. package/lib/generated/injectedScriptSource.js +1 -1
  42. package/lib/generated/pollingRecorderSource.js +1 -1
  43. package/lib/generated/storageScriptSource.js +1 -1
  44. package/lib/generated/utilityScriptSource.js +1 -1
  45. package/lib/mcpBundle.js +0 -6
  46. package/lib/mcpBundleImpl.js +91 -0
  47. package/lib/protocol/validator.js +224 -138
  48. package/lib/protocol/validatorPrimitives.js +1 -1
  49. package/lib/remote/playwrightConnection.js +10 -8
  50. package/lib/remote/playwrightPipeServer.js +100 -0
  51. package/lib/remote/playwrightServer.js +13 -8
  52. package/lib/remote/playwrightWebSocketServer.js +73 -0
  53. package/lib/remote/serverTransport.js +96 -0
  54. package/lib/server/android/android.js +2 -2
  55. package/lib/server/bidi/bidiBrowser.js +30 -8
  56. package/lib/server/bidi/bidiChromium.js +18 -5
  57. package/lib/server/bidi/bidiNetworkManager.js +39 -11
  58. package/lib/server/bidi/bidiPage.js +31 -15
  59. package/lib/server/bidi/third_party/firefoxPrefs.js +3 -1
  60. package/lib/server/browser.js +84 -21
  61. package/lib/server/browserContext.js +110 -58
  62. package/lib/server/browserType.js +14 -12
  63. package/lib/server/chromium/chromium.js +15 -12
  64. package/lib/server/chromium/chromiumSwitches.js +14 -2
  65. package/lib/server/chromium/crBrowser.js +20 -17
  66. package/lib/server/chromium/crCoverage.js +1 -13
  67. package/lib/server/chromium/crDevTools.js +1 -0
  68. package/lib/server/chromium/crNetworkManager.js +12 -267
  69. package/lib/server/chromium/crPage.js +67 -199
  70. package/lib/server/chromium/crServiceWorker.js +7 -14
  71. package/lib/server/clock.js +33 -41
  72. package/lib/server/console.js +5 -1
  73. package/lib/server/debugController.js +12 -6
  74. package/lib/server/debugger.js +40 -47
  75. package/lib/server/deviceDescriptorsSource.json +137 -137
  76. package/lib/server/dispatchers/browserContextDispatcher.js +29 -30
  77. package/lib/server/dispatchers/browserDispatcher.js +11 -5
  78. package/lib/server/dispatchers/browserTypeDispatcher.js +7 -0
  79. package/lib/server/dispatchers/cdpSessionDispatcher.js +4 -1
  80. package/lib/server/dispatchers/debuggerDispatcher.js +84 -0
  81. package/lib/server/dispatchers/dispatcher.js +1 -1
  82. package/lib/server/dispatchers/disposableDispatcher.js +39 -0
  83. package/lib/server/dispatchers/electronDispatcher.js +2 -1
  84. package/lib/server/dispatchers/frameDispatcher.js +6 -6
  85. package/lib/server/dispatchers/jsHandleDispatcher.js +2 -2
  86. package/lib/server/dispatchers/localUtilsDispatcher.js +37 -1
  87. package/lib/server/dispatchers/networkDispatchers.js +6 -5
  88. package/lib/server/dispatchers/pageDispatcher.js +101 -38
  89. package/lib/server/dispatchers/webSocketRouteDispatcher.js +4 -5
  90. package/lib/server/disposable.js +41 -0
  91. package/lib/server/dom.js +44 -26
  92. package/lib/server/download.js +3 -2
  93. package/lib/server/electron/electron.js +12 -7
  94. package/lib/server/firefox/ffBrowser.js +9 -19
  95. package/lib/server/firefox/ffInput.js +21 -5
  96. package/lib/server/firefox/ffNetworkManager.js +2 -2
  97. package/lib/server/firefox/ffPage.js +24 -27
  98. package/lib/server/frameSelectors.js +5 -172
  99. package/lib/server/frames.js +234 -687
  100. package/lib/server/har/harRecorder.js +2 -2
  101. package/lib/server/har/harTracer.js +5 -4
  102. package/lib/server/input.js +49 -4
  103. package/lib/server/instrumentation.js +5 -0
  104. package/lib/server/javascript.js +6 -26
  105. package/lib/server/launchApp.js +1 -3
  106. package/lib/server/localUtils.js +6 -6
  107. package/lib/server/network.js +9 -8
  108. package/lib/server/overlay.js +138 -0
  109. package/lib/server/page.js +157 -105
  110. package/lib/server/progress.js +6 -0
  111. package/lib/server/recorder/recorderApp.js +9 -8
  112. package/lib/server/recorder.js +76 -40
  113. package/lib/server/registry/index.js +55 -82
  114. package/lib/server/registry/nativeDeps.js +1 -0
  115. package/lib/server/screencast.js +90 -143
  116. package/lib/server/screenshotter.js +0 -6
  117. package/lib/server/trace/recorder/snapshotter.js +8 -17
  118. package/lib/server/trace/recorder/snapshotterInjected.js +82 -20
  119. package/lib/server/trace/recorder/tracing.js +87 -44
  120. package/lib/server/trace/viewer/traceViewer.js +3 -4
  121. package/lib/server/usKeyboardLayout.js +7 -0
  122. package/lib/server/utils/comparators.js +1 -1
  123. package/lib/server/utils/disposable.js +32 -0
  124. package/lib/server/utils/eventsHelper.js +3 -1
  125. package/lib/server/utils/fileUtils.js +16 -2
  126. package/lib/server/utils/happyEyeballs.js +15 -12
  127. package/lib/server/utils/hostPlatform.js +0 -15
  128. package/lib/server/utils/httpServer.js +5 -3
  129. package/lib/server/utils/network.js +2 -1
  130. package/lib/server/utils/nodePlatform.js +0 -6
  131. package/lib/server/utils/processLauncher.js +6 -5
  132. package/lib/server/utils/zipFile.js +2 -2
  133. package/lib/server/videoRecorder.js +82 -12
  134. package/lib/server/webkit/wkBrowser.js +1 -6
  135. package/lib/server/webkit/wkPage.js +27 -25
  136. package/lib/server/webkit/wkWorkers.js +2 -1
  137. package/lib/serverRegistry.js +156 -0
  138. package/lib/tools/backend/browserBackend.js +79 -0
  139. package/lib/tools/backend/common.js +63 -0
  140. package/lib/tools/backend/config.js +41 -0
  141. package/lib/tools/backend/console.js +66 -0
  142. package/lib/tools/backend/context.js +296 -0
  143. package/lib/tools/backend/cookies.js +152 -0
  144. package/lib/tools/backend/devtools.js +69 -0
  145. package/lib/tools/backend/dialogs.js +59 -0
  146. package/lib/tools/backend/evaluate.js +64 -0
  147. package/lib/tools/backend/files.js +60 -0
  148. package/lib/tools/backend/form.js +64 -0
  149. package/lib/tools/backend/keyboard.js +155 -0
  150. package/lib/tools/backend/logFile.js +95 -0
  151. package/lib/tools/backend/mouse.js +168 -0
  152. package/lib/tools/backend/navigate.js +106 -0
  153. package/lib/tools/backend/network.js +135 -0
  154. package/lib/tools/backend/pdf.js +48 -0
  155. package/lib/tools/backend/response.js +305 -0
  156. package/lib/tools/backend/route.js +140 -0
  157. package/lib/tools/backend/runCode.js +77 -0
  158. package/lib/tools/backend/screenshot.js +88 -0
  159. package/lib/tools/backend/sessionLog.js +74 -0
  160. package/lib/tools/backend/snapshot.js +208 -0
  161. package/lib/tools/backend/storage.js +68 -0
  162. package/lib/tools/backend/tab.js +445 -0
  163. package/lib/tools/backend/tabs.js +67 -0
  164. package/lib/tools/backend/tool.js +47 -0
  165. package/lib/tools/backend/tools.js +102 -0
  166. package/lib/tools/backend/tracing.js +78 -0
  167. package/lib/tools/backend/utils.js +83 -0
  168. package/lib/tools/backend/verify.js +151 -0
  169. package/lib/tools/backend/video.js +98 -0
  170. package/lib/tools/backend/wait.js +63 -0
  171. package/lib/tools/backend/webstorage.js +223 -0
  172. package/lib/tools/cli-client/cli.js +6 -0
  173. package/lib/tools/cli-client/help.json +399 -0
  174. package/lib/tools/cli-client/minimist.js +128 -0
  175. package/lib/tools/cli-client/program.js +350 -0
  176. package/lib/tools/cli-client/registry.js +176 -0
  177. package/lib/tools/cli-client/session.js +289 -0
  178. package/lib/tools/cli-client/skill/SKILL.md +328 -0
  179. package/lib/tools/cli-client/skill/references/element-attributes.md +23 -0
  180. package/lib/tools/cli-client/skill/references/playwright-tests.md +39 -0
  181. package/lib/tools/cli-client/skill/references/request-mocking.md +87 -0
  182. package/lib/tools/cli-client/skill/references/running-code.md +231 -0
  183. package/lib/tools/cli-client/skill/references/session-management.md +169 -0
  184. package/lib/tools/cli-client/skill/references/storage-state.md +275 -0
  185. package/lib/tools/cli-client/skill/references/test-generation.md +88 -0
  186. package/lib/tools/cli-client/skill/references/tracing.md +139 -0
  187. package/lib/tools/cli-client/skill/references/video-recording.md +143 -0
  188. package/lib/tools/cli-daemon/command.js +73 -0
  189. package/lib/tools/cli-daemon/commands.js +956 -0
  190. package/lib/tools/cli-daemon/daemon.js +157 -0
  191. package/lib/tools/cli-daemon/helpGenerator.js +177 -0
  192. package/lib/tools/cli-daemon/program.js +129 -0
  193. package/lib/tools/dashboard/appIcon.png +0 -0
  194. package/lib/tools/dashboard/dashboardApp.js +284 -0
  195. package/lib/tools/dashboard/dashboardController.js +296 -0
  196. package/lib/tools/exports.js +60 -0
  197. package/lib/tools/mcp/browserFactory.js +233 -0
  198. package/lib/tools/mcp/cdpRelay.js +352 -0
  199. package/lib/tools/mcp/cli-stub.js +7 -0
  200. package/lib/tools/mcp/config.d.js +16 -0
  201. package/lib/tools/mcp/config.js +446 -0
  202. package/lib/tools/mcp/configIni.js +189 -0
  203. package/lib/tools/mcp/extensionContextFactory.js +55 -0
  204. package/lib/tools/mcp/index.js +62 -0
  205. package/lib/tools/mcp/log.js +35 -0
  206. package/lib/tools/mcp/program.js +107 -0
  207. package/lib/tools/mcp/protocol.js +28 -0
  208. package/lib/tools/mcp/watchdog.js +44 -0
  209. package/lib/tools/trace/SKILL.md +171 -0
  210. package/lib/{server/trace/viewer/traceParser.js → tools/trace/installSkill.js} +15 -39
  211. package/lib/tools/trace/traceActions.js +142 -0
  212. package/lib/tools/trace/traceAttachments.js +69 -0
  213. package/lib/tools/trace/traceCli.js +87 -0
  214. package/lib/tools/trace/traceConsole.js +97 -0
  215. package/lib/tools/trace/traceErrors.js +55 -0
  216. package/lib/tools/trace/traceOpen.js +69 -0
  217. package/lib/tools/trace/traceParser.js +96 -0
  218. package/lib/tools/trace/traceRequests.js +182 -0
  219. package/lib/tools/trace/traceScreenshot.js +68 -0
  220. package/lib/tools/trace/traceSnapshot.js +149 -0
  221. package/lib/tools/trace/traceUtils.js +153 -0
  222. package/lib/tools/utils/connect.js +32 -0
  223. package/lib/tools/utils/mcp/http.js +152 -0
  224. package/lib/tools/utils/mcp/server.js +230 -0
  225. package/lib/tools/utils/mcp/tool.js +47 -0
  226. package/lib/tools/utils/socketConnection.js +108 -0
  227. package/lib/utils/isomorphic/formatUtils.js +64 -0
  228. package/lib/utils/isomorphic/jsonSchema.js +89 -0
  229. package/lib/utils/isomorphic/mimeType.js +7 -2
  230. package/lib/utils/isomorphic/protocolFormatter.js +2 -2
  231. package/lib/utils/isomorphic/protocolMetainfo.js +127 -106
  232. package/lib/utils/isomorphic/stringUtils.js +3 -3
  233. package/lib/utils/isomorphic/timeoutRunner.js +3 -3
  234. package/lib/utils/isomorphic/trace/snapshotRenderer.js +35 -42
  235. package/lib/utils/isomorphic/trace/traceLoader.js +15 -14
  236. package/lib/utils/isomorphic/trace/traceModel.js +3 -2
  237. package/lib/utils/isomorphic/trace/traceModernizer.js +1 -0
  238. package/lib/utils/isomorphic/urlMatch.js +54 -1
  239. package/lib/utils/isomorphic/utilityScriptSerializers.js +11 -0
  240. package/lib/utils.js +6 -2
  241. package/lib/utilsBundle.js +3 -21
  242. package/lib/utilsBundleImpl/index.js +132 -133
  243. package/lib/vite/dashboard/assets/index-BAOybkp8.js +50 -0
  244. package/lib/vite/dashboard/assets/index-CZAYOG76.css +1 -0
  245. package/lib/vite/dashboard/index.html +28 -0
  246. package/lib/vite/htmlReport/index.html +2 -70
  247. package/lib/vite/htmlReport/report.css +1 -0
  248. package/lib/vite/htmlReport/report.js +72 -0
  249. package/lib/vite/recorder/assets/{codeMirrorModule-CFUTFUO7.js → codeMirrorModule-C8KMvO9L.js} +20 -20
  250. package/lib/vite/recorder/assets/index-CqAYX1I3.js +193 -0
  251. package/lib/vite/recorder/index.html +1 -1
  252. package/lib/vite/traceViewer/assets/{codeMirrorModule-BVA4h_ZY.js → codeMirrorModule-DS0FLvoc.js} +20 -20
  253. package/lib/vite/traceViewer/assets/defaultSettingsView-GTWI-W_B.js +262 -0
  254. package/lib/vite/traceViewer/defaultSettingsView.B4dS75f0.css +1 -0
  255. package/lib/vite/traceViewer/{index.BtyWtaE-.js → index.C5466mMT.js} +1 -1
  256. package/lib/vite/traceViewer/{index.BVu7tZDe.css → index.CzXZzn5A.css} +1 -1
  257. package/lib/vite/traceViewer/index.html +4 -4
  258. package/lib/vite/traceViewer/sw.bundle.js +4 -4
  259. package/lib/vite/traceViewer/uiMode.Vipi55dB.js +6 -0
  260. package/lib/vite/traceViewer/uiMode.html +3 -3
  261. package/lib/zipBundleImpl.js +2 -2
  262. package/lib/zodBundle.js +39 -0
  263. package/lib/zodBundleImpl.js +40 -0
  264. package/package.json +6 -1
  265. package/types/protocol.d.ts +947 -51
  266. package/types/types.d.ts +854 -74
  267. package/lib/client/pageAgent.js +0 -64
  268. package/lib/mcpBundleImpl/index.js +0 -147
  269. package/lib/server/agent/actionRunner.js +0 -335
  270. package/lib/server/agent/actions.js +0 -128
  271. package/lib/server/agent/codegen.js +0 -111
  272. package/lib/server/agent/context.js +0 -150
  273. package/lib/server/agent/expectTools.js +0 -156
  274. package/lib/server/agent/pageAgent.js +0 -204
  275. package/lib/server/agent/performTools.js +0 -262
  276. package/lib/server/agent/tool.js +0 -109
  277. package/lib/server/dispatchers/pageAgentDispatcher.js +0 -96
  278. package/lib/server/pageBinding.js +0 -87
  279. package/lib/utils/isomorphic/oldUtilityScriptSerializers.js +0 -248
  280. package/lib/vite/recorder/assets/index-CVkBxsGf.js +0 -193
  281. package/lib/vite/traceViewer/assets/defaultSettingsView-CjfmcdOz.js +0 -266
  282. package/lib/vite/traceViewer/defaultSettingsView.7ch9cixO.css +0 -1
  283. package/lib/vite/traceViewer/uiMode.fyrXARf2.js +0 -5
  284. /package/lib/{server/utils → utils/isomorphic}/imageUtils.js +0 -0
  285. /package/lib/utils/isomorphic/{traceUtils.js → trace/traceUtils.js} +0 -0
@@ -32,11 +32,12 @@ __export(page_exports, {
32
32
  Page: () => Page,
33
33
  PageBinding: () => PageBinding,
34
34
  Worker: () => Worker,
35
- WorkerEvent: () => WorkerEvent
35
+ WorkerEvent: () => WorkerEvent,
36
+ ariaSnapshotForFrame: () => ariaSnapshotForFrame
36
37
  });
37
38
  module.exports = __toCommonJS(page_exports);
38
- var import_pageBinding = require("./pageBinding");
39
39
  var import_browserContext = require("./browserContext");
40
+ var import_disposable = require("./disposable");
40
41
  var import_console = require("./console");
41
42
  var import_errors = require("./errors");
42
43
  var import_fileChooser = require("./fileChooser");
@@ -54,6 +55,9 @@ var import_selectorParser = require("../utils/isomorphic/selectorParser");
54
55
  var import_manualPromise = require("../utils/isomorphic/manualPromise");
55
56
  var import_utilityScriptSerializers = require("../utils/isomorphic/utilityScriptSerializers");
56
57
  var import_callLog = require("./callLog");
58
+ var rawBindingsControllerSource = __toESM(require("../generated/bindingsControllerSource"));
59
+ var import_overlay = require("./overlay");
60
+ var import_dom = require("./dom");
57
61
  var import_screencast = require("./screencast");
58
62
  const PageEvent = {
59
63
  Close: "close",
@@ -65,16 +69,15 @@ const PageEvent = {
65
69
  FrameDetached: "framedetached",
66
70
  InternalFrameNavigatedToNewDocument: "internalframenavigatedtonewdocument",
67
71
  LocatorHandlerTriggered: "locatorhandlertriggered",
68
- ScreencastFrame: "screencastframe",
69
- Video: "video",
70
72
  WebSocket: "websocket",
71
73
  Worker: "worker"
72
74
  };
75
+ const navigationMarkSymbol = Symbol("navigationMark");
73
76
  class Page extends import_instrumentation.SdkObject {
74
77
  constructor(delegate, browserContext) {
75
78
  super(browserContext, "page");
76
79
  this._closedState = "open";
77
- this._closedPromise = new import_manualPromise.ManualPromise();
80
+ this.closedPromise = new import_manualPromise.ManualPromise();
78
81
  this._initializedPromise = new import_manualPromise.ManualPromise();
79
82
  this._consoleMessages = [];
80
83
  this._pageErrors = [];
@@ -86,7 +89,6 @@ class Page extends import_instrumentation.SdkObject {
86
89
  this.initScripts = [];
87
90
  this._workers = /* @__PURE__ */ new Map();
88
91
  this.requestInterceptors = [];
89
- this.video = null;
90
92
  this._locatorHandlers = /* @__PURE__ */ new Map();
91
93
  this._lastLocatorHandlerUid = 0;
92
94
  this._locatorHandlerRunningCounter = 0;
@@ -99,6 +101,7 @@ class Page extends import_instrumentation.SdkObject {
99
101
  this.touchscreen = new input.Touchscreen(delegate.rawTouchscreen, this);
100
102
  this.screenshotter = new import_screenshotter.Screenshotter(this);
101
103
  this.frameManager = new frames.FrameManager(this);
104
+ this.overlay = new import_overlay.Overlay(this);
102
105
  this.screencast = new import_screencast.Screencast(this);
103
106
  if (delegate.pdf)
104
107
  this.pdf = delegate.pdf.bind(delegate);
@@ -159,17 +162,20 @@ class Page extends import_instrumentation.SdkObject {
159
162
  }
160
163
  _didClose() {
161
164
  this.frameManager.dispose();
162
- this.screencast.stopFrameThrottler();
165
+ this.screencast.dispose();
166
+ this.overlay.dispose();
163
167
  (0, import_utils.assert)(this._closedState !== "closed", "Page closed twice");
164
168
  this._closedState = "closed";
165
169
  this.emit(Page.Events.Close);
166
- this._closedPromise.resolve();
170
+ this.browserContext.emit(import_browserContext.BrowserContext.Events.PageClosed, this);
171
+ this.closedPromise.resolve();
167
172
  this.instrumentation.onPageClose(this);
168
173
  this.openScope.close(new import_errors.TargetClosedError(this.closeReason()));
169
174
  }
170
175
  _didCrash() {
171
176
  this.frameManager.dispose();
172
- this.screencast.stopFrameThrottler();
177
+ this.screencast.dispose();
178
+ this.overlay.dispose();
173
179
  this.emit(Page.Events.Crash);
174
180
  this._crashed = true;
175
181
  this.instrumentation.onPageClose(this);
@@ -203,16 +209,25 @@ class Page extends import_instrumentation.SdkObject {
203
209
  throw new Error(`Function "${name}" has been already registered`);
204
210
  if (this.browserContext._pageBindings.has(name))
205
211
  throw new Error(`Function "${name}" has been already registered in the browser context`);
206
- const binding = new PageBinding(name, playwrightBinding, needsHandle);
212
+ await progress.race(this.browserContext.exposePlaywrightBindingIfNeeded());
213
+ const binding = new PageBinding(this, name, playwrightBinding, needsHandle);
207
214
  this._pageBindings.set(name, binding);
208
- await this.delegate.exposeBinding(binding);
209
- }
210
- async removeExposedBindings(bindings) {
211
- for (const key of this._pageBindings.keys()) {
212
- if (!key.startsWith("__pw"))
213
- this._pageBindings.delete(key);
215
+ try {
216
+ await progress.race(this.delegate.addInitScript(binding.initScript));
217
+ await progress.race(this.safeNonStallingEvaluateInAllFrames(binding.initScript.source, "main"));
218
+ return binding;
219
+ } catch (error) {
220
+ this._pageBindings.delete(name);
221
+ throw error;
214
222
  }
215
- await this.delegate.removeExposedBindings();
223
+ }
224
+ async removeExposedBinding(binding) {
225
+ if (this._pageBindings.get(binding.name) !== binding)
226
+ return;
227
+ this._pageBindings.delete(binding.name);
228
+ await this.delegate.removeInitScripts([binding.initScript]);
229
+ const cleanup = `{ ${binding.cleanupScript} };`;
230
+ await this.safeNonStallingEvaluateInAllFrames(cleanup, "main");
216
231
  }
217
232
  async setExtraHTTPHeaders(progress, headers) {
218
233
  const oldHeaders = this._extraHTTPHeaders;
@@ -241,8 +256,8 @@ class Page extends import_instrumentation.SdkObject {
241
256
  return;
242
257
  await PageBinding.dispatch(this, payload, context);
243
258
  }
244
- addConsoleMessage(worker, type, args, location, text) {
245
- const message = new import_console.ConsoleMessage(this, worker, type, text, args, location);
259
+ addConsoleMessage(worker, type, args, location, text, timestamp) {
260
+ const message = new import_console.ConsoleMessage(this, worker, type, text, args, location, timestamp);
246
261
  const intercepted = this.frameManager.interceptConsoleMessage(message);
247
262
  if (intercepted) {
248
263
  args.forEach((arg) => arg.dispose());
@@ -253,8 +268,14 @@ class Page extends import_instrumentation.SdkObject {
253
268
  if (this._initialized)
254
269
  this.emitOnContext(import_browserContext.BrowserContext.Events.Console, message);
255
270
  }
256
- consoleMessages() {
257
- return this._consoleMessages;
271
+ clearConsoleMessages() {
272
+ this._consoleMessages.length = 0;
273
+ }
274
+ consoleMessages(filter) {
275
+ if (filter === "all")
276
+ return this._consoleMessages;
277
+ const marked = this._consoleMessages.findLastIndex((m) => m[navigationMarkSymbol]);
278
+ return marked === -1 ? this._consoleMessages : this._consoleMessages.slice(marked + 1);
258
279
  }
259
280
  addPageError(pageError) {
260
281
  this._pageErrors.push(pageError);
@@ -262,8 +283,14 @@ class Page extends import_instrumentation.SdkObject {
262
283
  if (this._initialized)
263
284
  this.emitOnContext(import_browserContext.BrowserContext.Events.PageError, pageError, this);
264
285
  }
265
- pageErrors() {
266
- return this._pageErrors;
286
+ clearPageErrors() {
287
+ this._pageErrors.length = 0;
288
+ }
289
+ pageErrors(filter) {
290
+ if (filter === "all")
291
+ return this._pageErrors;
292
+ const marked = this._pageErrors.findLastIndex((e) => e[navigationMarkSymbol]);
293
+ return marked === -1 ? this._pageErrors : this._pageErrors.slice(marked + 1);
267
294
  }
268
295
  async reload(progress, options) {
269
296
  return this.mainFrame().raceNavigationAction(progress, async () => {
@@ -440,21 +467,21 @@ class Page extends import_instrumentation.SdkObject {
440
467
  async bringToFront() {
441
468
  await this.delegate.bringToFront();
442
469
  }
443
- async addInitScript(progress, source) {
444
- const initScript = new InitScript(source);
470
+ async addInitScript(source) {
471
+ const initScript = new InitScript(this, source);
445
472
  this.initScripts.push(initScript);
446
473
  try {
447
- await progress.race(this.delegate.addInitScript(initScript));
474
+ await this.delegate.addInitScript(initScript);
448
475
  } catch (error) {
449
- this.removeInitScripts([initScript]).catch(() => {
476
+ initScript.dispose().catch(() => {
450
477
  });
451
478
  throw error;
452
479
  }
453
480
  return initScript;
454
481
  }
455
- async removeInitScripts(initScripts) {
456
- this.initScripts.splice(0, this.initScripts.length);
457
- await this.delegate.removeInitScripts();
482
+ async removeInitScript(initScript) {
483
+ this.initScripts = this.initScripts.filter((script) => initScript !== script);
484
+ await this.delegate.removeInitScripts([initScript]);
458
485
  }
459
486
  needsRequestInterception() {
460
487
  return this.requestInterceptors.length > 0 || this.browserContext.requestInterceptors.length > 0;
@@ -570,13 +597,15 @@ class Page extends import_instrumentation.SdkObject {
570
597
  if (options.reason)
571
598
  this._closeReason = options.reason;
572
599
  const runBeforeUnload = !!options.runBeforeUnload;
600
+ if (!runBeforeUnload)
601
+ await this.screencast.handlePageOrContextClose();
573
602
  if (this._closedState !== "closing") {
574
603
  if (!runBeforeUnload)
575
604
  this._closedState = "closing";
576
605
  await this.delegate.closePage(runBeforeUnload).catch((e) => import_debugLogger.debugLogger.log("error", e));
577
606
  }
578
607
  if (!runBeforeUnload)
579
- await this._closedPromise;
608
+ await this.closedPromise;
580
609
  }
581
610
  isClosed() {
582
611
  return this._closedState === "closed";
@@ -618,9 +647,22 @@ class Page extends import_instrumentation.SdkObject {
618
647
  }
619
648
  frameNavigatedToNewDocument(frame) {
620
649
  this.emit(Page.Events.InternalFrameNavigatedToNewDocument, frame);
650
+ this.browserContext.emit(import_browserContext.BrowserContext.Events.InternalFrameNavigatedToNewDocument, frame, this);
621
651
  const origin = frame.origin();
622
652
  if (origin)
623
653
  this.browserContext.addVisitedOrigin(origin);
654
+ if (frame === this.mainFrame()) {
655
+ if (this._consoleMessages.length > 0)
656
+ this._consoleMessages[this._consoleMessages.length - 1][navigationMarkSymbol] = true;
657
+ if (this._pageErrors.length > 0)
658
+ this._pageErrors[this._pageErrors.length - 1][navigationMarkSymbol] = true;
659
+ }
660
+ }
661
+ allInitScripts() {
662
+ const bindings = [...this.browserContext._pageBindings.values(), ...this._pageBindings.values()].map((binding) => binding.initScript);
663
+ if (this.browserContext.bindingsInitScript)
664
+ bindings.unshift(this.browserContext.bindingsInitScript);
665
+ return [...bindings, ...this.browserContext.initScripts, ...this.initScripts];
624
666
  }
625
667
  getBinding(name) {
626
668
  return this._pageBindings.get(name) || this.browserContext._pageBindings.get(name);
@@ -639,12 +681,8 @@ class Page extends import_instrumentation.SdkObject {
639
681
  await Promise.all(this.frames().map((frame) => frame.hideHighlight().catch(() => {
640
682
  })));
641
683
  }
642
- async snapshotForAI(progress, options = {}) {
643
- const snapshot = await snapshotFrameForAI(progress, this.mainFrame(), options);
644
- return { full: snapshot.full.join("\n"), incremental: snapshot.incremental?.join("\n") };
645
- }
646
- allBindings() {
647
- return [...this.browserContext._pageBindings.values(), ...this._pageBindings.values()];
684
+ async setDockTile(image) {
685
+ await this.delegate.setDockTile(image);
648
686
  }
649
687
  }
650
688
  const WorkerEvent = {
@@ -673,70 +711,54 @@ class Worker extends import_instrumentation.SdkObject {
673
711
  if (this.existingExecutionContext)
674
712
  this._executionContextPromise.resolve(this.existingExecutionContext);
675
713
  }
714
+ _prepareContextForRestart() {
715
+ if (this.existingExecutionContext)
716
+ this.existingExecutionContext.contextDestroyed("Service worker restarted");
717
+ this.existingExecutionContext = null;
718
+ this._workerScriptLoaded = false;
719
+ this._executionContextPromise = new import_manualPromise.ManualPromise();
720
+ }
676
721
  didClose() {
677
722
  if (this.existingExecutionContext)
678
723
  this.existingExecutionContext.contextDestroyed("Worker was closed");
679
724
  this.emit(Worker.Events.Close, this);
680
725
  this.openScope.close(new Error("Worker closed"));
681
726
  }
682
- async evaluateExpression(expression, isFunction, arg, isolatedContext) {
683
- let context = await this._executionContextPromise;
684
- if (context.constructor.name === "FrameExecutionContext") {
685
- const frame = context.frame;
686
- if (frame) {
687
- if (isolatedContext) context = await frame._utilityContext();
688
- else if (!isolatedContext) context = await frame._mainContext();
689
- }
690
- }
691
- return js.evaluateExpression(context, expression, { returnByValue: true, isFunction }, arg);
692
- }
693
- async evaluateExpressionHandle(expression, isFunction, arg, isolatedContext) {
694
- let context = await this._executionContextPromise;
695
- if (context.constructor.name === "FrameExecutionContext") {
696
- const frame = this._context.frame;
697
- if (frame) {
698
- if (isolatedContext) context = await frame._utilityContext();
699
- else if (!isolatedContext) context = await frame._mainContext();
700
- }
701
- }
702
- return js.evaluateExpression(context, expression, { returnByValue: false, isFunction }, arg);
727
+ async evaluateExpression(expression, isFunction, arg) {
728
+ return js.evaluateExpression(await this._executionContextPromise, expression, { returnByValue: true, isFunction }, arg);
729
+ }
730
+ async evaluateExpressionHandle(expression, isFunction, arg) {
731
+ return js.evaluateExpression(await this._executionContextPromise, expression, { returnByValue: false, isFunction }, arg);
703
732
  }
704
733
  }
705
- class PageBinding {
706
- constructor(name, playwrightFunction, needsHandle) {
734
+ class PageBinding extends import_disposable.DisposableObject {
735
+ static {
736
+ this.kController = "__playwright__binding__controller__";
737
+ }
738
+ static {
739
+ this.kBindingName = "__playwright__binding__";
740
+ }
741
+ static createInitScript(browserContext) {
742
+ return new InitScript(browserContext, `
743
+ (() => {
744
+ const module = {};
745
+ ${rawBindingsControllerSource.source}
746
+ const property = '${PageBinding.kController}';
747
+ if (!globalThis[property])
748
+ globalThis[property] = new (module.exports.BindingsController())(globalThis, '${PageBinding.kBindingName}');
749
+ })();
750
+ `);
751
+ }
752
+ constructor(parent, name, playwrightFunction, needsHandle) {
753
+ super(parent);
707
754
  this.name = name;
708
755
  this.playwrightFunction = playwrightFunction;
709
- this.source = (0, import_pageBinding.createPageBindingScript)(name, needsHandle);
756
+ this.initScript = new InitScript(parent, `globalThis['${PageBinding.kController}'].addBinding(${JSON.stringify(name)}, ${needsHandle})`);
710
757
  this.needsHandle = needsHandle;
758
+ this.cleanupScript = `globalThis['${PageBinding.kController}'].removeBinding(${JSON.stringify(name)})`;
711
759
  }
712
760
  static async dispatch(page, payload, context) {
713
761
  const { name, seq, serializedArgs } = JSON.parse(payload);
714
- const deliver = async (deliverPayload) => {
715
- let deliveryError;
716
- try {
717
- await context.evaluate(import_pageBinding.deliverBindingResult, deliverPayload);
718
- return;
719
- } catch (e) {
720
- deliveryError = e;
721
- }
722
- const frame = context.frame;
723
- if (!frame) {
724
- import_debugLogger.debugLogger.log("error", deliveryError);
725
- return;
726
- }
727
- const mainContext = await frame._mainContext().catch(() => null);
728
- const utilityContext = await frame._utilityContext().catch(() => null);
729
- for (const ctx of [mainContext, utilityContext]) {
730
- if (!ctx || ctx === context)
731
- continue;
732
- try {
733
- await ctx.evaluate(import_pageBinding.deliverBindingResult, deliverPayload);
734
- return;
735
- } catch {
736
- }
737
- }
738
- import_debugLogger.debugLogger.log("error", deliveryError);
739
- };
740
762
  try {
741
763
  (0, import_utils.assert)(context.world);
742
764
  const binding = page.getBinding(name);
@@ -744,38 +766,62 @@ class PageBinding {
744
766
  throw new Error(`Function "${name}" is not exposed`);
745
767
  let result;
746
768
  if (binding.needsHandle) {
747
- const handle = await context.evaluateHandle(import_pageBinding.takeBindingHandle, { name, seq }).catch((e) => null);
748
- result = await binding.playwrightFunction({ frame: context.frame, page, context: page._browserContext }, handle);
769
+ const handle = await context.evaluateExpressionHandle(`arg => globalThis['${PageBinding.kController}'].takeBindingHandle(arg)`, { isFunction: true }, { name, seq }).catch((e) => null);
770
+ result = await binding.playwrightFunction({ frame: context.frame, page, context: page.browserContext }, handle);
749
771
  } else {
750
772
  if (!Array.isArray(serializedArgs))
751
773
  throw new Error(`serializedArgs is not an array. This can happen when Array.prototype.toJSON is defined incorrectly`);
752
774
  const args = serializedArgs.map((a) => (0, import_utilityScriptSerializers.parseEvaluationResultValue)(a));
753
- result = await binding.playwrightFunction({ frame: context.frame, page, context: page._browserContext }, ...args);
775
+ result = await binding.playwrightFunction({ frame: context.frame, page, context: page.browserContext }, ...args);
754
776
  }
755
- await deliver({ name, seq, result });
777
+ context.evaluateExpressionHandle(`arg => globalThis['${PageBinding.kController}'].deliverBindingResult(arg)`, { isFunction: true }, { name, seq, result }).catch((e) => import_debugLogger.debugLogger.log("error", e));
756
778
  } catch (error) {
757
- await deliver({ name, seq, error });
779
+ context.evaluateExpressionHandle(`arg => globalThis['${PageBinding.kController}'].deliverBindingResult(arg)`, { isFunction: true }, { name, seq, error }).catch((e) => import_debugLogger.debugLogger.log("error", e));
758
780
  }
759
781
  }
782
+ async dispose() {
783
+ await this.parent.removeExposedBinding(this);
784
+ }
760
785
  }
761
- class InitScript {
762
- constructor(source) {
763
- this.source = `(() => { ${source} })();`;
786
+ class InitScript extends import_disposable.DisposableObject {
787
+ constructor(owner, source) {
788
+ super(owner);
789
+ this.source = `(() => {
790
+ ${source}
791
+ })();`;
792
+ }
793
+ async dispose() {
794
+ await this.parent.removeInitScript(this);
764
795
  }
765
796
  }
766
- async function snapshotFrameForAI(progress, frame, options = {}) {
797
+ async function ariaSnapshotForFrame(progress, frame, options = {}) {
767
798
  const snapshot = await frame.retryWithProgressAndTimeouts(progress, [1e3, 2e3, 4e3, 8e3], async (continuePolling) => {
768
799
  try {
769
800
  const context = await progress.race(frame._utilityContext());
770
801
  const injectedScript = await progress.race(context.injectedScript());
771
802
  const snapshotOrRetry = await progress.race(injectedScript.evaluate((injected, options2) => {
803
+ if (options2.info) {
804
+ const element = injected.querySelector(options2.info.parsed, injected.document, options2.info.strict);
805
+ if (!element)
806
+ return false;
807
+ return injected.incrementalAriaSnapshot(element, options2);
808
+ }
772
809
  const node = injected.document.body;
773
810
  if (!node)
774
811
  return true;
775
- return injected.incrementalAriaSnapshot(node, { mode: "ai", ...options2 });
776
- }, { refPrefix: frame.seq ? "f" + frame.seq : "", track: options.track, doNotRenderActive: options.doNotRenderActive }));
812
+ return injected.incrementalAriaSnapshot(node, options2);
813
+ }, {
814
+ mode: options.mode ?? "default",
815
+ refPrefix: frame.seq ? "f" + frame.seq : "",
816
+ track: options.track,
817
+ doNotRenderActive: options.doNotRenderActive,
818
+ info: options.info,
819
+ depth: options.depth
820
+ }));
777
821
  if (snapshotOrRetry === true)
778
822
  return continuePolling;
823
+ if (snapshotOrRetry === false)
824
+ throw new import_dom.NonRecoverableDOMError(`Selector "${(0, import_selectorParser.stringifySelector)(options.info.parsed)}" does not match any element`);
779
825
  return snapshotOrRetry;
780
826
  } catch (e) {
781
827
  if (frame.isNonRetriableError(e))
@@ -783,18 +829,23 @@ async function snapshotFrameForAI(progress, frame, options = {}) {
783
829
  return continuePolling;
784
830
  }
785
831
  });
786
- const childSnapshotPromises = snapshot.iframeRefs.map((ref) => snapshotFrameRefForAI(progress, frame, ref, options));
832
+ const renderedIframeRefs = snapshot.iframeRefs.filter((ref) => ref in snapshot.iframeDepths);
833
+ const childSnapshotPromises = renderedIframeRefs.map((ref) => {
834
+ const iframeDepth = snapshot.iframeDepths[ref];
835
+ const childDepth = options.depth ? options.depth - iframeDepth - 1 : void 0;
836
+ return ariaSnapshotFrameRef(progress, frame, ref, { ...options, depth: childDepth });
837
+ });
787
838
  const childSnapshots = await Promise.all(childSnapshotPromises);
788
839
  const full = [];
789
840
  let incremental;
790
841
  if (snapshot.incremental !== void 0) {
791
842
  incremental = snapshot.incremental.split("\n");
792
- for (let i = 0; i < snapshot.iframeRefs.length; i++) {
843
+ for (let i = 0; i < renderedIframeRefs.length; i++) {
793
844
  const childSnapshot = childSnapshots[i];
794
845
  if (childSnapshot.incremental)
795
846
  incremental.push(...childSnapshot.incremental);
796
847
  else if (childSnapshot.full.length)
797
- incremental.push("- <changed> iframe [ref=" + snapshot.iframeRefs[i] + "]:", ...childSnapshot.full.map((l) => " " + l));
848
+ incremental.push("- <changed> iframe [ref=" + renderedIframeRefs[i] + "]:", ...childSnapshot.full.map((l) => " " + l));
798
849
  }
799
850
  }
800
851
  for (const line of snapshot.full.split("\n")) {
@@ -805,20 +856,20 @@ async function snapshotFrameForAI(progress, frame, options = {}) {
805
856
  }
806
857
  const leadingSpace = match[1];
807
858
  const ref = match[2];
808
- const childSnapshot = childSnapshots[snapshot.iframeRefs.indexOf(ref)] ?? { full: [] };
859
+ const childSnapshot = childSnapshots[renderedIframeRefs.indexOf(ref)] ?? { full: [] };
809
860
  full.push(childSnapshot.full.length ? line + ":" : line);
810
861
  full.push(...childSnapshot.full.map((l) => leadingSpace + " " + l));
811
862
  }
812
863
  return { full, incremental };
813
864
  }
814
- async function snapshotFrameRefForAI(progress, parentFrame, frameRef, options) {
865
+ async function ariaSnapshotFrameRef(progress, parentFrame, frameRef, options) {
815
866
  const frameSelector = `aria-ref=${frameRef} >> internal:control=enter-frame`;
816
867
  const frameBodySelector = `${frameSelector} >> body`;
817
868
  const child = await progress.race(parentFrame.selectors.resolveFrameForSelector(frameBodySelector, { strict: true }));
818
869
  if (!child)
819
870
  return { full: [] };
820
871
  try {
821
- return await snapshotFrameForAI(progress, child.frame, options);
872
+ return await ariaSnapshotForFrame(progress, child.frame, { ...options, info: void 0 });
822
873
  } catch {
823
874
  return { full: [] };
824
875
  }
@@ -834,5 +885,6 @@ function ensureArrayLimit(array, limit) {
834
885
  Page,
835
886
  PageBinding,
836
887
  Worker,
837
- WorkerEvent
888
+ WorkerEvent,
889
+ ariaSnapshotForFrame
838
890
  });
@@ -39,10 +39,16 @@ class ProgressController {
39
39
  static createForSdkObject(sdkObject, callMetadata) {
40
40
  const logName = sdkObject.logName || "api";
41
41
  return new ProgressController(callMetadata, (message) => {
42
+ if (logName === "api" && sdkObject.attribution.playwright?.options.isInternalPlaywright)
43
+ return;
42
44
  import_utils.debugLogger.log(logName, message);
43
45
  sdkObject.instrumentation.onCallLog(sdkObject, callMetadata, logName, message);
44
46
  });
45
47
  }
48
+ static runInternalTask(task, timeout) {
49
+ const progress = new ProgressController();
50
+ return progress.run(task, timeout);
51
+ }
46
52
  async abort(error) {
47
53
  if (this._state === "running") {
48
54
  error[kAbortErrorSymbol] = true;
@@ -125,7 +125,7 @@ class RecorderApp {
125
125
  if (source) {
126
126
  if (source.isRecorded)
127
127
  this._selectedGeneratorId = source.id;
128
- this._recorder.setLanguage(source.language);
128
+ await this._recorder.setLanguage(source.language);
129
129
  }
130
130
  },
131
131
  setAutoExpect: async (params) => {
@@ -133,7 +133,7 @@ class RecorderApp {
133
133
  this._updateActions();
134
134
  },
135
135
  setMode: async (params) => {
136
- this._recorder.setMode(params.mode);
136
+ await this._recorder.setMode(params.mode);
137
137
  },
138
138
  resume: async () => {
139
139
  this._recorder.resume();
@@ -146,9 +146,9 @@ class RecorderApp {
146
146
  },
147
147
  highlightRequested: async (params) => {
148
148
  if (params.selector)
149
- this._recorder.setHighlightedSelector(params.selector);
149
+ await this._recorder.setHighlightedSelector(params.selector);
150
150
  if (params.ariaTemplate)
151
- this._recorder.setHighlightedAriaTemplate(params.ariaTemplate);
151
+ await this._recorder.setHighlightedAriaTemplate(params.ariaTemplate);
152
152
  }
153
153
  };
154
154
  await this._page.exposeBinding(progress, "sendCommand", false, async (_, data) => {
@@ -181,6 +181,7 @@ class RecorderApp {
181
181
  return;
182
182
  inspectedContext[recorderAppSymbol] = true;
183
183
  const sdkLanguage = inspectedContext._browser.sdkLanguage();
184
+ const isChromium = inspectedContext._browser.options.browserType === "chromium";
184
185
  const headed = !!inspectedContext._browser.options.headful;
185
186
  const recorderPlaywright = require("../playwright").createPlaywright({ sdkLanguage: "javascript", isInternalPlaywright: true });
186
187
  const { context: appContext, page } = await (0, import_launchApp2.launchApp)(recorderPlaywright.chromium, {
@@ -192,9 +193,9 @@ class RecorderApp {
192
193
  headless: !!process.env.PWTEST_CLI_HEADLESS || (0, import_debug.isUnderTest)() && !headed,
193
194
  cdpPort: (0, import_debug.isUnderTest)() ? 0 : void 0,
194
195
  handleSIGINT: params.handleSIGINT,
195
- executablePath: inspectedContext._browser.options.isChromium ? inspectedContext._browser.options.customExecutablePath : void 0,
196
+ executablePath: isChromium ? inspectedContext._browser.options.customExecutablePath : void 0,
196
197
  // Use the same channel as the inspected context to guarantee that the browser is installed.
197
- channel: inspectedContext._browser.options.isChromium ? inspectedContext._browser.options.channel : void 0
198
+ channel: isChromium ? inspectedContext._browser.options.channel : void 0
198
199
  }
199
200
  });
200
201
  const controller = new import_progress.ProgressController();
@@ -206,8 +207,8 @@ class RecorderApp {
206
207
  sdkLanguage: inspectedContext._browser.sdkLanguage(),
207
208
  wsEndpointForTest: inspectedContext._browser.options.wsEndpoint,
208
209
  headed: !!inspectedContext._browser.options.headful,
209
- executablePath: inspectedContext._browser.options.isChromium ? inspectedContext._browser.options.customExecutablePath : void 0,
210
- channel: inspectedContext._browser.options.isChromium ? inspectedContext._browser.options.channel : void 0,
210
+ executablePath: isChromium ? inspectedContext._browser.options.customExecutablePath : void 0,
211
+ channel: isChromium ? inspectedContext._browser.options.channel : void 0,
211
212
  ...params
212
213
  };
213
214
  const recorderApp = new RecorderApp(recorder, appParams, page, appContext._browser.options.wsEndpoint);