appsignal 2.11.1-java → 3.0.0.beta.1-java

Sign up to get free protection for your applications and to get access to all the features.
Files changed (81) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop.yml +6 -1
  3. data/.semaphore/semaphore.yml +197 -23
  4. data/CHANGELOG.md +25 -0
  5. data/README.md +9 -0
  6. data/Rakefile +9 -6
  7. data/build_matrix.yml +13 -4
  8. data/ext/agent.yml +17 -17
  9. data/ext/base.rb +12 -9
  10. data/gemfiles/no_dependencies.gemfile +7 -0
  11. data/gemfiles/resque-2.gemfile +0 -1
  12. data/gemfiles/webmachine.gemfile +1 -0
  13. data/lib/appsignal.rb +1 -27
  14. data/lib/appsignal/auth_check.rb +2 -8
  15. data/lib/appsignal/cli.rb +1 -23
  16. data/lib/appsignal/cli/diagnose/utils.rb +8 -11
  17. data/lib/appsignal/cli/install.rb +5 -8
  18. data/lib/appsignal/config.rb +0 -24
  19. data/lib/appsignal/event_formatter.rb +0 -25
  20. data/lib/appsignal/helpers/instrumentation.rb +32 -0
  21. data/lib/appsignal/hooks.rb +0 -23
  22. data/lib/appsignal/hooks/action_cable.rb +3 -34
  23. data/lib/appsignal/hooks/active_support_notifications.rb +7 -86
  24. data/lib/appsignal/hooks/celluloid.rb +5 -9
  25. data/lib/appsignal/hooks/net_http.rb +2 -12
  26. data/lib/appsignal/hooks/puma.rb +3 -5
  27. data/lib/appsignal/hooks/que.rb +1 -1
  28. data/lib/appsignal/hooks/rake.rb +2 -24
  29. data/lib/appsignal/hooks/redis.rb +2 -13
  30. data/lib/appsignal/hooks/resque.rb +2 -43
  31. data/lib/appsignal/hooks/shoryuken.rb +43 -4
  32. data/lib/appsignal/hooks/unicorn.rb +3 -24
  33. data/lib/appsignal/hooks/webmachine.rb +1 -7
  34. data/lib/appsignal/integrations/action_cable.rb +34 -0
  35. data/lib/appsignal/integrations/active_support_notifications.rb +77 -0
  36. data/lib/appsignal/integrations/net_http.rb +16 -0
  37. data/lib/appsignal/integrations/object.rb +44 -17
  38. data/lib/appsignal/integrations/padrino.rb +5 -7
  39. data/lib/appsignal/integrations/que.rb +26 -33
  40. data/lib/appsignal/integrations/railtie.rb +1 -4
  41. data/lib/appsignal/integrations/rake.rb +26 -2
  42. data/lib/appsignal/integrations/redis.rb +17 -0
  43. data/lib/appsignal/integrations/resque.rb +39 -10
  44. data/lib/appsignal/integrations/unicorn.rb +28 -0
  45. data/lib/appsignal/integrations/webmachine.rb +22 -24
  46. data/lib/appsignal/minutely.rb +0 -12
  47. data/lib/appsignal/system.rb +4 -0
  48. data/lib/appsignal/transaction.rb +30 -2
  49. data/lib/appsignal/version.rb +1 -1
  50. data/spec/lib/appsignal/auth_check_spec.rb +1 -24
  51. data/spec/lib/appsignal/cli_spec.rb +1 -1
  52. data/spec/lib/appsignal/config_spec.rb +0 -66
  53. data/spec/lib/appsignal/event_formatter_spec.rb +0 -37
  54. data/spec/lib/appsignal/hooks/celluloid_spec.rb +6 -1
  55. data/spec/lib/appsignal/hooks/rake_spec.rb +1 -2
  56. data/spec/lib/appsignal/hooks/redis_spec.rb +50 -15
  57. data/spec/lib/appsignal/hooks/resque_spec.rb +10 -2
  58. data/spec/lib/appsignal/hooks/shoryuken_spec.rb +151 -104
  59. data/spec/lib/appsignal/hooks/sidekiq_spec.rb +4 -2
  60. data/spec/lib/appsignal/hooks/unicorn_spec.rb +14 -3
  61. data/spec/lib/appsignal/hooks/webmachine_spec.rb +2 -13
  62. data/spec/lib/appsignal/hooks_spec.rb +0 -57
  63. data/spec/lib/appsignal/integrations/object_spec.rb +25 -10
  64. data/spec/lib/appsignal/integrations/padrino_spec.rb +2 -3
  65. data/spec/lib/appsignal/integrations/railtie_spec.rb +0 -45
  66. data/spec/lib/appsignal/integrations/webmachine_spec.rb +26 -8
  67. data/spec/lib/appsignal/minutely_spec.rb +0 -19
  68. data/spec/lib/appsignal/transaction_spec.rb +56 -14
  69. data/spec/lib/appsignal/transmitter_spec.rb +1 -1
  70. data/spec/lib/appsignal_spec.rb +30 -69
  71. data/spec/spec_helper.rb +1 -15
  72. metadata +13 -22
  73. data/lib/appsignal/cli/notify_of_deploy.rb +0 -131
  74. data/lib/appsignal/integrations/resque_active_job.rb +0 -19
  75. data/lib/appsignal/js_exception_transaction.rb +0 -56
  76. data/lib/appsignal/rack/js_exception_catcher.rb +0 -80
  77. data/spec/lib/appsignal/cli/notify_of_deploy_spec.rb +0 -180
  78. data/spec/lib/appsignal/integrations/resque_active_job_spec.rb +0 -28
  79. data/spec/lib/appsignal/integrations/resque_spec.rb +0 -28
  80. data/spec/lib/appsignal/js_exception_transaction_spec.rb +0 -128
  81. data/spec/lib/appsignal/rack/js_exception_catcher_spec.rb +0 -170
