airbrake-ruby 5.1.0-java → 6.0.0-java

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (75) hide show
  1. checksums.yaml +4 -4
  2. data/lib/airbrake-ruby/async_sender.rb +3 -1
  3. data/lib/airbrake-ruby/config/processor.rb +2 -1
  4. data/lib/airbrake-ruby/config.rb +15 -6
  5. data/lib/airbrake-ruby/context.rb +51 -0
  6. data/lib/airbrake-ruby/file_cache.rb +1 -1
  7. data/lib/airbrake-ruby/filter_chain.rb +2 -0
  8. data/lib/airbrake-ruby/filters/context_filter.rb +4 -5
  9. data/lib/airbrake-ruby/filters/exception_attributes_filter.rb +1 -1
  10. data/lib/airbrake-ruby/filters/git_last_checkout_filter.rb +1 -1
  11. data/lib/airbrake-ruby/filters/git_repository_filter.rb +1 -1
  12. data/lib/airbrake-ruby/filters/git_revision_filter.rb +1 -1
  13. data/lib/airbrake-ruby/filters/keys_filter.rb +2 -2
  14. data/lib/airbrake-ruby/filters/sql_filter.rb +2 -2
  15. data/lib/airbrake-ruby/filters/thread_filter.rb +2 -3
  16. data/lib/airbrake-ruby/grouppable.rb +1 -1
  17. data/lib/airbrake-ruby/ignorable.rb +0 -2
  18. data/lib/airbrake-ruby/mergeable.rb +1 -1
  19. data/lib/airbrake-ruby/monotonic_time.rb +1 -1
  20. data/lib/airbrake-ruby/notice_notifier.rb +3 -4
  21. data/lib/airbrake-ruby/performance_notifier.rb +1 -2
  22. data/lib/airbrake-ruby/remote_settings/callback.rb +1 -1
  23. data/lib/airbrake-ruby/remote_settings/settings_data.rb +2 -2
  24. data/lib/airbrake-ruby/remote_settings.rb +8 -7
  25. data/lib/airbrake-ruby/tdigest.rb +10 -9
  26. data/lib/airbrake-ruby/thread_pool.rb +5 -3
  27. data/lib/airbrake-ruby/timed_trace.rb +1 -3
  28. data/lib/airbrake-ruby/version.rb +2 -2
  29. data/lib/airbrake-ruby.rb +3 -2
  30. data/spec/airbrake_spec.rb +139 -76
  31. data/spec/async_sender_spec.rb +10 -8
  32. data/spec/backtrace_spec.rb +13 -10
  33. data/spec/benchmark_spec.rb +5 -3
  34. data/spec/code_hunk_spec.rb +24 -15
  35. data/spec/config/processor_spec.rb +20 -3
  36. data/spec/config/validator_spec.rb +5 -2
  37. data/spec/config_spec.rb +26 -17
  38. data/spec/context_spec.rb +54 -0
  39. data/spec/deploy_notifier_spec.rb +6 -4
  40. data/spec/file_cache_spec.rb +1 -0
  41. data/spec/filter_chain_spec.rb +29 -24
  42. data/spec/filters/context_filter_spec.rb +14 -5
  43. data/spec/filters/dependency_filter_spec.rb +3 -1
  44. data/spec/filters/exception_attributes_filter_spec.rb +5 -3
  45. data/spec/filters/gem_root_filter_spec.rb +5 -2
  46. data/spec/filters/git_last_checkout_filter_spec.rb +10 -12
  47. data/spec/filters/git_repository_filter.rb +9 -9
  48. data/spec/filters/git_revision_filter_spec.rb +19 -19
  49. data/spec/filters/keys_allowlist_spec.rb +25 -16
  50. data/spec/filters/keys_blocklist_spec.rb +25 -18
  51. data/spec/filters/root_directory_filter_spec.rb +3 -3
  52. data/spec/filters/sql_filter_spec.rb +26 -26
  53. data/spec/filters/system_exit_filter_spec.rb +4 -2
  54. data/spec/filters/thread_filter_spec.rb +16 -14
  55. data/spec/loggable_spec.rb +2 -2
  56. data/spec/monotonic_time_spec.rb +8 -6
  57. data/spec/nested_exception_spec.rb +46 -46
  58. data/spec/notice_notifier/options_spec.rb +23 -13
  59. data/spec/notice_notifier_spec.rb +52 -47
  60. data/spec/notice_spec.rb +6 -2
  61. data/spec/performance_notifier_spec.rb +67 -60
  62. data/spec/promise_spec.rb +38 -32
  63. data/spec/remote_settings/callback_spec.rb +27 -8
  64. data/spec/remote_settings/settings_data_spec.rb +4 -4
  65. data/spec/remote_settings_spec.rb +40 -7
  66. data/spec/response_spec.rb +34 -12
  67. data/spec/stashable_spec.rb +5 -5
  68. data/spec/stat_spec.rb +7 -5
  69. data/spec/sync_sender_spec.rb +49 -16
  70. data/spec/tdigest_spec.rb +61 -56
  71. data/spec/thread_pool_spec.rb +65 -55
  72. data/spec/time_truncate_spec.rb +4 -2
  73. data/spec/timed_trace_spec.rb +32 -30
  74. data/spec/truncator_spec.rb +72 -43
  75. metadata +52 -49
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: b6e38e61b0caa09af3b9a0e0bf2deb678369bfe2c31e5923f9ec64d93f8456a7
4
- data.tar.gz: 1936144cbf286ab6e43fbd8874d4093357ee4f7c2a7c43f0d7e507290e081d53
3
+ metadata.gz: e62872ef39cf99827e1c0e7395c645acace3addb2b61919d23504ba686fc57c1
4
+ data.tar.gz: f769f0604e3dd7118df53cb6de2e3115beed43a898e9eefb5828174c29f16f67
5
5
  SHA512:
