playwright-ruby-client 0.6.3 → 0.7.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 (37) hide show
  1. checksums.yaml +4 -4
  2. data/documentation/docs/api/browser.md +12 -1
  3. data/documentation/docs/api/browser_context.md +11 -1
  4. data/documentation/docs/api/browser_type.md +54 -1
  5. data/documentation/docs/api/cdp_session.md +41 -1
  6. data/documentation/docs/api/experimental/android.md +3 -2
  7. data/documentation/docs/api/page.md +18 -0
  8. data/documentation/docs/api/route.md +20 -21
  9. data/documentation/docs/api/tracing.md +8 -15
  10. data/documentation/docs/api/web_socket.md +38 -1
  11. data/documentation/docs/article/guides/launch_browser.md +2 -0
  12. data/documentation/docs/article/guides/rails_integration.md +45 -2
  13. data/documentation/docs/article/guides/recording_video.md +79 -0
  14. data/documentation/docs/article/guides/semi_automation.md +67 -0
  15. data/documentation/docs/include/api_coverage.md +13 -14
  16. data/documentation/package.json +1 -1
  17. data/documentation/yarn.lock +478 -498
  18. data/lib/playwright/channel_owners/browser.rb +19 -10
  19. data/lib/playwright/channel_owners/browser_context.rb +14 -2
  20. data/lib/playwright/channel_owners/browser_type.rb +23 -8
  21. data/lib/playwright/channel_owners/cdp_session.rb +19 -0
  22. data/lib/playwright/channel_owners/page.rb +8 -0
  23. data/lib/playwright/channel_owners/response.rb +1 -1
  24. data/lib/playwright/channel_owners/web_socket.rb +87 -0
  25. data/lib/playwright/tracing_impl.rb +9 -9
  26. data/lib/playwright/version.rb +1 -1
  27. data/lib/playwright_api/android.rb +3 -2
  28. data/lib/playwright_api/browser.rb +4 -3
  29. data/lib/playwright_api/browser_context.rb +3 -3
  30. data/lib/playwright_api/browser_type.rb +6 -5
  31. data/lib/playwright_api/cdp_session.rb +24 -2
  32. data/lib/playwright_api/page.rb +9 -9
  33. data/lib/playwright_api/response.rb +0 -5
  34. data/lib/playwright_api/tracing.rb +6 -12
  35. data/lib/playwright_api/web_socket.rb +28 -6
  36. data/playwright.gemspec +2 -1
  37. metadata +34 -16
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 77f49d82e8b6b94210f79ee9e031dcfb73072a11da4c366626ad3bcf3e18bfa9
4
- data.tar.gz: '098cbff788ed38a7647de0271d6f3c38a757e3c750ebf8aaa3f96dccbb626921'
3
+ metadata.gz: d8e3e3982a30add91ed67641a29dcff9778c40788c8434d2ef581cb926951968
4
+ data.tar.gz: bc7c51236c2d9c2632c53dfe25ae7f9f357c1118a434bb1c41f735a0c67c7625
5
5
  SHA512:
6
- metadata.gz: 46997fb7eff8b747560a6f8658bc2b50cbeb2a489f75ed716ccfb84fc8dfddea171bbd4812dc897840507c7d9267e1c81e9f79ae05679ccece322dff7c8adc8b
7
- data.tar.gz: 134a0003575cbe1501af23dad3a2f706cf9a961a8c067a858ecd25e61fe7a20f018d382d8d38be40c5aaa0c603dd0b1d02bd62b674405bfa5b5e130cf8593196
6
+ metadata.gz: b438126a715d3c427408fb4d0b13483bb6f96444cb9c359a946da70125f00b0eee488e5753493a5f9e37ff1294209fd58a044721e0c7b0b2e5c06ef2a8611aef
7
+ data.tar.gz: a13605776cfca08333630a2e18cf53035d71b6b0ea454a27f76bf0562ef1d505844c70b1119bdca2c2cfd400d402d2c62e06fe38d53abf561c005b6127900c83
@@ -61,6 +61,16 @@ def connected?
61
61
 
62
62
  Indicates that the browser is connected.
63
63
 
64
+ ## new_browser_cdp_session
65
+
66
+ ```
67
+ def new_browser_cdp_session
68
+ ```
69
+
70
+ > NOTE: CDP Sessions are only supported on Chromium-based browsers.
71
+
72
+ Returns the newly created browser session.
73
+
64
74
  ## new_context