@@ -119,30 +119,33 @@ def download_archive(type)
119
119
 
120
120
  version = AGENT_CONFIG["version"]
121
121
  filename = ARCH_CONFIG[type]["filename"]
122
- attempted_mirror_urls = []
122
+ download_errors = []
123
123
 
124
124
  AGENT_CONFIG["mirrors"].each do |mirror|
125
125
  download_url = [mirror, version, filename].join("/")
126
- attempted_mirror_urls << download_url
127
126
  report["download"]["download_url"] = download_url
128
127
 
129
128
  begin
130
- return open(
129
+ args = [
131
130
  download_url,
132
131
  :ssl_ca_cert => CA_CERT_PATH,
133
132
  :proxy => http_proxy
134
- )
135
- rescue
133
+ ]
134
+ if URI.respond_to?(:open) # rubocop:disable Style/GuardClause
135
+ return URI.open(*args)
136
+ else
137
+ return open(*args)
138
+ end
139
+ rescue => error
140
+ download_errors << "- URL: #{download_url}\n Error: #{error.class}: #{error.message}"
136
141
  next
137
142
  end
138
143
  end
139
144
 
140
- attempted_mirror_urls_mapped = attempted_mirror_urls.map { |mirror| "- #{mirror}" }
141
145
  abort_installation(
142
146
  "Could not download archive from any of our mirrors. " \
143
- "Attempted to download the archive from the following urls:\n" \
144
- "#{attempted_mirror_urls_mapped.join("\n")}\n" \
145
- "Please make sure your network allows access to any of these mirrors."
147
+ "Please make sure your network allows access to any of these mirrors.\n" \
148
+ "Attempted to download the archive from the following urls:\n#{download_errors.join("\n")}"
146
149
  )
147
150
  end
148
151
 
@@ -2,4 +2,11 @@ source 'https://rubygems.org'
2
2
 
3
3
  gem 'rack', '~> 1.6'
