puppeteer-ruby 0.50.1 → 0.51.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 5e905c9995f718c953c11c9c199e7c945c0d413750becae8bdbc13cc4c0c1e5f
4
- data.tar.gz: 9fec2af23369834b277ec50ef655b4a086b9df67698465f133b1af2ed059b11e
3
+ metadata.gz: 74f00095ae82e1e4502260b99ff766cc46c758ae5e762050a6e7c46b7249f469
4
+ data.tar.gz: a197f92fc8b7ccbe2904c088d52e60409af119d94449a6a4e9f518601c4c5788
5
5
  SHA512:
6
- metadata.gz: e636edbdf0dcb3731e7b688936f4c04bf7b9f21668ce6ed712d993e2dac41b748f4e49e89b9b43ddfcdd2b37138275bf1b95e5191d7d09cd1d3df664f6838358
7
- data.tar.gz: 1e7478c8a4757743d6e31321af550b0900b04a46785b51ac2bb0203060d1456e8917722ad6631ae86a546b8fccb7f1947b185b7c9007e7720773a1772146557a
6
+ metadata.gz: df595ba0c4996b100b1d8b22bb35e0e0ce9b6552d368c11fc25b9c8cf60c1a270b651f6f96e6c1b65b64d32550b71c402a059a0fd4d3a1393a394b65de472aef
7
+ data.tar.gz: f82344aba53b730d5fdb7273ef29fdb07d0b8aadc831d680fd5611d55df980955cb5fd5cbdbe78d0de88c70d689f738952187193b4f006386a2170970f928dd2
data/docs/api_coverage.md CHANGED
@@ -1,6 +1,6 @@
1
1
  # API coverages
2
- - Puppeteer version: v24.35.0
3
- - puppeteer-ruby version: 0.50.1
2
+ - Puppeteer version: v24.37.0
3
+ - puppeteer-ruby version: 0.51.0
4
4
 
5
5
  ## Puppeteer
6
6
 
@@ -34,6 +34,7 @@
34
34
  * ~~removeScreen~~
35
35
  * ~~screens~~
36
36
  * ~~setCookie~~
37
+ * setPermission => `#set_permission`
37
38
  * ~~setWindowBounds~~
38
39
  * target
39
40
  * targets
@@ -55,6 +56,7 @@
55
56
  * overridePermissions => `#override_permissions`
56
57
  * pages
57
58
  * setCookie => `#set_cookie`
59
+ * setPermission => `#set_permission`
58
60
  * targets
59
61
  * waitForTarget => `#wait_for_target`
60
62
 
@@ -321,6 +323,7 @@
321
323
  * bringToFront => `#bring_to_front`
322
324
  * browser
323
325
  * browserContext => `#browser_context`
326
+ * captureHeapSnapshot => `#capture_heap_snapshot`
324
327
  * click
325
328
  * close
326
329
  * content
@@ -196,6 +196,13 @@ class Puppeteer::Browser
196
196
  @default_context
197
197
  end
198
198
 
199
+ # @rbs origin: String -- Origin URL, or '*' for all origins
200
+ # @rbs permissions: Array[Hash[Symbol | String, untyped]] -- Permission descriptors and states
201
+ # @rbs return: void -- No return value
202
+ def set_permission(origin, *permissions)
203
+ @default_context.set_permission(origin, *permissions)
204
+ end
205
+
199
206
  # @rbs context_id: String? -- Browser context ID
200
207
  # @rbs return: void -- No return value
201
208
  def dispose_context(context_id)
@@ -153,6 +153,44 @@ class Puppeteer::BrowserContext
153
153
  }.compact)
154
154
  end
155
155
 