6
- metadata.gz: 565a30fe46379d2da490d164e6d14462cba6bbb7817e8a008e676a396aa117abd6ac416cdc5b6c019204a2ab4b93c7d6cdd257c02c8ac4a335722463414f3933
7
- data.tar.gz: 371aea04d52fef881b2b74c9781f0788b536711e1cfeecfd328ee6778f629e7f19eab793a557f42f6fa1603709ae7e20b1ec1abba527f26149acb3581a633f6c
6
+ metadata.gz: 1fef60cb8667cd9c5582dcab3f4d6562efc4ced3bafa89b2b538efe8b4f6dbbffa1663f27423d83d35f13d591f5b88675f8f5993731c2af4c09e52cffbb2af8c
7
+ data.tar.gz: 737a3900b60024d24303d10277d89ab782f60c58cadeb8e7fef3b7da17e983c8dd0033724e3640fe07d3428f1f86952f65ef378f81547213c2a8b11a9271eaa7
@@ -7,9 +7,10 @@ module Airbrake
7
7
  class AsyncSender
8
8
  include Loggable
9
9
 
10
- def initialize(method = :post)
10
+ def initialize(method = :post, name = 'async-sender')
11
11
  @config = Airbrake::Config.instance
12
12
  @method = method
13
+ @name = name
13
14
  end
14
15
 
15
16
  # Asynchronously sends a notice to Airbrake.
@@ -47,6 +48,7 @@ module Airbrake
47
48
  @thread_pool ||= begin
48
49
  sender = SyncSender.new(@method)