4
4
 
5
+ ruby_version = Gem::Version.new(RUBY_VERSION)
6
+ if ruby_version < Gem::Version.new("2.0.0")
7
+ # Newer versions of this gem have rexml as a dependency which doesn't work on
8
+ # Ruby 1.9
9
+ gem "crack", "0.4.4"
10
+ end
11
+
5
12
  gemspec :path => '../'
@@ -2,7 +2,6 @@ source 'https://rubygems.org'
2
2
 
3
3
  gem 'resque', "~> 2.0"
4
4
  gem 'sinatra'
5
- gem 'mime-types', '~> 2.6'
6
5
 
7
6
  gemspec :path => '../'
8
7
 
@@ -1,5 +1,6 @@
1
1
  source 'https://rubygems.org'
2
2
 
3
3
  gem 'webmachine'
4
+ gem 'webrick'
4
5
 
5
6
  gemspec :path => '../'
@@ -129,7 +129,6 @@ module Appsignal
129
129
  config.write_to_environment
130
130
  Appsignal::Extension.start
131
131
  Appsignal::Hooks.load_hooks
132
- Appsignal::EventFormatter.initialize_deprecated_formatters
133
132
  initialize_extensions
134
133
 
135
134
  if config[:enable_allocation_tracking] && !Appsignal::System.jruby?
@@ -222,15 +221,9 @@ module Appsignal
222
221
  # Sets the log level and sets the logger. Uses a file-based logger or the
223
222
  # STDOUT-based logger. See the `:log` configuration option.
224
223
  #
225
- # @param path_arg [nil] Deprecated param. Use the `:log_path`
226
- # configuration option instead.
227
224
  # @return [void]
228
225
  # @since 0.7.0
229
- def start_logger(path_arg = nil)
230
- if path_arg
231
- logger.info("Setting the path in start_logger has no effect anymore, set it in the config instead")
232
- end
233
-
226
+ def start_logger
234
227
  if config && config[:log] == "file" && config.log_file_path
235
228
  start_file_logger(config.log_file_path)
236
229
  else
@@ -285,21 +278,6 @@ module Appsignal
285
278
  config && config.active? && extension_loaded?
286
279
  end
287
280
 
288
- # @deprecated No replacement
289
- def is_ignored_error?(error) # rubocop:disable Naming/PredicateName
290
- deprecation_message "Appsignal.is_ignored_error? is deprecated " \
291
- "with no replacement and will be removed in version 3.0."
292
- Appsignal.config[:ignore_errors].include?(error.class.name)
293
- end
294
- alias :is_ignored_exception? :is_ignored_error?
295
-
296
- # @deprecated No replacement
297
- def is_ignored_action?(action) # rubocop:disable Naming/PredicateName
298
- deprecation_message "Appsignal.is_ignored_action? is deprecated " \
299
- "with no replacement and will be removed in version 3.0."
300
- Appsignal.config[:ignore_actions].include?(action)
301
- end
302
-
303
281
  private
304
282
 
305
283
  def start_stdout_logger
@@ -344,11 +322,7 @@ require "appsignal/marker"
344
322
  require "appsignal/minutely"
345
323
  require "appsignal/garbage_collection_profiler"
346
324
  require "appsignal/integrations/railtie" if defined?(::Rails)
347
- require "appsignal/integrations/resque"
348
- require "appsignal/integrations/resque_active_job"
349
325
  require "appsignal/transaction"
350
326
  require "appsignal/version"
351
327
  require "appsignal/rack/generic_instrumentation"
352
- require "appsignal/rack/js_exception_catcher"
353
- require "appsignal/js_exception_transaction"
354
328
  require "appsignal/transmitter"
@@ -20,16 +20,10 @@ module Appsignal
20
20
  # https://push.appsignal.com/1/auth
21
21
  ACTION = "auth".freeze
22
22
 
23
- attr_reader :config, :logger
23
+ attr_reader :config
24
24
 
