appsignal 3.7.0-java → 3.7.2-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.
data/ext/agent.rb CHANGED
@@ -6,7 +6,7 @@
6
6
  # Modifications to this file will be overwritten with the next agent release.
7
7
 
8
8
  APPSIGNAL_AGENT_CONFIG = {
9
- "version" => "0.35.2",
9
+ "version" => "0.35.5",
10
10
  "mirrors" => [
11
11
  "https://appsignal-agent-releases.global.ssl.fastly.net",
12
12
  "https://d135dj0rjqvssy.cloudfront.net"
@@ -14,131 +14,131 @@ APPSIGNAL_AGENT_CONFIG = {
14
14
  "triples" => {
15
15
  "x86_64-darwin" => {
16
16
  "static" => {
17
- "checksum" => "4a01803fae744971e2da08a325acb88a5f79bf44cbde03456652affb91fa0817",
17
+ "checksum" => "3985b53b2a2814d44737182890e6fbe31b4b88361025140477a598e0e41fd948",
18
18
  "filename" => "appsignal-x86_64-darwin-all-static.tar.gz"
19
19
  },
20
20
  "dynamic" => {
21
- "checksum" => "843f6bfd798b7ae829c4a169f249a5576f01eb102755e1851f2901d4ddfff1b0",
21
+ "checksum" => "d135e2daf5c041a4ce7a7ab720cfd977fbae8375a007995e33a96558d3635792",
22
22
  "filename" => "appsignal-x86_64-darwin-all-dynamic.tar.gz"
23
23
  }
24
24
  },
25
25
  "universal-darwin" => {
26
26
  "static" => {
27
- "checksum" => "4a01803fae744971e2da08a325acb88a5f79bf44cbde03456652affb91fa0817",
27
+ "checksum" => "3985b53b2a2814d44737182890e6fbe31b4b88361025140477a598e0e41fd948",
28
28
  "filename" => "appsignal-x86_64-darwin-all-static.tar.gz"
29
29
  },
30
30
  "dynamic" => {
31
- "checksum" => "843f6bfd798b7ae829c4a169f249a5576f01eb102755e1851f2901d4ddfff1b0",
31
+ "checksum" => "d135e2daf5c041a4ce7a7ab720cfd977fbae8375a007995e33a96558d3635792",
32
32
  "filename" => "appsignal-x86_64-darwin-all-dynamic.tar.gz"
33
33
  }
34
34
  },
35
35
  "aarch64-darwin" => {
36
36
  "static" => {
37
- "checksum" => "c80fa534a0f34d0056102ed5ec21cb558b714b17dc2a91f62fabdb992acc8a54",
37
+ "checksum" => "79d22436bfe32dab4661f2a4149c6ab34c71e810c5d808ee3e60cd9f8a1395e4",
38
38
  "filename" => "appsignal-aarch64-darwin-all-static.tar.gz"
39
39
  },
40
40
  "dynamic" => {
41
- "checksum" => "53139766b4a6459f6db2ef0e9175ab7828652594f32a885fe0d650bdd1748719",
41
+ "checksum" => "2c49c8f24a9dd8f9d55c28015b3e1096180807e7b13d4a9cd8ed30f58bc6612f",
42
42
  "filename" => "appsignal-aarch64-darwin-all-dynamic.tar.gz"
43
43
  }
44
44
  },
45
45
  "arm64-darwin" => {
46
46
  "static" => {
47
- "checksum" => "c80fa534a0f34d0056102ed5ec21cb558b714b17dc2a91f62fabdb992acc8a54",
47
+ "checksum" => "79d22436bfe32dab4661f2a4149c6ab34c71e810c5d808ee3e60cd9f8a1395e4",
48
48
  "filename" => "appsignal-aarch64-darwin-all-static.tar.gz"
49
49
  },
50
50
  "dynamic" => {
51
- "checksum" => "53139766b4a6459f6db2ef0e9175ab7828652594f32a885fe0d650bdd1748719",
51
+ "checksum" => "2c49c8f24a9dd8f9d55c28015b3e1096180807e7b13d4a9cd8ed30f58bc6612f",
52
52
  "filename" => "appsignal-aarch64-darwin-all-dynamic.tar.gz"
53
53
  }
54
54
  },
55
55
  "arm-darwin" => {
56
56
  "static" => {
57
- "checksum" => "c80fa534a0f34d0056102ed5ec21cb558b714b17dc2a91f62fabdb992acc8a54",
57
+ "checksum" => "79d22436bfe32dab4661f2a4149c6ab34c71e810c5d808ee3e60cd9f8a1395e4",
58
58
  "filename" => "appsignal-aarch64-darwin-all-static.tar.gz"
59
59
  },
60
60
  "dynamic" => {
61
- "checksum" => "53139766b4a6459f6db2ef0e9175ab7828652594f32a885fe0d650bdd1748719",
61
+ "checksum" => "2c49c8f24a9dd8f9d55c28015b3e1096180807e7b13d4a9cd8ed30f58bc6612f",
62
62
  "filename" => "appsignal-aarch64-darwin-all-dynamic.tar.gz"
63
63
  }
64
64
  },
65
65
  "aarch64-linux" => {
66
66
  "static" => {
67
- "checksum" => "71236975f40316d67c2b0e797814d52a49df8c5941375c0aed81c6870d82f299",
67
+ "checksum" => "4a54587bb61f59d0b60032b2e0c1d14d2e726e20af049353c2ff279d07dd3028",
68
68
  "filename" => "appsignal-aarch64-linux-all-static.tar.gz"
69
69
  },
70
70
  "dynamic" => {
71
- "checksum" => "b9dffb56bbf0f1fe5538e914c9a0124c10390ce88077351b1e47cb93efbce1e5",
71
+ "checksum" => "aa2d011c538ce547c87110e7c8e49a24597d60ea2d1418032fc3db06267efba2",
72
72
  "filename" => "appsignal-aarch64-linux-all-dynamic.tar.gz"
73
73
  }
74
74
  },
75
75
  "i686-linux" => {
76
76
  "static" => {
77
- "checksum" => "00ab0d029ede31225b2d134cdfab1e2c75e15e96229ef9e89ac14f51b8329988",
77
+ "checksum" => "01e2237029c3af23cc6f348fb63f65a92b8caf8f4731b78d014bb4001559aad5",
78
78
  "filename" => "appsignal-i686-linux-all-static.tar.gz"
79
79
  },
80
80
  "dynamic" => {
81
- "checksum" => "8a6aba576fc1c9ba419758e49d6d5fc9ffd636f983e160a7595871f09f382e9b",
81
+ "checksum" => "c1043ac92b000a406d9afb77b6ec1d3ab6cfffd63c218a720c11daa3edb7fd1f",
82
82
  "filename" => "appsignal-i686-linux-all-dynamic.tar.gz"
83
83
  }
84
84
  },
85
85
  "x86-linux" => {
86
86
  "static" => {
87
- "checksum" => "00ab0d029ede31225b2d134cdfab1e2c75e15e96229ef9e89ac14f51b8329988",
87
+ "checksum" => "01e2237029c3af23cc6f348fb63f65a92b8caf8f4731b78d014bb4001559aad5",
88
88
  "filename" => "appsignal-i686-linux-all-static.tar.gz"
89
89
  },
90
90
  "dynamic" => {
91
- "checksum" => "8a6aba576fc1c9ba419758e49d6d5fc9ffd636f983e160a7595871f09f382e9b",
91
+ "checksum" => "c1043ac92b000a406d9afb77b6ec1d3ab6cfffd63c218a720c11daa3edb7fd1f",
92
92
  "filename" => "appsignal-i686-linux-all-dynamic.tar.gz"
93
93
  }
94
94
  },
95
95
  "x86_64-linux" => {
96
96
  "static" => {
97
- "checksum" => "2e96245f692f47ee8fd12cca92b620baf79845ec920fb19b38612dd1cb051961",
97
+ "checksum" => "beae1db2c122eb579f1ccb450177b0c64d65569d774efc7a1ee72c42d3382d39",
98
98
  "filename" => "appsignal-x86_64-linux-all-static.tar.gz"
99
99
  },
100
100
  "dynamic" => {
101
- "checksum" => "c64e9903bddf0478ab9bbc316ce8ab46c0998173c922312fee527045e91554ad",
101
+ "checksum" => "67650f59d2ea9c99cde7dfe44da65a506522a3cdccabe697931d89ebaea96d18",
102
102
  "filename" => "appsignal-x86_64-linux-all-dynamic.tar.gz"
103
103
  }
104
104
  },
105
105
  "x86_64-linux-musl" => {
106
106
  "static" => {
107
- "checksum" => "a99ebcdf993cd740dc556de9fba6e7ce1c802704c290c4d8b842cb4dc971473a",
107
+ "checksum" => "521c4486d10cdafa1f72103cc439d6f0e4f549f1522c4473bf43dc487ec42436",
108
108
  "filename" => "appsignal-x86_64-linux-musl-all-static.tar.gz"
109
109
  },
110
110
  "dynamic" => {
111
- "checksum" => "bfb583eebc82c2ae22f904a423df5af3cbf899225ffd8a3f96d0158985aa6e7c",
111
+ "checksum" => "0a94fcee8eb1f8fd06fce3eacffbcf9f2a52f5cde040796e19a589176525db4b",
112
112
  "filename" => "appsignal-x86_64-linux-musl-all-dynamic.tar.gz"
113
113
  }
114
114
  },
115
115
  "aarch64-linux-musl" => {
116
116
  "static" => {
117
- "checksum" => "874542de2899dc7ef6d286f1cb719614877651c6cafc9f5ae73d37d1aa0e61da",
117
+ "checksum" => "c29aab31f4ca59efb1483f48c0cb3c27d799347b81655a28f24c146b55aa7db6",
118
118
  "filename" => "appsignal-aarch64-linux-musl-all-static.tar.gz"
119
119
  },
120
120
  "dynamic" => {
121
- "checksum" => "02f895487486732bce4cbbed251275a3fc4830a4e890c592f2e95559a5ca11d5",
121
+ "checksum" => "4b77ea0c1f50ada6e5f6ed693002e56db1e34e0e9d5fdb4ac80fc52fd51099b8",
122
122
  "filename" => "appsignal-aarch64-linux-musl-all-dynamic.tar.gz"
123
123
  }
124
124
  },
125
125
  "x86_64-freebsd" => {
126
126
  "static" => {
127
- "checksum" => "f30c529ed4fffe4f0668bcb59881061b22050813d9d10acf5a4bf03f4547a51b",
127
+ "checksum" => "a3598e9df1b6b5970aabbbccbe4e77c2372d2320cd87bfa20f32fca53b8505e4",
128
128
  "filename" => "appsignal-x86_64-freebsd-all-static.tar.gz"
129
129
  },
130
130
  "dynamic" => {
131
- "checksum" => "da6f4e31097ab2315b5bbffa8752284e40b535f4900057dc273a7bc7a23ac1ac",
131
+ "checksum" => "4cbfd5e16776c8ea4308ee7f3a096c5cc137f2506f8a05d9c8504e3483fcd8ac",
132
132
  "filename" => "appsignal-x86_64-freebsd-all-dynamic.tar.gz"
133
133
  }
134
134
  },
135
135
  "amd64-freebsd" => {
136
136
  "static" => {
137
- "checksum" => "f30c529ed4fffe4f0668bcb59881061b22050813d9d10acf5a4bf03f4547a51b",
137
+ "checksum" => "a3598e9df1b6b5970aabbbccbe4e77c2372d2320cd87bfa20f32fca53b8505e4",
138
138
  "filename" => "appsignal-x86_64-freebsd-all-static.tar.gz"
139
139
  },
140
140
  "dynamic" => {
141
- "checksum" => "da6f4e31097ab2315b5bbffa8752284e40b535f4900057dc273a7bc7a23ac1ac",
141
+ "checksum" => "4cbfd5e16776c8ea4308ee7f3a096c5cc137f2506f8a05d9c8504e3483fcd8ac",
142
142
  "filename" => "appsignal-x86_64-freebsd-all-dynamic.tar.gz"
143
143
  }
144
144
  }
data/ext/base.rb CHANGED
@@ -190,6 +190,9 @@ def store_download_version_on_report
190
190
  end
191
191
 
192
192
  def http_proxy
193
+ proxy = try_http_proxy_value(ENV.fetch("APPSIGNAL_HTTP_PROXY", nil))
194
+ return [proxy, nil] if proxy
195
+
193
196
  proxy, error =
194
197
  begin
195
198
  [try_http_proxy_value(Gem.configuration[:http_proxy]), nil]
@@ -8,7 +8,7 @@ require "tmpdir"
8
8
 
9
9
  module Appsignal
10
10
  class Config
11
- include Appsignal::Utils::DeprecationMessage
11
+ include Appsignal::Utils::StdoutAndLoggerMessage
12
12
 
13
13
  DEFAULT_CONFIG = {
14
14
  :activejob_report_errors => "all",
@@ -320,20 +320,29 @@ module Appsignal
320
320
  end
321
321
 
322
322
  def log_file_path
323
+ return @log_file_path if defined? @log_file_path
324
+
323
325
  path = config_hash[:log_path] || (root_path && File.join(root_path, "log"))
324
- return File.join(File.realpath(path), "appsignal.log") if path && File.writable?(path)
326
+ if path && File.writable?(path)
327
+ @log_file_path = File.join(File.realpath(path), "appsignal.log")
328
+ return @log_file_path
329
+ end
325
330
 
326
331
  system_tmp_dir = self.class.system_tmp_dir
327
332
  if File.writable? system_tmp_dir
328
333
  $stdout.puts "appsignal: Unable to log to '#{path}'. Logging to " \
329
- "'#{system_tmp_dir}' instead. Please check the " \
330
- "permissions for the application's (log) directory."
331
- File.join(system_tmp_dir, "appsignal.log")
334
+ "'#{system_tmp_dir}' instead. " \
335
+ "Please check the permissions for the application's (log) " \
336
+ "directory."
337
+ @log_file_path = File.join(system_tmp_dir, "appsignal.log")
332
338
  else
333
339
  $stdout.puts "appsignal: Unable to log to '#{path}' or the " \
334
340
  "'#{system_tmp_dir}' fallback. Please check the permissions " \
335
341
  "for the application's (log) directory."
342
+ @log_file_path = nil
336
343
  end
344
+
345
+ @log_file_path
337
346
  end
338
347
 
339
348
  def valid?
@@ -476,7 +485,7 @@ module Appsignal
476
485
  def maintain_backwards_compatibility
477
486
  return unless config_hash.key?(:working_dir_path)
478
487
 
479
- deprecation_message \
488
+ stdout_and_logger_warning \
480
489
  "The `working_dir_path` option is deprecated, please use " \
481
490
  "`working_directory_path` instead and specify the " \
482
491
  "full path to the working directory",
@@ -542,7 +551,7 @@ module Appsignal
542
551
  config[:send_session_data] = true # Set default value
543
552
  end
544
553
  else
545
- deprecation_message "The `skip_session_data` config option is " \
554
+ stdout_and_logger_warning "The `skip_session_data` config option is " \
546
555
  "deprecated. Please use `send_session_data` instead.",
547
556
  logger
548
557
  # Not configured by user
@@ -14,8 +14,6 @@ module Appsignal
14
14
  # @api private
15
15
  class EventFormatter
16
16
  class << self
17
- include Appsignal::Utils::DeprecationMessage
18
-
19
17
  def formatters
20
18
  @formatters ||= {}
21
19
  end
@@ -3,7 +3,7 @@
3
3
  module Appsignal
4
4
  module Helpers
5
5
  module Instrumentation # rubocop:disable Metrics/ModuleLength
6
- include Appsignal::Utils::DeprecationMessage
6
+ include Appsignal::Utils::StdoutAndLoggerMessage
7
7
 
8
8
  # Creates an AppSignal transaction for the given block.
9
9
  #
@@ -207,7 +207,7 @@ module Appsignal
207
207
  )
208
208
  if tags
209
209
  call_location = caller(1..1).first
210
- deprecation_message \
210
+ stdout_and_logger_warning \
211
211
  "The tags argument for `Appsignal.send_error` is deprecated. " \
212
212
  "Please use the block method to set tags instead.\n\n" \
213
213
  " Appsignal.send_error(error) do |transaction|\n" \
@@ -217,7 +217,7 @@ module Appsignal
217
217
  end
218
218
  if namespace
219
219
  call_location = caller(1..1).first
220
- deprecation_message \
220
+ stdout_and_logger_warning \
221
221
  "The namespace argument for `Appsignal.send_error` is deprecated. " \
222
222
  "Please use the block method to set the namespace instead.\n\n" \
223
223
  " Appsignal.send_error(error) do |transaction|\n" \
@@ -300,7 +300,7 @@ module Appsignal
300
300
  def set_error(exception, tags = nil, namespace = nil)
301
301
  if tags
302
302
  call_location = caller(1..1).first
303
- deprecation_message \
303
+ stdout_and_logger_warning \
304
304
  "The tags argument for `Appsignal.set_error` is deprecated. " \
305
305
  "Please use the block method to set tags instead.\n\n" \
306
306
  " Appsignal.set_error(error) do |transaction|\n" \
@@ -310,7 +310,7 @@ module Appsignal
310
310
  end
311
311
  if namespace
312
312
  call_location = caller(1..1).first
313
- deprecation_message \
313
+ stdout_and_logger_warning \
314
314
  "The namespace argument for `Appsignal.set_error` is deprecated. " \
315
315
  "Please use the block method to set the namespace instead.\n\n" \
316
316
  " Appsignal.set_error(error) do |transaction|\n" \
@@ -15,7 +15,7 @@ module Appsignal
15
15
  end
16
16
 
17
17
  def set_host_gauge(_key, _value)
18
- Appsignal::Utils::DeprecationMessage.message \
18
+ Appsignal::Utils::StdoutAndLoggerMessage.warning \
19
19
  "The `set_host_gauge` method has been deprecated. " \
20
20
  "Calling this method has no effect. " \
21
21
  "Please remove method call in the following file to remove " \
@@ -23,7 +23,7 @@ module Appsignal
23
23
  end
24
24
 
25
25
  def set_process_gauge(_key, _value)
26
- Appsignal::Utils::DeprecationMessage.message \
26
+ Appsignal::Utils::StdoutAndLoggerMessage.warning \
27
27
  "The `set_process_gauge` method has been deprecated. " \
28
28
  "Calling this method has no effect. " \
29
29
  "Please remove method call in the following file to remove " \
@@ -16,7 +16,7 @@ module Appsignal
16
16
  end
17
17
 
18
18
  def install
19
- Appsignal::Minutely.probes.register :gvl, Appsignal::Probes::GvlProbe
19
+ Appsignal::Probes.register :gvl, Appsignal::Probes::GvlProbe
20
20
  ::GVLTools::GlobalTimer.enable if Appsignal.config[:enable_gvl_global_timer]
21
21
  ::GVLTools::WaitingThreads.enable if Appsignal.config[:enable_gvl_waiting_threads]
22
22
  end
@@ -11,7 +11,7 @@ module Appsignal
11
11
  end
12
12
 
13
13
  def install
14
- Appsignal::Minutely.probes.register :mri, Appsignal::Probes::MriProbe
14
+ Appsignal::Probes.register :mri, Appsignal::Probes::MriProbe
15
15
  end
16
16
  end
17
17
  end
@@ -11,7 +11,7 @@ module Appsignal
11
11
 
12
12
  def install
13
13
  require "appsignal/integrations/sidekiq"
14
- Appsignal::Minutely.probes.register :sidekiq, Appsignal::Probes::SidekiqProbe
14
+ Appsignal::Probes.register :sidekiq, Appsignal::Probes::SidekiqProbe
15
15
 
16
16
  ::Sidekiq.configure_server do |config|
17
17
  config.error_handlers <<
@@ -76,7 +76,7 @@ module Appsignal
76
76
  when :SidekiqPlugin
77
77
  require "appsignal/integrations/sidekiq"
78
78
  callers = caller
79
- Appsignal::Utils::DeprecationMessage.message \
79
+ Appsignal::Utils::StdoutAndLoggerMessage.warning \
80
80
  "The constant Appsignal::Hooks::SidekiqPlugin has been deprecated. " \
81
81
  "Please update the constant name to Appsignal::Integrations::SidekiqMiddleware " \
82
82
  "in the following file to remove this message.\n#{callers.first}"
@@ -14,7 +14,7 @@ module Appsignal
14
14
  end
15
15
 
16
16
  console do
17
- Appsignal::Minutely.stop
17
+ Appsignal::Probes.stop
18
18
  end
19
19
 
20
20
  def self.initialize_appsignal(app)
@@ -2,6 +2,274 @@
2
2
 
3
3
  module Appsignal
4
4
  module Probes
5
+ class ProbeCollection
6
+ def initialize
7
+ @probes = {}
8
+ end
9
+
10
+ # @return [Integer] Number of probes that are registered.
11
+ def count
12
+ probes.count
13
+ end
14
+
15
+ # Clears all probes from the list.
16
+ # @return [void]
17
+ def clear
18
+ probes.clear
19
+ end
20
+
21
+ # Fetch a probe using its name.
22
+ # @param key [Symbol/String] The name of the probe to fetch.
23
+ # @return [Object] Returns the registered probe.
24
+ def [](key)
25
+ probes[key]
26
+ end
27
+
28
+ # @deprecated Use {Appsignal::Probes.register} instead.
29
+ def register(name, probe)
30
+ Appsignal::Utils::StdoutAndLoggerMessage.warning(
31
+ "The method 'Appsignal::Probes.probes.register' is deprecated. " \
32
+ "Use 'Appsignal::Probes.register' instead."
33
+ )
34
+ Appsignal::Probes.register(name, probe)
35
+ end
36
+
37
+ # @api private
38
+ def internal_register(name, probe)
39
+ if probes.key?(name)
40
+ logger.debug "A probe with the name `#{name}` is already " \
41
+ "registered. Overwriting the entry with the new probe."
42
+ end
43
+ probes[name] = probe
44
+ end
45
+
46
+ # @api private
47
+ def unregister(name)
48
+ probes.delete(name)
49
+ end
50
+
51
+ # @api private
52
+ def each(&block)
53
+ probes.each(&block)
54
+ end
55
+
56
+ private
57
+
58
+ attr_reader :probes
59
+
60
+ def logger
61
+ Appsignal.internal_logger
62
+ end
63
+ end
64
+
65
+ class << self
66
+ # @api private
67
+ def mutex
68
+ @mutex ||= Thread::Mutex.new
69
+ end
70
+
71
+ # @see ProbeCollection
72
+ # @return [ProbeCollection] Returns list of probes.
73
+ def probes
74
+ @probes ||= ProbeCollection.new
75
+ end
76
+
77
+ # Register a new minutely probe.
78
+ #
79
+ # Supported probe types are:
80
+ #
81
+ # - Lambda - A lambda is an object that listens to a `call` method call.
82
+ # This `call` method is called every minute.
83
+ # - Class - A class object is an object that listens to a `new` and
84
+ # `call` method call. The `new` method is called when the minutely
85
+ # probe thread is started to initialize all probes. This allows probes
86
+ # to load dependencies once beforehand. Their `call` method is called
87
+ # every minute.
88
+ # - Class instance - A class instance object is an object that listens to
89
+ # a `call` method call. The `call` method is called every minute.
90
+ #
91
+ # @example Register a new probe
92
+ # Appsignal::Probes.register :my_probe, lambda {}
93
+ #
94
+ # @example Overwrite an existing registered probe
95
+ # Appsignal::Probes.register :my_probe, lambda {}
96
+ # Appsignal::Probes.register :my_probe, lambda { puts "hello" }
97
+ #
98
+ # @example Add a lambda as a probe
99
+ # Appsignal::Probes.register :my_probe, lambda { puts "hello" }
100
+ # # "hello" # printed every minute
101
+ #
102
+ # @example Add a probe instance
103
+ # class MyProbe
104
+ # def initialize
105
+ # puts "started"
106
+ # end
107
+ #
108
+ # def call
109
+ # puts "called"
110
+ # end
111
+ # end
112
+ #
113
+ # Appsignal::Probes.register :my_probe, MyProbe.new
114
+ # # "started" # printed immediately
115
+ # # "called" # printed every minute
116
+ #
117
+ # @example Add a probe class
118
+ # class MyProbe
119
+ # def initialize
120
+ # # Add things that only need to be done on start up for this probe
121
+ # require "some/library/dependency"
122
+ # @cache = {} # initialize a local cache variable
123
+ # puts "started"
124
+ # end
125
+ #
126
+ # def call
127
+ # puts "called"
128
+ # end
129
+ # end
130
+ #
131
+ # Appsignal::Probes.register :my_probe, MyProbe
132
+ # Appsignal::Probes.start # This is called for you
133
+ # # "started" # Printed on Appsignal::Probes.start
134
+ # # "called" # Repeated every minute
135
+ #
136
+ # @param name [Symbol/String] Name of the probe. Can be used with
137
+ # {ProbeCollection#[]}. This name will be used in errors in the log and
138
+ # allows overwriting of probes by registering new ones with the same
139
+ # name.
140
+ # @param probe [Object] Any object that listens to the `call` method will
141
+ # be used as a probe.
142
+ # @return [void]
143
+ def register(name, probe)
144
+ probes.internal_register(name, probe)
145
+
146
+ initialize_probe(name, probe) if started?
147
+ end
148
+
149
+ # Unregister a probe that's registered with {register}.
150
+ # Can also be used to unregister automatically registered probes by the
151
+ # gem.
152
+ #
153
+ # @example Unregister probes
154
+ # # First register a probe
155
+ # Appsignal::Probes.register :my_probe, lambda {}
156
+ #
157
+ # # Then unregister a probe if needed
158
+ # Appsignal::Probes.unregister :my_probe
159
+ #
160
+ # @param name [Symbol/String] Name of the probe used to {register} the
161
+ # probe.
162
+ # @return [void]
163
+ def unregister(name)
164
+ probes.unregister(name)
165
+
166
+ uninitialize_probe(name)
167
+ end
168
+
169
+ # @api private
170
+ def start
171
+ stop
172
+ @started = true
173
+ @thread = Thread.new do
174
+ # Advise multi-threaded app servers to ignore this thread
175
+ # for the purposes of fork safety warnings
176
+ if Thread.current.respond_to?(:thread_variable_set)
177
+ Thread.current.thread_variable_set(:fork_safe, true)
178
+ end
179
+
180
+ sleep initial_wait_time
181
+ initialize_probes
182
+ loop do
183
+ logger = Appsignal.internal_logger
184
+ mutex.synchronize do
185
+ logger.debug("Gathering minutely metrics with #{probe_instances.count} probes")
186
+ probe_instances.each do |name, probe|
187
+ logger.debug("Gathering minutely metrics with '#{name}' probe")
188
+ probe.call
189
+ rescue => ex
190
+ logger.error "Error in minutely probe '#{name}': #{ex}"
191
+ logger.debug ex.backtrace.join("\n")
192
+ end
193
+ end
194
+ sleep wait_time
195
+ end
196
+ end
197
+ end
198
+
199
+ # Returns if the probes thread has been started. If the value is false or
200
+ # nil, it has not been started yet.
201
+ #
202
+ # @return [Boolean, nil]
203
+ def started?
204
+ @started
205
+ end
206
+
207
+ # Stop the minutely probes mechanism. Stop the thread and clear all probe
208
+ # instances.
209
+ def stop
210
+ defined?(@thread) && @thread.kill
211
+ @started = false
212
+ probe_instances.clear
213
+ end
214
+
215
+ # @api private
216
+ def wait_time
217
+ 60 - Time.now.sec
218
+ end
219
+
220
+ private
221
+
222
+ def initial_wait_time
223
+ remaining_seconds = 60 - Time.now.sec
224
+ return remaining_seconds if remaining_seconds > 30
225
+
226
+ remaining_seconds + 60
227
+ end
228
+
229
+ def initialize_probes
230
+ probes.each do |name, probe|
231
+ initialize_probe(name, probe)
232
+ end
233
+ end
234
+
235
+ def initialize_probe(name, probe)
236
+ if probe.respond_to? :new
237
+ instance = probe.new
238
+ klass = probe
239
+ else
240
+ instance = probe
241
+ klass = instance.class
242
+ end
243
+ unless dependencies_present?(klass)
244
+ Appsignal.internal_logger.debug "Skipping '#{name}' probe, " \
245
+ "#{klass}.dependency_present? returned falsy"
246
+ return
247
+ end
248
+ mutex.synchronize do
249
+ probe_instances[name] = instance
250
+ end
251
+ rescue => error
252
+ logger = Appsignal.internal_logger
253
+ logger.error "Error while initializing minutely probe '#{name}': #{error}"
254
+ logger.debug error.backtrace.join("\n")
255
+ end
256
+
257
+ def uninitialize_probe(name)
258
+ mutex.synchronize do
259
+ probe_instances.delete(name)
260
+ end
261
+ end
262
+
263
+ def dependencies_present?(probe)
264
+ return true unless probe.respond_to? :dependencies_present?
265
+
266
+ probe.dependencies_present?
267
+ end
268
+
269
+ def probe_instances
270
+ @probe_instances ||= {}
271
+ end
272
+ end
5
273
  end
6
274
  end
7
275
 
@@ -0,0 +1,17 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Appsignal
4
+ module Utils
5
+ # @api private
6
+ module StdoutAndLoggerMessage
7
+ def self.warning(message, logger = Appsignal.internal_logger)
8
+ Kernel.warn "appsignal WARNING: #{message}"
9
+ logger.warn message
10
+ end
11
+
12
+ def stdout_and_logger_warning(message, logger = Appsignal.internal_logger)
13
+ Appsignal::Utils::StdoutAndLoggerMessage.warning(message, logger)
14
+ end
15
+ end
16
+ end
17
+ end
@@ -1,6 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require "appsignal/utils/deprecation_message"
3
+ require "appsignal/utils/stdout_and_logger_message"
4
4
  require "appsignal/utils/data"
5
5
  require "appsignal/utils/hash_sanitizer"
6
6
  require "appsignal/utils/integration_logger"
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Appsignal
4
- VERSION = "3.7.0"
4
+ VERSION = "3.7.2"
5
5
  end