49
50
  ThreadPool.new(
51
+ name: @name,
50
52
  worker_size: @config.workers,
51
53
  queue_size: @config.queue_size,
52
54
  block: proc { |args| sender.send(*args) },
@@ -3,7 +3,7 @@ module Airbrake
3
3
  # Processor is a helper class, which is responsible for setting default
4
4
  # config values, default notifier filters and remote configuration changes.
5
5
  #
6
- # @since 5.0.0
6
+ # @since v5.0.0
7
7
  # @api private
8
8
  class Processor
9
9
  # @param [Airbrake::Config] config
@@ -41,6 +41,7 @@ module Airbrake
41
41
 
42
42
  # @return [Airbrake::RemoteSettings]
43
43
  def process_remote_configuration
44
+ return unless @config.remote_config
44
45
  return unless @project_id
45
46
  return if @config.environment == 'test'
46
47
 
@@ -121,13 +121,21 @@ module Airbrake
121
121
  # @return [Boolean] true if the library should send error reports to
122
122
  # Airbrake, false otherwise
123
123
  # @api public
124
- # @since 5.0.0
124
+ # @since v5.0.0
125
125
  attr_accessor :error_notifications
126
126
 
127
- # @return [String] the host such as which should be used for fetching remote
128
- # configuration options (example: "https://bucket-name.s3.amazonaws.com")
127
+ # @return [String] the host which should be used for fetching remote
128
+ # configuration options
129
+ # @api public
130
+ # @since v5.0.0
129
131
  attr_accessor :remote_config_host
130
132
 
133
+ # @return [String] true if notifier should periodically fetch remote
134
+ # configuration, false otherwise
135
+ # @api public
136
+ # @since v5.2.0
137
+ attr_accessor :remote_config
138
+
131
139
  class << self
132
140
  # @return [Config]
133
141
  attr_writer :instance
@@ -140,7 +148,7 @@ module Airbrake
140
148
 
141
149
  # @param [Hash{Symbol=>Object}] user_config the hash to be used to build the
142
150
  # config
143
- # rubocop:disable Metrics/AbcSize
151
+ # rubocop:disable Metrics/AbcSize, Metrics/MethodLength
144
152
  def initialize(user_config = {})
145
153
  self.proxy = {}
146
154
  self.queue_size = 100
@@ -151,7 +159,7 @@ module Airbrake
151
159
  self.project_key = user_config[:project_key]
152
160
  self.error_host = 'https://api.airbrake.io'
153
161
  self.apm_host = 'https://api.airbrake.io'
154
- self.remote_config_host = 'https://v1-production-notifier-configs.s3.amazonaws.com'
162
+ self.remote_config_host = 'https://notifier-configs.airbrake.io'
155
163
 
156
164
  self.ignore_environments = []
157
165
 
@@ -171,10 +179,11 @@ module Airbrake
171
179
  self.query_stats = true
172
180
  self.job_stats = true
173
181
  self.error_notifications = true
182
+ self.remote_config = true
174
183
 
175
184
  merge(user_config)
176
185
  end
177
- # rubocop:enable Metrics/AbcSize
186
+ # rubocop:enable Metrics/AbcSize, Metrics/MethodLength
178
187
 
179
188
  # The full URL to the Airbrake Notice API. Based on the +:error_host+ option.
180
189
  # @return [URI] the endpoint address
@@ -0,0 +1,51 @@
1
+ module Airbrake
2
+ # Represents a thread-safe Airbrake context object, which carries arbitrary
3
+ # information added via {Airbrake.merge_context} calls.
4
+ #
5
+ # @example
6
+ # Airbrake::Context.current.merge!(foo: 'bar')
7
+ #
8
+ # @api private
9
+ # @since v5.2.1
10
+ class Context
11
+ # Returns current, thread-local, context.
12
+ # @return [self]
13
+ def self.current
14
+ Thread.current[:airbrake_context] ||= new
15
+ end
16
+
17
+ def initialize
18
+ @mutex = Mutex.new
19
+ @context = {}
20
+ end
21
+
22
+ # Merges the given context with the current one.
23
+ #
24
+ # @param [Hash{Object=>Object}] other
25
+ # @return [void]
26
+ def merge!(other)
27
+ @mutex.synchronize do
28
+ @context.merge!(other)
29
+ end
30
+ end
31
+
32
+ # @return [Hash] duplicated Hash context
33
+ def to_h
34
+ @mutex.synchronize do
35
+ @context.dup
36
+ end
37
+ end
38
+
39
+ # @return [Hash] clears (resets) the current context
40
+ def clear
41
+ @mutex.synchronize do
42
+ @context.clear
43
+ end
44
+ end
45
+
46
+ # @return [Boolean] checks whether the context has any data
47
+ def empty?
48
+ @context.empty?
49
+ end
50
+ end
51
+ end
@@ -40,7 +40,7 @@ module Airbrake
40
40
  data.empty?
41
41
  end
42
42
 
43
- # @since 4.7.0
43
+ # @since v4.7.0
44
44
  # @return [void]
45
45
  def self.reset
46
46
  @data = {}
@@ -57,7 +57,9 @@ module Airbrake
57
57
  # @return [void]
58
58
  # @since v3.1.0
59
59
  def delete_filter(filter_class)
60
+ # rubocop:disable Style/ClassEqualityComparison
60
61
  index = @filters.index { |f| f.class.name == filter_class.name }
62
+ # rubocop:enable Style/ClassEqualityComparison
61
63
  @filters.delete_at(index) if index
62
64
  end
63
65
 
@@ -9,8 +9,7 @@ module Airbrake
9
9
  # @return [Integer]
10
10
  attr_reader :weight
11
11
 
12
- def initialize(context)
13
- @context = context
12
+ def initialize
14
13
  @weight = 119
15
14
  @mutex = Mutex.new
16
15
  end
@@ -18,10 +17,10 @@ module Airbrake
18
17
  # @macro call_filter
19
18
  def call(notice)
20
19
  @mutex.synchronize do
21
- return if @context.empty?
20
+ return if Airbrake::Context.current.empty?
22
21
 
23
- notice[:params][:airbrake_context] = @context.dup
24
- @context.clear
22
+ notice[:params][:airbrake_context] = Airbrake::Context.current.to_h
23
+ Airbrake::Context.current.clear
25
24
  end
26
25
  end
27
26
  end
@@ -13,7 +13,7 @@ module Airbrake
13
13
  end
14
14
 
15
15
  # @macro call_filter
16
- def call(notice)
16
+ def call(notice) # rubocop:disable Metrics/AbcSize
17
17
  exception = notice.stash[:exception]
18
18
  return unless exception.respond_to?(:to_airbrake)
19
19
 
@@ -50,7 +50,7 @@ module Airbrake
50
50
  def last_checkout
51
51
  return unless (line = last_checkout_line)
52
52
 
53
- parts = line.chomp.split("\t").first.split(' ')
53
+ parts = line.chomp.split("\t").first.split
54
54
  if parts.size < MIN_HEAD_COLS
55
55
  logger.error(
56
56
  "#{LOG_LABEL} Airbrake::#{self.class.name}: can't parse line: #{line}",
@@ -36,7 +36,7 @@ module Airbrake
36
36
  `cd #{@git_path} && git config --get remote.origin.url`.chomp
37
37
  else
38
38
  "`git remote get-url` is unsupported in git #{@git_version}. " \
39
- 'Consider an upgrade to 2.7+'
39
+ 'Consider an upgrade to 2.7+'
40
40
  end
41
41
 
42
42
  return unless @repository
@@ -57,7 +57,7 @@ module Airbrake
57
57
 
58
58
  File.readlines(packed_refs_path).each do |line|
59
59
  next if %w[# ^].include?(line[0])
60
- next unless (parts = line.split(' ')).size == 2
60
+ next unless (parts = line.split).size == 2
61
61
  return parts.first if parts.last == head
62
62
  end
63
63
 
@@ -82,7 +82,7 @@ module Airbrake
82
82
 
83
83
  private
84
84
 
85
- def filter_hash(hash)
85
+ def filter_hash(hash) # rubocop:disable Metrics/AbcSize
86
86
  return hash unless hash.is_a?(Hash)
87
87
 
88
88
  hash_copy = hash.dup
@@ -103,7 +103,7 @@ module Airbrake
103
103
  end
104
104
 
105
105
  def filter_url_params(url)
106
- url.query = Hash[URI.decode_www_form(url.query)].map do |key, val|
106
+ url.query = URI.decode_www_form(url.query).to_h.map do |key, val|
107
107
  should_filter?(key) ? "#{key}=[Filtered]" : "#{key}=#{val}"
108
108
  end.join('&')
109
109
 
@@ -27,13 +27,13 @@ module Airbrake
27
27
  single_quotes: /'(?:[^']|'')*?(?:\\'.*|'(?!'))/,
28
28
  double_quotes: /"(?:[^"]|"")*?(?:\\".*|"(?!"))/,
29
29
  dollar_quotes: /(\$(?!\d)[^$]*?\$).*?(?:\1|$)/,
30
- uuids: /\{?(?:[0-9a-fA-F]\-*){32}\}?/,
30
+ uuids: /\{?(?:[0-9a-fA-F]-*){32}\}?/,
31
31
  numeric_literals: /\b-?(?:[0-9]+\.)?[0-9]+([eE][+-]?[0-9]+)?\b/,
32
32
  boolean_literals: /\b(?:true|false|null)\b/i,
33
33
  hexadecimal_literals: /0x[0-9a-fA-F]+/,
34
34
  comments: /(?:#|--).*?(?=\r|\n|$)/i,
35
35
  multi_line_comments: %r{/\*(?:[^/]|/[^*])*?(?:\*/|/\*.*)},
36
- oracle_quoted_strings: /q'\[.*?(?:\]'|$)|q'\{.*?(?:\}'|$)|q'\<.*?(?:\>'|$)|q'\(.*?(?:\)'|$)/,
36
+ oracle_quoted_strings: /q'\[.*?(?:\]'|$)|q'\{.*?(?:\}'|$)|q'<.*?(?:>'|$)|q'\(.*?(?:\)'|$)/,
37
37
  # rubocop:enable Layout/LineLength