156
+ # @param origin [String] Use '*' to apply to all origins.
157
+ # @param permissions [Array<Hash>] { permission: { name:, userVisibleOnly:, sysex:, panTiltZoom:, allowWithoutSanitization: }, state: 'granted'|'denied'|'prompt' }
158
+ def set_permission(origin, *permissions)
159
+ permissions.each do |permission|
160
+ descriptor = hash_value(permission, 'permission')
161
+ state = hash_value(permission, 'state')
162
+ unless descriptor.is_a?(Hash)
163
+ raise ArgumentError.new('Each permission entry must include a permission descriptor')
164
+ end
165
+ unless state
166
+ raise ArgumentError.new('Each permission entry must include state')
167
+ end
168
+
169
+ name = hash_value(descriptor, 'name')
170
+ unless name
171
+ raise ArgumentError.new('Permission descriptor must include name')
172
+ end
173
+
174
+ protocol_permission = { name: name.to_s }
175
+ {
176
+ userVisibleOnly: %w[userVisibleOnly user_visible_only],
177
+ sysex: %w[sysex],
178
+ panTiltZoom: %w[panTiltZoom pan_tilt_zoom],
179
+ allowWithoutSanitization: %w[allowWithoutSanitization allow_without_sanitization],
180
+ }.each do |protocol_key, keys|
181
+ value = hash_value(descriptor, *keys)
182
+ protocol_permission[protocol_key] = value unless value.nil?
183
+ end
184
+
185
+ @connection.send_message('Browser.setPermission', {
186
+ origin: origin == '*' ? nil : origin,
187
+ browserContextId: @id,
188
+ permission: protocol_permission,
189
+ setting: state.to_s,
190
+ }.compact)
191
+ end
192
+ end
193
+
156
194
  def clear_permission_overrides
157
195
  if @id
158
196
  @connection.send_message('Browser.resetPermissions', browserContextId: @id)
@@ -214,6 +252,9 @@ class Puppeteer::BrowserContext
214
252
  normalized = normalize_cookie_hash(cookie)
215
253
  partition_key = normalized.delete('partitionKey') || normalized.delete('partition_key')
216
254
  normalized['partitionKey'] = convert_partition_key_for_cdp(partition_key) if partition_key
255
+ same_site = normalized.delete('sameSite') || normalized.delete('same_site')
256
+ converted_same_site = convert_same_site_for_cdp(same_site)
257
+ normalized['sameSite'] = converted_same_site if converted_same_site
217
258
  normalized
218
259
  end
