appsignal 2.1.2 → 2.2.0.beta.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.rubocop.yml +14 -0
- data/.rubocop_todo.yml +16 -171
- data/.travis.yml +14 -1
- data/.yardopts +8 -0
- data/CHANGELOG.md +21 -3
- data/README.md +20 -2
- data/Rakefile +60 -62
- data/appsignal.gemspec +24 -23
- data/ext/agent.yml +11 -11
- data/ext/appsignal_extension.c +43 -12
- data/ext/extconf.rb +9 -9
- data/gemfiles/padrino.gemfile +1 -1
- data/lib/appsignal.rb +403 -26
- data/lib/appsignal/auth_check.rb +28 -1
- data/lib/appsignal/cli.rb +1 -0
- data/lib/appsignal/cli/demo.rb +40 -0
- data/lib/appsignal/cli/diagnose.rb +345 -89
- data/lib/appsignal/cli/helpers.rb +9 -4
- data/lib/appsignal/cli/install.rb +6 -6
- data/lib/appsignal/cli/notify_of_deploy.rb +58 -0
- data/lib/appsignal/config.rb +40 -38
- data/lib/appsignal/demo.rb +20 -0
- data/lib/appsignal/event_formatter.rb +4 -0
- data/lib/appsignal/event_formatter/action_view/render_formatter.rb +1 -0
- data/lib/appsignal/event_formatter/active_record/instantiation_formatter.rb +1 -0
- data/lib/appsignal/event_formatter/active_record/sql_formatter.rb +1 -0
- data/lib/appsignal/event_formatter/elastic_search/search_formatter.rb +1 -0
- data/lib/appsignal/event_formatter/faraday/request_formatter.rb +1 -0
- data/lib/appsignal/event_formatter/mongo_ruby_driver/query_formatter.rb +2 -1
- data/lib/appsignal/event_formatter/moped/query_formatter.rb +1 -0
- data/lib/appsignal/extension.rb +1 -0
- data/lib/appsignal/garbage_collection_profiler.rb +20 -19
- data/lib/appsignal/hooks.rb +1 -0
- data/lib/appsignal/hooks/active_support_notifications.rb +1 -0
- data/lib/appsignal/hooks/celluloid.rb +1 -0
- data/lib/appsignal/hooks/data_mapper.rb +1 -0
- data/lib/appsignal/hooks/delayed_job.rb +1 -0
- data/lib/appsignal/hooks/mongo_ruby_driver.rb +1 -0
- data/lib/appsignal/hooks/net_http.rb +1 -0
- data/lib/appsignal/hooks/passenger.rb +1 -0
- data/lib/appsignal/hooks/puma.rb +1 -0
- data/lib/appsignal/hooks/rake.rb +1 -0
- data/lib/appsignal/hooks/redis.rb +1 -0
- data/lib/appsignal/hooks/sequel.rb +1 -0
- data/lib/appsignal/hooks/shoryuken.rb +1 -0
- data/lib/appsignal/hooks/sidekiq.rb +1 -0
- data/lib/appsignal/hooks/unicorn.rb +1 -0
- data/lib/appsignal/hooks/webmachine.rb +1 -0
- data/lib/appsignal/integrations/capistrano/appsignal.cap +4 -4
- data/lib/appsignal/integrations/capistrano/capistrano_2_tasks.rb +2 -0
- data/lib/appsignal/integrations/data_mapper.rb +1 -1
- data/lib/appsignal/integrations/delayed_job_plugin.rb +1 -0
- data/lib/appsignal/integrations/grape.rb +3 -1
- data/lib/appsignal/integrations/mongo_ruby_driver.rb +1 -0
- data/lib/appsignal/integrations/padrino.rb +36 -21
- data/lib/appsignal/integrations/railtie.rb +2 -2
- data/lib/appsignal/integrations/resque.rb +1 -0
- data/lib/appsignal/integrations/resque_active_job.rb +1 -0
- data/lib/appsignal/integrations/webmachine.rb +27 -24
- data/lib/appsignal/js_exception_transaction.rb +8 -8
- data/lib/appsignal/marker.rb +41 -4
- data/lib/appsignal/minutely.rb +1 -0
- data/lib/appsignal/rack/generic_instrumentation.rb +3 -2
- data/lib/appsignal/rack/js_exception_catcher.rb +55 -15
- data/lib/appsignal/rack/rails_instrumentation.rb +2 -1
- data/lib/appsignal/rack/sinatra_instrumentation.rb +4 -2
- data/lib/appsignal/rack/streaming_listener.rb +4 -2
- data/lib/appsignal/system.rb +5 -31
- data/lib/appsignal/transaction.rb +71 -6
- data/lib/appsignal/transmitter.rb +24 -13
- data/lib/appsignal/utils.rb +18 -11
- data/lib/appsignal/utils/params_sanitizer.rb +2 -1
- data/lib/appsignal/utils/query_params_sanitizer.rb +1 -0
- data/lib/appsignal/version.rb +1 -1
- data/resources/appsignal.yml.erb +1 -1
- data/spec/lib/appsignal/auth_check_spec.rb +64 -22
- data/spec/lib/appsignal/cli/diagnose_spec.rb +539 -81
- data/spec/lib/appsignal/cli/helpers_spec.rb +74 -2
- data/spec/lib/appsignal/cli/install_spec.rb +3 -3
- data/spec/lib/appsignal/config_spec.rb +38 -72
- data/spec/lib/appsignal/demo_spec.rb +2 -2
- data/spec/lib/appsignal/event_formatter_spec.rb +2 -2
- data/spec/lib/appsignal/extension_spec.rb +4 -0
- data/spec/lib/appsignal/garbage_collection_profiler_spec.rb +18 -21
- data/spec/lib/appsignal/hooks/mongo_ruby_driver_spec.rb +1 -1
- data/spec/lib/appsignal/hooks/redis_spec.rb +34 -44
- data/spec/lib/appsignal/hooks/sidekiq_spec.rb +2 -2
- data/spec/lib/appsignal/integrations/grape_spec.rb +6 -6
- data/spec/lib/appsignal/integrations/padrino_spec.rb +241 -122
- data/spec/lib/appsignal/integrations/railtie_spec.rb +34 -16
- data/spec/lib/appsignal/integrations/resque_spec.rb +1 -1
- data/spec/lib/appsignal/integrations/sinatra_spec.rb +38 -10
- data/spec/lib/appsignal/integrations/webmachine_spec.rb +2 -2
- data/spec/lib/appsignal/rack/generic_instrumentation_spec.rb +7 -6
- data/spec/lib/appsignal/rack/js_exception_catcher_spec.rb +95 -58
- data/spec/lib/appsignal/rack/rails_instrumentation_spec.rb +9 -6
- data/spec/lib/appsignal/rack/sinatra_instrumentation_spec.rb +11 -10
- data/spec/lib/appsignal/rack/streaming_listener_spec.rb +20 -13
- data/spec/lib/appsignal/system_spec.rb +2 -32
- data/spec/lib/appsignal/transaction_spec.rb +48 -7
- data/spec/lib/appsignal/transmitter_spec.rb +52 -33
- data/spec/lib/appsignal/utils/params_sanitizer_spec.rb +3 -1
- data/spec/lib/appsignal/utils/query_params_sanitizer_spec.rb +3 -3
- data/spec/lib/appsignal/utils_spec.rb +49 -6
- data/spec/lib/appsignal_spec.rb +60 -5
- data/spec/spec_helper.rb +4 -3
- data/spec/support/helpers/api_request_helper.rb +1 -4
- data/spec/support/helpers/dependency_helper.rb +4 -0
- data/spec/support/helpers/system_helpers.rb +1 -17
- data/spec/support/helpers/time_helpers.rb +1 -1
- metadata +19 -8
- data/spec/lib/appsignal/system/container_spec.rb +0 -67
- data/spec/lib/appsignal/utils/gzip_spec.rb +0 -10
@@ -37,6 +37,9 @@ module Appsignal
|
|
37
37
|
def ask_for_input
|
38
38
|
value = stdin.gets
|
39
39
|
value ? value.chomp : ""
|
40
|
+
rescue Interrupt
|
41
|
+
puts "\nExiting..."
|
42
|
+
exit 1
|
40
43
|
end
|
41
44
|
|
42
45
|
def required_input(prompt)
|
@@ -47,13 +50,15 @@ module Appsignal
|
|
47
50
|
end
|
48
51
|
end
|
49
52
|
|
50
|
-
def yes_or_no(prompt)
|
53
|
+
def yes_or_no(prompt, options = {})
|
51
54
|
loop do
|
52
55
|
print prompt
|
53
|
-
|
54
|
-
|
56
|
+
input = ask_for_input.strip
|
57
|
+
input = options[:default] if input.empty? && options[:default]
|
58
|
+
case input
|
59
|
+
when "y", "Y", "yes"
|
55
60
|
return true
|
56
|
-
when "n"
|
61
|
+
when "n", "N", "no"
|
57
62
|
return false
|
58
63
|
end
|
59
64
|
end
|
@@ -85,7 +85,7 @@ module Appsignal
|
|
85
85
|
puts "Installing for Sinatra"
|
86
86
|
config[:name] = required_input(" Enter application name: ")
|
87
87
|
puts
|
88
|
-
configure(config,
|
88
|
+
configure(config, %w(development production staging), true)
|
89
89
|
|
90
90
|
puts "Finish Sinatra configuration"
|
91
91
|
puts " Sinatra requires some manual configuration."
|
@@ -94,7 +94,7 @@ module Appsignal
|
|
94
94
|
puts " require 'appsignal/integrations/sinatra'"
|
95
95
|
puts
|
96
96
|
puts " You can find more information in the documentation:"
|
97
|
-
puts " http://docs.appsignal.com/
|
97
|
+
puts " http://docs.appsignal.com/ruby/integrations/sinatra.html"
|
98
98
|
press_any_key
|
99
99
|
done_notice
|
100
100
|
end
|
@@ -103,7 +103,7 @@ module Appsignal
|
|
103
103
|
puts "Installing for Padrino"
|
104
104
|
config[:name] = required_input(" Enter application name: ")
|
105
105
|
puts
|
106
|
-
configure(config,
|
106
|
+
configure(config, %w(development production staging), true)
|
107
107
|
|
108
108
|
puts "Finish Padrino installation"
|
109
109
|
puts " Padrino requires some manual configuration."
|
@@ -112,7 +112,7 @@ module Appsignal
|
|
112
112
|
puts " require 'appsignal/integrations/padrino"
|
113
113
|
puts
|
114
114
|
puts " You can find more information in the documentation:"
|
115
|
-
puts " http://docs.appsignal.com/
|
115
|
+
puts " http://docs.appsignal.com/ruby/integrations/padrino.html"
|
116
116
|
press_any_key
|
117
117
|
done_notice
|
118
118
|
end
|
@@ -123,11 +123,11 @@ module Appsignal
|
|
123
123
|
config[:name] = required_input(" Enter application name: ")
|
124
124
|
puts
|
125
125
|
|
126
|
-
configure(config,
|
126
|
+
configure(config, %w(development production staging), true)
|
127
127
|
|
128
128
|
puts "Manual Grape configuration needed"
|
129
129
|
puts " See the installation instructions at:"
|
130
|
-
puts " http://docs.appsignal.com/
|
130
|
+
puts " http://docs.appsignal.com/ruby/integrations/grape.html"
|
131
131
|
press_any_key
|
132
132
|
done_notice
|
133
133
|
end
|
@@ -1,7 +1,65 @@
|
|
1
1
|
module Appsignal
|
2
2
|
class CLI
|
3
|
+
# Command line tool to send a "Deploy Marker" for an application to
|
4
|
+
# AppSignal.
|
5
|
+
#
|
6
|
+
# Deploy markers are used on AppSignal.com to indicate changes in an
|
7
|
+
# application, "Deploy markers" indicate a deploy of an application.
|
8
|
+
#
|
9
|
+
# Incidents for exceptions and performance issues will be closed and
|
10
|
+
# reopened if they occur again in the new deploy.
|
11
|
+
#
|
12
|
+
# @note The same logic is used in the Capistrano integration. A deploy
|
13
|
+
# marker is created on each deploy.
|
14
|
+
#
|
15
|
+
# ## Options
|
16
|
+
#
|
17
|
+
# - `--environment` required. The environment of the application being
|
18
|
+
# deployed.
|
19
|
+
# - `--user` required. User that triggered the deploy.
|
20
|
+
# - `--revision` required. Git commit SHA or other identifiable revision id.
|
21
|
+
# - `--name` If no "name" config can be found in a `config/appsignal.yml`
|
22
|
+
# file or based on the `APPSIGNAL_APP_NAME` environment variable, this
|
23
|
+
# option is required.
|
24
|
+
#
|
25
|
+
# ## Exit codes
|
26
|
+
#
|
27
|
+
# - Exits with status code `0` if the deploy marker is sent.
|
28
|
+
# - Exits with status code `1` if the configuration is not valid and active.
|
29
|
+
# - Exits with status code `1` if the required options aren't present.
|
30
|
+
#
|
31
|
+
# @example basic example
|
32
|
+
# appsignal notify_of_deploy \
|
33
|
+
# --user=tom \
|
34
|
+
# --environment=production \
|
35
|
+
# --revision=abc1234
|
36
|
+
#
|
37
|
+
# @example using a custom app name
|
38
|
+
# appsignal notify_of_deploy \
|
39
|
+
# --user=tom \
|
40
|
+
# --environment=production \
|
41
|
+
# --revision=abc1234 \
|
42
|
+
# --name="My app"
|
43
|
+
#
|
44
|
+
# @example help command
|
45
|
+
# appsignal notify_of_deploy --help
|
46
|
+
#
|
47
|
+
# @since 0.2.5
|
48
|
+
# @see Appsignal::Marker Appsignal::Marker
|
49
|
+
# @see http://docs.appsignal.com/ruby/command-line/notify_of_deploy.html
|
50
|
+
# AppSignal notify_of_deploy documentation
|
51
|
+
# @see http://docs.appsignal.com/appsignal/terminology.html#markers
|
52
|
+
# Terminology: Deploy marker
|
3
53
|
class NotifyOfDeploy
|
4
54
|
class << self
|
55
|
+
# @param options [Hash]
|
56
|
+
# @option options :environment [String] environment to load
|
57
|
+
# configuration for.
|
58
|
+
# @option options :name [String] custom name of the application.
|
59
|
+
# @option options :user [String] user who triggered the deploy.
|
60
|
+
# @option options :revision [String] the revision that has been
|
61
|
+
# deployed. E.g. a git commit SHA.
|
62
|
+
# @return [void]
|
5
63
|
def run(options)
|
6
64
|
config = config_for(options[:environment])
|
7
65
|
config[:name] = options[:name] if options[:name]
|
data/lib/appsignal/config.rb
CHANGED
@@ -22,11 +22,11 @@ module Appsignal
|
|
22
22
|
:frontend_error_catching_path => "/appsignal_error_catcher",
|
23
23
|
:enable_allocation_tracking => true,
|
24
24
|
:enable_gc_instrumentation => false,
|
25
|
-
:running_in_container => false,
|
26
25
|
:enable_host_metrics => true,
|
27
26
|
:enable_minutely_probes => false,
|
28
27
|
:hostname => ::Socket.gethostname,
|
29
|
-
:ca_file_path => File.expand_path(File.join("../../../resources/cacert.pem"), __FILE__)
|
28
|
+
:ca_file_path => File.expand_path(File.join("../../../resources/cacert.pem"), __FILE__),
|
29
|
+
:dns_servers => []
|
30
30
|
}.freeze
|
31
31
|
|
32
32
|
ENV_TO_KEY_MAPPING = {
|
@@ -55,7 +55,8 @@ module Appsignal
|
|
55
55
|
"APPSIGNAL_ENABLE_HOST_METRICS" => :enable_host_metrics,
|
56
56
|
"APPSIGNAL_ENABLE_MINUTELY_PROBES" => :enable_minutely_probes,
|
57
57
|
"APPSIGNAL_HOSTNAME" => :hostname,
|
58
|
-
"APPSIGNAL_CA_FILE_PATH" => :ca_file_path
|
58
|
+
"APPSIGNAL_CA_FILE_PATH" => :ca_file_path,
|
59
|
+
"APPSIGNAL_DNS_SERVERS" => :dns_servers
|
59
60
|
}.freeze
|
60
61
|
|
61
62
|
attr_reader :root_path, :env, :initial_config, :config_hash
|
@@ -115,33 +116,35 @@ module Appsignal
|
|
115
116
|
@valid && config_hash[:active]
|
116
117
|
end
|
117
118
|
|
118
|
-
def write_to_environment
|
119
|
-
ENV["
|
120
|
-
ENV["
|
121
|
-
ENV["
|
122
|
-
ENV["
|
123
|
-
ENV["
|
124
|
-
ENV["
|
125
|
-
ENV["
|
126
|
-
ENV["
|
127
|
-
ENV["
|
128
|
-
ENV["
|
129
|
-
ENV["
|
130
|
-
ENV["
|
131
|
-
ENV["
|
132
|
-
ENV["
|
133
|
-
ENV["
|
134
|
-
ENV["
|
135
|
-
ENV["
|
136
|
-
ENV["
|
137
|
-
ENV["
|
138
|
-
ENV["
|
139
|
-
ENV["
|
140
|
-
ENV["
|
141
|
-
ENV["
|
119
|
+
def write_to_environment # rubocop:disable Metrics/AbcSize
|
120
|
+
ENV["_APPSIGNAL_ACTIVE"] = active?.to_s
|
121
|
+
ENV["_APPSIGNAL_APP_PATH"] = root_path.to_s
|
122
|
+
ENV["_APPSIGNAL_AGENT_PATH"] = File.expand_path("../../../ext", __FILE__).to_s
|
123
|
+
ENV["_APPSIGNAL_ENVIRONMENT"] = env
|
124
|
+
ENV["_APPSIGNAL_AGENT_VERSION"] = Appsignal::Extension.agent_version
|
125
|
+
ENV["_APPSIGNAL_LANGUAGE_INTEGRATION_VERSION"] = "ruby-#{Appsignal::VERSION}"
|
126
|
+
ENV["_APPSIGNAL_DEBUG_LOGGING"] = config_hash[:debug].to_s
|
127
|
+
ENV["_APPSIGNAL_LOG"] = config_hash[:log]
|
128
|
+
ENV["_APPSIGNAL_LOG_FILE_PATH"] = log_file_path.to_s if log_file_path
|
129
|
+
ENV["_APPSIGNAL_PUSH_API_ENDPOINT"] = config_hash[:endpoint]
|
130
|
+
ENV["_APPSIGNAL_PUSH_API_KEY"] = config_hash[:push_api_key]
|
131
|
+
ENV["_APPSIGNAL_APP_NAME"] = config_hash[:name]
|
132
|
+
ENV["_APPSIGNAL_HTTP_PROXY"] = config_hash[:http_proxy]
|
133
|
+
ENV["_APPSIGNAL_IGNORE_ACTIONS"] = config_hash[:ignore_actions].join(",")
|
134
|
+
ENV["_APPSIGNAL_IGNORE_ERRORS"] = config_hash[:ignore_errors].join(",")
|
135
|
+
ENV["_APPSIGNAL_FILTER_PARAMETERS"] = config_hash[:filter_parameters].join(",")
|
136
|
+
ENV["_APPSIGNAL_SEND_PARAMS"] = config_hash[:send_params].to_s
|
137
|
+
ENV["_APPSIGNAL_RUNNING_IN_CONTAINER"] = config_hash[:running_in_container].to_s
|
138
|
+
ENV["_APPSIGNAL_WORKING_DIR_PATH"] = config_hash[:working_dir_path] if config_hash[:working_dir_path]
|
139
|
+
ENV["_APPSIGNAL_ENABLE_HOST_METRICS"] = config_hash[:enable_host_metrics].to_s
|
140
|
+
ENV["_APPSIGNAL_ENABLE_MINUTELY_PROBES"] = config_hash[:enable_minutely_probes].to_s
|
141
|
+
ENV["_APPSIGNAL_HOSTNAME"] = config_hash[:hostname].to_s
|
142
|
+
ENV["_APPSIGNAL_PROCESS_NAME"] = $PROGRAM_NAME
|
143
|
+
ENV["_APPSIGNAL_CA_FILE_PATH"] = config_hash[:ca_file_path].to_s
|
144
|
+
ENV["_APPSIGNAL_DNS_SERVERS"] = config_hash[:dns_servers].join(",")
|
142
145
|
end
|
143
146
|
|
144
|
-
|
147
|
+
private
|
145
148
|
|
146
149
|
def config_file
|
147
150
|
@config_file ||=
|
@@ -149,7 +152,6 @@ module Appsignal
|
|
149
152
|
end
|
150
153
|
|
151
154
|
def detect_from_system
|
152
|
-
config_hash[:running_in_container] = true if Appsignal::System.container?
|
153
155
|
config_hash[:log] = "stdout" if Appsignal::System.heroku?
|
154
156
|
|
155
157
|
# Make active by default if APPSIGNAL_PUSH_API_KEY is present
|
@@ -189,9 +191,9 @@ module Appsignal
|
|
189
191
|
APPSIGNAL_FRONTEND_ERROR_CATCHING_PATH APPSIGNAL_HTTP_PROXY
|
190
192
|
APPSIGNAL_LOG APPSIGNAL_LOG_PATH APPSIGNAL_WORKING_DIR_PATH
|
191
193
|
APPSIGNAL_HOSTNAME APPSIGNAL_CA_FILE_PATH).each do |var|
|
192
|
-
|
193
|
-
|
194
|
-
|
194
|
+
env_var = ENV[var]
|
195
|
+
next unless env_var
|
196
|
+
config[ENV_TO_KEY_MAPPING[var]] = env_var
|
195
197
|
end
|
196
198
|
|
197
199
|
# Configuration with boolean type
|
@@ -201,17 +203,17 @@ module Appsignal
|
|
201
203
|
APPSIGNAL_ENABLE_ALLOCATION_TRACKING APPSIGNAL_ENABLE_GC_INSTRUMENTATION
|
202
204
|
APPSIGNAL_RUNNING_IN_CONTAINER APPSIGNAL_ENABLE_HOST_METRICS
|
203
205
|
APPSIGNAL_SEND_PARAMS APPSIGNAL_ENABLE_MINUTELY_PROBES).each do |var|
|
204
|
-
|
205
|
-
|
206
|
-
|
206
|
+
env_var = ENV[var]
|
207
|
+
next unless env_var
|
208
|
+
config[ENV_TO_KEY_MAPPING[var]] = env_var == "true"
|
207
209
|
end
|
208
210
|
|
209
211
|
# Configuration with array of strings type
|
210
212
|
%w(APPSIGNAL_IGNORE_ERRORS APPSIGNAL_IGNORE_ACTIONS
|
211
213
|
APPSIGNAL_FILTER_PARAMETERS).each do |var|
|
212
|
-
|
213
|
-
|
214
|
-
|
214
|
+
env_var = ENV[var]
|
215
|
+
next unless env_var
|
216
|
+
config[ENV_TO_KEY_MAPPING[var]] = env_var.split(",")
|
215
217
|
end
|
216
218
|
|
217
219
|
merge(@config_hash, config)
|
data/lib/appsignal/demo.rb
CHANGED
@@ -1,10 +1,30 @@
|
|
1
1
|
require "rack/mock"
|
2
2
|
|
3
3
|
module Appsignal
|
4
|
+
# {Appsignal::Demo} is a way to send demonstration / test samples for a
|
5
|
+
# exception and a performance issue.
|
6
|
+
#
|
7
|
+
# @example Loading config automatically
|
8
|
+
# Appsignal::Demo.transmit
|
9
|
+
#
|
10
|
+
# @example With custom config
|
11
|
+
# # If another configuration should be used, set it beforehand.
|
12
|
+
# Appsignal.config = Appsignal::Config.new(Dir.pwd, "production")
|
13
|
+
# Appsignal::Demo.transmit
|
14
|
+
#
|
15
|
+
# @since 2.0.0
|
16
|
+
# @see Appsignal::CLI::Demo
|
17
|
+
# @api private
|
4
18
|
class Demo
|
19
|
+
# Error type used to create demonstration exception.
|
5
20
|
class TestError < StandardError; end
|
6
21
|
|
7
22
|
class << self
|
23
|
+
# Starts AppSignal and transmits the demonstration samples to AppSignal
|
24
|
+
# using the loaded configuration.
|
25
|
+
#
|
26
|
+
# @return [Boolean]
|
27
|
+
# - returns `false` if Appsignal is not active.
|
8
28
|
def transmit
|
9
29
|
Appsignal.start
|
10
30
|
Appsignal.start_logger
|
@@ -8,6 +8,8 @@ module Appsignal
|
|
8
8
|
# event, the same object will be called intermittently in a threaded environment.
|
9
9
|
# So only keep global configuration as state and pass the payload around as an
|
10
10
|
# argument if you need to use helper methods.
|
11
|
+
#
|
12
|
+
# @api private
|
11
13
|
class EventFormatter
|
12
14
|
class << self
|
13
15
|
def formatters
|
@@ -60,7 +62,9 @@ module Appsignal
|
|
60
62
|
end
|
61
63
|
end
|
62
64
|
|
65
|
+
# @api public
|
63
66
|
DEFAULT = 0
|
67
|
+
# @api public
|
64
68
|
SQL_BODY_FORMAT = 1
|
65
69
|
end
|
66
70
|
end
|
@@ -1,5 +1,6 @@
|
|
1
1
|
module Appsignal
|
2
2
|
class EventFormatter
|
3
|
+
# @api private
|
3
4
|
module MongoRubyDriver
|
4
5
|
class QueryFormatter
|
5
6
|
ALLOWED = {
|
@@ -44,7 +45,7 @@ module Appsignal
|
|
44
45
|
"multi" => :allow,
|
45
46
|
"upsert" => :allow
|
46
47
|
}
|
47
|
-
}
|
48
|
+
}.freeze
|
48
49
|
|
49
50
|
# Format command based on given strategy
|
50
51
|
def self.format(strategy, command)
|
data/lib/appsignal/extension.rb
CHANGED
@@ -1,41 +1,42 @@
|
|
1
1
|
module Appsignal
|
2
|
-
# Appsignal::GarbageCollectionProfiler wraps Ruby's GC::Profiler to be
|
3
|
-
# to track garbage collection time for multiple transactions, while
|
4
|
-
# constantly clearing GC::Profiler's total_time to make sure it doesn't
|
5
|
-
# memory by keeping garbage collection run samples in memory.
|
6
|
-
|
2
|
+
# {Appsignal::GarbageCollectionProfiler} wraps Ruby's `GC::Profiler` to be
|
3
|
+
# able to track garbage collection time for multiple transactions, while
|
4
|
+
# constantly clearing `GC::Profiler`'s total_time to make sure it doesn't
|
5
|
+
# leak memory by keeping garbage collection run samples in memory.
|
6
|
+
#
|
7
|
+
# @api private
|
7
8
|
class GarbageCollectionProfiler
|
9
|
+
def self.lock
|
10
|
+
@lock ||= Mutex.new
|
11
|
+
end
|
12
|
+
|
8
13
|
def initialize
|
9
14
|
@total_time = 0
|
10
15
|
end
|
11
16
|
|
12
|
-
# Whenever #total_time is called, the current GC::Profiler
|
13
|
-
# added to
|
14
|
-
# it from leaking memory. A class-level lock is used to make
|
15
|
-
# collection time is never counted more than once.
|
17
|
+
# Whenever {#total_time} is called, the current `GC::Profiler#total_time`
|
18
|
+
# gets added to `@total_time`, after which `GC::Profiler.clear` is called
|
19
|
+
# to prevent it from leaking memory. A class-level lock is used to make
|
20
|
+
# sure garbage collection time is never counted more than once.
|
16
21
|
#
|
17
|
-
# Whenever
|
18
|
-
# it's reset to make sure the result fits in a signed 32-bit
|
19
|
-
|
22
|
+
# Whenever `@total_time` gets above two billion milliseconds (about 23
|
23
|
+
# days), it's reset to make sure the result fits in a signed 32-bit
|
24
|
+
# integer.
|
25
|
+
#
|
26
|
+
# @return [Integer]
|
20
27
|
def total_time
|
21
28
|
lock.synchronize do
|
22
29
|
@total_time += (internal_profiler.total_time * 1000).round
|
23
30
|
internal_profiler.clear
|
24
31
|
end
|
25
32
|
|
26
|
-
if @total_time > 2_000_000_000
|
27
|
-
@total_time = 0
|
28
|
-
end
|
33
|
+
@total_time = 0 if @total_time > 2_000_000_000
|
29
34
|
|
30
35
|
@total_time
|
31
36
|
end
|
32
37
|
|
33
38
|
private
|
34
39
|
|
35
|
-
def self.lock
|
36
|
-
@lock ||= Mutex.new
|
37
|
-
end
|
38
|
-
|
39
40
|
def internal_profiler
|
40
41
|
GC::Profiler
|
41
42
|
end
|