38
38
  }.freeze
39
39
 
@@ -41,8 +41,7 @@ module Airbrake
41
41
  thread_info[:fiber_variables] = vars
42
42
  end
43
43
 
44
- # Present in Ruby 2.3+.
45
- if th.respond_to?(:name) && (name = th.name)
44
+ if (name = th.name)
46
45
  thread_info[:name] = name
47
46
  end
48
47
 
@@ -84,7 +83,7 @@ module Airbrake
84
83
  when Array
85
84
  value = value.map { |elem| sanitize_value(elem) }
86
85
  when Hash
87
- Hash[value.map { |k, v| [k, sanitize_value(v)] }]
86
+ value.transform_values { |v| sanitize_value(v) }
88
87
  else
89
88
  value.to_s
90
89
  end
@@ -2,7 +2,7 @@ module Airbrake
2
2
  # Grouppable adds the `#groups` method, so that we don't need to define it in
3
3
  # all of performance models every time we add a model without groups.
4
4
  #
5
- # @since 4.9.0
5
+ # @since v4.9.0
6
6
  # @api private
7
7
  module Grouppable
8
8
  def groups
@@ -18,11 +18,9 @@ module Airbrake
18
18
  # Checks whether the instance was ignored.
19
19
  # @return [Boolean]
20
20
  # @see #ignore!
