newrelic_rpm 3.7.0.174.beta → 3.7.0.177
Sign up to get free protection for your applications and to get access to all the features.
- data.tar.gz.sig +0 -0
- data/CHANGELOG +27 -4
- data/bin/nrdebug +10 -4
- data/lib/new_relic/agent.rb +33 -11
- data/lib/new_relic/agent/agent.rb +83 -120
- data/lib/new_relic/agent/agent_logger.rb +28 -16
- data/lib/new_relic/agent/audit_logger.rb +3 -4
- data/lib/new_relic/agent/autostart.rb +20 -8
- data/lib/new_relic/agent/commands/agent_command_router.rb +26 -17
- data/lib/new_relic/agent/commands/thread_profiler_session.rb +2 -2
- data/lib/new_relic/agent/configuration/default_source.rb +146 -59
- data/lib/new_relic/agent/configuration/manager.rb +3 -3
- data/lib/new_relic/agent/cross_app_monitor.rb +15 -40
- data/lib/new_relic/agent/cross_app_tracing.rb +20 -12
- data/lib/new_relic/agent/database.rb +24 -0
- data/lib/new_relic/agent/error_collector.rb +6 -2
- data/lib/new_relic/agent/instrumentation/merb/controller.rb +3 -1
- data/lib/new_relic/agent/javascript_instrumentor.rb +187 -0
- data/lib/new_relic/agent/new_relic_service.rb +30 -22
- data/lib/new_relic/agent/obfuscator.rb +48 -0
- data/lib/new_relic/agent/request_sampler.rb +5 -13
- data/lib/new_relic/agent/shim_agent.rb +1 -0
- data/lib/new_relic/agent/sql_sampler.rb +15 -5
- data/lib/new_relic/agent/stats_engine/metric_stats.rb +9 -4
- data/lib/new_relic/agent/transaction.rb +0 -1
- data/lib/new_relic/agent/transaction_sampler.rb +28 -16
- data/lib/new_relic/agent/transaction_state.rb +9 -0
- data/lib/new_relic/agent/transaction_timings.rb +5 -1
- data/lib/new_relic/agent/worker_loop.rb +0 -10
- data/lib/new_relic/cli/deployments.rb +1 -1
- data/lib/new_relic/control/instance_methods.rb +1 -1
- data/lib/new_relic/helper.rb +3 -1
- data/lib/new_relic/rack/browser_monitoring.rb +1 -2
- data/lib/new_relic/transaction_sample.rb +11 -13
- data/lib/newrelic_rpm.rb +1 -0
- data/test/agent_helper.rb +20 -5
- data/test/environments/lib/environments/runner.rb +1 -0
- data/test/helpers/file_searching.rb +28 -0
- data/test/multiverse/lib/multiverse/suite.rb +36 -19
- data/test/multiverse/suites/agent_only/collector_exception_handling_test.rb +49 -0
- data/test/multiverse/suites/agent_only/http_response_code_test.rb +2 -2
- data/test/multiverse/suites/agent_only/rum_instrumentation_test.rb +4 -2
- data/test/multiverse/suites/agent_only/service_timeout_test.rb +1 -1
- data/test/multiverse/suites/agent_only/set_transaction_name_test.rb +7 -4
- data/test/multiverse/suites/agent_only/thread_profiling_test.rb +2 -1
- data/test/multiverse/suites/rails/error_tracing_test.rb +34 -4
- data/test/multiverse/suites/rails/ignore_test.rb +1 -1
- data/test/multiverse/suites/rails/request_statistics_test.rb +1 -3
- data/test/multiverse/suites/sequel/sequel_instrumentation_test.rb +10 -7
- data/test/multiverse/suites/sinatra/ignoring_test.rb +1 -1
- data/test/new_relic/agent/agent/start_worker_thread_test.rb +1 -1
- data/test/new_relic/agent/agent_logger_test.rb +108 -114
- data/test/new_relic/agent/agent_test.rb +139 -21
- data/test/new_relic/agent/audit_logger_test.rb +22 -20
- data/test/new_relic/agent/autostart_test.rb +3 -2
- data/test/new_relic/agent/commands/agent_command_router_test.rb +51 -32
- data/test/new_relic/agent/configuration/default_source_test.rb +8 -2
- data/test/new_relic/agent/configuration/manager_test.rb +5 -1
- data/test/new_relic/agent/configuration/orphan_configuration_test.rb +57 -0
- data/test/new_relic/agent/cross_app_monitor_test.rb +10 -26
- data/test/new_relic/agent/database_test.rb +32 -0
- data/test/new_relic/agent/error_collector_test.rb +33 -16
- data/test/new_relic/agent/instrumentation/active_record_instrumentation_test.rb +88 -71
- data/test/new_relic/agent/instrumentation/task_instrumentation_test.rb +2 -2
- data/test/new_relic/agent/javascript_instrumentor_test.rb +341 -0
- data/test/new_relic/agent/memcache_instrumentation_test.rb +91 -89
- data/test/new_relic/agent/method_tracer_test.rb +1 -1
- data/test/new_relic/agent/obfuscator_test.rb +77 -0
- data/test/new_relic/agent/pipe_channel_manager_test.rb +5 -5
- data/test/new_relic/agent/pipe_service_test.rb +1 -1
- data/test/new_relic/agent/request_sampler_test.rb +21 -11
- data/test/new_relic/agent/sql_sampler_test.rb +52 -8
- data/test/new_relic/agent/stats_engine/metric_stats_test.rb +6 -6
- data/test/new_relic/agent/stats_engine_test.rb +18 -2
- data/test/new_relic/agent/transaction_sampler_test.rb +98 -53
- data/test/new_relic/agent/transaction_state_test.rb +44 -0
- data/test/new_relic/agent/transaction_test.rb +1 -1
- data/test/new_relic/agent/transaction_timings_test.rb +15 -5
- data/test/new_relic/agent/worker_loop_test.rb +0 -9
- data/test/new_relic/agent_test.rb +9 -21
- data/test/new_relic/data_container_tests.rb +72 -0
- data/test/new_relic/fake_collector.rb +69 -20
- data/test/new_relic/http_client_test_cases.rb +17 -2
- data/test/new_relic/license_test.rb +6 -15
- data/test/new_relic/multiverse_helpers.rb +2 -3
- data/test/new_relic/rack/browser_monitoring_test.rb +15 -37
- data/test/new_relic/transaction_sample_test.rb +92 -62
- data/test/performance/suites/rum_autoinsertion.rb +0 -3
- data/test/rum/x_ua_meta_tag_spaces_around_equals.result.html +10 -0
- data/test/rum/x_ua_meta_tag_spaces_around_equals.source.html +10 -0
- data/test/test_helper.rb +9 -5
- metadata +29 -11
- metadata.gz.sig +0 -0
- data/lib/new_relic/agent/beacon_configuration.rb +0 -37
- data/lib/new_relic/agent/browser_monitoring.rb +0 -257
- data/test/new_relic/agent/beacon_configuration_test.rb +0 -44
- data/test/new_relic/agent/browser_monitoring_test.rb +0 -474
@@ -32,7 +32,7 @@ module NewRelic
|
|
32
32
|
@metric_id_cache = {}
|
33
33
|
@last_metric_harvest_time = Time.now
|
34
34
|
|
35
|
-
@audit_logger = ::NewRelic::Agent::AuditLogger.new
|
35
|
+
@audit_logger = ::NewRelic::Agent::AuditLogger.new
|
36
36
|
Agent.config.register_callback(:'audit_log.enabled') do |enabled|
|
37
37
|
@audit_logger.enabled = enabled
|
38
38
|
end
|
@@ -178,25 +178,35 @@ module NewRelic
|
|
178
178
|
def session(&block)
|
179
179
|
raise ArgumentError, "#{self.class}#shared_connection must be passed a block" unless block_given?
|
180
180
|
|
181
|
-
http = create_http_connection
|
182
|
-
|
183
181
|
# Immediately open a TCP connection to the server and leave it open for
|
184
182
|
# multiple requests.
|
185
183
|
begin
|
186
184
|
t0 = Time.now
|
187
|
-
|
188
|
-
|
189
|
-
@shared_tcp_connection = http
|
185
|
+
@in_session = true
|
186
|
+
establish_shared_connection
|
190
187
|
block.call
|
191
188
|
rescue Timeout::Error
|
192
189
|
elapsed = Time.now - t0
|
193
|
-
::NewRelic::Agent.logger.warn "Timed out opening connection to
|
190
|
+
::NewRelic::Agent.logger.warn "Timed out opening connection to collector after #{elapsed} seconds. If this problem persists, please see http://status.newrelic.com"
|
194
191
|
raise
|
195
192
|
ensure
|
193
|
+
@in_session = false
|
194
|
+
close_shared_connection
|
195
|
+
end
|
196
|
+
end
|
197
|
+
|
198
|
+
def establish_shared_connection
|
199
|
+
connection = create_http_connection
|
200
|
+
NewRelic::Agent.logger.debug("Opening shared TCP connection to #{connection.address}:#{connection.port}")
|
201
|
+
NewRelic::TimerLib.timeout(@request_timeout) { connection.start }
|
202
|
+
@shared_tcp_connection = connection
|
203
|
+
end
|
204
|
+
|
205
|
+
def close_shared_connection
|
206
|
+
if @shared_tcp_connection
|
207
|
+
::NewRelic::Agent.logger.debug("Closing shared TCP connection to #{@shared_tcp_connection.address}:#{@shared_tcp_connection.port}")
|
208
|
+
@shared_tcp_connection.finish if @shared_tcp_connection.started?
|
196
209
|
@shared_tcp_connection = nil
|
197
|
-
# Close the TCP socket
|
198
|
-
::NewRelic::Agent.logger.debug("Closing TCP connection to #{http.address}:#{http.port}")
|
199
|
-
http.finish if http.started?
|
200
210
|
end
|
201
211
|
end
|
202
212
|
|
@@ -204,7 +214,9 @@ module NewRelic
|
|
204
214
|
# We'll reuse the same handle for cases where we're using keep-alive, or
|
205
215
|
# otherwise create a new one.
|
206
216
|
def http_connection
|
207
|
-
@shared_tcp_connection ||
|
217
|
+
(@shared_tcp_connection ||
|
218
|
+
(@in_session && establish_shared_connection) ||
|
219
|
+
create_http_connection)
|
208
220
|
end
|
209
221
|
|
210
222
|
# Return the Net::HTTP with proxy configuration given the NewRelic::Control::Server object.
|
@@ -329,14 +341,9 @@ module NewRelic
|
|
329
341
|
response = nil
|
330
342
|
http = http_connection
|
331
343
|
http.read_timeout = nil
|
332
|
-
|
333
|
-
NewRelic::
|
334
|
-
|
335
|
-
response = http.request(request)
|
336
|
-
end
|
337
|
-
rescue Timeout::Error
|
338
|
-
::NewRelic::Agent.logger.warn "Timed out trying to post data to New Relic (timeout = #{@request_timeout} seconds)"
|
339
|
-
raise
|
344
|
+
NewRelic::TimerLib.timeout(@request_timeout) do
|
345
|
+
::NewRelic::Agent.logger.debug "Sending request to #{opts[:collector]}#{opts[:uri]}"
|
346
|
+
response = http.request(request)
|
340
347
|
end
|
341
348
|
case response
|
342
349
|
when Net::HTTPSuccess
|
@@ -346,7 +353,6 @@ module NewRelic
|
|
346
353
|
when Net::HTTPServiceUnavailable
|
347
354
|
raise ServerConnectionException, "Service unavailable (#{response.code}): #{response.message}"
|
348
355
|
when Net::HTTPGatewayTimeOut
|
349
|
-
::NewRelic::Agent.logger.warn("Timed out getting response: #{response.message}")
|
350
356
|
raise Timeout::Error, response.message
|
351
357
|
when Net::HTTPRequestEntityTooLarge
|
352
358
|
raise UnrecoverableServerException, '413 Request Entity Too Large'
|
@@ -356,8 +362,10 @@ module NewRelic
|
|
356
362
|
raise ServerConnectionException, "Unexpected response from server (#{response.code}): #{response.message}"
|
357
363
|
end
|
358
364
|
response
|
359
|
-
rescue SystemCallError, SocketError => e
|
360
|
-
# These include Errno connection errors
|
365
|
+
rescue Timeout::Error, EOFError, SystemCallError, SocketError => e
|
366
|
+
# These include Errno connection errors, and all signify that the
|
367
|
+
# connection may be in a bad state, so drop it and re-create if needed.
|
368
|
+
close_shared_connection
|
361
369
|
raise NewRelic::Agent::ServerConnectionException, "Recoverable error connecting to #{@collector}: #{e}"
|
362
370
|
end
|
363
371
|
|
@@ -0,0 +1,48 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
# This file is distributed under New Relic's license terms.
|
3
|
+
# See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
|
4
|
+
|
5
|
+
#require 'base64'
|
6
|
+
|
7
|
+
module NewRelic
|
8
|
+
module Agent
|
9
|
+
class Obfuscator
|
10
|
+
|
11
|
+
attr_reader :key_bytes
|
12
|
+
|
13
|
+
EMPTY_KEY_BYTES = [0]
|
14
|
+
|
15
|
+
# RUM uses a shortened key, so just trim it up front
|
16
|
+
def initialize(key, length=nil)
|
17
|
+
if key.nil? || key.empty?
|
18
|
+
@key_bytes = EMPTY_KEY_BYTES
|
19
|
+
else
|
20
|
+
@key_bytes = key.bytes.to_a
|
21
|
+
@key_bytes = @key_bytes.first(length) if length
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
def obfuscate(text)
|
26
|
+
[ encode(text) ].pack('m').chomp.gsub(/\n/, '')
|
27
|
+
end
|
28
|
+
|
29
|
+
def deobfuscate(text)
|
30
|
+
encode(text.unpack('m').first )
|
31
|
+
end
|
32
|
+
|
33
|
+
def encode(text)
|
34
|
+
return text unless key_bytes
|
35
|
+
|
36
|
+
encoded = ""
|
37
|
+
encoded.force_encoding('binary') if encoded.respond_to?( :force_encoding )
|
38
|
+
index = 0
|
39
|
+
text.each_byte do |byte|
|
40
|
+
encoded.concat((byte ^ key_bytes[index % key_bytes.length]))
|
41
|
+
index+=1
|
42
|
+
end
|
43
|
+
encoded
|
44
|
+
end
|
45
|
+
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
@@ -13,10 +13,7 @@ class NewRelic::Agent::RequestSampler
|
|
13
13
|
MonitorMixin
|
14
14
|
|
15
15
|
# The namespace and keys of config values
|
16
|
-
MAX_SAMPLES_KEY = :'analytics_events.max_samples_stored'
|
17
16
|
ENABLED_KEY = :'analytics_events.enabled'
|
18
|
-
ENABLED_TXN_KEY = :'analytics_events.transactions.enabled'
|
19
|
-
INCLUDE_CUSTOM_PARAMS_KEY = :'capture_attributes.transaction_events'
|
20
17
|
|
21
18
|
# The type field of the sample
|
22
19
|
SAMPLE_TYPE = 'Transaction'
|
@@ -31,7 +28,7 @@ class NewRelic::Agent::RequestSampler
|
|
31
28
|
super()
|
32
29
|
|
33
30
|
@enabled = false
|
34
|
-
@samples = ::NewRelic::Agent::SampledBuffer.new(NewRelic::Agent.config[
|
31
|
+
@samples = ::NewRelic::Agent::SampledBuffer.new(NewRelic::Agent.config[:'analytics_events.max_samples_stored'])
|
35
32
|
@notified_full = false
|
36
33
|
|
37
34
|
event_listener.subscribe( :transaction_finished, &method(:on_transaction_finished) )
|
@@ -67,7 +64,7 @@ class NewRelic::Agent::RequestSampler
|
|
67
64
|
|
68
65
|
# Clear any existing samples, reset the last sample time, and return the
|
69
66
|
# previous set of samples. (Synchronized)
|
70
|
-
def harvest
|
67
|
+
def harvest!
|
71
68
|
old_samples, sample_count, request_count = reset!
|
72
69
|
record_sampling_rate(request_count, sample_count) if @enabled
|
73
70
|
old_samples
|
@@ -99,7 +96,7 @@ class NewRelic::Agent::RequestSampler
|
|
99
96
|
end
|
100
97
|
|
101
98
|
def register_config_callbacks
|
102
|
-
NewRelic::Agent.config.register_callback(
|
99
|
+
NewRelic::Agent.config.register_callback(:'analytics_events.max_samples_stored') do |max_samples|
|
103
100
|
NewRelic::Agent.logger.debug "RequestSampler max_samples set to #{max_samples}"
|
104
101
|
self.synchronize { @samples.capacity = max_samples }
|
105
102
|
self.reset!
|
@@ -107,12 +104,7 @@ class NewRelic::Agent::RequestSampler
|
|
107
104
|
|
108
105
|
NewRelic::Agent.config.register_callback(ENABLED_KEY) do |enabled|
|
109
106
|
NewRelic::Agent.logger.info "%sabling the Request Sampler." % [ enabled ? 'En' : 'Dis' ]
|
110
|
-
@enabled = enabled
|
111
|
-
end
|
112
|
-
|
113
|
-
NewRelic::Agent.config.register_callback(ENABLED_TXN_KEY) do |enabled|
|
114
|
-
NewRelic::Agent.logger.info "%sabling the Request Sampler." % [ enabled ? 'En' : 'Dis' ]
|
115
|
-
@enabled = enabled && NewRelic::Agent.config[ENABLED_KEY]
|
107
|
+
@enabled = enabled
|
116
108
|
end
|
117
109
|
end
|
118
110
|
|
@@ -128,7 +120,7 @@ class NewRelic::Agent::RequestSampler
|
|
128
120
|
# The order in which these are merged is important. We want to ensure that
|
129
121
|
# custom parameters can't override required fields (e.g. type)
|
130
122
|
sample = {}
|
131
|
-
if ::NewRelic::Agent.config[
|
123
|
+
if ::NewRelic::Agent.config[:'capture_attributes.transaction_events']
|
132
124
|
sample.merge!(event_params(payload[:custom_params] || {}))
|
133
125
|
end
|
134
126
|
sample.merge!(payload[:overview_metrics] || {})
|
@@ -96,7 +96,6 @@ module NewRelic
|
|
96
96
|
sql_item, transaction_sql_data.path, transaction_sql_data.uri)
|
97
97
|
end
|
98
98
|
end
|
99
|
-
|
100
99
|
end
|
101
100
|
|
102
101
|
def notice_sql(sql, metric_name, config, duration, &explainer)
|
@@ -104,7 +103,7 @@ module NewRelic
|
|
104
103
|
if NewRelic::Agent.is_sql_recorded?
|
105
104
|
if duration > Agent.config[:'slow_sql.explain_threshold']
|
106
105
|
backtrace = caller.join("\n")
|
107
|
-
transaction_data.sql_data << SlowSql.new(
|
106
|
+
transaction_data.sql_data << SlowSql.new(Database.capture_query(sql),
|
108
107
|
metric_name, config,
|
109
108
|
duration, backtrace, &explainer)
|
110
109
|
end
|
@@ -113,12 +112,18 @@ module NewRelic
|
|
113
112
|
|
114
113
|
def merge!(sql_traces)
|
115
114
|
@samples_lock.synchronize do
|
116
|
-
|
117
|
-
|
115
|
+
sql_traces.each do |trace|
|
116
|
+
existing_trace = @sql_traces[trace.sql]
|
117
|
+
if existing_trace
|
118
|
+
existing_trace.aggregate_trace(trace)
|
119
|
+
else
|
120
|
+
@sql_traces[trace.sql] = trace
|
121
|
+
end
|
122
|
+
end
|
118
123
|
end
|
119
124
|
end
|
120
125
|
|
121
|
-
def harvest
|
126
|
+
def harvest!
|
122
127
|
return [] if !Agent.config[:'slow_sql.enabled']
|
123
128
|
result = []
|
124
129
|
@samples_lock.synchronize do
|
@@ -203,6 +208,7 @@ module NewRelic
|
|
203
208
|
attr_reader :sql
|
204
209
|
attr_reader :database_metric_name
|
205
210
|
attr_reader :params
|
211
|
+
attr_reader :slow_sql
|
206
212
|
|
207
213
|
def initialize(normalized_query, slow_sql, path, uri)
|
208
214
|
super()
|
@@ -230,6 +236,10 @@ module NewRelic
|
|
230
236
|
record_data_point(float(slow_sql.duration))
|
231
237
|
end
|
232
238
|
|
239
|
+
def aggregate_trace(trace)
|
240
|
+
aggregate(trace.slow_sql, trace.path, trace.url)
|
241
|
+
end
|
242
|
+
|
233
243
|
def prepare_to_send
|
234
244
|
params[:explain_plan] = @slow_sql.explain if need_to_explain?
|
235
245
|
@sql = @slow_sql.obfuscate if need_to_obfuscate?
|
@@ -116,7 +116,7 @@ module NewRelic
|
|
116
116
|
end
|
117
117
|
end
|
118
118
|
|
119
|
-
def
|
119
|
+
def reset!
|
120
120
|
with_stats_lock do
|
121
121
|
old = @stats_hash
|
122
122
|
@stats_hash = StatsHash.new
|
@@ -124,6 +124,11 @@ module NewRelic
|
|
124
124
|
end
|
125
125
|
end
|
126
126
|
|
127
|
+
# Renamed to reset!, here for backwards compatibility with 3rd-party
|
128
|
+
# gems (though this really isn't part of the public API).
|
129
|
+
# @deprecated
|
130
|
+
def reset_stats; reset!; end
|
131
|
+
|
127
132
|
# merge data from previous harvests into this stats engine
|
128
133
|
def merge!(other_stats_hash)
|
129
134
|
with_stats_lock do
|
@@ -131,9 +136,9 @@ module NewRelic
|
|
131
136
|
end
|
132
137
|
end
|
133
138
|
|
134
|
-
def harvest
|
139
|
+
def harvest!
|
135
140
|
now = Time.now
|
136
|
-
snapshot =
|
141
|
+
snapshot = reset!
|
137
142
|
snapshot = apply_rules_to_metric_data(@metric_rules, snapshot)
|
138
143
|
snapshot.harvested_at = now
|
139
144
|
snapshot
|
@@ -165,7 +170,7 @@ module NewRelic
|
|
165
170
|
|
166
171
|
# For use by test code only.
|
167
172
|
def clear_stats
|
168
|
-
|
173
|
+
reset!
|
169
174
|
NewRelic::Agent::BusyCalculator.reset
|
170
175
|
end
|
171
176
|
|
@@ -276,7 +276,6 @@ module NewRelic
|
|
276
276
|
|
277
277
|
# Do not call this. Invoke the class method instead.
|
278
278
|
def notice_error(e, options={}) # :nodoc:
|
279
|
-
params = custom_parameters
|
280
279
|
options[:referer] = referer if referer
|
281
280
|
options[:request_params] = filtered_params if filtered_params
|
282
281
|
options[:uri] = uri if uri
|
@@ -92,6 +92,14 @@ module NewRelic
|
|
92
92
|
builder.trace_exit(scope, time.to_f)
|
93
93
|
end
|
94
94
|
|
95
|
+
def custom_parameters_from_transaction(txn)
|
96
|
+
if Agent.config[:'capture_attributes.traces']
|
97
|
+
txn.custom_parameters
|
98
|
+
else
|
99
|
+
{}
|
100
|
+
end
|
101
|
+
end
|
102
|
+
|
95
103
|
# This is called when we are done with the transaction. We've
|
96
104
|
# unwound the stack to the top level. It also clears the
|
97
105
|
# transaction sample builder so that it won't continue to have
|
@@ -105,7 +113,7 @@ module NewRelic
|
|
105
113
|
|
106
114
|
return unless last_builder
|
107
115
|
|
108
|
-
last_builder.finish_trace(time.to_f, txn
|
116
|
+
last_builder.finish_trace(time.to_f, custom_parameters_from_transaction(txn))
|
109
117
|
clear_builder
|
110
118
|
return if last_builder.ignored?
|
111
119
|
|
@@ -156,9 +164,9 @@ module NewRelic
|
|
156
164
|
segment = builder.current_segment
|
157
165
|
if segment
|
158
166
|
if key != :sql
|
159
|
-
segment[key] = self.class.truncate_message(
|
160
|
-
message))
|
167
|
+
segment[key] = self.class.truncate_message(message)
|
161
168
|
else
|
169
|
+
# message is expected to have been pre-truncated by notice_sql
|
162
170
|
segment[key] = message
|
163
171
|
end
|
164
172
|
append_backtrace(segment, duration)
|
@@ -178,16 +186,6 @@ module NewRelic
|
|
178
186
|
end
|
179
187
|
end
|
180
188
|
|
181
|
-
# Allows the addition of multiple pieces of metadata to one
|
182
|
-
# segment - i.e. traced method calls multiple sql queries
|
183
|
-
def append_new_message(old_message, message)
|
184
|
-
if old_message
|
185
|
-
old_message + ";\n" + message
|
186
|
-
else
|
187
|
-
message
|
188
|
-
end
|
189
|
-
end
|
190
|
-
|
191
189
|
# Appends a backtrace to a segment if that segment took longer
|
192
190
|
# than the specified duration
|
193
191
|
def append_backtrace(segment, duration)
|
@@ -208,7 +206,7 @@ module NewRelic
|
|
208
206
|
end
|
209
207
|
|
210
208
|
def build_database_statement(sql, config, explainer)
|
211
|
-
statement = Database::Statement.new(
|
209
|
+
statement = Database::Statement.new(Database.capture_query(sql))
|
212
210
|
if config
|
213
211
|
statement.adapter = config[:adapter]
|
214
212
|
statement.config = config
|
@@ -235,13 +233,27 @@ module NewRelic
|
|
235
233
|
end
|
236
234
|
|
237
235
|
# Gather transaction traces that we'd like to transmit to the server.
|
238
|
-
def harvest
|
236
|
+
def harvest!
|
239
237
|
return [] unless enabled?
|
240
238
|
|
241
|
-
@samples_lock.synchronize do
|
239
|
+
samples = @samples_lock.synchronize do
|
242
240
|
@last_sample = nil
|
243
241
|
harvest_from_sample_buffers
|
244
242
|
end
|
243
|
+
prepare_samples(samples)
|
244
|
+
end
|
245
|
+
|
246
|
+
def prepare_samples(samples)
|
247
|
+
samples.select do |sample|
|
248
|
+
begin
|
249
|
+
sample.prepare_to_send!
|
250
|
+
rescue => e
|
251
|
+
NewRelic::Agent.logger.error("Failed to prepare transaction trace. Error: ", e)
|
252
|
+
false
|
253
|
+
else
|
254
|
+
true
|
255
|
+
end
|
256
|
+
end
|
245
257
|
end
|
246
258
|
|
247
259
|
def merge!(previous)
|
@@ -63,6 +63,15 @@ module NewRelic
|
|
63
63
|
# Request data
|
64
64
|
attr_accessor :request, :request_token, :request_guid, :request_ignore_enduser
|
65
65
|
|
66
|
+
def request_guid_to_include
|
67
|
+
return "" unless include_guid?
|
68
|
+
request_guid
|
69
|
+
end
|
70
|
+
|
71
|
+
def include_guid?
|
72
|
+
request_token && timings.app_time_in_seconds > transaction.apdex_t
|
73
|
+
end
|
74
|
+
|
66
75
|
# Current transaction stack and sample building
|
67
76
|
attr_accessor :transaction, :transaction_sample_builder
|
68
77
|
attr_writer :current_transaction_stack
|
@@ -15,7 +15,11 @@ module NewRelic
|
|
15
15
|
end
|
16
16
|
|
17
17
|
attr_reader :transaction_name,
|
18
|
-
|
18
|
+
:start_time_in_seconds, :queue_time_in_seconds
|
19
|
+
|
20
|
+
def transaction_name_or_unknown
|
21
|
+
transaction_name || ::NewRelic::Agent::UNKNOWN_METRIC
|
22
|
+
end
|
19
23
|
|
20
24
|
def start_time_as_time
|
21
25
|
Time.at(@start_time_in_seconds)
|
@@ -85,19 +85,9 @@ module NewRelic
|
|
85
85
|
else
|
86
86
|
begin
|
87
87
|
@task.call
|
88
|
-
rescue ServerError => e
|
89
|
-
::NewRelic::Agent.logger.debug "Server Error:", e
|
90
88
|
rescue NewRelic::Agent::ForceRestartException, NewRelic::Agent::ForceDisconnectException
|
91
89
|
# blow out the loop
|
92
90
|
raise
|
93
|
-
rescue RuntimeError => e
|
94
|
-
# This is probably a server error which has been logged in the server along
|
95
|
-
# with your account name.
|
96
|
-
::NewRelic::Agent.logger.error "Error running task in worker loop, likely a server error:", e
|
97
|
-
rescue Timeout::Error, NewRelic::Agent::ServerConnectionException
|
98
|
-
# Want to ignore these because they are handled already
|
99
|
-
rescue SystemExit, NoMemoryError, SignalException
|
100
|
-
raise
|
101
91
|
rescue => e
|
102
92
|
# Don't blow out the stack for anything that hasn't already propagated
|
103
93
|
::NewRelic::Agent.logger.error "Error running task in Agent Worker Loop:", e
|