puppeteer-ruby 0.44.3 → 0.45.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +8 -1
- data/README.md +0 -6
- data/docs/api_coverage.md +12 -3
- data/lib/puppeteer/browser_context.rb +2 -0
- data/lib/puppeteer/coverage.rb +5 -1
- data/lib/puppeteer/element_handle.rb +7 -0
- data/lib/puppeteer/frame_manager.rb +6 -1
- data/lib/puppeteer/isolated_world.rb +4 -6
- data/lib/puppeteer/js_coverage.rb +9 -2
- data/lib/puppeteer/keyboard.rb +4 -3
- data/lib/puppeteer/launcher/chrome.rb +10 -8
- data/lib/puppeteer/lifecycle_watcher.rb +9 -1
- data/lib/puppeteer/puppeteer.rb +36 -6
- data/lib/puppeteer/version.rb +1 -1
- metadata +2 -3
- data/lib/puppeteer/browser_fetcher.rb +0 -6
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 037ab626560f55e8fe53f7ac978eccd187132d795bdda193b9afc5d761593c77
|
4
|
+
data.tar.gz: ee5cd15db34563d127fc4d58c846d92273cb47916096de025bed43e7580a1e81
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: a92921b6c243605d715fb3514c1965f69d2c7446236d33d45a0657a9a9a4c401a3223ee4e68eefcd8cadd6cda7cb598c845a74a152ef8ba1f980f3ea29d335d2
|
7
|
+
data.tar.gz: eb07704a147fa0029b0ac328dee0ec2a6757528058f102669cf2f8e2d6eae954f195665f1cbc4b2bc6a33e02e6b948fea18a78232c65407b9ce0c5762195c2c7
|
data/CHANGELOG.md
CHANGED
@@ -1,4 +1,11 @@
|
|
1
|
-
### main [[diff](https://github.com/YusukeIwaki/puppeteer-ruby/compare/0.
|
1
|
+
### main [[diff](https://github.com/YusukeIwaki/puppeteer-ruby/compare/0.45.0...main)]
|
2
|
+
|
3
|
+
### 0.45.0 [[diff](https://github.com/YusukeIwaki/puppeteer-ruby/compare/0.44.3...0.45.0)]
|
4
|
+
|
5
|
+
- Port Puppeteer v18.0-v19.5 features except for 3 features below (If wanted, please create a issue of the feature request :)
|
6
|
+
- Extra headers for Puppeteer.connect ([#9314](https://github.com/puppeteer/puppeteer/pull/9314))
|
7
|
+
- Improvement of missing product message ([#9207](https://github.com/puppeteer/puppeteer/pull/9207))
|
8
|
+
- Configuration file (.puppeteerrc/puppeteer.config.js) ([#9140](https://github.com/puppeteer/puppeteer/pull/9140)).
|
2
9
|
|
3
10
|
### 0.44.3 [[diff](https://github.com/YusukeIwaki/puppeteer-ruby/compare/0.44.2...0.44.3)]
|
4
11
|
|
data/README.md
CHANGED
@@ -229,12 +229,6 @@ end
|
|
229
229
|
|
230
230
|
https://yusukeiwaki.github.io/puppeteer-ruby-docs/
|
231
231
|
|
232
|
-
## Limitations
|
233
|
-
|
234
|
-
### Not compatible with Firefox >= v97.0
|
235
|
-
|
236
|
-
:sos: Help and contribution wanted! :sos:
|
237
|
-
https://github.com/YusukeIwaki/puppeteer-ruby/issues/220
|
238
232
|
|
239
233
|
## Contributing
|
240
234
|
|
data/docs/api_coverage.md
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
# API coverages
|
2
|
-
- Puppeteer version:
|
3
|
-
- puppeteer-ruby version: 0.
|
2
|
+
- Puppeteer version: v19.5.0
|
3
|
+
- puppeteer-ruby version: 0.45.0
|
4
4
|
|
5
5
|
## Puppeteer
|
6
6
|
|
@@ -14,7 +14,8 @@
|
|
14
14
|
* executablePath => `#executable_path`
|
15
15
|
* launch
|
16
16
|
* networkConditions => `#network_conditions`
|
17
|
-
* ~~
|
17
|
+
* ~~puppeteer~~
|
18
|
+
* registerCustomQueryHandler => `#register_custom_query_handler`
|
18
19
|
* ~~unregisterCustomQueryHandler~~
|
19
20
|
|
20
21
|
## ~~Accessibility~~
|
@@ -134,6 +135,7 @@
|
|
134
135
|
* screenshot
|
135
136
|
* select
|
136
137
|
* tap
|
138
|
+
* toElement => `#to_element`
|
137
139
|
* type => `#type_text`
|
138
140
|
* uploadFile => `#upload_file`
|
139
141
|
* waitForSelector => `#wait_for_selector`
|
@@ -282,6 +284,7 @@
|
|
282
284
|
* addScriptTag => `#add_script_tag`
|
283
285
|
* addStyleTag => `#add_style_tag`
|
284
286
|
* addStyleTag => `#add_style_tag`
|
287
|
+
* addStyleTag => `#add_style_tag`
|
285
288
|
* authenticate
|
286
289
|
* bringToFront => `#bring_to_front`
|
287
290
|
* browser
|
@@ -356,6 +359,12 @@
|
|
356
359
|
* waitForXPath => `#wait_for_xpath`
|
357
360
|
* workers
|
358
361
|
|
362
|
+
## ~~ProductLauncher~~
|
363
|
+
|
364
|
+
* ~~defaultArgs~~
|
365
|
+
* ~~executablePath~~
|
366
|
+
* ~~launch~~
|
367
|
+
|
359
368
|
## ~~ProtocolError~~
|
360
369
|
|
361
370
|
|
@@ -11,6 +11,8 @@ class Puppeteer::BrowserContext
|
|
11
11
|
@id = context_id
|
12
12
|
end
|
13
13
|
|
14
|
+
attr_reader :id
|
15
|
+
|
14
16
|
# @param event_name [Symbol] either of :disconnected, :targetcreated, :targetchanged, :targetdestroyed
|
15
17
|
def on(event_name, &block)
|
16
18
|
unless BrowserContextEmittedEvents.values.include?(event_name.to_s)
|
data/lib/puppeteer/coverage.rb
CHANGED
@@ -8,11 +8,13 @@ class Puppeteer::Coverage
|
|
8
8
|
def start_js_coverage(
|
9
9
|
reset_on_navigation: nil,
|
10
10
|
report_anonymous_scripts: nil,
|
11
|
-
include_raw_script_coverage: nil
|
11
|
+
include_raw_script_coverage: nil,
|
12
|
+
use_block_coverage: nil)
|
12
13
|
@js.start(
|
13
14
|
reset_on_navigation: reset_on_navigation,
|
14
15
|
report_anonymous_scripts: report_anonymous_scripts,
|
15
16
|
include_raw_script_coverage: include_raw_script_coverage,
|
17
|
+
use_block_coverage: use_block_coverage,
|
16
18
|
)
|
17
19
|
end
|
18
20
|
|
@@ -24,6 +26,7 @@ class Puppeteer::Coverage
|
|
24
26
|
reset_on_navigation: nil,
|
25
27
|
report_anonymous_scripts: nil,
|
26
28
|
include_raw_script_coverage: nil,
|
29
|
+
use_block_coverage: nil,
|
27
30
|
&block)
|
28
31
|
unless block
|
29
32
|
raise ArgumentError.new('Block must be given')
|
@@ -33,6 +36,7 @@ class Puppeteer::Coverage
|
|
33
36
|
reset_on_navigation: reset_on_navigation,
|
34
37
|
report_anonymous_scripts: report_anonymous_scripts,
|
35
38
|
include_raw_script_coverage: include_raw_script_coverage,
|
39
|
+
use_block_coverage: use_block_coverage,
|
36
40
|
)
|
37
41
|
block.call
|
38
42
|
stop_js_coverage
|
@@ -126,6 +126,13 @@ class Puppeteer::ElementHandle < Puppeteer::JSHandle
|
|
126
126
|
|
127
127
|
define_async_method :async_wait_for_xpath
|
128
128
|
|
129
|
+
def to_element(tag_name)
|
130
|
+
unless evaluate('(node, tagName) => node.nodeName === tagName.toUpperCase()', tag_name)
|
131
|
+
raise ArgumentError.new("Element is not a(n) `#{tag_name}` element")
|
132
|
+
end
|
133
|
+
self
|
134
|
+
end
|
135
|
+
|
129
136
|
def as_element
|
130
137
|
self
|
131
138
|
end
|
@@ -21,6 +21,8 @@ class Puppeteer::FrameManager
|
|
21
21
|
# @type {!Map<string, !Frame>}
|
22
22
|
@frames = {}
|
23
23
|
|
24
|
+
@frame_naviigated_received = Set.new
|
25
|
+
|
24
26
|
# @type {!Map<number, !ExecutionContext>}
|
25
27
|
@context_id_to_context = {}
|
26
28
|
|
@@ -42,6 +44,7 @@ class Puppeteer::FrameManager
|
|
42
44
|
handle_frame_attached(client, event['frameId'], event['parentFrameId'])
|
43
45
|
end
|
44
46
|
client.on_event('Page.frameNavigated') do |event|
|
47
|
+
@frame_naviigated_received << event['frame']['id']
|
45
48
|
handle_frame_navigated(event['frame'])
|
46
49
|
end
|
47
50
|
client.on_event('Page.navigatedWithinDocument') do |event|
|
@@ -227,7 +230,9 @@ class Puppeteer::FrameManager
|
|
227
230
|
if frame_tree['frame']['parentId']
|
228
231
|
handle_frame_attached(session, frame_tree['frame']['id'], frame_tree['frame']['parentId'])
|
229
232
|
end
|
230
|
-
|
233
|
+
unless @frame_naviigated_received.delete?(frame_tree['frame']['id'])
|
234
|
+
handle_frame_navigated(frame_tree['frame'])
|
235
|
+
end
|
231
236
|
return if !frame_tree['childFrames']
|
232
237
|
|
233
238
|
frame_tree['childFrames'].each do |child|
|
@@ -562,18 +562,16 @@ class Puppeteer::IsolaatedWorld
|
|
562
562
|
node.nodeType === Node.TEXT_NODE ? node.parentElement : node;
|
563
563
|
|
564
564
|
const style = window.getComputedStyle(element);
|
565
|
+
const hidden_visibility_values = ['hidden', 'collapse'];
|
565
566
|
const isVisible =
|
566
|
-
style && style.visibility
|
567
|
+
style && !hidden_visibility_values.includes(style.visibility) && !isBoundingBoxEmpty(element);
|
567
568
|
const success =
|
568
569
|
waitForVisible === isVisible || waitForHidden === !isVisible;
|
569
570
|
return success ? node : null;
|
570
571
|
|
571
|
-
|
572
|
-
* @return {boolean}
|
573
|
-
*/
|
574
|
-
function hasVisibleBoundingBox() {
|
572
|
+
function isBoundingBoxEmpty(element) {
|
575
573
|
const rect = element.getBoundingClientRect();
|
576
|
-
return
|
574
|
+
return rect.width === 0 || rect.height === 0;
|
577
575
|
}
|
578
576
|
}
|
579
577
|
}
|
@@ -31,7 +31,8 @@ class Puppeteer::JSCoverage
|
|
31
31
|
def start(
|
32
32
|
reset_on_navigation: nil,
|
33
33
|
report_anonymous_scripts: nil,
|
34
|
-
include_raw_script_coverage: nil
|
34
|
+
include_raw_script_coverage: nil,
|
35
|
+
use_block_coverage: nil)
|
35
36
|
raise 'JSCoverage is already enabled' if @enabled
|
36
37
|
|
37
38
|
@reset_on_navigation =
|
@@ -40,6 +41,12 @@ class Puppeteer::JSCoverage
|
|
40
41
|
else
|
41
42
|
true
|
42
43
|
end
|
44
|
+
@use_block_coverage =
|
45
|
+
if [true, false].include?(use_block_coverage)
|
46
|
+
use_block_coverage
|
47
|
+
else
|
48
|
+
true
|
49
|
+
end
|
43
50
|
@report_anonymous_scripts = report_anonymous_scripts || false
|
44
51
|
@include_raw_script_coverage = include_raw_script_coverage || false
|
45
52
|
@enabled = true
|
@@ -56,7 +63,7 @@ class Puppeteer::JSCoverage
|
|
56
63
|
@client.async_send_message('Profiler.enable'),
|
57
64
|
@client.async_send_message('Profiler.startPreciseCoverage',
|
58
65
|
callCount: @include_raw_script_coverage,
|
59
|
-
detailed:
|
66
|
+
detailed: @use_block_coverage,
|
60
67
|
),
|
61
68
|
@client.async_send_message('Debugger.enable'),
|
62
69
|
@client.async_send_message('Debugger.setSkipAllPauses', skip: true),
|
data/lib/puppeteer/keyboard.rb
CHANGED
@@ -15,7 +15,7 @@ class Puppeteer::Keyboard
|
|
15
15
|
|
16
16
|
# @param key [String]
|
17
17
|
# @param text [String]
|
18
|
-
def down(key, text: nil)
|
18
|
+
def down(key, text: nil, commands: nil)
|
19
19
|
description = key_description_for_string(key)
|
20
20
|
|
21
21
|
auto_repeat = @pressed_keys.include?(description.code)
|
@@ -34,6 +34,7 @@ class Puppeteer::Keyboard
|
|
34
34
|
autoRepeat: auto_repeat,
|
35
35
|
location: description.location,
|
36
36
|
isKeypad: description.location == 3,
|
37
|
+
commands: commands,
|
37
38
|
}.compact
|
38
39
|
@client.send_message('Input.dispatchKeyEvent', params)
|
39
40
|
end
|
@@ -151,8 +152,8 @@ class Puppeteer::Keyboard
|
|
151
152
|
# @param key [String]
|
152
153
|
# @param text [String]
|
153
154
|
# @return [Future]
|
154
|
-
def press(key, delay: nil, text: nil)
|
155
|
-
down(key, text: text)
|
155
|
+
def press(key, delay: nil, text: nil, commands: nil)
|
156
|
+
down(key, text: text, commands: commands)
|
156
157
|
if delay
|
157
158
|
sleep(delay.to_i / 1000.0)
|
158
159
|
end
|
@@ -114,36 +114,38 @@ module Puppeteer::Launcher
|
|
114
114
|
|
115
115
|
# @param options [Launcher::ChromeArgOptions]
|
116
116
|
def initialize(chrome_arg_options)
|
117
|
+
# See https://github.com/GoogleChrome/chrome-launcher/blob/main/docs/chrome-flags-for-tools.md
|
117
118
|
chrome_arguments = [
|
119
|
+
'--allow-pre-commit-input',
|
118
120
|
'--disable-background-networking',
|
119
|
-
'--enable-features=NetworkService,NetworkServiceInProcess',
|
120
121
|
'--disable-background-timer-throttling',
|
121
122
|
'--disable-backgrounding-occluded-windows',
|
122
123
|
'--disable-breakpad',
|
123
124
|
'--disable-client-side-phishing-detection',
|
124
125
|
'--disable-component-extensions-with-background-pages',
|
126
|
+
'--disable-component-update',
|
125
127
|
'--disable-default-apps',
|
126
128
|
'--disable-dev-shm-usage',
|
127
129
|
'--disable-extensions',
|
128
|
-
# TODO: remove AvoidUnnecessaryBeforeUnloadCheckSync below
|
129
|
-
# once crbug.com/1324138 is fixed and released.
|
130
130
|
# AcceptCHFrame disabled because of crbug.com/1348106.
|
131
|
-
'--disable-features=Translate,BackForwardCache,AcceptCHFrame,
|
131
|
+
'--disable-features=Translate,BackForwardCache,AcceptCHFrame,MediaRouter,OptimizationHints',
|
132
132
|
'--disable-hang-monitor',
|
133
133
|
'--disable-ipc-flooding-protection',
|
134
134
|
'--disable-popup-blocking',
|
135
135
|
'--disable-prompt-on-repost',
|
136
136
|
'--disable-renderer-backgrounding',
|
137
137
|
'--disable-sync',
|
138
|
+
'--enable-automation',
|
139
|
+
# TODO(sadym): remove '--enable-blink-features=IdleDetection' once
|
140
|
+
# IdleDetection is turned on by default.
|
141
|
+
'--enable-blink-features=IdleDetection',
|
142
|
+
'--enable-features=NetworkServiceInProcess2',
|
143
|
+
'--export-tagged-pdf',
|
138
144
|
'--force-color-profile=srgb',
|
139
145
|
'--metrics-recording-only',
|
140
146
|
'--no-first-run',
|
141
|
-
'--enable-automation',
|
142
147
|
'--password-store=basic',
|
143
148
|
'--use-mock-keychain',
|
144
|
-
# TODO(sadym): remove '--enable-blink-features=IdleDetection'
|
145
|
-
# once IdleDetection is turned on by default.
|
146
|
-
'--enable-blink-features=IdleDetection',
|
147
149
|
]
|
148
150
|
|
149
151
|
if chrome_arg_options.user_data_dir
|
@@ -84,6 +84,7 @@ class Puppeteer::LifecycleWatcher
|
|
84
84
|
@listener_ids['network_manager'] = [
|
85
85
|
@frame_manager.network_manager.add_event_listener(NetworkManagerEmittedEvents::Request, &method(:handle_request)),
|
86
86
|
@frame_manager.network_manager.add_event_listener(NetworkManagerEmittedEvents::Response, &method(:handle_response)),
|
87
|
+
@frame_manager.network_manager.add_event_listener(NetworkManagerEmittedEvents::RequestFailed, &method(:handle_request_failed)),
|
87
88
|
]
|
88
89
|
|
89
90
|
@same_document_navigation_promise = resolvable_future
|
@@ -107,9 +108,16 @@ class Puppeteer::LifecycleWatcher
|
|
107
108
|
end
|
108
109
|
end
|
109
110
|
|
111
|
+
# @param [Puppeteer::HTTPRequest] request
|
112
|
+
def handle_request_failed(request)
|
113
|
+
return if @navigation_request&.internal&.request_id != request.internal.request_id
|
114
|
+
|
115
|
+
@navigation_response_received.fulfill(nil) unless @navigation_response_received.resolved?
|
116
|
+
end
|
117
|
+
|
110
118
|
# @param [Puppeteer::HTTPResponse] response
|
111
119
|
def handle_response(response)
|
112
|
-
return if @navigation_request&.internal&.request_id
|
120
|
+
return if @navigation_request&.internal&.request_id != response.request.internal.request_id
|
113
121
|
|
114
122
|
@navigation_response_received.fulfill(nil) unless @navigation_response_received.resolved?
|
115
123
|
end
|
data/lib/puppeteer/puppeteer.rb
CHANGED
@@ -141,6 +141,42 @@ class Puppeteer::Puppeteer
|
|
141
141
|
launcher.product
|
142
142
|
end
|
143
143
|
|
144
|
+
def register_custom_query_handler(name:, query_one:, query_all:)
|
145
|
+
unless name =~ /\A[a-zA-Z]+\z/
|
146
|
+
raise ArgumentError.new("Custom query handler names may only contain [a-zA-Z]")
|
147
|
+
end
|
148
|
+
|
149
|
+
handler_name = name.to_sym
|
150
|
+
if query_handler_manager.query_handlers.key?(handler_name)
|
151
|
+
raise ArgumentError.new("A query handler named #{name} already exists")
|
152
|
+
end
|
153
|
+
|
154
|
+
handler = Puppeteer::CustomQueryHandler.new(query_one: query_one, query_all: query_all)
|
155
|
+
Puppeteer::QueryHandlerManager.instance.query_handlers[handler_name] = handler
|
156
|
+
end
|
157
|
+
|
158
|
+
def with_custom_query_handler(name:, query_one:, query_all:, &block)
|
159
|
+
unless name =~ /\A[a-zA-Z]+\z/
|
160
|
+
raise ArgumentError.new("Custom query handler names may only contain [a-zA-Z]")
|
161
|
+
end
|
162
|
+
|
163
|
+
handler_name = name.to_sym
|
164
|
+
|
165
|
+
handler = Puppeteer::CustomQueryHandler.new(query_one: query_one, query_all: query_all)
|
166
|
+
query_handler_manager = Puppeteer::QueryHandlerManager.instance
|
167
|
+
original = query_handler_manager.query_handlers.delete(handler_name)
|
168
|
+
query_handler_manager.query_handlers[handler_name] = handler
|
169
|
+
begin
|
170
|
+
block.call
|
171
|
+
ensure
|
172
|
+
if original
|
173
|
+
query_handler_manager.query_handlers[handler_name] = original
|
174
|
+
else
|
175
|
+
query_handler_manager.query_handlers.delete(handler_name)
|
176
|
+
end
|
177
|
+
end
|
178
|
+
end
|
179
|
+
|
144
180
|
# @return [Puppeteer::Devices]
|
145
181
|
def devices
|
146
182
|
Puppeteer::Devices
|
@@ -170,10 +206,4 @@ class Puppeteer::Puppeteer
|
|
170
206
|
}.compact
|
171
207
|
launcher.default_args(options)
|
172
208
|
end
|
173
|
-
|
174
|
-
# @param {!BrowserFetcher.Options=} options
|
175
|
-
# @return {!BrowserFetcher}
|
176
|
-
def createBrowserFetcher(options = {})
|
177
|
-
BrowserFetcher.new(@project_root, options)
|
178
|
-
end
|
179
209
|
end
|
data/lib/puppeteer/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: puppeteer-ruby
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.45.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- YusukeIwaki
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-01-
|
11
|
+
date: 2023-01-10 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: concurrent-ruby
|
@@ -257,7 +257,6 @@ files:
|
|
257
257
|
- lib/puppeteer/browser.rb
|
258
258
|
- lib/puppeteer/browser_connector.rb
|
259
259
|
- lib/puppeteer/browser_context.rb
|
260
|
-
- lib/puppeteer/browser_fetcher.rb
|
261
260
|
- lib/puppeteer/browser_runner.rb
|
262
261
|
- lib/puppeteer/cdp_session.rb
|
263
262
|
- lib/puppeteer/chrome_target_manager.rb
|