25
- def initialize(config, logger = nil)
25
+ def initialize(config)
26
26
  @config = config
27
- if logger # rubocop:disable Style/GuardClause
28
- Appsignal::Utils::DeprecationMessage.message \
29
- "`Appsignal::AuthCheck.new`'s `logger` argument will be removed " \
30
- "in the next major version. Please configure the logger " \
31
- "using `Appsignal.logger`."
32
- end
33
27
  end
34
28
 
35
29
  # Perform push api validation request and return response status code.
@@ -7,12 +7,11 @@ require "appsignal/cli/helpers"
7
7
  require "appsignal/cli/demo"
8
8
  require "appsignal/cli/diagnose"
9
9
  require "appsignal/cli/install"
10
- require "appsignal/cli/notify_of_deploy"
11
10
 
12
11
  module Appsignal
13
12
  # @api private
14
13
  class CLI
15
- AVAILABLE_COMMANDS = %w[demo diagnose install notify_of_deploy].freeze
14
+ AVAILABLE_COMMANDS = %w[demo diagnose install].freeze
16
15
 
17
16
  class << self
18
17
  attr_accessor :options
@@ -33,8 +32,6 @@ module Appsignal
33
32
  Appsignal::CLI::Diagnose.run(options)
34
33
  when :install
35
34
  Appsignal::CLI::Install.run(argv.shift, options)
36
- when :notify_of_deploy
37
- Appsignal::CLI::NotifyOfDeploy.run(options)
38
35
  end
39
36
  else
40
37
  puts "Command '#{command}' does not exist, run appsignal -h to "\
@@ -93,25 +90,6 @@ module Appsignal
93
90
  o.on "--[no-]color", "Colorize the output of the diagnose command" do |arg|
94
91
  options[:color] = arg
95
92
  end
96
- end,
97
- "notify_of_deploy" => OptionParser.new do |o|
98
- o.banner = "Usage: appsignal notify_of_deploy [options]"
99
-
100
- o.on "--revision=<revision>", "The revision you're deploying" do |arg|
101
- options[:revision] = arg
102
- end
103
-
104
- o.on "--user=<user>", "The name of the user that's deploying" do |arg|
105
- options[:user] = arg
106
- end
107
-
108
- o.on "--environment=<app_env>", "The environment you're deploying to" do |arg|
109
- options[:environment] = arg
110
- end
111
-
112
- o.on "--name=<name>", "The name of the app (optional)" do |arg|
113
- options[:name] = arg
114
- end
115
93
  end
116
94
  }
117
95
  end
@@ -34,20 +34,17 @@ module Appsignal
34
34
  end
35
35
 
36
36
  def self.parse_yaml(contents)
37
- arguments = [contents]
38
37
  if YAML.respond_to? :safe_load
39
- method = :safe_load
40
- arguments << \
41
- if Gem::Version.new(RUBY_VERSION) >= Gem::Version.new("2.6.0")
42
- # Use keyword params for Ruby 2.6 and up
43
- { :permitted_classes => [Time] }
44
- else
45
- [Time]
46
- end
38
+ if Gem::Version.new(RUBY_VERSION) >= Gem::Version.new("2.6.0")
39
+ # Use keyword params for Ruby 2.6 and up
40
+ YAML.safe_load(contents, :permitted_classes => [Time])
41
+ else
42
+ YAML.safe_load(contents, [Time])
43
+ end
47
44
  else
48
- method = :load
45
+ # Support for Ruby versions without YAML.safe_load
46
+ YAML.load(contents) # rubocop:disable Security/YAMLLoad
49
47
  end
50
- YAML.send(method, *arguments)
51
48
  end
52
49
  end
53
50
  end
@@ -278,14 +278,11 @@ module Appsignal
278
278
  "../../../resources/appsignal.yml.erb"
279
279
  )
280
280
  file_contents = File.read(filename)