21
- # rubocop:disable Style/DoubleNegation
22
21
  def ignored?
23
22
  !!ignored
24
23
  end
25
- # rubocop:enable Style/DoubleNegation
26
24
 
27
25
  # Ignores an instance. Ignored instances must never reach the Airbrake
28
26
  # dashboard.
@@ -2,7 +2,7 @@ module Airbrake
2
2
  # Mergeable adds the `#merge` method, so that we don't need to define it in
3
3
  # all of performance models every time we add a model.
4
4
  #
5
- # @since 4.9.0
5
+ # @since v4.9.0
6
6
  # @api private
7
7
  module Mergeable
8
8
  def merge(_other)
@@ -39,7 +39,7 @@ module Airbrake
39
39
 
40
40
  def time_in_nanoseconds
41
41
  time = Time.now
42
- time.to_i * (10**9) + time.nsec
42
+ (time.to_i * (10**9)) + time.nsec
43
43
  end
44
44
 
45
45
  end
@@ -20,14 +20,13 @@ module Airbrake
20
20
 
21
21
  def initialize
22
22
  @config = Airbrake::Config.instance
23
- @context = {}
24
23
  @filter_chain = FilterChain.new
25
- @async_sender = AsyncSender.new
24
+ @async_sender = AsyncSender.new(:post, self.class.name)
26
25
  @sync_sender = SyncSender.new
