puppeteer-ruby 0.40.4 → 0.40.7
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 +15 -1
- data/README.md +7 -0
- data/docs/api_coverage.md +4 -4
- data/lib/puppeteer/browser_runner.rb +1 -1
- data/lib/puppeteer/connection.rb +1 -0
- data/lib/puppeteer/element_handle/box_model.rb +3 -2
- data/lib/puppeteer/element_handle.rb +51 -7
- data/lib/puppeteer/events.rb +1 -0
- data/lib/puppeteer/frame_manager.rb +3 -1
- data/lib/puppeteer/http_request.rb +90 -34
- data/lib/puppeteer/js_handle.rb +1 -0
- data/lib/puppeteer/launcher/chrome.rb +1 -1
- data/lib/puppeteer/lifecycle_watcher.rb +11 -0
- data/lib/puppeteer/network_event_manager.rb +4 -0
- data/lib/puppeteer/network_manager.rb +9 -0
- data/lib/puppeteer/page.rb +15 -3
- data/lib/puppeteer/version.rb +1 -1
- data/puppeteer-ruby.gemspec +1 -1
- metadata +4 -4
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 674e5731f3d469805214a3ddb7e56ae83aaaa6850db3ccddd02002cffe4e1ca4
|
|
4
|
+
data.tar.gz: 47f5ad6e1a7b30c394ce950991c067c9b2dd42c144ec561eaa3dbbc9efb9b77a
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: b4f53e004dbbba48ebfaa5a1197d5bfdf9d2364a6bd84edf94d378b4b193661f0dc43de51fd61e009d91d5ca1eff7afb62e824fc23ce6bfc6dfa2b36aeda0457
|
|
7
|
+
data.tar.gz: 537e1dc87b4fa9d7644035e1a7a590ec32d64275ee7166940a9e6454b94997b873b1e06c1f2f8ad25c33f39caed4eb05601de46808f09748e13f9db15868c750
|
data/CHANGELOG.md
CHANGED
|
@@ -1,7 +1,21 @@
|
|
|
1
|
-
### main [[diff](https://github.com/YusukeIwaki/puppeteer-ruby/compare/0.40.
|
|
1
|
+
### main [[diff](https://github.com/YusukeIwaki/puppeteer-ruby/compare/0.40.7...main)]
|
|
2
2
|
|
|
3
3
|
- xxx
|
|
4
4
|
|
|
5
|
+
### 0.40.7 [[diff](https://github.com/YusukeIwaki/puppeteer-ruby/compare/0.40.6...0.40.7)]
|
|
6
|
+
|
|
7
|
+
- Port Puppeteer v13.6-v13.7 features.
|
|
8
|
+
|
|
9
|
+
### 0.40.6 [[diff](https://github.com/YusukeIwaki/puppeteer-ruby/compare/0.40.5...0.40.6)]
|
|
10
|
+
|
|
11
|
+
- Port Puppeteer v13.1-v13.5 features mainly for request interception.
|
|
12
|
+
|
|
13
|
+
### 0.40.5 [[diff](https://github.com/YusukeIwaki/puppeteer-ruby/compare/0.40.4...0.40.5)]
|
|
14
|
+
|
|
15
|
+
Bugfix:
|
|
16
|
+
|
|
17
|
+
- Port Puppeteer v13.1-v13.5 bugfixes mainly for OOPIFs.
|
|
18
|
+
|
|
5
19
|
### 0.40.4 [[diff](https://github.com/YusukeIwaki/puppeteer-ruby/compare/0.40.3...0.40.4)]
|
|
6
20
|
|
|
7
21
|
Bugfix:
|
data/README.md
CHANGED
|
@@ -229,6 +229,13 @@ 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
|
## Contributing
|
|
233
240
|
|
|
234
241
|
Bug reports and pull requests are welcome on GitHub at https://github.com/YusukeIwaki/puppeteer-ruby.
|
data/docs/api_coverage.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# API coverages
|
|
2
|
-
- Puppeteer version: v13.5.
|
|
3
|
-
- puppeteer-ruby version: 0.40.
|
|
2
|
+
- Puppeteer version: v13.5.2
|
|
3
|
+
- puppeteer-ruby version: 0.40.7
|
|
4
4
|
|
|
5
5
|
## Puppeteer
|
|
6
6
|
|
|
@@ -310,8 +310,8 @@
|
|
|
310
310
|
* frame
|
|
311
311
|
* headers
|
|
312
312
|
* initiator
|
|
313
|
-
*
|
|
314
|
-
*
|
|
313
|
+
* interceptResolutionState => `#intercept_resolution_state`
|
|
314
|
+
* isInterceptResolutionHandled => `#intercept_resolution_handled?`
|
|
315
315
|
* isNavigationRequest => `#navigation_request?`
|
|
316
316
|
* method
|
|
317
317
|
* postData => `#post_data`
|
data/lib/puppeteer/connection.rb
CHANGED
|
@@ -2,12 +2,13 @@ class Puppeteer::ElementHandle < Puppeteer::JSHandle
|
|
|
2
2
|
class BoxModel
|
|
3
3
|
QUAD_ATTRIBUTE_NAMES = %i(content padding border margin)
|
|
4
4
|
# @param result [Hash]
|
|
5
|
-
|
|
5
|
+
# @param offset [Point]
|
|
6
|
+
def initialize(result_model, offset:)
|
|
6
7
|
QUAD_ATTRIBUTE_NAMES.each do |attr_name|
|
|
7
8
|
quad = result_model[attr_name.to_s]
|
|
8
9
|
instance_variable_set(
|
|
9
10
|
:"@#{attr_name}",
|
|
10
|
-
quad.each_slice(2).map { |x, y| Point.new(x: x, y: y) },
|
|
11
|
+
quad.each_slice(2).map { |x, y| Point.new(x: x, y: y) + offset },
|
|
11
12
|
)
|
|
12
13
|
end
|
|
13
14
|
@width = result_model['width']
|
|
@@ -11,10 +11,12 @@ class Puppeteer::ElementHandle < Puppeteer::JSHandle
|
|
|
11
11
|
# @param context [Puppeteer::ExecutionContext]
|
|
12
12
|
# @param client [Puppeteer::CDPSession]
|
|
13
13
|
# @param remote_object [Puppeteer::RemoteObject]
|
|
14
|
+
# @param frame [Puppeteer::Frame]
|
|
14
15
|
# @param page [Puppeteer::Page]
|
|
15
16
|
# @param frame_manager [Puppeteer::FrameManager]
|
|
16
|
-
def initialize(context:, client:, remote_object:, page:, frame_manager:)
|
|
17
|
+
def initialize(context:, client:, remote_object:, frame:, page:, frame_manager:)
|
|
17
18
|
super(context: context, client: client, remote_object: remote_object)
|
|
19
|
+
@frame = frame
|
|
18
20
|
@page = page
|
|
19
21
|
@frame_manager = frame_manager
|
|
20
22
|
@disposed = false
|
|
@@ -134,6 +136,37 @@ class Puppeteer::ElementHandle < Puppeteer::JSHandle
|
|
|
134
136
|
end
|
|
135
137
|
end
|
|
136
138
|
|
|
139
|
+
class ElementNotClickableError < StandardError
|
|
140
|
+
def initialize
|
|
141
|
+
super("Node is either not clickable or not an HTMLElement")
|
|
142
|
+
end
|
|
143
|
+
end
|
|
144
|
+
|
|
145
|
+
# @param quad [Array<Array<Point>>]]
|
|
146
|
+
# @param offset [Point]
|
|
147
|
+
private def apply_offsets_to_quad(quad, offset)
|
|
148
|
+
quad.map { |part| part + offset }
|
|
149
|
+
end
|
|
150
|
+
|
|
151
|
+
# @param frame [Puppeteer::Frame]
|
|
152
|
+
# @return [Point]
|
|
153
|
+
private def oopif_offsets(frame)
|
|
154
|
+
offset = Point.new(x: 0, y: 0)
|
|
155
|
+
while frame.parent_frame
|
|
156
|
+
parent = frame.parent_frame
|
|
157
|
+
unless frame.oop_frame?
|
|
158
|
+
frame = parent
|
|
159
|
+
next
|
|
160
|
+
end
|
|
161
|
+
backend_node_id = parent._client.send_message('DOM.getFrameOwner', frameId: frame.id)['backendNodeId']
|
|
162
|
+
result = parent._client.send_message('DOM.getBoxModel', backendNodeId: backend_node_id)
|
|
163
|
+
break unless result
|
|
164
|
+
offset = BoxModel.new(result['model'], offset: offset).content.first
|
|
165
|
+
frame = parent
|
|
166
|
+
end
|
|
167
|
+
offset
|
|
168
|
+
end
|
|
169
|
+
|
|
137
170
|
def clickable_point(offset = nil)
|
|
138
171
|
offset_param = Offset.from(offset)
|
|
139
172
|
|
|
@@ -150,12 +183,22 @@ class Puppeteer::ElementHandle < Puppeteer::JSHandle
|
|
|
150
183
|
end
|
|
151
184
|
|
|
152
185
|
# Filter out quads that have too small area to click into.
|
|
153
|
-
layout_metrics = @client.send_message('Page.getLayoutMetrics')
|
|
154
|
-
|
|
155
|
-
|
|
186
|
+
layout_metrics = @page.client.send_message('Page.getLayoutMetrics')
|
|
187
|
+
|
|
188
|
+
if result.empty? || result["quads"].empty?
|
|
189
|
+
raise ElementNotClickableError.new
|
|
190
|
+
end
|
|
191
|
+
|
|
192
|
+
# Filter out quads that have too small area to click into.
|
|
193
|
+
# Fallback to `layoutViewport` in case of using Firefox.
|
|
194
|
+
layout_viewport = layout_metrics["cssLayoutViewport"] || layout_metrics["layoutViewport"]
|
|
195
|
+
client_width = layout_viewport["clientWidth"]
|
|
196
|
+
client_height = layout_viewport["clientHeight"]
|
|
156
197
|
|
|
198
|
+
oopif_offset = oopif_offsets(@frame)
|
|
157
199
|
quads = result["quads"].
|
|
158
200
|
map { |quad| from_protocol_quad(quad) }.
|
|
201
|
+
map { |quad| apply_offsets_to_quad(quad, oopif_offset) }.
|
|
159
202
|
map { |quad| intersect_quad_with_viewport(quad, client_width, client_height) }.
|
|
160
203
|
select { |quad| compute_quad_area(quad) > 1 }
|
|
161
204
|
if quads.empty?
|
|
@@ -357,13 +400,14 @@ class Puppeteer::ElementHandle < Puppeteer::JSHandle
|
|
|
357
400
|
# @return [BoundingBox|nil]
|
|
358
401
|
def bounding_box
|
|
359
402
|
if_present(box_model) do |result_model|
|
|
403
|
+
offset = oopif_offsets(@frame)
|
|
360
404
|
quads = result_model.border
|
|
361
405
|
|
|
362
406
|
x = quads.map(&:x).min
|
|
363
407
|
y = quads.map(&:y).min
|
|
364
408
|
BoundingBox.new(
|
|
365
|
-
x: x,
|
|
366
|
-
y: y,
|
|
409
|
+
x: x + offset.x,
|
|
410
|
+
y: y + offset.y,
|
|
367
411
|
width: quads.map(&:x).max - x,
|
|
368
412
|
height: quads.map(&:y).max - y,
|
|
369
413
|
)
|
|
@@ -373,7 +417,7 @@ class Puppeteer::ElementHandle < Puppeteer::JSHandle
|
|
|
373
417
|
# @return [BoxModel|nil]
|
|
374
418
|
def box_model
|
|
375
419
|
if_present(@remote_object.box_model(@client)) do |result|
|
|
376
|
-
BoxModel.new(result['model'])
|
|
420
|
+
BoxModel.new(result['model'], offset: oopif_offsets(@frame))
|
|
377
421
|
end
|
|
378
422
|
end
|
|
379
423
|
|
data/lib/puppeteer/events.rb
CHANGED
|
@@ -96,6 +96,7 @@ module FrameManagerEmittedEvents ; end
|
|
|
96
96
|
FrameAttached: EventsDefinitionUtils.symbol('FrameManager.FrameAttached'),
|
|
97
97
|
FrameNavigated: EventsDefinitionUtils.symbol('FrameManager.FrameNavigated'),
|
|
98
98
|
FrameDetached: EventsDefinitionUtils.symbol('FrameManager.FrameDetached'),
|
|
99
|
+
FrameSwapped: EventsDefinitionUtils.symbol('FrameManager.FrameSwapped'),
|
|
99
100
|
LifecycleEvent: EventsDefinitionUtils.symbol('FrameManager.LifecycleEvent'),
|
|
100
101
|
FrameNavigatedWithinDocument: EventsDefinitionUtils.symbol('FrameManager.FrameNavigatedWithinDocument'),
|
|
101
102
|
ExecutionContextCreated: EventsDefinitionUtils.symbol('FrameManager.ExecutionContextCreated'),
|
|
@@ -178,7 +178,7 @@ class Puppeteer::FrameManager
|
|
|
178
178
|
frame = @frames[event['targetInfo']['targetId']]
|
|
179
179
|
session = Puppeteer::Connection.from_session(@client).session(event['sessionId'])
|
|
180
180
|
|
|
181
|
-
frame
|
|
181
|
+
frame&.send(:update_client, session)
|
|
182
182
|
setup_listeners(session)
|
|
183
183
|
async_init(session)
|
|
184
184
|
end
|
|
@@ -353,6 +353,8 @@ class Puppeteer::FrameManager
|
|
|
353
353
|
if frame
|
|
354
354
|
remove_frame_recursively(frame)
|
|
355
355
|
end
|
|
356
|
+
elsif reason == 'swap'
|
|
357
|
+
emit_event(FrameManagerEmittedEvents::FrameSwapped, frame)
|
|
356
358
|
end
|
|
357
359
|
end
|
|
358
360
|
|
|
@@ -2,6 +2,8 @@ class Puppeteer::HTTPRequest
|
|
|
2
2
|
include Puppeteer::DebugPrint
|
|
3
3
|
include Puppeteer::IfPresent
|
|
4
4
|
|
|
5
|
+
DEFAULT_INTERCEPT_RESOLUTION_PRIORITY = 0
|
|
6
|
+
|
|
5
7
|
# defines some methods used only in NetworkManager, Response
|
|
6
8
|
class InternalAccessor
|
|
7
9
|
def initialize(request)
|
|
@@ -38,6 +40,43 @@ class Puppeteer::HTTPRequest
|
|
|
38
40
|
end
|
|
39
41
|
end
|
|
40
42
|
|
|
43
|
+
class InterceptResolutionState
|
|
44
|
+
def self.abort(priority: nil)
|
|
45
|
+
new(action: 'abort', priority: priority)
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
def self.respond(priority: nil)
|
|
49
|
+
new(action: 'respond', priority: priority)
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
def self.continue(priority: nil)
|
|
53
|
+
new(action: 'continue', priority: priority)
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
def self.disabled(priority: nil)
|
|
57
|
+
new(action: 'disabled', priority: priority)
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
def self.none(priority: nil)
|
|
61
|
+
new(action: 'none', priority: priority)
|
|
62
|
+
end
|
|
63
|
+
|
|
64
|
+
def self.already_handled(priority: nil)
|
|
65
|
+
new(action: 'already-handled', priority: priority)
|
|
66
|
+
end
|
|
67
|
+
|
|
68
|
+
private def initialize(action:, priority:)
|
|
69
|
+
@action = action
|
|
70
|
+
@priority = priority
|
|
71
|
+
end
|
|
72
|
+
|
|
73
|
+
def priority_unspecified?
|
|
74
|
+
@priority.nil?
|
|
75
|
+
end
|
|
76
|
+
|
|
77
|
+
attr_reader :action, :priority
|
|
78
|
+
end
|
|
79
|
+
|
|
41
80
|
# @param client [Puppeteer::CDPSession]
|
|
42
81
|
# @param frame [Puppeteer::Frame]
|
|
43
82
|
# @param interception_id [string|nil]
|
|
@@ -57,9 +96,8 @@ class Puppeteer::HTTPRequest
|
|
|
57
96
|
@frame = frame
|
|
58
97
|
@redirect_chain = redirect_chain
|
|
59
98
|
@continue_request_overrides = {}
|
|
60
|
-
@
|
|
61
|
-
@
|
|
62
|
-
@intercept_actions = []
|
|
99
|
+
@intercept_resolution_state = InterceptResolutionState.none
|
|
100
|
+
@intercept_handlers = []
|
|
63
101
|
@initiator = event['initiator']
|
|
64
102
|
|
|
65
103
|
@headers = {}
|
|
@@ -115,19 +153,29 @@ class Puppeteer::HTTPRequest
|
|
|
115
153
|
@abort_error_reason
|
|
116
154
|
end
|
|
117
155
|
|
|
118
|
-
# @returns An
|
|
119
|
-
#
|
|
120
|
-
#
|
|
121
|
-
|
|
156
|
+
# @returns An InterceptResolutionState object describing the current resolution
|
|
157
|
+
# action and priority.
|
|
158
|
+
#
|
|
159
|
+
# InterceptResolutionState contains:
|
|
160
|
+
# action: InterceptResolutionAction
|
|
161
|
+
# priority?: number
|
|
162
|
+
#
|
|
163
|
+
# InterceptResolutionAction is one of: `abort`, `respond`, `continue`,
|
|
164
|
+
# `disabled`, `none`, or `alreay-handled`
|
|
165
|
+
def intercept_resolution_state
|
|
122
166
|
if !@allow_interception
|
|
123
|
-
|
|
167
|
+
InterceptResolutionState.disabled
|
|
124
168
|
elsif @interception_handled
|
|
125
|
-
|
|
169
|
+
InterceptResolutionState.already_handled
|
|
126
170
|
else
|
|
127
|
-
|
|
171
|
+
@intercept_resolution_state.dup
|
|
128
172
|
end
|
|
129
173
|
end
|
|
130
174
|
|
|
175
|
+
def intercept_resolution_handled?
|
|
176
|
+
@interception_handled
|
|
177
|
+
end
|
|
178
|
+
|
|
131
179
|
# Adds an async request handler to the processing queue.
|
|
132
180
|
# Deferred handlers are not guaranteed to execute in any particular order,
|
|
133
181
|
# but they are guarnateed to resolve before the request interception
|
|
@@ -135,19 +183,19 @@ class Puppeteer::HTTPRequest
|
|
|
135
183
|
#
|
|
136
184
|
# @param pending_handler [Proc]
|
|
137
185
|
def enqueue_intercept_action(pending_handler)
|
|
138
|
-
@
|
|
186
|
+
@intercept_handlers << pending_handler
|
|
139
187
|
end
|
|
140
188
|
|
|
141
189
|
# Awaits pending interception handlers and then decides how to fulfill
|
|
142
190
|
# the request interception.
|
|
143
191
|
def finalize_interceptions
|
|
144
|
-
@
|
|
145
|
-
case
|
|
146
|
-
when
|
|
192
|
+
@intercept_handlers.each(&:call)
|
|
193
|
+
case intercept_resolution_state.action
|
|
194
|
+
when 'abort'
|
|
147
195
|
abort_impl(**@abort_error_reason)
|
|
148
|
-
when
|
|
196
|
+
when 'respond'
|
|
149
197
|
respond_impl(**@response_for_request)
|
|
150
|
-
when
|
|
198
|
+
when 'continue'
|
|
151
199
|
continue_impl(@continue_request_overrides)
|
|
152
200
|
end
|
|
153
201
|
end
|
|
@@ -169,8 +217,14 @@ class Puppeteer::HTTPRequest
|
|
|
169
217
|
private def headers_to_array(headers)
|
|
170
218
|
return nil unless headers
|
|
171
219
|
|
|
172
|
-
headers.
|
|
173
|
-
|
|
220
|
+
headers.flat_map do |key, value|
|
|
221
|
+
if value.is_a?(Enumerable)
|
|
222
|
+
value.map do |v|
|
|
223
|
+
{ name: key, value: v.to_s }
|
|
224
|
+
end
|
|
225
|
+
else
|
|
226
|
+
{ name: key, value: value.to_s }
|
|
227
|
+
end
|
|
174
228
|
end
|
|
175
229
|
end
|
|
176
230
|
|
|
@@ -220,17 +274,16 @@ class Puppeteer::HTTPRequest
|
|
|
220
274
|
end
|
|
221
275
|
|
|
222
276
|
@continue_request_overrides = overrides
|
|
223
|
-
if @
|
|
224
|
-
@
|
|
225
|
-
@current_priority = priority
|
|
277
|
+
if @intercept_resolution_state.priority_unspecified? || priority > @intercept_resolution_state.priority
|
|
278
|
+
@intercept_resolution_state = InterceptResolutionState.continue(priority: priority)
|
|
226
279
|
return
|
|
227
280
|
end
|
|
228
281
|
|
|
229
|
-
if priority == @
|
|
230
|
-
if @
|
|
282
|
+
if priority == @intercept_resolution_state.priority
|
|
283
|
+
if @intercept_resolution_state.action == :abort || @intercept_resolution_state.action == :respond
|
|
231
284
|
return
|
|
232
285
|
end
|
|
233
|
-
@
|
|
286
|
+
@intercept_resolution_state = InterceptResolutionState.continue(priority: priority)
|
|
234
287
|
end
|
|
235
288
|
end
|
|
236
289
|
|
|
@@ -284,17 +337,16 @@ class Puppeteer::HTTPRequest
|
|
|
284
337
|
body: body,
|
|
285
338
|
}
|
|
286
339
|
|
|
287
|
-
if @
|
|
288
|
-
@
|
|
289
|
-
@current_priority = priority
|
|
340
|
+
if @intercept_resolution_state.priority_unspecified? || priority > @intercept_resolution_state.priority
|
|
341
|
+
@intercept_resolution_state = InterceptResolutionState.respond(priority: priority)
|
|
290
342
|
return
|
|
291
343
|
end
|
|
292
344
|
|
|
293
|
-
if priority == @
|
|
294
|
-
if @
|
|
345
|
+
if priority == @intercept_resolution_state.priority
|
|
346
|
+
if @intercept_resolution_state.action == :abort
|
|
295
347
|
return
|
|
296
348
|
end
|
|
297
|
-
@
|
|
349
|
+
@intercept_resolution_state = InterceptResolutionState.respond(priority: priority)
|
|
298
350
|
end
|
|
299
351
|
end
|
|
300
352
|
|
|
@@ -303,7 +355,12 @@ class Puppeteer::HTTPRequest
|
|
|
303
355
|
|
|
304
356
|
mock_response_headers = {}
|
|
305
357
|
headers&.each do |key, value|
|
|
306
|
-
mock_response_headers[key.downcase] =
|
|
358
|
+
mock_response_headers[key.downcase] =
|
|
359
|
+
if value.is_a?(Enumerable)
|
|
360
|
+
value.map(&:to_s)
|
|
361
|
+
else
|
|
362
|
+
value.to_s
|
|
363
|
+
end
|
|
307
364
|
end
|
|
308
365
|
if content_type
|
|
309
366
|
mock_response_headers['content-type'] = content_type
|
|
@@ -360,9 +417,8 @@ class Puppeteer::HTTPRequest
|
|
|
360
417
|
end
|
|
361
418
|
@abort_error_reason = error_reason
|
|
362
419
|
|
|
363
|
-
if @
|
|
364
|
-
@
|
|
365
|
-
@current_priority = priority
|
|
420
|
+
if @intercept_resolution_state.priority_unspecified? || priority > @intercept_resolution_state.priority
|
|
421
|
+
@intercept_resolution_state = InterceptResolutionState.abort(priority: priority)
|
|
366
422
|
end
|
|
367
423
|
end
|
|
368
424
|
|
data/lib/puppeteer/js_handle.rb
CHANGED
|
@@ -122,7 +122,7 @@ module Puppeteer::Launcher
|
|
|
122
122
|
'--disable-default-apps',
|
|
123
123
|
'--disable-dev-shm-usage',
|
|
124
124
|
'--disable-extensions',
|
|
125
|
-
'--disable-features=Translate',
|
|
125
|
+
'--disable-features=Translate,BackForwardCache',
|
|
126
126
|
'--disable-hang-monitor',
|
|
127
127
|
'--disable-ipc-flooding-protection',
|
|
128
128
|
'--disable-popup-blocking',
|
|
@@ -77,6 +77,7 @@ class Puppeteer::LifecycleWatcher
|
|
|
77
77
|
check_lifecycle_complete
|
|
78
78
|
end,
|
|
79
79
|
@frame_manager.add_event_listener(FrameManagerEmittedEvents::FrameNavigatedWithinDocument, &method(:navigated_within_document)),
|
|
80
|
+
@frame_manager.add_event_listener(FrameManagerEmittedEvents::FrameSwapped, &method(:handle_frame_swapped)),
|
|
80
81
|
@frame_manager.add_event_listener(FrameManagerEmittedEvents::FrameDetached, &method(:handle_frame_detached)),
|
|
81
82
|
]
|
|
82
83
|
@listener_ids['network_manager'] = @frame_manager.network_manager.add_event_listener(NetworkManagerEmittedEvents::Request, &method(:handle_request))
|
|
@@ -142,11 +143,21 @@ class Puppeteer::LifecycleWatcher
|
|
|
142
143
|
check_lifecycle_complete
|
|
143
144
|
end
|
|
144
145
|
|
|
146
|
+
private def handle_frame_swapped(frame)
|
|
147
|
+
return if frame != @frame
|
|
148
|
+
@swapped = true
|
|
149
|
+
check_lifecycle_complete
|
|
150
|
+
end
|
|
151
|
+
|
|
145
152
|
private def check_lifecycle_complete
|
|
146
153
|
# We expect navigation to commit.
|
|
147
154
|
return unless @expected_lifecycle.completed?(@frame)
|
|
148
155
|
@lifecycle_promise.fulfill(true) if @lifecycle_promise.pending?
|
|
149
156
|
if @frame.loader_id == @initial_loader_id && !@has_same_document_navigation
|
|
157
|
+
if @swapped
|
|
158
|
+
@swapped = false
|
|
159
|
+
@new_document_navigation_promise.fulfill(true)
|
|
160
|
+
end
|
|
150
161
|
return
|
|
151
162
|
end
|
|
152
163
|
if @has_same_document_navigation && @same_document_navigation_promise.pending?
|
|
@@ -119,4 +119,8 @@ class Puppeteer::NetworkEventManager
|
|
|
119
119
|
def get_queued_event_group(network_request_id)
|
|
120
120
|
@queued_event_group_map[network_request_id]
|
|
121
121
|
end
|
|
122
|
+
|
|
123
|
+
def forget_queued_event_group(network_request_id)
|
|
124
|
+
@queued_event_group_map.delete(network_request_id)
|
|
125
|
+
end
|
|
122
126
|
end
|
|
@@ -217,6 +217,7 @@ class Puppeteer::NetworkManager
|
|
|
217
217
|
# CDP may have sent a Fetch.requestPaused event already. Check for it.
|
|
218
218
|
if_present(@network_event_manager.get_request_paused(network_request_id)) do |request_paused_event|
|
|
219
219
|
fetch_request_id = request_paused_event['requestId']
|
|
220
|
+
patch_request_event_headers(event, request_paused_event)
|
|
220
221
|
handle_request(event, fetch_request_id)
|
|
221
222
|
@network_event_manager.forget_request_paused(network_request_id)
|
|
222
223
|
end
|
|
@@ -277,12 +278,19 @@ class Puppeteer::NetworkManager
|
|
|
277
278
|
end
|
|
278
279
|
|
|
279
280
|
if request_will_be_sent_event
|
|
281
|
+
patch_request_event_headers(request_will_be_sent_event, event)
|
|
280
282
|
handle_request(request_will_be_sent_event, fetch_request_id)
|
|
281
283
|
else
|
|
282
284
|
@network_event_manager.store_request_paused(network_request_id, event)
|
|
283
285
|
end
|
|
284
286
|
end
|
|
285
287
|
|
|
288
|
+
private def patch_request_event_headers(request_will_be_sent_event, request_paused_event)
|
|
289
|
+
request_will_be_sent_event['request']['headers'].merge!(
|
|
290
|
+
# includes extra headers, like: Accept, Origin
|
|
291
|
+
request_paused_event['request']['headers'])
|
|
292
|
+
end
|
|
293
|
+
|
|
286
294
|
private def handle_request(event, fetch_request_id)
|
|
287
295
|
redirect_chain = []
|
|
288
296
|
if event['redirectResponse']
|
|
@@ -387,6 +395,7 @@ class Puppeteer::NetworkManager
|
|
|
387
395
|
# We may have skipped response and loading events because we didn't have
|
|
388
396
|
# this ExtraInfo event yet. If so, emit those events now.
|
|
389
397
|
if_present(@network_event_manager.get_queued_event_group(event['requestId'])) do |queued_events|
|
|
398
|
+
@network_event_manager.forget_queued_event_group(event['requestId'])
|
|
390
399
|
emit_response_event(queued_events.response_received_event, event)
|
|
391
400
|
if_present(queued_events.loading_finished_event) do |loading_finished_event|
|
|
392
401
|
emit_loading_finished(loading_finished_event)
|
data/lib/puppeteer/page.rb
CHANGED
|
@@ -227,7 +227,7 @@ class Puppeteer::Page
|
|
|
227
227
|
@client.send_message('Emulation.setGeolocationOverride', geolocation.to_h)
|
|
228
228
|
end
|
|
229
229
|
|
|
230
|
-
attr_reader :javascript_enabled, :target
|
|
230
|
+
attr_reader :javascript_enabled, :target, :client
|
|
231
231
|
alias_method :javascript_enabled?, :javascript_enabled
|
|
232
232
|
|
|
233
233
|
def browser
|
|
@@ -389,7 +389,18 @@ class Puppeteer::Page
|
|
|
389
389
|
@client.send_message('Network.getCookies', urls: (urls.empty? ? [url] : urls))['cookies']
|
|
390
390
|
end
|
|
391
391
|
|
|
392
|
+
# check if each cookie element has required fields ('name' and 'value')
|
|
393
|
+
private def assert_cookie_params(cookies, requires:)
|
|
394
|
+
return if cookies.all? do |cookie|
|
|
395
|
+
requires.all? { |field_name| cookie[field_name] || cookie[field_name.to_s] }
|
|
396
|
+
end
|
|
397
|
+
|
|
398
|
+
raise ArgumentError.new("Each coookie must have #{requires.join(" and ")} attribute.")
|
|
399
|
+
end
|
|
400
|
+
|
|
392
401
|
def delete_cookie(*cookies)
|
|
402
|
+
assert_cookie_params(cookies, requires: %i(name))
|
|
403
|
+
|
|
393
404
|
page_url = url
|
|
394
405
|
starts_with_http = page_url.start_with?("http")
|
|
395
406
|
cookies.each do |cookie|
|
|
@@ -399,12 +410,14 @@ class Puppeteer::Page
|
|
|
399
410
|
end
|
|
400
411
|
|
|
401
412
|
def set_cookie(*cookies)
|
|
413
|
+
assert_cookie_params(cookies, requires: %i(name value))
|
|
414
|
+
|
|
402
415
|
page_url = url
|
|
403
416
|
starts_with_http = page_url.start_with?("http")
|
|
404
417
|
items = cookies.map do |cookie|
|
|
405
418
|
(starts_with_http ? { url: page_url } : {}).merge(cookie).tap do |item|
|
|
406
419
|
raise ArgumentError.new("Blank page can not have cookie \"#{item[:name]}\"") if item[:url] == "about:blank"
|
|
407
|
-
raise
|
|
420
|
+
raise ArgumentError.new("Data URL page can not have cookie \"#{item[:name]}\"") if item[:url]&.start_with?("data:")
|
|
408
421
|
end
|
|
409
422
|
end
|
|
410
423
|
delete_cookie(*items)
|
|
@@ -508,7 +521,6 @@ class Puppeteer::Page
|
|
|
508
521
|
end
|
|
509
522
|
|
|
510
523
|
private def handle_console_api(event)
|
|
511
|
-
puts "~~~~~~~~~~~~~~#{event}"
|
|
512
524
|
if event['executionContextId'] == 0
|
|
513
525
|
# DevTools protocol stores the last 1000 console messages. These
|
|
514
526
|
# messages are always reported even for removed execution contexts. In
|
data/lib/puppeteer/version.rb
CHANGED
data/puppeteer-ruby.gemspec
CHANGED
|
@@ -32,7 +32,7 @@ Gem::Specification.new do |spec|
|
|
|
32
32
|
spec.add_development_dependency 'rollbar'
|
|
33
33
|
spec.add_development_dependency 'rspec', '~> 3.11.0'
|
|
34
34
|
spec.add_development_dependency 'rspec_junit_formatter' # for CircleCI.
|
|
35
|
-
spec.add_development_dependency 'rubocop', '~> 1.
|
|
35
|
+
spec.add_development_dependency 'rubocop', '~> 1.29.0'
|
|
36
36
|
spec.add_development_dependency 'rubocop-rspec'
|
|
37
37
|
spec.add_development_dependency 'sinatra'
|
|
38
38
|
spec.add_development_dependency 'webrick'
|
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.40.
|
|
4
|
+
version: 0.40.7
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- YusukeIwaki
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: exe
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date: 2022-
|
|
11
|
+
date: 2022-05-10 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: concurrent-ruby
|
|
@@ -170,14 +170,14 @@ dependencies:
|
|
|
170
170
|
requirements:
|
|
171
171
|
- - "~>"
|
|
172
172
|
- !ruby/object:Gem::Version
|
|
173
|
-
version: 1.
|
|
173
|
+
version: 1.29.0
|
|
174
174
|
type: :development
|
|
175
175
|
prerelease: false
|
|
176
176
|
version_requirements: !ruby/object:Gem::Requirement
|
|
177
177
|
requirements:
|
|
178
178
|
- - "~>"
|
|
179
179
|
- !ruby/object:Gem::Version
|
|
180
|
-
version: 1.
|
|
180
|
+
version: 1.29.0
|
|
181
181
|
- !ruby/object:Gem::Dependency
|
|
182
182
|
name: rubocop-rspec
|
|
183
183
|
requirement: !ruby/object:Gem::Requirement
|