281
- arguments = [file_contents]
282
- if ruby_2_6_or_up?
283
- arguments << { :trim_mode => "-" }
284
- else
285
- arguments << nil
286
- arguments << "-"
287
- end
288
- template = ERB.new(*arguments)
281
+ template = if ruby_2_6_or_up?
282
+ ERB.new(file_contents, :trim_mode => "-")
283
+ else
284
+ ERB.new(file_contents, nil, "-")
285
+ end
289
286
  config = template.result(OpenStruct.new(data).instance_eval { binding })
290
287
 
291
288
  FileUtils.mkdir_p(File.join(Dir.pwd, "config"))
@@ -32,8 +32,6 @@ module Appsignal
32
32
  :instrument_redis => true,
33
33
  :instrument_sequel => true,
34
34
  :skip_session_data => false,
35
- :enable_frontend_error_catching => false,
36
- :frontend_error_catching_path => "/appsignal_error_catcher",
37
35
  :enable_allocation_tracking => true,
38
36
  :enable_gc_instrumentation => false,
39
37
  :enable_host_metrics => true,
@@ -49,7 +47,6 @@ module Appsignal
49
47
  "APPSIGNAL_PUSH_API_KEY" => :push_api_key,
50
48
  "APPSIGNAL_APP_NAME" => :name,
51
49
  "APPSIGNAL_PUSH_API_ENDPOINT" => :endpoint,
52
- "APPSIGNAL_FRONTEND_ERROR_CATCHING_PATH" => :frontend_error_catching_path,
53
50
  "APPSIGNAL_DEBUG" => :debug,
54
51
  "APPSIGNAL_LOG" => :log,
55
52
  "APPSIGNAL_LOG_PATH" => :log_path,
@@ -57,7 +54,6 @@ module Appsignal
57
54
  "APPSIGNAL_INSTRUMENT_REDIS" => :instrument_redis,
58
55
  "APPSIGNAL_INSTRUMENT_SEQUEL" => :instrument_sequel,
59
56
  "APPSIGNAL_SKIP_SESSION_DATA" => :skip_session_data,
60
- "APPSIGNAL_ENABLE_FRONTEND_ERROR_CATCHING" => :enable_frontend_error_catching,
61
57
  "APPSIGNAL_IGNORE_ACTIONS" => :ignore_actions,
62
58
  "APPSIGNAL_IGNORE_ERRORS" => :ignore_errors,
63
59
  "APPSIGNAL_IGNORE_NAMESPACES" => :ignore_namespaces,
@@ -86,7 +82,6 @@ module Appsignal
86
82
  APPSIGNAL_APP_NAME
87
83
  APPSIGNAL_CA_FILE_PATH
88
84
  APPSIGNAL_DNS_SERVERS
89
- APPSIGNAL_FRONTEND_ERROR_CATCHING_PATH
90
85
  APPSIGNAL_HOSTNAME
91
86
  APPSIGNAL_HTTP_PROXY
92
87
  APPSIGNAL_LOG
@@ -102,7 +97,6 @@ module Appsignal
102
97
  APPSIGNAL_ACTIVE
103
98
  APPSIGNAL_DEBUG
104
99
  APPSIGNAL_ENABLE_ALLOCATION_TRACKING
105
- APPSIGNAL_ENABLE_FRONTEND_ERROR_CATCHING
106
100
  APPSIGNAL_ENABLE_GC_INSTRUMENTATION
107
101
  APPSIGNAL_ENABLE_HOST_METRICS
108
102
  APPSIGNAL_ENABLE_MINUTELY_PROBES
@@ -126,12 +120,6 @@ module Appsignal
126
120
  APPSIGNAL_REQUEST_HEADERS
127
121
  ].freeze
128
122
 
129
- # Mapping of old and deprecated AppSignal configuration keys
130
- DEPRECATED_CONFIG_KEY_MAPPING = {
131
- :api_key => :push_api_key,
132
- :ignore_exceptions => :ignore_errors
133
- }.freeze
134
-
135
123
  # @attribute [r] system_config