219
260
  @connection.send_message('Storage.setCookies', {
@@ -277,9 +318,7 @@ class Puppeteer::BrowserContext
277
318
  end
278
319
 
279
320
  private def normalize_cookie_hash(cookie)
280
- cookie.each_with_object({}) do |(key, value), normalized|
281
- normalized[key.to_s] = value
282
- end
321
+ cookie.transform_keys(&:to_s)
283
322
  end
284
323
 
285
324
  private def hash_value(hash, *keys)
@@ -305,6 +344,15 @@ class Puppeteer::BrowserContext
305
344
  }
306
345
  end
307
346
 
347
+ private def convert_same_site_for_cdp(same_site)
348
+ case same_site
349
+ when 'Strict', 'Lax', 'None'
350
+ same_site
351
+ else
352
+ nil
353
+ end
354
+ end
355
+
308
356
  private def convert_partition_key_from_cdp(partition_key)
309
357
  return nil if partition_key.nil?
310
358
  return partition_key if partition_key.is_a?(String)
@@ -149,11 +149,11 @@ class Puppeteer::ChromeTargetManager
149
149
  target_info = @discovered_targets_by_target_id.delete(target_id)
150
150
  finish_initialization_if_ready(target_id)
151
151
 
152
- if target_info.type == 'service_worker' && @attached_targets_by_target_id.has_key?(target_id)
152
+ if target_info&.type == 'service_worker'
153
153
  # Special case for service workers: report TargetGone event when
154
154
  # the worker is destroyed.
155
155
  target = @attached_targets_by_target_id.delete(target_id)
156
- emit_event(TargetManagerEmittedEvents::TargetGone, target)
156
+ emit_event(TargetManagerEmittedEvents::TargetGone, target) if target
157
157
  end
158
158
  end
159
159
 
@@ -161,11 +161,11 @@ class Puppeteer::ChromeTargetManager
161
161
  target_info = Puppeteer::Target::TargetInfo.new(event['targetInfo'])
162
162
  @discovered_targets_by_target_id[target_info.target_id] = target_info
163
163
 
164
- if @ignored_targets.include?(target_info.target_id) || !@attached_targets_by_target_id.has_key?(target_info.target_id) || !target_info.attached
164
+ if @ignored_targets.include?(target_info.target_id) || !target_info.attached
165
165
  return
166
166
  end
167
167
  original_target = @attached_targets_by_target_id[target_info.target_id]
168
- emit_event(TargetManagerEmittedEvents::TargetChanged, original_target, target_info)
168
+ emit_event(TargetManagerEmittedEvents::TargetChanged, original_target, target_info) if original_target
169
169
  end
170
170
 
171
171
  class SessionNotCreatedError < Puppeteer::Error ; end
@@ -1,5 +1,7 @@
1
1
  # rbs_inline: enabled
2
2
 
3
+ require 'base64'
4
+
3
5
  class Puppeteer::HTTPRequest
4
6
  include Puppeteer::DebugPrint
5
7
  include Puppeteer::IfPresent
@@ -101,7 +103,7 @@ class Puppeteer::HTTPRequest
101
103
  resource_type = event['type'] || event['resourceType'] || 'other'
102
104
  @resource_type = resource_type.downcase
103
105
  @method = event['request']['method']
104
- @post_data = event['request']['postData']
106
+ @post_data = parse_post_data(event)
105
107
  has_post_data = event.dig('request', 'hasPostData')
106
108
  @has_post_data = has_post_data.nil? ? !@post_data.nil? : has_post_data
107
109
  @frame = frame
@@ -160,6 +162,18 @@ class Puppeteer::HTTPRequest
160
162
  end
161
163
  end
162
164
 
165
+ private def parse_post_data(event)
166
+ post_data_entries = event.dig('request', 'postDataEntries')
167
+ if post_data_entries && !post_data_entries.empty?
168
+ post_data_entries
169
+ .filter_map { |entry| entry['bytes'] ? Base64.decode64(entry['bytes']) : nil }
170
+ .join
171
+ .force_encoding('UTF-8')
172
+ else
173
+ event.dig('request', 'postData')
174
+ end
175
+ end
176
+
163
177
  private def assert_interception_not_handled
164
178
  if @interception_handled
165
179
  raise AlreadyHandledError.new
@@ -113,7 +113,12 @@ class Puppeteer::HTTPResponse
113
113
  # @param text [String]
114
114
  # @rbs return: String -- Response body as text
115
115
  def text
116
- buffer
116
+ content = buffer
117
+ content = content.dup.force_encoding('UTF-8')
118
+ unless content.valid_encoding?
119
+ raise Puppeteer::Error.new('Could not decode response body as UTF-8')
120
+ end
121
+ content
117
122
  end
118
123
 
119
124
  # @param json [Hash]
@@ -131,7 +131,7 @@ module Puppeteer::Launcher
131
131
  '--disable-dev-shm-usage',
132
132
  '--disable-extensions',
133
133
  # AcceptCHFrame disabled because of crbug.com/1348106.
134
- '--disable-features=Translate,BackForwardCache,AcceptCHFrame,MediaRouter,OptimizationHints',
134
+ '--disable-features=Translate,BackForwardCache,AcceptCHFrame,MediaRouter,OptimizationHints,IPH_ReadingModePageActionLabel,ReadAnythingOmniboxChip',
135
135
  '--disable-hang-monitor',
136
136
  '--disable-ipc-flooding-protection',
137
137
  '--disable-popup-blocking',
@@ -213,15 +213,16 @@ class Puppeteer::Locator
213
213
  end
214
214
 
215
215
  # @rbs value: String -- Value to fill
216
+ # @rbs typing_threshold: Integer -- Minimum length to switch to direct assignment
216
217
  # @rbs return: void -- No return value
217
- def fill(value)
218
+ def fill(value, typing_threshold: 100)
218
219
  perform_action('Locator.fill',
219
220
  conditions: [
220
221
  method(:ensure_element_is_in_viewport_if_needed),
221
222
  method(:wait_for_stable_bounding_box_if_needed),
222
223
  method(:wait_for_enabled_if_needed),
223
224
  ]) do |handle, _options|
224
- fill_element(handle, value)
225
+ fill_element(handle, value, typing_threshold: typing_threshold)
225
226
  end
226
227
  end
227
228
 
@@ -422,7 +423,7 @@ class Puppeteer::Locator
422
423
  end
423
424
  end
424
425
 
425
- private def fill_element(handle, value)
426
+ private def fill_element(handle, value, typing_threshold: 100)
426
427
  input_type = handle.evaluate(<<~JAVASCRIPT)
427
428
  el => {
428
429
  if (el instanceof HTMLSelectElement) {
@@ -461,52 +462,70 @@ class Puppeteer::Locator
461
462
  when 'select'
462
463
  handle.select(value)
463
464
  when 'contenteditable', 'typeable-input'
464
- text_to_type = handle.evaluate(<<~JAVASCRIPT, value)
465
- (input, newValue) => {
466
- const currentValue = input.isContentEditable
467
- ? input.innerText
468
- : input.value;
465
+ if value.length < typing_threshold
466
+ text_to_type = handle.evaluate(<<~JAVASCRIPT, value)
467
+ (input, newValue) => {
468
+ const currentValue = input.isContentEditable
469
+ ? input.innerText
470
+ : input.value;
471
+
472
+ if (
473
+ newValue.length <= currentValue.length ||
474
+ !newValue.startsWith(input.value)
475
+ ) {
476
+ if (input.isContentEditable) {
477
+ input.innerText = '';
478
+ } else {
479
+ input.value = '';
480
+ }
481
+ return newValue;
482
+ }
483
+ const originalValue = input.isContentEditable
484
+ ? input.innerText
485
+ : input.value;
469
486
 
470
- if (
471
- newValue.length <= currentValue.length ||
472
- !newValue.startsWith(input.value)
473
- ) {
474
487
  if (input.isContentEditable) {
475
488
  input.innerText = '';
489
+ input.innerText = originalValue;
476
490
  } else {
477
491
  input.value = '';
492
+ input.value = originalValue;
478
493
  }
479
- return newValue;
494
+ return newValue.substring(originalValue.length);
480
495
  }
481
- const originalValue = input.isContentEditable
482
- ? input.innerText
483
- : input.value;
484
-
485
- if (input.isContentEditable) {
486
- input.innerText = '';
487
- input.innerText = originalValue;
488
- } else {
489
- input.value = '';
490
- input.value = originalValue;
491
- }
492
- return newValue.substring(originalValue.length);
493
- }
494
- JAVASCRIPT
495
- text_to_type = text_to_type.to_s
496
- handle.type_text(text_to_type)
496
+ JAVASCRIPT
497
+ text_to_type = text_to_type.to_s
498
+ handle.type_text(text_to_type) unless text_to_type.empty?
499
+ else
500
+ fill_directly(handle, value)
501
+ end
497
502
  when 'other-input'
498
- handle.focus
499
- handle.evaluate(<<~JAVASCRIPT, value)
500
- (input, newValue) => {
501
- input.value = newValue;
502
- input.dispatchEvent(new Event('input', { bubbles: true }));
503
- input.dispatchEvent(new Event('change', { bubbles: true }));
504
- }
505
- JAVASCRIPT
503
+ fill_directly(handle, value)
506
504
  else
507
505
  raise Puppeteer::Error.new('Element cannot be filled out.')
508
506
  end
509
507
  end
508
+
509
+ private def fill_directly(handle, value)
510
+ handle.focus
511
+ handle.evaluate(<<~JAVASCRIPT, value)
512
+ (input, newValue) => {
513
+ const currentValue = input.isContentEditable
514
+ ? input.innerText
515
+ : input.value;
516
+ if (currentValue === newValue) {
517
+ return;
518
+ }
519
+ if (input.isContentEditable) {
520
+ input.innerText = newValue;
521
+ } else {
522
+ input.value = newValue;
523
+ }
524
+ input.dispatchEvent(new Event('input', { bubbles: true }));
525
+ input.dispatchEvent(new Event('change', { bubbles: true }));
526
+ }
527
+ JAVASCRIPT
528
+ end
510
529
  end
511
530
 
512
531
  class Puppeteer::FunctionLocator < Puppeteer::Locator
@@ -193,7 +193,6 @@ class Puppeteer::Page
193
193
  @workers[session.id] = worker
194
194
  emit_event(PageEmittedEvents::WorkerCreated, worker)
195
195
  end
196
-
197
196
  end
198
197
 
199
198
  # @rbs return: Array[untyped] -- Initialization results
@@ -560,6 +559,15 @@ class Puppeteer::Page
560
559
  raise ArgumentError.new("Each coookie must have #{requires.join(" and ")} attribute.")
561
560
  end
562
561
 
562
+ private def convert_same_site_for_cdp(same_site)
563
+ case same_site
564
+ when 'Strict', 'Lax', 'None'
565
+ same_site
566
+ else
567
+ nil
568
+ end
569
+ end
570
+
563
571
  # @rbs cookies: Array[Hash[Symbol | String, untyped]] -- cookies parameter
564
572
  # @rbs return: void -- No return value
565
573
  def delete_cookie(*cookies)
@@ -582,8 +590,28 @@ class Puppeteer::Page
582
590
  starts_with_http = page_url.start_with?("http")
583
591
  items = cookies.map do |cookie|
584
592
  (starts_with_http ? { url: page_url } : {}).merge(cookie).tap do |item|
585
- raise ArgumentError.new("Blank page can not have cookie \"#{item[:name]}\"") if item[:url] == "about:blank"
586
- raise ArgumentError.new("Data URL page can not have cookie \"#{item[:name]}\"") if item[:url]&.start_with?("data:")
593
+ item_name = item[:name] || item['name']
594
+ item_url = item[:url] || item['url']
595
+ raise ArgumentError.new("Blank page can not have cookie \"#{item_name}\"") if item_url == "about:blank"
596
+ raise ArgumentError.new("Data URL page can not have cookie \"#{item_name}\"") if item_url&.start_with?("data:")
597
+
598
+ same_site =
599
+ if item.key?(:sameSite)
600
+ item[:sameSite]
601
+ elsif item.key?('sameSite')
602
+ item['sameSite']
603
+ elsif item.key?(:same_site)
604
+ item[:same_site]
605
+ else
606
+ item['same_site']
607
+ end
608
+
609
+ converted_same_site = convert_same_site_for_cdp(same_site)
610
+ item.delete(:sameSite)
611
+ item.delete('sameSite')
612
+ item.delete(:same_site)
613
+ item.delete('same_site')
614
+ item[:sameSite] = converted_same_site if converted_same_site
587
615
  end
588
616
  end
589
617
  delete_cookie(*items)
@@ -708,6 +736,29 @@ class Puppeteer::Page
708
736
  Metrics.new(response['metrics'])
709
737
  end
710
738
 
739
+ # @rbs path: String -- Output path for the heap snapshot
740
+ # @rbs return: void -- No return value
741
+ def capture_heap_snapshot(path:)
742
+ @client.send_message('HeapProfiler.enable')
743
+ @client.send_message('HeapProfiler.collectGarbage')
744
+
745
+ begin
746
+ File.open(path, 'w') do |file|
747
+ listener_id = @client.add_event_listener('HeapProfiler.addHeapSnapshotChunk') do |event|
748
+ file.write(event['chunk'])
749
+ end
750
+
751
+ begin
752
+ @client.send_message('HeapProfiler.takeHeapSnapshot', reportProgress: false)
753
+ ensure
754
+ @client.remove_event_listener(listener_id)
755
+ end
756
+ end
757
+ ensure
758
+ @client.send_message('HeapProfiler.disable')
759
+ end
760
+ end
761
+
711
762
  class PageError < Puppeteer::Error ; end
712
763
 
713
764
  private def handle_exception(exception_details)
@@ -1,3 +1,4 @@
1
1
  module Puppeteer
2
- VERSION = '0.50.1'
2
+ VERSION = '0.51.0'
3
+ REF_PUPPETEER_VERSION = '24.37.0'
3
4
  end
@@ -36,7 +36,7 @@ Gem::Specification.new do |spec|
36
36
  spec.add_development_dependency 'rspec', '~> 3.13.2'
37
37
  spec.add_development_dependency 'rspec_junit_formatter' # for CircleCI.
38
38
  spec.add_development_dependency 'rbs-inline'
39
- spec.add_development_dependency 'rubocop', '~> 1.82.1'
39
+ spec.add_development_dependency 'rubocop', '~> 1.84.0'
40
40
  spec.add_development_dependency 'rubocop-rspec', '~> 3.9.0'
41
41
  spec.add_development_dependency 'sinatra', '< 5.0.0'
42
42
  spec.add_development_dependency 'steep'
@@ -134,12 +134,14 @@ class Puppeteer::BrowserContext
134
134
  def delete_cookie: (*Hash[Symbol | String, untyped] cookies) -> void
135
135
  def delete_matching_cookies: (*Hash[Symbol | String, untyped] filters) -> void
136
136
  def set_download_behavior: (Hash[Symbol | String, untyped] download_behavior) -> void
137
+ def set_permission: (String origin, *Hash[Symbol | String, untyped] permissions) -> void
137
138
 
138
139
  private
139
140
  def normalize_cookie_hash: (Hash[Symbol | String, untyped] cookie) -> Hash[String, untyped]
140
141
  def hash_value: (Hash[untyped, untyped]? hash, *(String | Symbol) keys) -> untyped
141
142
  def convert_partition_key_for_cdp: (untyped partition_key) -> Hash[Symbol, untyped]?
142
143
  def convert_partition_key_from_cdp: (untyped partition_key) -> (Hash[String, untyped] | String | nil)
144
+ def convert_same_site_for_cdp: (untyped same_site) -> String?
143
145
  end
144
146
 
145
147
  class Puppeteer::Frame
@@ -73,6 +73,11 @@ class Puppeteer::Browser
73
73
  # @rbs return: Puppeteer::BrowserContext -- Default browser context
74
74
  def default_browser_context: () -> Puppeteer::BrowserContext
75
75
 
76
+ # @rbs origin: String -- Origin URL, or '*' for all origins
77
+ # @rbs permissions: Array[Hash[Symbol | String, untyped]] -- Permission descriptors and states
78
+ # @rbs return: void -- No return value
79
+ def set_permission: (String origin, *untyped permissions) -> void
80
+
76
81
  # @rbs context_id: String? -- Browser context ID
77
82
  # @rbs return: void -- No return value
78
83
  def dispose_context: (String? context_id) -> void
@@ -91,6 +91,8 @@ class Puppeteer::HTTPRequest
91
91
 
92
92
  private def assert_interception_allowed: () -> untyped
93
93
 
94
+ private def parse_post_data: (untyped event) -> untyped
95
+
94
96
  private def assert_interception_not_handled: () -> untyped
95
97
 
96
98
  private def can_be_intercepted?: () -> untyped
@@ -94,8 +94,9 @@ class Puppeteer::Locator
94
94
  def click: (?delay: Numeric?, ?button: String?, ?click_count: Integer?, ?count: Integer?, ?offset: Hash[Symbol, Numeric]?) -> void
95
95
 
96
96
  # @rbs value: String -- Value to fill
97
+ # @rbs typing_threshold: Integer -- Minimum length to switch to direct assignment
97
98
  # @rbs return: void -- No return value
98
- def fill: (String value) -> void
99
+ def fill: (String value, ?typing_threshold: Integer) -> void
99
100
 
100
101
  # @rbs return: void -- No return value
101
102
  def hover: () -> void
@@ -133,7 +134,9 @@ class Puppeteer::Locator
133
134
 
134
135
  private def ensure_element_is_in_viewport_if_needed: (untyped handle, untyped options) -> untyped
135
136
 
136
- private def fill_element: (untyped handle, untyped value) -> untyped
137
+ private def fill_element: (untyped handle, untyped value, ?typing_threshold: untyped) -> untyped
138
+
139
+ private def fill_directly: (untyped handle, untyped value) -> untyped
137
140
  end
138
141
 
139
142
  class Puppeteer::FunctionLocator < Puppeteer::Locator
@@ -191,6 +191,8 @@ class Puppeteer::Page
191
191
  # check if each cookie element has required fields ('name' and 'value')
192
192
  private def assert_cookie_params: (untyped cookies, requires: untyped) -> untyped
193
193
 
194
+ private def convert_same_site_for_cdp: (untyped same_site) -> untyped
195
+
194
196
  # @rbs cookies: Array[Hash[Symbol | String, untyped]] -- cookies parameter
195
197
  # @rbs return: void -- No return value
196
198
  def delete_cookie: (*untyped cookies) -> void
@@ -239,6 +241,10 @@ class Puppeteer::Page
239
241
  # @rbs return: Puppeteer::Page::Metrics -- Page metrics
240
242
  def metrics: () -> Puppeteer::Page::Metrics
241
243
 
244
+ # @rbs path: String -- Output path for the heap snapshot
245
+ # @rbs return: void -- No return value
246
+ def capture_heap_snapshot: (path: String) -> void
247
+
242
248
  class PageError < Puppeteer::Error
243
249
  end
244
250
 
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.50.1
4
+ version: 0.51.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - YusukeIwaki
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2026-01-28 00:00:00.000000000 Z
11
+ date: 2026-02-09 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: async
@@ -216,14 +216,14 @@ dependencies:
216
216
  requirements:
217
217
  - - "~>"
218
218
  - !ruby/object:Gem::Version
219
- version: 1.82.1
219
+ version: 1.84.0
220
220
  type: :development
221
221
  prerelease: false
222
222
  version_requirements: !ruby/object:Gem::Requirement
223
223
  requirements:
224
224
  - - "~>"
225
225
  - !ruby/object:Gem::Version
226
- version: 1.82.1
226
+ version: 1.84.0
227
227
  - !ruby/object:Gem::Dependency
228
228
  name: rubocop-rspec
229
229
  requirement: !ruby/object:Gem::Requirement