65
75
 
66
76
  ```
@@ -138,7 +148,8 @@ def new_page(
138
148
  storageState: nil,
139
149
  timezoneId: nil,
140
150
  userAgent: nil,
141
- viewport: nil)
151
+ viewport: nil,
152
+ &block)
142
153
  ```
143
154
 
144
155
  Creates a new page in a new browser context. Closing this page will close the context as well.
@@ -226,10 +226,20 @@ def grant_permissions(permissions, origin: nil)
226
226
  Grants specified permissions to the browser context. Only grants corresponding permissions to the given origin if
227
227
  specified.
228
228
 
229
+ ## new_cdp_session
230
+
231
+ ```
232
+ def new_cdp_session(page)
233
+ ```
234
+
235
+ > NOTE: CDP sessions are only supported on Chromium-based browsers.
236
+
237
+ Returns the newly created session.
238
+
229
239
  ## new_page
230
240
 
231
241
  ```
232
- def new_page
242
+ def new_page(&block)
233
243
  ```
234
244
 
235
245
  Creates a new page in the browser context.
@@ -65,7 +65,7 @@ def launch(
65
65
  proxy: nil,
66
66
  slowMo: nil,
67
67
  timeout: nil,
68
- traceDir: nil,
68
+ tracesDir: nil,
69
69
  &block)
70
70
  ```
71
71
 
@@ -96,6 +96,59 @@ differences between Chromium and Chrome.
96
96
  [This article](https://chromium.googlesource.com/chromium/src/+/lkgr/docs/chromium_browser_vs_google_chrome.md)
97
97
  describes some differences for Linux users.
98
98
 
99
+ ## launch_persistent_context
100
+
101
+ ```
102
+ def launch_persistent_context(
103
+ userDataDir,
104
+ acceptDownloads: nil,
105
+ args: nil,
106
+ bypassCSP: nil,
107
+ channel: nil,
108
+ chromiumSandbox: nil,
109
+ colorScheme: nil,
110
+ deviceScaleFactor: nil,
111
+ devtools: nil,
112
+ downloadsPath: nil,
113
+ env: nil,
114
+ executablePath: nil,
115
+ extraHTTPHeaders: nil,
116
+ geolocation: nil,
117
+ handleSIGHUP: nil,
118
+ handleSIGINT: nil,
119
+ handleSIGTERM: nil,
120
+ hasTouch: nil,
121
+ headless: nil,
122
+ httpCredentials: nil,
123
+ ignoreDefaultArgs: nil,
124
+ ignoreHTTPSErrors: nil,
125
+ isMobile: nil,
126
+ javaScriptEnabled: nil,
127
+ locale: nil,
128
+ noViewport: nil,
129
+ offline: nil,
130
+ permissions: nil,
131
+ proxy: nil,
132
+ record_har_omit_content: nil,
133
+ record_har_path: nil,
134
+ record_video_dir: nil,
135
+ record_video_size: nil,
136
+ reducedMotion: nil,
137
+ screen: nil,
138
+ slowMo: nil,
139
+ timeout: nil,
140
+ timezoneId: nil,
141
+ tracesDir: nil,
142
+ userAgent: nil,
143
+ viewport: nil,
144
+ &block)
145
+ ```
146
+
147
+ Returns the persistent browser context instance.
148
+
149
+ Launches browser that uses persistent storage located at `userDataDir` and returns the only context. Closing this
150
+ context will automatically close the browser.
151
+
99
152
  ## name
100
153
 
101
154
  ```
@@ -4,4 +4,44 @@ sidebar_position: 10
4
4
 
5
5
  # CDPSession
6
6
 