136
124
  # Config detected on the system level.
137
125
  # Used in diagnose report.
@@ -376,18 +364,6 @@ module Appsignal
376
364
  # Used by {#load_from_disk}. No compatibility for env variables or initial config currently.
377
365
  def maintain_backwards_compatibility(configuration)
378
366
  configuration.tap do |config|
379
- DEPRECATED_CONFIG_KEY_MAPPING.each do |old_key, new_key|
380
- old_config_value = config.delete(old_key)
381
- next unless old_config_value
382
- deprecation_message \
383
- "Old configuration key found. Please update the "\
384
- "'#{old_key}' to '#{new_key}'.",
385
- logger
386
-
387
- next if config[new_key] # Skip if new key is already in use
388
- config[new_key] = old_config_value
389
- end
390
-
391
367
  if config.include?(:working_dir_path)
392
368
  deprecation_message \
393
369
  "'working_dir_path' is deprecated, please use " \
@@ -20,20 +20,11 @@ module Appsignal
20
20
  @formatters ||= {}
21
21
  end
22
22
 
23
- def deprecated_formatter_classes
24
- @deprecated_formatter_classes ||= {}
25
- end
26
-
27
23
  def formatter_classes
28
24
  @formatter_classes ||= {}
29
25
  end
30
26
 
31
27
  def register(name, formatter = nil)
32
- unless formatter
33
- register_deprecated_formatter(name)
34
- return
35
- end
36
-
37
28
  if registered?(name, formatter)
