playwright-ruby-client 0.8.1 → 1.14.beta3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/documentation/docs/api/accessibility.md +51 -1
- data/documentation/docs/api/browser_context.md +28 -0
- data/documentation/docs/api/download.md +97 -0
- data/documentation/docs/api/element_handle.md +28 -3
- data/documentation/docs/api/experimental/android.md +15 -2
- data/documentation/docs/api/frame.md +116 -114
- data/documentation/docs/api/locator.md +650 -0
- data/documentation/docs/api/mouse.md +3 -4
- data/documentation/docs/api/page.md +109 -19
- data/documentation/docs/api/request.md +15 -19
- data/documentation/docs/api/touchscreen.md +8 -0
- data/documentation/docs/api/tracing.md +13 -12
- data/documentation/docs/api/worker.md +37 -0
- data/documentation/docs/article/guides/inspector.md +31 -0
- data/documentation/docs/article/guides/playwright_on_alpine_linux.md +1 -1
- data/documentation/docs/article/guides/semi_automation.md +1 -1
- data/documentation/docs/include/api_coverage.md +70 -14
- data/lib/playwright.rb +0 -1
- data/lib/playwright/accessibility_impl.rb +50 -0
- data/lib/playwright/channel_owners/browser_context.rb +70 -0
- data/lib/playwright/channel_owners/frame.rb +79 -33
- data/lib/playwright/channel_owners/page.rb +133 -42
- data/lib/playwright/channel_owners/request.rb +8 -8
- data/lib/playwright/channel_owners/worker.rb +23 -0
- data/lib/playwright/{download.rb → download_impl.rb} +1 -1
- data/lib/playwright/javascript/expression.rb +5 -4
- data/lib/playwright/locator_impl.rb +314 -0
- data/lib/playwright/timeout_settings.rb +4 -4
- data/lib/playwright/touchscreen_impl.rb +7 -0
- data/lib/playwright/tracing_impl.rb +9 -8
- data/lib/playwright/version.rb +2 -2
- data/lib/playwright_api/accessibility.rb +1 -1
- data/lib/playwright_api/android.rb +21 -8
- data/lib/playwright_api/android_device.rb +6 -6
- data/lib/playwright_api/browser.rb +6 -6
- data/lib/playwright_api/browser_context.rb +16 -11
- data/lib/playwright_api/browser_type.rb +6 -6
- data/lib/playwright_api/cdp_session.rb +6 -6
- data/lib/playwright_api/console_message.rb +6 -6
- data/lib/playwright_api/dialog.rb +6 -6
- data/lib/playwright_api/download.rb +70 -0
- data/lib/playwright_api/element_handle.rb +34 -20
- data/lib/playwright_api/frame.rb +85 -53
- data/lib/playwright_api/js_handle.rb +6 -6
- data/lib/playwright_api/locator.rb +509 -0
- data/lib/playwright_api/page.rb +91 -57
- data/lib/playwright_api/playwright.rb +6 -6
- data/lib/playwright_api/request.rb +6 -6
- data/lib/playwright_api/response.rb +6 -6
- data/lib/playwright_api/route.rb +6 -6
- data/lib/playwright_api/selectors.rb +6 -6
- data/lib/playwright_api/touchscreen.rb +1 -1
- data/lib/playwright_api/web_socket.rb +6 -6
- data/lib/playwright_api/worker.rb +16 -6
- metadata +13 -6
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 88c8fbe4451b00ed8eba172f656e0171fb2580d555eefb4d2aa0cc1a13f86fc4
|
4
|
+
data.tar.gz: 3d307147cc4a23356d561f9528ef95343984bf4623ad77ebb6e479ce4f4f9462
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 647702705f820c268e5b858a1cd587b0e8f32f16415df2fd7b91505a221cadc20400fc9f2db188964fe4759f4734c8b30bc15c265434d2ac2b78e0683228c192
|
7
|
+
data.tar.gz: b4af0552e547d28be8c9390441bb7131d61fcea36fb5d3d293fd6985d6b47d3925e1c3bf27aa5f4e59243fc03ad751355acc20cb4e63b6e7489c47abb55b1864
|
@@ -4,4 +4,54 @@ sidebar_position: 10
|
|
4
4
|
|
5
5
|
# Accessibility
|
6
6
|
|
7
|
-
|
7
|
+
The Accessibility class provides methods for inspecting Chromium's accessibility tree. The accessibility tree is used by
|
8
|
+
assistive technology such as [screen readers](https://en.wikipedia.org/wiki/Screen_reader) or
|
9
|
+
[switches](https://en.wikipedia.org/wiki/Switch_access).
|
10
|
+
|
11
|
+
Accessibility is a very platform-specific thing. On different platforms, there are different screen readers that might
|
12
|
+
have wildly different output.
|
13
|
+
|
14
|
+
Rendering engines of Chromium, Firefox and WebKit have a concept of "accessibility tree", which is then translated into
|
15
|
+
different platform-specific APIs. Accessibility namespace gives access to this Accessibility Tree.
|
16
|
+
|
17
|
+
Most of the accessibility tree gets filtered out when converting from internal browser AX Tree to Platform-specific
|
18
|
+
AX-Tree or by assistive technologies themselves. By default, Playwright tries to approximate this filtering, exposing
|
19
|
+
only the "interesting" nodes of the tree.
|
20
|
+
|
21
|
+
## snapshot
|
22
|
+
|
23
|
+
```
|
24
|
+
def snapshot(interestingOnly: nil, root: nil)
|
25
|
+
```
|
26
|
+
|
27
|
+
Captures the current state of the accessibility tree. The returned object represents the root accessible node of the
|
28
|
+
page.
|
29
|
+
|
30
|
+
> NOTE: The Chromium accessibility tree contains nodes that go unused on most platforms and by most screen readers.
|
31
|
+
Playwright will discard them as well for an easier to process tree, unless `interestingOnly` is set to `false`.
|
32
|
+
|
33
|
+
An example of dumping the entire accessibility tree:
|
34
|
+
|
35
|
+
```ruby
|
36
|
+
snapshot = page.accessibility.snapshot
|
37
|
+
puts snapshot
|
38
|
+
```
|
39
|
+
|
40
|
+
An example of logging the focused node's name:
|
41
|
+
|
42
|
+
```ruby
|
43
|
+
def find_focused_node(node)
|
44
|
+
if node['focused']
|
45
|
+
node
|
46
|
+
else
|
47
|
+
node['children']&.find do |child|
|
48
|
+
find_focused_node(child)
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
|
53
|
+
snapshot = page.accessibility.snapshot
|
54
|
+
node = find_focused_node(snapshot)
|
55
|
+
puts node['name']
|
56
|
+
```
|
57
|
+
|
@@ -67,6 +67,16 @@ browser_context.add_init_script(path: "preload.js")
|
|
67
67
|
> NOTE: The order of evaluation of multiple scripts installed via [BrowserContext#add_init_script](./browser_context#add_init_script) and
|
68
68
|
[Page#add_init_script](./page#add_init_script) is not defined.
|
69
69
|
|
70
|
+
## background_pages
|
71
|
+
|
72
|
+
```
|
73
|
+
def background_pages
|
74
|
+
```
|
75
|
+
|
76
|
+
> NOTE: Background pages are only supported on Chromium-based browsers.
|
77
|
+
|
78
|
+
All existing background pages in the context.
|
79
|
+
|
70
80
|
## browser
|
71
81
|
|
72
82
|
```
|
@@ -301,6 +311,16 @@ To remove a route with its handler you can use [BrowserContext#unroute](./browse
|
|
301
311
|
|
302
312
|
> NOTE: Enabling routing disables http cache.
|
303
313
|
|
314
|
+
## service_workers
|
315
|
+
|
316
|
+
```
|
317
|
+
def service_workers
|
318
|
+
```
|
319
|
+
|
320
|
+
> NOTE: Service workers are only supported on Chromium-based browsers.
|
321
|
+
|
322
|
+
All existing service workers in the context.
|
323
|
+
|
304
324
|
## set_default_navigation_timeout
|
305
325
|
|
306
326
|
```
|
@@ -369,6 +389,14 @@ alias: `offline=`
|
|
369
389
|
|
370
390
|
|
371
391
|
|
392
|
+
## storage_state
|
393
|
+
|
394
|
+
```
|
395
|
+
def storage_state(path: nil)
|
396
|
+
```
|
397
|
+
|
398
|
+
Returns storage state for this browser context, contains current cookies and local storage snapshot.
|
399
|
+
|
372
400
|
## unroute
|
373
401
|
|
374
402
|
```
|
@@ -0,0 +1,97 @@
|
|
1
|
+
---
|
2
|
+
sidebar_position: 10
|
3
|
+
---
|
4
|
+
|
5
|
+
# Download
|
6
|
+
|
7
|
+
[Download](./download) objects are dispatched by page via the [`event: Page.download`] event.
|
8
|
+
|
9
|
+
All the downloaded files belonging to the browser context are deleted when the browser context is closed.
|
10
|
+
|
11
|
+
Download event is emitted once the download starts. Download path becomes available once download completes:
|
12
|
+
|
13
|
+
```ruby
|
14
|
+
download = page.expect_download do
|
15
|
+
page.click('a')
|
16
|
+
end
|
17
|
+
|
18
|
+
# wait for download to complete
|
19
|
+
path = download.path
|
20
|
+
```
|
21
|
+
|
22
|
+
> NOTE: Browser context **must** be created with the `acceptDownloads` set to `true` when user needs access to the
|
23
|
+
downloaded content. If `acceptDownloads` is not set, download events are emitted, but the actual download is not
|
24
|
+
performed and user has no access to the downloaded files.
|
25
|
+
|
26
|
+
## cancel
|
27
|
+
|
28
|
+
```
|
29
|
+
def cancel
|
30
|
+
```
|
31
|
+
|
32
|
+
Cancels a download. Will not fail if the download is already finished or canceled. Upon successful cancellations,
|
33
|
+
`download.failure()` would resolve to `'canceled'`.
|
34
|
+
|
35
|
+
## delete
|
36
|
+
|
37
|
+
```
|
38
|
+
def delete
|
39
|
+
```
|
40
|
+
|
41
|
+
Deletes the downloaded file. Will wait for the download to finish if necessary.
|
42
|
+
|
43
|
+
## failure
|
44
|
+
|
45
|
+
```
|
46
|
+
def failure
|
47
|
+
```
|
48
|
+
|
49
|
+
Returns download error if any. Will wait for the download to finish if necessary.
|
50
|
+
|
51
|
+
## page
|
52
|
+
|
53
|
+
```
|
54
|
+
def page
|
55
|
+
```
|
56
|
+
|
57
|
+
Get the page that the download belongs to.
|
58
|
+
|
59
|
+
## path
|
60
|
+
|
61
|
+
```
|
62
|
+
def path
|
63
|
+
```
|
64
|
+
|
65
|
+
Returns path to the downloaded file in case of successful download. The method will wait for the download to finish if
|
66
|
+
necessary. The method throws when connected remotely.
|
67
|
+
|
68
|
+
Note that the download's file name is a random GUID, use [Download#suggested_filename](./download#suggested_filename) to get suggested file
|
69
|
+
name.
|
70
|
+
|
71
|
+
## save_as
|
72
|
+
|
73
|
+
```
|
74
|
+
def save_as(path)
|
75
|
+
```
|
76
|
+
|
77
|
+
Copy the download to a user-specified path. It is safe to call this method while the download is still in progress. Will
|
78
|
+
wait for the download to finish if necessary.
|
79
|
+
|
80
|
+
## suggested_filename
|
81
|
+
|
82
|
+
```
|
83
|
+
def suggested_filename
|
84
|
+
```
|
85
|
+
|
86
|
+
Returns suggested filename for this download. It is typically computed by the browser from the
|
87
|
+
[`Content-Disposition`](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Disposition) response header
|
88
|
+
or the `download` attribute. See the spec on [whatwg](https://html.spec.whatwg.org/#downloading-resources). Different
|
89
|
+
browsers can use different logic for computing it.
|
90
|
+
|
91
|
+
## url
|
92
|
+
|
93
|
+
```
|
94
|
+
def url
|
95
|
+
```
|
96
|
+
|
97
|
+
Returns downloaded url.
|
@@ -10,10 +10,8 @@ ElementHandle represents an in-page DOM element. ElementHandles can be created w
|
|
10
10
|
method.
|
11
11
|
|
12
12
|
```ruby
|
13
|
-
page.goto("https://example.com")
|
14
13
|
href_element = page.query_selector("a")
|
15
14
|
href_element.click
|
16
|
-
# ...
|
17
15
|
```
|
18
16
|
|
19
17
|
ElementHandle prevents DOM element from garbage collection unless the handle is disposed with
|
@@ -22,6 +20,33 @@ ElementHandle prevents DOM element from garbage collection unless the handle is
|
|
22
20
|
ElementHandle instances can be used as an argument in [Page#eval_on_selector](./page#eval_on_selector) and [Page#evaluate](./page#evaluate)
|
23
21
|
methods.
|
24
22
|
|
23
|
+
> NOTE: In most cases, you would want to use the [Locator](./locator) object instead. You should only use [ElementHandle](./element_handle) if you
|
24
|
+
want to retain a handle to a particular DOM Node that you intend to pass into [Page#evaluate](./page#evaluate) as an argument.
|
25
|
+
|
26
|
+
The difference between the [Locator](./locator) and ElementHandle is that the ElementHandle points to a particular element, while
|
27
|
+
[Locator](./locator) captures the logic of how to retrieve an element.
|
28
|
+
|
29
|
+
In the example below, handle points to a particular DOM element on page. If that element changes text or is used by
|
30
|
+
React to render an entirely different component, handle is still pointing to that very DOM element. This can lead to
|
31
|
+
unexpected behaviors.
|
32
|
+
|
33
|
+
```ruby
|
34
|
+
handle = page.query_selector("text=Submit")
|
35
|
+
handle.hover
|
36
|
+
handle.click
|
37
|
+
```
|
38
|
+
|
39
|
+
With the locator, every time the `element` is used, up-to-date DOM element is located in the page using the selector. So
|
40
|
+
in the snippet below, underlying DOM element is going to be located twice.
|
41
|
+
|
42
|
+
```ruby
|
43
|
+
locator = page.locator("text=Submit")
|
44
|
+
locator.hover
|
45
|
+
locator.click
|
46
|
+
```
|
47
|
+
|
48
|
+
|
49
|
+
|
25
50
|
## bounding_box
|
26
51
|
|
27
52
|
```
|
@@ -306,7 +331,7 @@ Returns the `element.innerText`.
|
|
306
331
|
def input_value(timeout: nil)
|
307
332
|
```
|
308
333
|
|
309
|
-
Returns `input.value` for `<input>` or `<textarea>` element. Throws for non-input elements.
|
334
|
+
Returns `input.value` for `<input>` or `<textarea>` or `<select>` element. Throws for non-input elements.
|
310
335
|
|
311
336
|
## checked?
|
312
337
|
|
@@ -4,8 +4,21 @@ sidebar_position: 10
|
|
4
4
|
|
5
5
|
# Android
|
6
6
|
|
7
|
-
Playwright has **experimental** support for Android automation.
|
8
|
-
|
7
|
+
Playwright has **experimental** support for Android automation. This includes Chrome for Android and Android WebView.
|
8
|
+
|
9
|
+
*Requirements*
|
10
|
+
- Android device or AVD Emulator.
|
11
|
+
- [ADB daemon](https://developer.android.com/studio/command-line/adb) running and authenticated with your device.
|
12
|
+
Typically running `adb devices` is all you need to do.
|
13
|
+
- [`Chrome 87`](https://play.google.com/store/apps/details?id=com.android.chrome) or newer installed on the device
|
14
|
+
- "Enable command line on non-rooted devices" enabled in `chrome://flags`.
|
15
|
+
|
16
|
+
*Known limitations*
|
17
|
+
- Raw USB operation is not yet supported, so you need ADB.
|
18
|
+
- Device needs to be awake to produce screenshots. Enabling "Stay awake" developer mode will help.
|
19
|
+
- We didn't run all the tests against the device, so not everything works.
|
20
|
+
|
21
|
+
*How to run*
|
9
22
|
|
10
23
|
An example of the Android automation script would be:
|
11
24
|
|
@@ -16,25 +16,16 @@ At every point of time, page exposes its current frame tree via the [Page#main_f
|
|
16
16
|
|
17
17
|
An example of dumping frame tree:
|
18
18
|
|
19
|
-
```
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
page.goto("https://www.theverge.com")
|
27
|
-
dump_frame_tree(page.main_frame, "")
|
28
|
-
browser.close()
|
29
|
-
|
30
|
-
def dump_frame_tree(frame, indent):
|
31
|
-
print(indent + frame.name + '@' + frame.url)
|
32
|
-
for child in frame.child_frames:
|
33
|
-
dump_frame_tree(child, indent + " ")
|
34
|
-
|
35
|
-
with sync_playwright() as playwright:
|
36
|
-
run(playwright)
|
19
|
+
```ruby
|
20
|
+
def dump_frame_tree(frame, indent = 0)
|
21
|
+
puts "#{' ' * indent}#{frame.name}@#{frame.url}"
|
22
|
+
frame.child_frames.each do |child|
|
23
|
+
dump_frame_tree(child, indent + 2)
|
24
|
+
end
|
25
|
+
end
|
37
26
|
|
27
|
+
page.goto("https://www.theverge.com")
|
28
|
+
dump_frame_tree(page.main_frame)
|
38
29
|
```
|
39
30
|
|
40
31
|
|
@@ -68,6 +59,7 @@ def check(
|
|
68
59
|
force: nil,
|
69
60
|
noWaitAfter: nil,
|
70
61
|
position: nil,
|
62
|
+
strict: nil,
|
71
63
|
timeout: nil,
|
72
64
|
trial: nil)
|
73
65
|
```
|
@@ -106,6 +98,7 @@ def click(
|
|
106
98
|
modifiers: nil,
|
107
99
|
noWaitAfter: nil,
|
108
100
|
position: nil,
|
101
|
+
strict: nil,
|
109
102
|
timeout: nil,
|
110
103
|
trial: nil)
|
111
104
|
```
|
@@ -140,6 +133,7 @@ def dblclick(
|
|
140
133
|
modifiers: nil,
|
141
134
|
noWaitAfter: nil,
|
142
135
|
position: nil,
|
136
|
+
strict: nil,
|
143
137
|
timeout: nil,
|
144
138
|
trial: nil)
|
145
139
|
```
|
@@ -161,16 +155,20 @@ zero timeout disables this.
|
|
161
155
|
## dispatch_event
|
162
156
|
|
163
157
|
```
|
164
|
-
def dispatch_event(
|
158
|
+
def dispatch_event(
|
159
|
+
selector,
|
160
|
+
type,
|
161
|
+
eventInit: nil,
|
162
|
+
strict: nil,
|
163
|
+
timeout: nil)
|
165
164
|
```
|
166
165
|
|
167
166
|
The snippet below dispatches the `click` event on the element. Regardless of the visibility state of the element,
|
168
167
|
`click` is dispatched. This is equivalent to calling
|
169
168
|
[element.click()](https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/click).
|
170
169
|
|
171
|
-
```
|
170
|
+
```ruby
|
172
171
|
frame.dispatch_event("button#submit", "click")
|
173
|
-
|
174
172
|
```
|
175
173
|
|
176
174
|
Under the hood, it creates an instance of an event based on the given `type`, initializes it with `eventInit` properties
|
@@ -187,11 +185,10 @@ Since `eventInit` is event-specific, please refer to the events documentation fo
|
|
187
185
|
|
188
186
|
You can also specify [JSHandle](./js_handle) as the property value if you want live objects to be passed into the event:
|
189
187
|
|
190
|
-
```
|
188
|
+
```ruby
|
191
189
|
# note you can only create data_transfer in chromium and firefox
|
192
190
|
data_transfer = frame.evaluate_handle("new DataTransfer()")
|
193
|
-
frame.dispatch_event("#source", "dragstart", {
|
194
|
-
|
191
|
+
frame.dispatch_event("#source", "dragstart", eventInit: { dataTransfer: data_transfer })
|
195
192
|
```
|
196
193
|
|
197
194
|
|
@@ -204,6 +201,9 @@ def drag_and_drop(
|
|
204
201
|
target,
|
205
202
|
force: nil,
|
206
203
|
noWaitAfter: nil,
|
204
|
+
sourcePosition: nil,
|
205
|
+
strict: nil,
|
206
|
+
targetPosition: nil,
|
207
207
|
timeout: nil,
|
208
208
|
trial: nil)
|
209
209
|
```
|
@@ -213,7 +213,7 @@ def drag_and_drop(
|
|
213
213
|
## eval_on_selector
|
214
214
|
|
215
215
|
```
|
216
|
-
def eval_on_selector(selector, expression, arg: nil)
|
216
|
+
def eval_on_selector(selector, expression, arg: nil, strict: nil)
|
217
217
|
```
|
218
218
|
|
219
219
|
Returns the return value of `expression`.
|
@@ -227,11 +227,10 @@ return its value.
|
|
227
227
|
|
228
228
|
Examples:
|
229
229
|
|
230
|
-
```
|
230
|
+
```ruby
|
231
231
|
search_value = frame.eval_on_selector("#search", "el => el.value")
|
232
232
|
preload_href = frame.eval_on_selector("link[rel=preload]", "el => el.href")
|
233
|
-
html = frame.eval_on_selector(".main-container", "(e, suffix) => e.outerHTML + suffix", "hello")
|
234
|
-
|
233
|
+
html = frame.eval_on_selector(".main-container", "(e, suffix) => e.outerHTML + suffix", arg: "hello")
|
235
234
|
```
|
236
235
|
|
237
236
|
|
@@ -252,9 +251,8 @@ return its value.
|
|
252
251
|
|
253
252
|
Examples:
|
254
253
|
|
255
|
-
```
|
256
|
-
divs_counts = frame.eval_on_selector_all("div", "(divs, min) => divs.length >= min", 10)
|
257
|
-
|
254
|
+
```ruby
|
255
|
+
divs_counts = frame.eval_on_selector_all("div", "(divs, min) => divs.length >= min", arg: 10)
|
258
256
|
```
|
259
257
|
|
260
258
|
|
@@ -274,28 +272,25 @@ If the function passed to the [Frame#evaluate](./frame#evaluate) returns a non-[
|
|
274
272
|
[Frame#evaluate](./frame#evaluate) returns `undefined`. Playwright also supports transferring some additional values that are
|
275
273
|
not serializable by `JSON`: `-0`, `NaN`, `Infinity`, `-Infinity`.
|
276
274
|
|
277
|
-
```
|
278
|
-
result = frame.evaluate("([x, y]) => Promise.resolve(x * y)", [7, 8])
|
279
|
-
|
280
|
-
|
275
|
+
```ruby
|
276
|
+
result = frame.evaluate("([x, y]) => Promise.resolve(x * y)", arg: [7, 8])
|
277
|
+
puts result # => "56"
|
281
278
|
```
|
282
279
|
|
283
280
|
A string can also be passed in instead of a function.
|
284
281
|
|
285
|
-
```
|
286
|
-
|
282
|
+
```ruby
|
283
|
+
puts frame.evaluate("1 + 2") # => 3
|
287
284
|
x = 10
|
288
|
-
|
289
|
-
|
285
|
+
puts frame.evaluate("1 + #{x}") # => "11"
|
290
286
|
```
|
291
287
|
|
292
288
|
[ElementHandle](./element_handle) instances can be passed as an argument to the [Frame#evaluate](./frame#evaluate):
|
293
289
|
|
294
|
-
```
|
290
|
+
```ruby
|
295
291
|
body_handle = frame.query_selector("body")
|
296
|
-
html = frame.evaluate("([body, suffix]) => body.innerHTML + suffix", [body_handle, "hello"])
|
297
|
-
body_handle.dispose
|
298
|
-
|
292
|
+
html = frame.evaluate("([body, suffix]) => body.innerHTML + suffix", arg: [body_handle, "hello"])
|
293
|
+
body_handle.dispose
|
299
294
|
```
|
300
295
|
|
301
296
|
|
@@ -314,10 +309,9 @@ The only difference between [Frame#evaluate](./frame#evaluate) and [Frame#evalua
|
|
314
309
|
If the function, passed to the [Frame#evaluate_handle](./frame#evaluate_handle), returns a [Promise](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise), then
|
315
310
|
[Frame#evaluate_handle](./frame#evaluate_handle) would wait for the promise to resolve and return its value.
|
316
311
|
|
317
|
-
```
|
312
|
+
```ruby
|
318
313
|
a_window_handle = frame.evaluate_handle("Promise.resolve(window)")
|
319
314
|
a_window_handle # handle for the window object.
|
320
|
-
|
321
315
|
```
|
322
316
|
|
323
317
|
A string can also be passed in instead of a function.
|
@@ -345,6 +339,7 @@ def fill(
|
|
345
339
|
value,
|
346
340
|
force: nil,
|
347
341
|
noWaitAfter: nil,
|
342
|
+
strict: nil,
|
348
343
|
timeout: nil)
|
349
344
|
```
|
350
345
|
|
@@ -362,7 +357,7 @@ To send fine-grained keyboard events, use [Frame#type](./frame#type).
|
|
362
357
|
## focus
|
363
358
|
|
364
359
|
```
|
365
|
-
def focus(selector, timeout: nil)
|
360
|
+
def focus(selector, strict: nil, timeout: nil)
|
366
361
|
```
|
367
362
|
|
368
363
|
This method fetches an element with `selector` and focuses it. If there's no element matching `selector`, the method
|
@@ -381,11 +376,10 @@ frame.
|
|
381
376
|
|
382
377
|
This method throws an error if the frame has been detached before `frameElement()` returns.
|
383
378
|
|
384
|
-
```
|
385
|
-
frame_element = frame.frame_element
|
386
|
-
content_frame = frame_element.content_frame
|
387
|
-
|
388
|
-
|
379
|
+
```ruby
|
380
|
+
frame_element = frame.frame_element
|
381
|
+
content_frame = frame_element.content_frame
|
382
|
+
puts frame == content_frame # => true
|
389
383
|
```
|
390
384
|
|
391
385
|
|
@@ -393,7 +387,7 @@ assert frame == content_frame
|
|
393
387
|
## get_attribute
|
394
388
|
|
395
389
|
```
|
396
|
-
def get_attribute(selector, name, timeout: nil)
|
390
|
+
def get_attribute(selector, name, strict: nil, timeout: nil)
|
397
391
|
```
|
398
392
|
|
399
393
|
Returns element attribute value.
|
@@ -431,6 +425,7 @@ def hover(
|
|
431
425
|
force: nil,
|
432
426
|
modifiers: nil,
|
433
427
|
position: nil,
|
428
|
+
strict: nil,
|
434
429
|
timeout: nil,
|
435
430
|
trial: nil)
|
436
431
|
```
|
@@ -449,7 +444,7 @@ zero timeout disables this.
|
|
449
444
|
## inner_html
|
450
445
|
|
451
446
|
```
|
452
|
-
def inner_html(selector, timeout: nil)
|
447
|
+
def inner_html(selector, strict: nil, timeout: nil)
|
453
448
|
```
|
454
449
|
|
455
450
|
Returns `element.innerHTML`.
|
@@ -457,7 +452,7 @@ Returns `element.innerHTML`.
|
|
457
452
|
## inner_text
|
458
453
|
|
459
454
|
```
|
460
|
-
def inner_text(selector, timeout: nil)
|
455
|
+
def inner_text(selector, strict: nil, timeout: nil)
|
461
456
|
```
|
462
457
|
|
463
458
|
Returns `element.innerText`.
|
@@ -465,15 +460,15 @@ Returns `element.innerText`.
|
|
465
460
|
## input_value
|
466
461
|
|
467
462
|
```
|
468
|
-
def input_value(selector, timeout: nil)
|
463
|
+
def input_value(selector, strict: nil, timeout: nil)
|
469
464
|
```
|
470
465
|
|
471
|
-
Returns `input.value` for the selected `<input>` or `<textarea>` element. Throws for non-input elements.
|
466
|
+
Returns `input.value` for the selected `<input>` or `<textarea>` or `<select>` element. Throws for non-input elements.
|
472
467
|
|
473
468
|
## checked?
|
474
469
|
|
475
470
|
```
|
476
|
-
def checked?(selector, timeout: nil)
|
471
|
+
def checked?(selector, strict: nil, timeout: nil)
|
477
472
|
```
|
478
473
|
|
479
474
|
Returns whether the element is checked. Throws if the element is not a checkbox or radio input.
|
@@ -489,7 +484,7 @@ Returns `true` if the frame has been detached, or `false` otherwise.
|
|
489
484
|
## disabled?
|
490
485
|
|
491
486
|
```
|
492
|
-
def disabled?(selector, timeout: nil)
|
487
|
+
def disabled?(selector, strict: nil, timeout: nil)
|
493
488
|
```
|
494
489
|
|
495
490
|
Returns whether the element is disabled, the opposite of [enabled](https://playwright.dev/python/docs/actionability).
|
@@ -497,7 +492,7 @@ Returns whether the element is disabled, the opposite of [enabled](https://playw
|
|
497
492
|
## editable?
|
498
493
|
|
499
494
|
```
|
500
|
-
def editable?(selector, timeout: nil)
|
495
|
+
def editable?(selector, strict: nil, timeout: nil)
|
501
496
|
```
|
502
497
|
|
503
498
|
Returns whether the element is [editable](https://playwright.dev/python/docs/actionability).
|
@@ -505,7 +500,7 @@ Returns whether the element is [editable](https://playwright.dev/python/docs/act
|
|
505
500
|
## enabled?
|
506
501
|
|
507
502
|
```
|
508
|
-
def enabled?(selector, timeout: nil)
|
503
|
+
def enabled?(selector, strict: nil, timeout: nil)
|
509
504
|
```
|
510
505
|
|
511
506
|
Returns whether the element is [enabled](https://playwright.dev/python/docs/actionability).
|
@@ -513,7 +508,7 @@ Returns whether the element is [enabled](https://playwright.dev/python/docs/acti
|
|
513
508
|
## hidden?
|
514
509
|
|
515
510
|
```
|
516
|
-
def hidden?(selector, timeout: nil)
|
511
|
+
def hidden?(selector, strict: nil, timeout: nil)
|
517
512
|
```
|
518
513
|
|
519
514
|
Returns whether the element is hidden, the opposite of [visible](https://playwright.dev/python/docs/actionability). `selector` that does not
|
@@ -522,12 +517,24 @@ match any elements is considered hidden.
|
|
522
517
|
## visible?
|
523
518
|
|
524
519
|
```
|
525
|
-
def visible?(selector, timeout: nil)
|
520
|
+
def visible?(selector, strict: nil, timeout: nil)
|
526
521
|
```
|
527
522
|
|
528
523
|
Returns whether the element is [visible](https://playwright.dev/python/docs/actionability). `selector` that does not match any elements is
|
529
524
|
considered not visible.
|
530
525
|
|
526
|
+
## locator
|
527
|
+
|
528
|
+
```
|
529
|
+
def locator(selector)
|
530
|
+
```
|
531
|
+
|
532
|
+
The method returns an element locator that can be used to perform actions in the frame. Locator is resolved to the
|
533
|
+
element immediately before performing an action, so a series of actions on the same locator can in fact be performed on
|
534
|
+
different DOM elements. That would happen if the DOM structure between those actions has changed.
|
535
|
+
|
536
|
+
Note that locator always implies visibility, so it will always be locating visible elements.
|
537
|
+
|
531
538
|
## name
|
532
539
|
|
533
540
|
```
|
@@ -564,6 +571,7 @@ def press(
|
|
564
571
|
key,
|
565
572
|
delay: nil,
|
566
573
|
noWaitAfter: nil,
|
574
|
+
strict: nil,
|
567
575
|
timeout: nil)
|
568
576
|
```
|
569
577
|
|
@@ -587,7 +595,7 @@ modifier, modifier is pressed and being held while the subsequent key is being p
|
|
587
595
|
## query_selector
|
588
596
|
|
589
597
|
```
|
590
|
-
def query_selector(selector)
|
598
|
+
def query_selector(selector, strict: nil)
|
591
599
|
```
|
592
600
|
|
593
601
|
Returns the ElementHandle pointing to the frame element.
|
@@ -617,6 +625,7 @@ def select_option(
|
|
617
625
|
label: nil,
|
618
626
|
force: nil,
|
619
627
|
noWaitAfter: nil,
|
628
|
+
strict: nil,
|
620
629
|
timeout: nil)
|
621
630
|
```
|
622
631
|
|
@@ -631,14 +640,13 @@ Returns the array of option values that have been successfully selected.
|
|
631
640
|
|
632
641
|
Triggers a `change` and `input` event once all the provided options have been selected.
|
633
642
|
|
634
|
-
```
|
643
|
+
```ruby
|
635
644
|
# single selection matching the value
|
636
|
-
frame.select_option("select#colors", "blue")
|
645
|
+
frame.select_option("select#colors", value: "blue")
|
637
646
|
# single selection matching both the label
|
638
|
-
frame.select_option("select#colors", label
|
647
|
+
frame.select_option("select#colors", label: "blue")
|
639
648
|
# multiple selection
|
640
|
-
frame.select_option("select#colors", value
|
641
|
-
|
649
|
+
frame.select_option("select#colors", value: ["red", "green", "blue"])
|
642
650
|
```
|
643
651
|
|
644
652
|
|
@@ -655,7 +663,12 @@ alias: `content=`
|
|
655
663
|
## set_input_files
|
656
664
|
|
657
665
|
```
|
658
|
-
def set_input_files(
|
666
|
+
def set_input_files(
|
667
|
+
selector,
|
668
|
+
files,
|
669
|
+
noWaitAfter: nil,
|
670
|
+
strict: nil,
|
671
|
+
timeout: nil)
|
659
672
|
```
|
660
673
|
|
661
674
|
This method expects `selector` to point to an
|
@@ -673,6 +686,7 @@ def tap_point(
|
|
673
686
|
modifiers: nil,
|
674
687
|
noWaitAfter: nil,
|
675
688
|
position: nil,
|
689
|
+
strict: nil,
|
676
690
|
timeout: nil,
|
677
691
|
trial: nil)
|
678
692
|
```
|
@@ -693,7 +707,7 @@ zero timeout disables this.
|
|
693
707
|
## text_content
|
694
708
|
|
695
709
|
```
|
696
|
-
def text_content(selector, timeout: nil)
|
710
|
+
def text_content(selector, strict: nil, timeout: nil)
|
697
711
|
```
|
698
712
|
|
699
713
|
Returns `element.textContent`.
|
@@ -714,6 +728,7 @@ def type(
|
|
714
728
|
text,
|
715
729
|
delay: nil,
|
716
730
|
noWaitAfter: nil,
|
731
|
+
strict: nil,
|
717
732
|
timeout: nil)
|
718
733
|
```
|
719
734
|
|
@@ -722,10 +737,9 @@ send fine-grained keyboard events. To fill values in form fields, use [Frame#fil
|
|
722
737
|
|
723
738
|
To press a special key, like `Control` or `ArrowDown`, use [Keyboard#press](./keyboard#press).
|
724
739
|
|
725
|
-
```
|
740
|
+
```ruby
|
726
741
|
frame.type("#mytextarea", "hello") # types instantly
|
727
|
-
frame.type("#mytextarea", "world", delay
|
728
|
-
|
742
|
+
frame.type("#mytextarea", "world", delay: 100) # types slower, like a user
|
729
743
|
```
|
730
744
|
|
731
745
|
|
@@ -738,6 +752,7 @@ def uncheck(
|
|
738
752
|
force: nil,
|
739
753
|
noWaitAfter: nil,
|
740
754
|
position: nil,
|
755
|
+
strict: nil,
|
741
756
|
timeout: nil,
|
742
757
|
trial: nil)
|
743
758
|
```
|
@@ -774,28 +789,16 @@ Returns when the `expression` returns a truthy value, returns that value.
|
|
774
789
|
|
775
790
|
The [Frame#wait_for_function](./frame#wait_for_function) can be used to observe viewport size change:
|
776
791
|
|
777
|
-
```
|
778
|
-
|
779
|
-
|
780
|
-
def run(playwright):
|
781
|
-
webkit = playwright.webkit
|
782
|
-
browser = webkit.launch()
|
783
|
-
page = browser.new_page()
|
784
|
-
page.evaluate("window.x = 0; setTimeout(() => { window.x = 100 }, 1000);")
|
785
|
-
page.main_frame.wait_for_function("() => window.x > 0")
|
786
|
-
browser.close()
|
787
|
-
|
788
|
-
with sync_playwright() as playwright:
|
789
|
-
run(playwright)
|
790
|
-
|
792
|
+
```ruby
|
793
|
+
frame.evaluate("window.x = 0; setTimeout(() => { window.x = 100 }, 1000);")
|
794
|
+
frame.wait_for_function("() => window.x > 0")
|
791
795
|
```
|
792
796
|
|
793
797
|
To pass an argument to the predicate of `frame.waitForFunction` function:
|
794
798
|
|
795
|
-
```
|
799
|
+
```ruby
|
796
800
|
selector = ".foo"
|
797
|
-
frame.wait_for_function("selector => !!document.querySelector(selector)", selector)
|
798
|
-
|
801
|
+
frame.wait_for_function("selector => !!document.querySelector(selector)", arg: selector)
|
799
802
|
```
|
800
803
|
|
801
804
|
|
@@ -811,10 +814,9 @@ Waits for the required load state to be reached.
|
|
811
814
|
This returns when the frame reaches a required load state, `load` by default. The navigation must have been committed
|
812
815
|
when this method is called. If current document has already reached the required state, resolves immediately.
|
813
816
|
|
814
|
-
```
|
817
|
+
```ruby
|
815
818
|
frame.click("button") # click triggers navigation.
|
816
|
-
frame.wait_for_load_state
|
817
|
-
|
819
|
+
frame.wait_for_load_state # the promise resolves after "load" event.
|
818
820
|
```
|
819
821
|
|
820
822
|
|
@@ -832,11 +834,10 @@ History API usage, the navigation will resolve with `null`.
|
|
832
834
|
This method waits for the frame to navigate to a new URL. It is useful for when you run code which will indirectly cause
|
833
835
|
the frame to navigate. Consider this example:
|
834
836
|
|
835
|
-
```
|
836
|
-
|
837
|
-
|
838
|
-
# Resolves after navigation has finished
|
839
|
-
|
837
|
+
```ruby
|
838
|
+
frame.expect_navigation do
|
839
|
+
frame.click("a.delayed-navigation") # clicking the link will indirectly cause a navigation
|
840
|
+
end # Resolves after navigation has finished
|
840
841
|
```
|
841
842
|
|
842
843
|
> NOTE: Usage of the [History API](https://developer.mozilla.org/en-US/docs/Web/API/History_API) to change the URL is
|
@@ -845,7 +846,7 @@ considered a navigation.
|
|
845
846
|
## wait_for_selector
|
846
847
|
|
847
848
|
```
|
848
|
-
def wait_for_selector(selector, state: nil, timeout: nil)
|
849
|
+
def wait_for_selector(selector, state: nil, strict: nil, timeout: nil)
|
849
850
|
```
|
850
851
|
|
851
852
|
Returns when element specified by selector satisfies `state` option. Returns `null` if waiting for `hidden` or
|
@@ -857,25 +858,27 @@ selector doesn't satisfy the condition for the `timeout` milliseconds, the funct
|
|
857
858
|
|
858
859
|
This method works across navigations:
|
859
860
|
|
860
|
-
```
|
861
|
-
|
861
|
+
```ruby
|
862
|
+
%w[https://google.com https://bbc.com].each do |current_url|
|
863
|
+
page.goto(current_url, waitUntil: "domcontentloaded")
|
864
|
+
frame = page.main_frame
|
865
|
+
element = frame.wait_for_selector("img")
|
866
|
+
puts "Loaded image: #{element["src"]}"
|
867
|
+
end
|
868
|
+
```
|
869
|
+
|
862
870
|
|
863
|
-
def run(playwright):
|
864
|
-
chromium = playwright.chromium
|
865
|
-
browser = chromium.launch()
|
866
|
-
page = browser.new_page()
|
867
|
-
for current_url in ["https://google.com", "https://bbc.com"]:
|
868
|
-
page.goto(current_url, wait_until="domcontentloaded")
|
869
|
-
element = page.main_frame.wait_for_selector("img")
|
870
|
-
print("Loaded image: " + str(element.get_attribute("src")))
|
871
|
-
browser.close()
|
872
871
|
|
873
|
-
|
874
|
-
run(playwright)
|
872
|
+
## wait_for_timeout
|
875
873
|
|
874
|
+
```
|
875
|
+
def wait_for_timeout(timeout)
|
876
876
|
```
|
877
877
|
|
878
|
+
Waits for the given `timeout` in milliseconds.
|
878
879
|
|
880
|
+
Note that `frame.waitForTimeout()` should only be used for debugging. Tests using the timer in production are going to
|
881
|
+
be flaky. Use signals such as network events, selectors becoming visible and others instead.
|
879
882
|
|
880
883
|
## wait_for_url
|
881
884
|
|
@@ -885,10 +888,9 @@ def wait_for_url(url, timeout: nil, waitUntil: nil)
|
|
885
888
|
|
886
889
|
Waits for the frame to navigate to the given URL.
|
887
890
|
|
888
|
-
```
|
891
|
+
```ruby
|
889
892
|
frame.click("a.delayed-navigation") # clicking the link will indirectly cause a navigation
|
890
893
|
frame.wait_for_url("**/target.html")
|
891
|
-
|
892
894
|
```
|
893
895
|
|
894
896
|
|