27
26
 
28
27
  DEFAULT_FILTERS.each { |filter| add_filter(filter.new) }
29
28
 
30
- add_filter(Airbrake::Filters::ContextFilter.new(@context))
29
+ add_filter(Airbrake::Filters::ContextFilter.new)
31
30
  add_filter(Airbrake::Filters::ExceptionAttributesFilter.new)
32
31
  end
33
32
 
@@ -79,7 +78,7 @@ module Airbrake
79
78
 
80
79
  # @see Airbrake.merge_context
81
80
  def merge_context(context)
82
- @context.merge!(context)
81
+ Airbrake::Context.current.merge!(context)
83
82
  end
84
83
 
85
84
  # @return [Boolean]
@@ -12,7 +12,7 @@ module Airbrake
12
12
  def initialize
13
13
  @config = Airbrake::Config.instance
14
14
  @flush_period = Airbrake::Config.instance.performance_stats_flush_period
15
- @async_sender = AsyncSender.new(:put)
15
+ @async_sender = AsyncSender.new(:put, self.class.name)
16
16
  @sync_sender = SyncSender.new(:put)
17
17
  @schedule_flush = nil
18
18
  @filter_chain = FilterChain.new
@@ -51,7 +51,6 @@ module Airbrake
51
51
  @payload.synchronize do
52
52
  @schedule_flush.kill if @schedule_flush
53
53
  @async_sender.close
54
- logger.debug("#{LOG_LABEL} performance notifier closed")
55
54
  end
56
55
  end
57
56
 
@@ -4,7 +4,7 @@ module Airbrake
4
4
  # updates the local config according to the data.
5
5
  #
6
6
  # @api private
7
- # @since 5.0.2
7
+ # @since v5.0.2
8
8
  class Callback
9
9
  def initialize(config)
10
10
  @config = config
@@ -11,7 +11,7 @@ module Airbrake
11
11
  #
12
12
  # settings_data.interval #=> 600
13
13
  #
14
- # @since 5.0.0
14
+ # @since v5.0.0
15
15
  # @api private
16
16
  class SettingsData
17
17
  # @return [Integer] how frequently we should poll the config API
@@ -59,7 +59,7 @@ module Airbrake
59
59
  # @return [String] where the config is stored on S3.
60
60
  def config_route(remote_config_host)
61
61
  if @data['config_route'] && !@data['config_route'].empty?
62
- return remote_config_host.chomp('/') + '/' + @data['config_route']
62
+ return "#{remote_config_host.chomp('/')}/#{@data['config_route']}"
63
63
  end
64
64
 
65
65
  format(
@@ -8,7 +8,7 @@ module Airbrake
8
8
  # config.error_notifications = data.error_notifications?
9
9
  # end
10
10
  #
11
- # @since 5.0.0
11
+ # @since v5.0.0
12
12
  # @api private
13
13
  class RemoteSettings
14
14
  include Airbrake::Loggable
@@ -22,6 +22,9 @@ module Airbrake
22
22
  language: "#{RUBY_ENGINE}/#{RUBY_VERSION}".freeze,
23
23
  ).freeze
24
24
 
25
+ # @return [String]
26
+ HTTP_OK = '200'.freeze
27
+
25
28
  # Polls remote config of the given project.
26
29
  #
27
30
  # @param [Integer] project_id
@@ -71,22 +74,20 @@ module Airbrake
71
74
  def fetch_config
72
75
  response = nil
73
76
  begin
74
- response = Net::HTTP.get(build_config_uri)
77
+ response = Net::HTTP.get_response(build_config_uri)
75
78
  rescue StandardError => ex
76
79
  logger.error(ex)
77
80
  return {}
78
81
  end
79
82
 
80
- # AWS S3 API returns XML when request is not valid. In this case we just
81
- # print the returned body and exit the method.
82
- if response.start_with?('<?xml ')
83
- logger.error(response)
83
+ unless response.code == HTTP_OK
84
+ logger.error(response.body)
84
85
  return {}
85
86
  end
86
87
 