38
29
  logger.warn(
39
30
  "Formatter for '#{name}' already registered, not registering "\
@@ -45,12 +36,6 @@ module Appsignal
45
36
  initialize_formatter name, formatter
46
37
  end
47
38
 
48
- def initialize_deprecated_formatters
49
- deprecated_formatter_classes.each do |name, formatter|
50
- register(name, formatter)
51
- end
52
- end
53
-
54
39
  def unregister(name, formatter = self)
55
40
  return unless formatter_classes[name] == formatter
56
41
 
@@ -86,16 +71,6 @@ module Appsignal
86
71
  logger.error("'#{ex.message}' when initializing #{name} event formatter")
87
72
  end
88
73
 
89
- def register_deprecated_formatter(name)
90
- deprecation_message \
91
- "Formatter for '#{name}' is using a deprecated registration " \
92
- "method. This event formatter will not be loaded. " \
93
- "Please update the formatter according to the documentation at: " \
94
- "https://docs.appsignal.com/ruby/instrumentation/event-formatters.html"
95
-
96
- EventFormatter.deprecated_formatter_classes[name] = self
97
- end
98
-
99
74
  def logger
100
75
  Appsignal.logger
101
76
  end
@@ -380,6 +380,38 @@ module Appsignal
380
380
  end
381
381
  alias :tag_job :tag_request
382
382
 
383
+ # Add breadcrumbs to the transaction.
384
+ #
385
+ # Breadcrumbs can be used to trace what path a user has taken
386
+ # before encounterin an error.
387
+ #
388
+ # Only the last 20 added breadcrumbs will be saved.
389
+ #
390
+ # @example
391
+ # Appsignal.add_breadcrumb("Navigation", "http://blablabla.com", "", { :response => 200 }, Time.now.utc)
392
+ # Appsignal.add_breadcrumb("Network", "[GET] http://blablabla.com", "", { :response => 500 })
393
+ # Appsignal.add_breadcrumb("UI", "closed modal(change_password)", "User closed modal without actions")
394
+ #
395
+ # @param category [String] category of breadcrumb
396
+ # e.g. "UI", "Network", "Navigation", "Console".
397
+ # @param action [String] name of breadcrumb
398
+ # e.g "The user clicked a button", "HTTP 500 from http://blablabla.com"
399
+ # @option message [String] optional message in string format
400
+ # @option metadata [Hash<String,String>] key/value metadata in <string, string> format
401
+ # @option time [Time] time of breadcrumb, should respond to `.to_i` defaults to `Time.now.utc`
402
+ # @return [void]
403
+ #
404
+ # @see Transaction#add_breadcrumb
405
+ # @see http://docs.appsignal.com/ruby/instrumentation/breadcrumbs.html
406
+ # Breadcrumb reference
407
+ # @since 2.12.0
408
+ def add_breadcrumb(category, action, message = "", metadata = {}, time = Time.now.utc)
409
+ return unless active?
410
+ transaction = Appsignal::Transaction.current
411
+ return false unless transaction
412
+ transaction.add_breadcrumb(category, action, message, metadata, time)
413
+ end
414
+
383
415
  # Instrument helper for AppSignal.
384
416
  #
385
417
  # For more help, read our custom instrumentation guide, listed under "See
@@ -69,29 +69,6 @@ module Appsignal
69
69
  text.size > 200 ? "#{text[0...197]}..." : text
70
70
  end
71
71
  end
72
-
73
- # Alias Probes constants that have moved to their own module in version
74
- # 2.11.0.
75
- def self.const_missing(name)
76
- case name
77
- when :SidekiqProbe
78
- callers = caller
79
- Appsignal::Utils::DeprecationMessage.message \
80
- "The constant Appsignal::Hooks::SidekiqProbe has been deprecated. " \
81
- "Please update the constant name to Appsignal::Probes::SidekiqProbe " \
82
- "in the following file to remove this message.\n#{callers.first}"
83
- Appsignal::Probes::SidekiqProbe
84
- when :PumaProbe
85
- callers = caller
86
- Appsignal::Utils::DeprecationMessage.message \
87
- "The constant Appsignal::Hooks::PumaProbe has been deprecated. " \
88
- "Please update the constant name to Appsignal::Probes::PumaProbe " \
89
- "in the following file to remove this message.\n#{callers.first}"
90
- Appsignal::Probes::PumaProbe
91
- else
92
- super
93
- end
94
- end
95
72
  end
96
73
  end
97
74
 
@@ -14,45 +14,14 @@ module Appsignal
14
14
  end
15
15
 
16
16
  def install
17
- patch_perform_action
17
+ require "appsignal/integrations/action_cable"
18
+ ActionCable::Channel::Base.send(:prepend, Appsignal::Integrations::ActionCableIntegration)
19
+
18
20
  install_callbacks
19
21
  end
20
22
 
21
23
  private
22
24
 
23
- def patch_perform_action
24
- ActionCable::Channel::Base.class_eval do
25
- alias_method :original_perform_action, :perform_action
26
-
27
- def perform_action(*args, &block)
28
- # The request is only the original websocket request
29
- env = connection.env
30
- request = ActionDispatch::Request.new(env)
31
- env[Appsignal::Hooks::ActionCableHook::REQUEST_ID] ||=
32
- request.request_id || SecureRandom.uuid
33
-
34
- transaction = Appsignal::Transaction.create(
35
- env[Appsignal::Hooks::ActionCableHook::REQUEST_ID],
36
- Appsignal::Transaction::ACTION_CABLE,
37
- request
38
- )
39
-
40
- begin
41
- original_perform_action(*args, &block)
42
- rescue Exception => exception # rubocop:disable Lint/RescueException
43
- transaction.set_error(exception)
44
- raise exception
45
- ensure
46
- transaction.params = args.first
47
- transaction.set_action_if_nil("#{self.class}##{args.first["action"]}")
48
- transaction.set_metadata("path", request.path)
49
- transaction.set_metadata("method", "websocket")
50
- Appsignal::Transaction.complete_current!
51
- end
52
- end
53
- end
54
- end
55
-
56
25
  def install_callbacks
57
26
  ActionCable::Channel::Base.set_callback :subscribe, :around, :prepend => true do |channel, inner|
58
27
  # The request is only the original websocket request