7
- Not Implemented
7
+ - extends: [EventEmitter]
8
+
9
+ The [CDPSession](./cdp_session) instances are used to talk raw Chrome Devtools Protocol:
10
+ - protocol methods can be called with `session.send_message` method.
11
+ - protocol events can be subscribed to with `session.on` method.
12
+
13
+ Useful links:
14
+ - Documentation on DevTools Protocol can be found here:
15
+ [DevTools Protocol Viewer](https://chromedevtools.github.io/devtools-protocol/).
16
+ - Getting Started with DevTools Protocol:
17
+ https://github.com/aslushnikov/getting-started-with-cdp/blob/master/README.md
18
+
19
+ ```ruby
20
+ client = page.context.new_cdp_session(page)
21
+ client.send_message('Animation.enable')
22
+ client.on('Animation.animationCreated', -> (_) { puts 'Animation Created' })
23
+ response = client.send_message('Animation.getPlaybackRate')
24
+ puts "Playback rate is #{response['playbackRate']}"
25
+ client.send_message(
26
+ 'Animation.setPlaybackRate',
27
+ params: { playbackRate: response['playbackRate'] / 2.0 },
28
+ )
29
+ ```
30
+
31
+
32
+ ## detach
33
+
34
+ ```
35
+ def detach
36
+ ```
37
+
38
+ Detaches the CDPSession from the target. Once detached, the CDPSession object won't emit any events and can't be used to
39
+ send messages.
40
+
41
+ ## send_message
42
+
43
+ ```
44
+ def send_message(method, params: nil)
45
+ ```
46
+
47
+
@@ -4,14 +4,15 @@ sidebar_position: 10
4
4
 
5
5
  # Android
6
6
 
7
- Playwright has **experimental** support for Android automation. You can access android namespace via:
7
+ Playwright has **experimental** support for Android automation. See [here](https://playwright.dev/python/docs/mobile) for more information. You can
8
+ access android namespace via:
8
9
 
9
10
  An example of the Android automation script would be:
10
11
 
11
12
  Note that since you don't need Playwright to install web browsers when testing Android, you can omit browser download
12
13
  via setting the following environment variable when installing Playwright:
13
14
 
14
- ```sh js
15
+ ```bash js
15
16
  PLAYWRIGHT_SKIP_BROWSER_DOWNLOAD=1 npm i -D playwright
16
17
  ```
17
18
 
@@ -1328,6 +1328,16 @@ puts request.headers
1328
1328
 
1329
1329
 
1330
1330
 
1331
+ ## expect_request_finished
1332
+
1333
+ ```
1334
+ def expect_request_finished(predicate: nil, timeout: nil, &block)
1335
+ ```
1336
+
1337
+ Performs action and waits for a [Request](./request) to finish loading. If predicate is provided, it passes [Request](./request) value into
1338
+ the `predicate` function and waits for `predicate(request)` to return a truthy value. Will throw an error if the page is
1339
+ closed before the [`event: Page.requestFinished`] event is fired.
1340
+
1331
1341
  ## expect_response
1332
1342
 
1333
1343
  ```
@@ -1393,6 +1403,14 @@ page.wait_for_url("**/target.html")
1393
1403
 
1394
1404
  Shortcut for main frame's [Frame#wait_for_url](./frame#wait_for_url).
1395
1405
 
1406
+ ## expect_websocket
1407
+
1408
+ ```
1409
+ def expect_websocket(predicate: nil, timeout: nil, &block)
1410
+ ```
1411
+
1412
+ Performs action and waits for a new [WebSocket](./web_socket). If predicate is provided, it passes [WebSocket](./web_socket) value into the `predicate` function and waits for `predicate.call(web_socket)` to return a truthy value. Will throw an error if the page is closed before the WebSocket event is fired.
1413
+
1396
1414
  ## accessibility
1397
1415
 
1398
1416
  ## keyboard
@@ -23,18 +23,16 @@ def continue(headers: nil, method: nil, postData: nil, url: nil)
23
23
 
24
24
  Continues route's request with optional overrides.
25
25
 
26
- ```python sync title=example_1960aabd58c9553683368e29429d39c1209d35e6e3625bbef1280a1fa022a9ee.py
27
- def handle(route, request):
28
- # override headers
29
- headers = {
30
- **request.headers,
31
- "foo": "bar" # set "foo" header
32
- "origin": None # remove "origin" header
33
- }
34
- route.continue_(headers=headers)
35
- }
36
- page.route("**/*", handle)
37
-
26
+ ```ruby
27
+ def handle(route, request)
28
+ # override headers
29
+ headers = request.headers
30
+ headers['foo'] = 'bar' # set "foo" header
31
+ headers['user-agent'] = 'Unknown Browser' # modify user-agent
32
+
33
+ route.continue(headers: headers)
34
+ end
35
+ page.route("**/*", method(:handle))
38
36
  ```
39
37
 
40
38
 
@@ -54,19 +52,20 @@ Fulfills route's request with given response.
54
52
 
55
53
  An example of fulfilling all requests with 404 responses:
56
54
 
57
- ```python sync title=example_6d2dfd4bb5c8360f8d80bb91c563b0bd9b99aa24595063cf85e5a6e1b105f89c.py
58
- page.route("**/*", lambda route: route.fulfill(
59
- status=404,
60
- content_type="text/plain",
61
- body="not found!"))
62
-
55
+ ```ruby
56
+ page.route("**/*", ->(route, request) {
57
+ route.fulfill(
58
+ status: 404,
59
+ contentType: 'text/plain',
60
+ body: 'not found!!',
61
+ )
62
+ })
63
63
  ```
64
64
 
65
65
  An example of serving static file:
66
66
 
67
- ```python sync title=example_c77fd0986d0b74c905cd9417756c76775e612cc86410f9a5aabc5b46d233d150.py
68
- page.route("**/xhr_endpoint", lambda route: route.fulfill(path="mock_data.json"))
69
-
67
+ ```ruby
68
+ page.route("**/xhr_endpoint", ->(route, _) { route.fulfill(path: "mock_data.json") })
70
69
  ```
71
70
 
72
71
 
@@ -9,24 +9,16 @@ Playwright script runs.
9
9
 
10
10
  Start with specifying the folder traces will be stored in:
11
11
 
12
- ```python sync title=example_b375e389cd6685ec49d1ef57f3186da60ef682785c646fe8db351b6f39b1a34c.py
13
- browser = chromium.launch(traceDir='traces')
12
+ ```python sync title=example_a767dfb400d98aef50f2767b94171d23474ea1ac1cf9b4d75d412936208e652d.py
13
+ browser = chromium.launch()
14
14
  context = browser.new_context()
15
- context.tracing.start(name="trace", screenshots=True, snapshots=True)
15
+ context.tracing.start(screenshots=True, snapshots=True)
16
16
  page.goto("https://playwright.dev")
17
- context.tracing.stop()
18
- context.tracing.export("trace.zip")
17
+ context.tracing.stop(path = "trace.zip")
19
18
 
20
19
  ```
21
20
 
22
21
 
23
- ## export
24
-
25
- ```
26
- def export(path)
27
- ```
28
-
29
- Export trace into the file with the given name. Should be called after the tracing has stopped.
30
22
 
31
23
  ## start
32
24
 
@@ -36,19 +28,20 @@ def start(name: nil, screenshots: nil, snapshots: nil)
36
28
 
37
29
  Start tracing.
38
30
 
39
- ```python sync title=example_4c72a858b35ec7bd7aaba231cb93acecb7ee4b7ea8048a534f28f7e16af966b8.py
31
+ ```python sync title=example_e611abc8b1066118d0c87eae1bbbb08df655f36d50a94402fc56b8713150997b.py
40
32
  context.tracing.start(name="trace", screenshots=True, snapshots=True)
41
33
  page.goto("https://playwright.dev")
42
34
  context.tracing.stop()
43
- context.tracing.export("trace.zip")
35
+ context.tracing.stop(path = "trace.zip")
44
36
 
45
37
  ```
46
38
 
47
39
 
40
+
48
41
  ## stop
49
42
 
50
43
  ```
51
- def stop
44
+ def stop(path: nil)
52
45
  ```
53
46
 
54
47
  Stop tracing.
@@ -4,4 +4,41 @@ sidebar_position: 10
4
4
 
5
5
  # WebSocket
6
6
 
7
- Not Implemented
7
+ The [WebSocket](./web_socket) class represents websocket connections in the page.
8
+
9
+ ## closed?
10
+
11
+ ```
12
+ def closed?
13
+ ```
14
+
15
+ Indicates that the web socket has been closed.
16
+
17
+ ## url
18
+
19
+ ```
20
+ def url
21
+ ```
22
+
23
+ Contains the URL of the WebSocket.
24
+
25
+ ## expect_event
26
+
27
+ ```
28
+ def expect_event(event, predicate: nil, timeout: nil, &block)
29
+ ```
30
+
31
+ Waits for event to fire and passes its value into the predicate function. Returns when the predicate returns truthy
32
+ value. Will throw an error if the webSocket is closed before the event is fired. Returns the event data value.
33
+
34
+ ## wait_for_event
35
+
36
+ ```
37
+ def wait_for_event(event, predicate: nil, timeout: nil, &block)
38
+ ```
39
+
40
+ > NOTE: In most cases, you should use [WebSocket#wait_for_event](./web_socket#wait_for_event).
41
+
42
+ Waits for given `event` to fire. If predicate is provided, it passes event's value into the `predicate` function and
43
+ waits for `predicate(event)` to return a truthy value. Will throw an error if the socket is closed before the `event` is
44
+ fired.
@@ -117,3 +117,5 @@ Playwright.create(playwright_cli_executable_path: 'npx playwright') do |playwrig
117
117
  end
118
118
  end
119
119
  ```
120
+
121
+ Note that each browser context is isolated and not persisted by default. When persistent browser context is needed, we can use [BrowserType#launch_persistent_context](/docs/api/browser_type#launch_persistent_context).
@@ -41,7 +41,7 @@ Capybara.default_max_wait_time = 15
41
41
 
42
42
  ### (Optional) Update default driver
43
43
 
44
- By default, Capybara driver is set to `:rack_test`, which works only with non-JS contents. If your Rails application has many JavaScript contents, it is recommended to change the default driver to `:playwrite`.
44
+ By default, Capybara driver is set to `:rack_test`, which works only with non-JS contents. If your Rails application has many JavaScript contents, it is recommended to change the default driver to `:playwright`.
45
45
 
46
46
  ```rb
47
47
  Capybara.default_driver = :playwright
@@ -155,8 +155,51 @@ end
155
155
 
156
156
  Generally, Capybara DSL seems simple, but Playwright-native scripting are more precise and efficient. Also `waitForNavigation`, `waitForSelector`, and many other Playwright functions are available with Playwright-native scripting.
157
157
 
158
+ ### Screen recording
159
+
160
+ NO NEED to keep sitting in front of screen during test. Just record what happened with video.
161
+
162
+ For example, we can store the video for [Allure report](https://github.com/allure-framework/allure-ruby) as below:
163
+
164
+ ```ruby
165
+ before do |example|
166
+ Capybara.current_session.driver.on_save_screenrecord do |video_path|
167
+ Allure.add_attachment(
168
+ name: "screenrecord - #{example.description}",
169
+ source: File.read(video_path),
170
+ type: Allure::ContentType::WEBM,
171
+ test_case: true,
172
+ )
173
+ end
174
+ end
175
+ ```
176
+
177
+ ![sceenrecord](https://user-images.githubusercontent.com/11763113/121126629-71b5f600-c863-11eb-8f88-7924ab669946.gif)
178
+
179
+ For more details, refer [Recording video](./recording_video.md#using-screen-recording-from-capybara-driver)
180
+
181
+
182
+ ### Screenshot just before teardown
183
+
184
+ In addition to `Capybara::Session#save_screenshot`, capybara-playwright-driver have another method for storing last screen state just before teardown.
185
+
186
+ For example, we can attach the screenshot for [Allure report](https://github.com/allure-framework/allure-ruby) as below:
187
+
188
+ ```ruby
189
+ before do |example|
190
+ Capybara.current_session.driver.on_save_raw_screenshot_before_reset do |raw_screenshot|
191
+ Allure.add_attachment(
192
+ name: "screenshot - #{example.description}",
193
+ source: raw_screenshot,
194
+ type: Allure::ContentType::PNG,
195
+ test_case: true,
196
+ )
197
+ end
198
+ end
199
+ ```
200
+
158
201
  ### Limitations
159
202
 
160
203
  * Playwright doesn't allow clicking invisible DOM elements or moving elements. `click` sometimes doesn't work as Selenium does. See the detail in https://playwright.dev/docs/actionability/
161
204
  * `current_window.maximize` and `current_window.fullscreen` work only on headful (non-headless) mode, as selenium driver does.
162
- * `Capybara::Node::Element#drag_to` does not accept `html5` parameter, since [Playwright doesn't implement the feature yet](https://github.com/microsoft/playwright/pull/6207).
205
+ * `Capybara::Node::Element#drag_to` does not accept `html5` parameter. HTML5 drag and drop is not fully supported in Playwright.