87
88
  json = nil
88
89
  begin
89
- json = JSON.parse(response)
90
+ json = JSON.parse(response.body)
90
91
  rescue JSON::ParserError => ex
91
92
  logger.error(ex)
92
93
  return {}
@@ -24,6 +24,7 @@ module Airbrake
24
24
  # @since v3.2.0
25
25
  class Centroid
26
26
  attr_accessor :mean, :n, :cumn, :mean_cumn
27
+
27
28
  def initialize(mean, n, cumn, mean_cumn = nil)
28
29
  @mean = mean
29
30
  @n = n
@@ -130,7 +131,7 @@ module Airbrake
130
131
  points = to_a
131
132
  reset!
132
133
  push_centroid(points.shuffle)
133
- _cumulate(true, true)
134
+ _cumulate(exact: true, force: true)
134
135
  nil
135
136
  end
136
137
 
@@ -175,7 +176,7 @@ module Airbrake
175
176
  elsif item > max[1].mean
176
177
  1.0
177
178
  else
178
- _cumulate(true)
179
+ _cumulate(exact: true)
179
180
  bound = bound_mean(item)
180
181
  lower, upper = bound
181
182
  mean_cumn = lower.mean_cumn
@@ -204,7 +205,7 @@ module Airbrake
204
205
  if size == 0
205
206
  nil
206
207
  else
207
- _cumulate(true)
208
+ _cumulate(exact: true)
208
209
  h = @size * item
209
210
  lower, upper = bound_mean_cumn(h)
210
211
  if lower.nil? && upper.nil?
@@ -255,7 +256,7 @@ module Airbrake
255
256
  array = bytes[start_idx..-1].unpack("G#{size}N#{size}")
256
257
  means, counts = array.each_slice(size).to_a if array.any?
257
258
  when SMALL_ENCODING
258
- means = bytes[start_idx..(start_idx + 4 * size)].unpack("g#{size}")
259
+ means = bytes[start_idx..(start_idx + (4 * size))].unpack("g#{size}")
259
260
  # Decode delta encoding of means
260
261
  x = 0
261
262
  means.map! do |m|
@@ -263,7 +264,7 @@ module Airbrake
263
264
  x = m
264
265
  m
265
266
  end
266
- counts_bytes = bytes[(start_idx + 4 * size)..-1].unpack('C*')
267
+ counts_bytes = bytes[(start_idx + (4 * size))..-1].unpack('C*')
267
268
  counts = []
268
269
  # Decode variable length integer bytes
269
270
  size.times do
@@ -306,7 +307,7 @@ module Airbrake
306
307
  centroid.mean += n * (x - centroid.mean) / (centroid.n + n)
307
308
  end
308
309
 
309
- _cumulate(false, true) if centroid.mean_cumn.nil?
310
+ _cumulate(exact: false, force: true) if centroid.mean_cumn.nil?
310
311
 
311
312
  centroid.cumn += n
312
313
  centroid.mean_cumn += n / 2.0
@@ -314,7 +315,7 @@ module Airbrake
314
315
  end
315
316
 
316
317
  # rubocop:disable Metrics/PerceivedComplexity, Metrics/CyclomaticComplexity
317
- def _cumulate(exact = false, force = false)
318
+ def _cumulate(exact: false, force: false)
318
319
  unless force
319
320
  factor = if @last_cumulate == 0
320
321
  Float::INFINITY
@@ -326,7 +327,7 @@ module Airbrake
326
327
 
327
328
  cumn = 0
328
329
  @centroids.each_value do |c|
329
- c.mean_cumn = cumn + c.n / 2.0
330
+ c.mean_cumn = cumn + (c.n / 2.0)
330
331
  cumn = c.cumn = cumn + c.n
331
332
  end
332
333
  @size = @last_cumulate = cumn
@@ -361,7 +362,7 @@ module Airbrake
361
362
  end
362
363
  end
363
364
 
364
- _cumulate(false)
365
+ _cumulate(exact: false)
365
366
 
366
367
  # If the number of centroids has grown to a very large size,
367
368
  # it may be due to values being inserted in sorted order.
@@ -6,6 +6,7 @@ module Airbrake
6
6
  # # Initialize a new thread pool with 5 workers and a queue size of 100. Set
7
7
  # # the block to be run concurrently.
8
8
  # thread_pool = ThreadPool.new(
9
+ # name: 'performance-notifier',
9
10
  # worker_size: 5,
10
11
  # queue_size: 100,
11
12
  # block: proc { |message| print "ECHO: #{message}..."}
@@ -24,7 +25,8 @@ module Airbrake
24
25
  # @note This is exposed for eaiser unit testing
25
26
  attr_reader :workers
26
27
 
27
- def initialize(worker_size:, queue_size:, block:)
28
+ def initialize(worker_size:, queue_size:, block:, name: nil)
29
+ @name = name
28
30
  @worker_size = worker_size
29
31
  @queue_size = queue_size
30
32
  @block = block
@@ -102,7 +104,7 @@ module Airbrake
102
104
 
103
105
  unless @queue.empty?
104
106
  msg = "#{LOG_LABEL} waiting to process #{@queue.size} task(s)..."
105
- logger.debug(msg + ' (Ctrl-C to abort)')
107
+ logger.debug("#{msg} (Ctrl-C to abort)")
106
108
  end
107
109
 
108
110
  @worker_size.times { @queue << :stop }
@@ -111,7 +113,7 @@ module Airbrake
111
113
  end
112
114
 
113
115
  threads.each(&:join)
114
- logger.debug("#{LOG_LABEL} thread pool closed")
116
+ logger.debug("#{LOG_LABEL} #{@name} thread pool closed")
115
117
  end
116
118
 
117
119
  def closed?
@@ -50,9 +50,7 @@ module Airbrake
50
50
 
51
51
  # @return [Hash<String=>Float>]
52
52
  def spans
53
- @spans.each_with_object({}) do |(label, benchmark), new_spans|
54
- new_spans[label] = benchmark.duration
55
- end
53
+ @spans.transform_values(&:duration)
56
54
  end
57
55
  end
58
56
  end
@@ -3,10 +3,10 @@
3
3
  module Airbrake
4
4
  # @return [String] the library version
5
5
  # @api public
6
- AIRBRAKE_RUBY_VERSION = '5.1.0'.freeze
6
+ AIRBRAKE_RUBY_VERSION = '6.0.0'.freeze
7
7
 
8
8
  # @return [Hash{Symbol=>String}] the information about the notifier library
9
- # @since 5.0.0
9
+ # @since v5.0.0
10
10
  # @api public
11
11
  NOTIFIER_INFO = {
12
12
  name: 'airbrake-ruby'.freeze,
data/lib/airbrake-ruby.rb CHANGED
@@ -58,6 +58,7 @@ require 'airbrake-ruby/benchmark'
58
58
  require 'airbrake-ruby/monotonic_time'
59
59
  require 'airbrake-ruby/timed_trace'
60
60
  require 'airbrake-ruby/queue'
61
+ require 'airbrake-ruby/context'
61
62
 
62
63
  # Airbrake is a thin wrapper around instances of the notifier classes (such as
63
64
  # notice, performance & deploy notifiers). It creates a way to access them via a
@@ -273,7 +274,7 @@ module Airbrake
273
274
  # Airbrake.notify('App crashed!') #=> raises Airbrake::Error
274
275
  #
275
276
  # @return [nil]
276
- # rubocop:disable Style/IfUnlessModifier, Metrics/CyclomaticComplexity
277
+ # rubocop:disable Style/IfUnlessModifier
277
278
  def close
278
279
  if defined?(@notice_notifier) && @notice_notifier
279
280
  @notice_notifier.close
@@ -289,7 +290,7 @@ module Airbrake
289
290
 
290
291
  nil
291
292
  end
292
- # rubocop:enable Style/IfUnlessModifier, Metrics/CyclomaticComplexity
293
+ # rubocop:enable Style/IfUnlessModifier
293
294
 
294
295
  # Pings the Airbrake Deploy API endpoint about the occurred deploy.
295
296
  #