newrelic_rpm 3.10.0.279 → 3.11.0.283

Sign up to get free protection for your applications and to get access to all the features.
Files changed (180) hide show
  1. checksums.yaml +7 -0
  2. data/CHANGELOG +61 -0
  3. data/lib/new_relic/agent.rb +14 -8
  4. data/lib/new_relic/agent/agent.rb +43 -28
  5. data/lib/new_relic/agent/agent_logger.rb +21 -20
  6. data/lib/new_relic/agent/configuration/default_source.rb +31 -1
  7. data/lib/new_relic/agent/database.rb +2 -1
  8. data/lib/new_relic/agent/datastores.rb +177 -0
  9. data/lib/new_relic/agent/datastores/metric_helper.rb +85 -0
  10. data/lib/new_relic/agent/datastores/mongo/metric_translator.rb +11 -20
  11. data/lib/new_relic/agent/deprecator.rb +18 -0
  12. data/lib/new_relic/agent/instrumentation/active_record.rb +20 -35
  13. data/lib/new_relic/agent/instrumentation/active_record_helper.rb +116 -57
  14. data/lib/new_relic/agent/instrumentation/active_record_subscriber.rb +11 -20
  15. data/lib/new_relic/agent/instrumentation/data_mapper.rb +104 -172
  16. data/lib/new_relic/agent/instrumentation/memcache.rb +104 -52
  17. data/lib/new_relic/agent/instrumentation/metric_frame.rb +9 -0
  18. data/lib/new_relic/agent/instrumentation/middleware_proxy.rb +15 -2
  19. data/lib/new_relic/agent/instrumentation/mongo.rb +5 -18
  20. data/lib/new_relic/agent/instrumentation/sequel_helper.rb +36 -0
  21. data/lib/new_relic/agent/new_relic_service.rb +4 -0
  22. data/lib/new_relic/agent/stats_engine/metric_stats.rb +2 -17
  23. data/lib/new_relic/agent/threading/backtrace_service.rb +28 -5
  24. data/lib/new_relic/agent/transaction.rb +63 -34
  25. data/lib/new_relic/agent/transaction_event_aggregator.rb +0 -4
  26. data/lib/new_relic/agent/transaction_sampler.rb +11 -5
  27. data/lib/new_relic/rack/error_collector.rb +0 -1
  28. data/lib/new_relic/version.rb +1 -1
  29. data/lib/sequel/extensions/newrelic_instrumentation.rb +28 -56
  30. data/lib/sequel/plugins/newrelic_instrumentation.rb +28 -45
  31. data/newrelic_rpm.gemspec +0 -7
  32. data/test/agent_helper.rb +35 -16
  33. data/test/environments/rails31/Gemfile +1 -0
  34. data/test/environments/rails32/Gemfile +1 -0
  35. data/test/helpers/mongo_metric_builder.rb +2 -3
  36. data/test/multiverse/lib/multiverse/output_collector.rb +24 -9
  37. data/test/multiverse/lib/multiverse/suite.rb +5 -0
  38. data/test/multiverse/suites/active_record/Envfile +6 -4
  39. data/test/multiverse/suites/active_record/active_record_test.rb +32 -73
  40. data/test/multiverse/suites/active_record/ar_method_aliasing.rb +0 -1
  41. data/test/multiverse/suites/activemerchant/activemerchant_test.rb +0 -3
  42. data/test/multiverse/suites/agent_only/agent_run_id_handling_test.rb +0 -1
  43. data/test/multiverse/suites/agent_only/audit_log_test.rb +0 -1
  44. data/test/multiverse/suites/agent_only/collector_exception_handling_test.rb +0 -2
  45. data/test/multiverse/suites/agent_only/cross_application_tracing_test.rb +0 -1
  46. data/test/multiverse/suites/agent_only/custom_analytics_events_test.rb +0 -2
  47. data/test/multiverse/suites/agent_only/custom_queue_time_test.rb +0 -1
  48. data/test/multiverse/suites/agent_only/encoding_handling_test.rb +0 -2
  49. data/test/multiverse/suites/agent_only/exclusive_time_test.rb +0 -2
  50. data/test/multiverse/suites/agent_only/harvest_timestamps_test.rb +0 -1
  51. data/test/multiverse/suites/agent_only/http_response_code_test.rb +0 -1
  52. data/test/multiverse/suites/agent_only/keepalive_test.rb +0 -1
  53. data/test/multiverse/suites/agent_only/key_transactions_test.rb +54 -9
  54. data/test/multiverse/suites/agent_only/labels_test.rb +0 -2
  55. data/test/multiverse/suites/agent_only/logging_test.rb +0 -1
  56. data/test/multiverse/suites/agent_only/marshaling_test.rb +0 -1
  57. data/test/multiverse/suites/agent_only/pipe_manager_test.rb +0 -2
  58. data/test/multiverse/suites/agent_only/rename_rule_test.rb +5 -7
  59. data/test/multiverse/suites/agent_only/rum_instrumentation_test.rb +0 -1
  60. data/test/multiverse/suites/agent_only/set_transaction_name_test.rb +0 -2
  61. data/test/multiverse/suites/agent_only/ssl_test.rb +0 -2
  62. data/test/multiverse/suites/agent_only/synthetics_test.rb +0 -1
  63. data/test/multiverse/suites/agent_only/testing_app.rb +21 -0
  64. data/test/multiverse/suites/agent_only/thread_profiling_test.rb +1 -2
  65. data/test/multiverse/suites/agent_only/transaction_ignoring_test.rb +0 -2
  66. data/test/multiverse/suites/agent_only/utilization_data_collection_test.rb +0 -1
  67. data/test/multiverse/suites/agent_only/xray_sessions_test.rb +69 -34
  68. data/test/multiverse/suites/capistrano/deployment_test.rb +0 -1
  69. data/test/multiverse/suites/capistrano2/deployment_test.rb +0 -1
  70. data/test/multiverse/suites/config_file_loading/config_file_loading_test.rb +0 -2
  71. data/test/multiverse/suites/curb/curb_test.rb +0 -2
  72. data/test/multiverse/suites/datamapper/Envfile +26 -3
  73. data/test/multiverse/suites/datamapper/config/newrelic.yml +1 -0
  74. data/test/multiverse/suites/datamapper/datamapper_test.rb +271 -37
  75. data/test/multiverse/suites/deferred_instrumentation/sinatra_test.rb +0 -1
  76. data/test/multiverse/suites/delayed_job/Envfile +31 -8
  77. data/test/multiverse/suites/delayed_job/delayed_job_sampler_test.rb +0 -3
  78. data/test/multiverse/suites/delayed_job/unsupported_backend_test.rb +0 -3
  79. data/test/multiverse/suites/excon/excon_test.rb +0 -2
  80. data/test/multiverse/suites/grape/grape_test.rb +0 -3
  81. data/test/multiverse/suites/grape/grape_versioning_test.rb +0 -3
  82. data/test/multiverse/suites/grape/unsupported_version_test.rb +0 -3
  83. data/test/multiverse/suites/high_security/high_security_test.rb +0 -1
  84. data/test/multiverse/suites/httpclient/httpclient_test.rb +0 -2
  85. data/test/multiverse/suites/json/json_test.rb +0 -1
  86. data/test/multiverse/suites/marshalling/marshalling_test.rb +0 -1
  87. data/test/multiverse/suites/memcached/Envfile +52 -0
  88. data/test/multiverse/suites/memcached/dalli_test.rb +89 -0
  89. data/test/multiverse/suites/memcached/memcache_client_test.rb +25 -0
  90. data/test/multiverse/suites/memcached/memcache_test_cases.rb +302 -0
  91. data/test/multiverse/suites/memcached/memcached_test.rb +159 -0
  92. data/test/multiverse/suites/mongo/helpers/mongo_operation_tests.rb +26 -17
  93. data/test/multiverse/suites/mongo/mongo_connection_test.rb +0 -1
  94. data/test/multiverse/suites/mongo/mongo_instrumentation_test.rb +0 -1
  95. data/test/multiverse/suites/mongo/mongo_unsupported_version_test.rb +0 -1
  96. data/test/multiverse/suites/net_http/net_http_test.rb +0 -2
  97. data/test/multiverse/suites/padrino/padrino_test.rb +0 -3
  98. data/test/multiverse/suites/rack/http_response_code_test.rb +0 -1
  99. data/test/multiverse/suites/rack/nested_non_rack_app_test.rb +1 -1
  100. data/test/multiverse/suites/rack/rack_auto_instrumentation_test.rb +12 -12
  101. data/test/multiverse/suites/rack/rack_cascade_test.rb +0 -1
  102. data/test/multiverse/suites/rack/rack_env_mutation_test.rb +0 -1
  103. data/test/multiverse/suites/rack/rack_parameter_filtering_test.rb +0 -1
  104. data/test/multiverse/suites/rack/rack_unsupported_version_test.rb +0 -2
  105. data/test/multiverse/suites/rack/url_map_test.rb +3 -2
  106. data/test/multiverse/suites/rails/Envfile +3 -0
  107. data/test/multiverse/suites/rails/activejob_test.rb +0 -1
  108. data/test/multiverse/suites/rails/app.rb +0 -1
  109. data/test/multiverse/suites/rails/parameter_capture_test.rb +13 -0
  110. data/test/multiverse/suites/rails/rails3_app/app_rails3_plus.rb +5 -0
  111. data/test/multiverse/suites/rails/transaction_ignoring_test.rb +0 -2
  112. data/test/multiverse/suites/resque/instrumentation_test.rb +0 -2
  113. data/test/multiverse/suites/resque/resque_marshalling_test.rb +0 -1
  114. data/test/multiverse/suites/sequel/sequel_extension_test.rb +135 -0
  115. data/test/multiverse/suites/sequel/sequel_helpers.rb +62 -0
  116. data/test/multiverse/suites/sequel/sequel_plugin_test.rb +230 -0
  117. data/test/multiverse/suites/sidekiq/sidekiq_instrumentation_test.rb +0 -2
  118. data/test/multiverse/suites/sinatra/ignoring_test.rb +0 -2
  119. data/test/multiverse/suites/sinatra/nested_middleware_test.rb +0 -2
  120. data/test/multiverse/suites/sinatra/sinatra_classic_test.rb +0 -1
  121. data/test/multiverse/suites/sinatra/sinatra_error_tracing_test.rb +0 -2
  122. data/test/multiverse/suites/sinatra/sinatra_metric_explosion_test.rb +14 -12
  123. data/test/multiverse/suites/sinatra/sinatra_modular_test.rb +0 -1
  124. data/test/multiverse/suites/sinatra/sinatra_routes_test.rb +0 -2
  125. data/test/multiverse/suites/sinatra/sinatra_test_cases.rb +0 -2
  126. data/test/multiverse/suites/typhoeus/typhoeus_test.rb +0 -2
  127. data/test/multiverse/suites/yajl/yajl_test.rb +0 -1
  128. data/test/new_relic/agent/agent/start_test.rb +2 -2
  129. data/test/new_relic/agent/agent_logger_test.rb +6 -3
  130. data/test/new_relic/agent/datastores/metric_helper_test.rb +61 -0
  131. data/test/new_relic/agent/datastores/mongo/metric_translator_test.rb +20 -21
  132. data/test/new_relic/agent/datastores_test.rb +195 -0
  133. data/test/new_relic/agent/deprecator_test.rb +52 -0
  134. data/test/new_relic/agent/instrumentation/action_view_subscriber_test.rb +20 -26
  135. data/test/new_relic/agent/instrumentation/active_record_helper_test.rb +58 -53
  136. data/test/new_relic/agent/instrumentation/active_record_subscriber_test.rb +7 -20
  137. data/test/new_relic/agent/instrumentation/middleware_proxy_test.rb +19 -0
  138. data/test/new_relic/agent/instrumentation/sequel_helper_test.rb +36 -0
  139. data/test/new_relic/agent/instrumentation/task_instrumentation_test.rb +1 -0
  140. data/test/new_relic/agent/method_tracer_test.rb +3 -4
  141. data/test/new_relic/agent/pipe_channel_manager_test.rb +1 -1
  142. data/test/new_relic/agent/threading/backtrace_service_test.rb +29 -4
  143. data/test/new_relic/agent/transaction_event_aggregator_test.rb +0 -4
  144. data/test/new_relic/agent/transaction_test.rb +100 -2
  145. data/test/new_relic/agent_test.rb +3 -3
  146. data/test/new_relic/http_client_test_cases.rb +0 -1
  147. data/test/new_relic/multiverse_helpers.rb +7 -0
  148. data/test/new_relic/transaction_ignoring_test_cases.rb +0 -2
  149. data/test/new_relic/transaction_sample_test.rb +11 -2
  150. data/test/performance/README.md +37 -17
  151. data/test/performance/lib/performance.rb +1 -0
  152. data/test/performance/lib/performance/baseline_compare_reporter.rb +11 -7
  153. data/test/performance/lib/performance/console_reporter.rb +29 -5
  154. data/test/performance/lib/performance/formatting_helpers.rb +22 -0
  155. data/test/performance/lib/performance/instrumentation/stackprof.rb +11 -1
  156. data/test/performance/lib/performance/result.rb +17 -6
  157. data/test/performance/lib/performance/runner.rb +7 -3
  158. data/test/performance/lib/performance/test_case.rb +89 -21
  159. data/test/performance/script/runner +13 -1
  160. data/test/performance/suites/active_record.rb +47 -0
  161. data/test/performance/suites/config.rb +4 -48
  162. data/test/performance/suites/marshalling.rb +20 -30
  163. data/test/performance/suites/queue_time.rb +1 -1
  164. data/test/performance/suites/rack_middleware.rb +1 -1
  165. data/test/performance/suites/rum_autoinsertion.rb +1 -1
  166. data/test/performance/suites/sql_obfuscation.rb +2 -2
  167. data/test/performance/suites/startup.rb +1 -1
  168. data/test/performance/suites/stats_hash.rb +7 -11
  169. data/test/performance/suites/thread_profiling.rb +20 -25
  170. data/test/performance/suites/trace_execution_scoped.rb +2 -2
  171. data/test/performance/suites/transaction_tracing.rb +4 -2
  172. data/test/test_helper.rb +5 -1
  173. metadata +53 -100
  174. data.tar.gz.sig +0 -0
  175. data/gem-public_cert.pem +0 -20
  176. data/lib/new_relic/agent/datastores/mongo/metric_generator.rb +0 -33
  177. data/test/multiverse/suites/sequel/sequel_instrumentation_test.rb +0 -289
  178. data/test/new_relic/agent/datastores/mongo/metric_generator_test.rb +0 -69
  179. data/test/new_relic/agent/memcache_instrumentation_test.rb +0 -155
  180. metadata.gz.sig +0 -2
@@ -186,14 +186,10 @@ class NewRelic::Agent::TransactionEventAggregator
186
186
 
187
187
  # Web Metrics
188
188
  map_metric('WebFrontend/QueueTime', :total_call_time => "queueDuration")
189
- map_metric('Memcache/allWeb', :total_call_time => "memcacheDuration")
190
-
191
189
  map_metric('External/allWeb', :total_call_time => "externalDuration")
192
190
  map_metric('External/allWeb', :call_count => "externalCallCount")
193
191
 
194
192
  # Background Metrics
195
- map_metric('Memcache/allOther', :total_call_time => "memcacheDuration")
196
-
197
193
  map_metric('External/allOther', :total_call_time => "externalDuration")
198
194
  map_metric('External/allOther', :call_count => "externalCallCount")
199
195
 
@@ -182,11 +182,16 @@ module NewRelic
182
182
  return unless builder
183
183
  segment = builder.current_segment
184
184
  if segment
185
- if key != :sql
186
- segment[key] = self.class.truncate_message(message)
185
+ if key == :sql
186
+ sql = segment[:sql]
187
+ if(sql && !sql.empty?)
188
+ sql = self.class.truncate_message(sql << "\n#{message}") if sql.length <= MAX_DATA_LENGTH
189
+ else
190
+ # message is expected to have been pre-truncated by notice_sql
191
+ segment[:sql] = message
192
+ end
187
193
  else
188
- # message is expected to have been pre-truncated by notice_sql
189
- segment[key] = message
194
+ segment[key] = self.class.truncate_message(message)
190
195
  end
191
196
  append_backtrace(segment, duration)
192
197
  end
@@ -199,7 +204,8 @@ module NewRelic
199
204
  # the UI
200
205
  def self.truncate_message(message)
201
206
  if message.length > (MAX_DATA_LENGTH - 4)
202
- message[0..MAX_DATA_LENGTH - 4] + '...'
207
+ message.slice!(MAX_DATA_LENGTH - 4..message.length)
208
+ message << "..."
203
209
  else
204
210
  message
205
211
  end
@@ -3,7 +3,6 @@
3
3
  # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
4
4
 
5
5
  require 'new_relic/rack/agent_middleware'
6
- require 'new_relic/agent/instrumentation/middleware_proxy'
7
6
 
8
7
  module NewRelic::Rack
9
8
  # This middleware is no longer used by the agent by default, but remains here
@@ -11,7 +11,7 @@ module NewRelic
11
11
  end
12
12
 
13
13
  MAJOR = 3
14
- MINOR = 10
14
+ MINOR = 11
15
15
  TINY = 0
16
16
 
17
17
  begin
@@ -5,7 +5,8 @@
5
5
 
6
6
  require 'sequel' unless defined?( Sequel )
7
7
  require 'newrelic_rpm' unless defined?( NewRelic )
8
- require 'new_relic/agent/instrumentation/active_record_helper'
8
+ require 'new_relic/agent/instrumentation/sequel_helper'
9
+ require 'new_relic/agent/datastores/metric_helper'
9
10
 
10
11
  module Sequel
11
12
 
@@ -30,75 +31,46 @@ module Sequel
30
31
  # `disable_activerecord_instrumentation` setting.
31
32
  #
32
33
  module NewRelicInstrumentation
33
- include NewRelic::Agent::MethodTracer,
34
- NewRelic::Agent::Instrumentation::ActiveRecordHelper
35
-
36
34
 
37
35
  # Instrument all queries that go through #execute_query.
38
36
  def log_yield(sql, args=nil) #THREAD_LOCAL_ACCESS
39
- state = NewRelic::Agent::TransactionState.tl_get
40
- return super unless state.is_execution_traced?
41
-
42
- t0 = Time.now
43
- rval = super
44
- t1 = Time.now
45
-
46
- begin
47
- duration = t1 - t0
48
- record_metrics(sql, args, duration)
49
- notice_sql(state, sql, args, t0, t1)
50
- rescue => err
51
- NewRelic::Agent.logger.debug "while recording metrics for Sequel", err
37
+ rval = nil
38
+ product = NewRelic::Agent::Instrumentation::SequelHelper.product_name_from_adapter(self.class.adapter_scheme)
39
+ metrics = NewRelic::Agent::Datastores::MetricHelper.metrics_from_sql(product, sql)
40
+ scoped_metric = metrics.first
41
+
42
+ NewRelic::Agent::MethodTracer.trace_execution_scoped(metrics) do
43
+ t0 = Time.now
44
+ begin
45
+ rval = super
46
+ rescue => err
47
+ NewRelic::Agent.logger.debug "while recording metrics for Sequel", err
48
+ ensure
49
+ notice_sql(sql, scoped_metric, args, t0, Time.now)
50
+ end
52
51
  end
53
52
 
54
53
  return rval
55
54
  end
56
55
 
57
- # Record metrics for the specified +sql+ and +args+ using the specified
58
- # +duration+.
59
- def record_metrics(sql, args, duration) #THREAD_LOCAL_ACCESS
60
- primary_metric = primary_metric_for(sql, args)
61
- engine = NewRelic::Agent.instance.stats_engine
62
-
63
- metrics = rollup_metrics_for(primary_metric)
64
- metrics << remote_service_metric(*self.opts.values_at(:adapter, :host)) if self.opts.key?(:adapter)
65
-
66
- engine.tl_record_scoped_and_unscoped_metrics(primary_metric, metrics, duration)
67
- end
68
-
69
56
  THREAD_SAFE_CONNECTION_POOL_CLASSES = [
70
- (defined?(::Sequel::ThreadedConnectionPool) && ::Sequel::ThreadedConnectionPool),
71
- ].compact.freeze
57
+ (defined?(::Sequel::ThreadedConnectionPool) && ::Sequel::ThreadedConnectionPool)
58
+ ].freeze
72
59
 
73
- # Record the given +sql+ within a new frame, using the given +start+ and
74
- # +finish+ times.
75
- def notice_sql(state, sql, args, start, finish)
76
- metric = primary_metric_for(sql, args)
77
- agent = NewRelic::Agent.instance
60
+ def notice_sql(sql, metric_name, args, start, finish)
61
+ state = NewRelic::Agent::TransactionState.tl_get
78
62
  duration = finish - start
79
- stack = state.traced_method_stack
80
63
 
81
- begin
82
- frame = stack.push_frame(state, :sequel, start)
83
- explainer = Proc.new do |*|
84
- if THREAD_SAFE_CONNECTION_POOL_CLASSES.include?(self.pool.class)
85
- self[ sql ].explain
86
- else
87
- NewRelic::Agent.logger.log_once(:info, :sequel_explain_skipped, "Not running SQL explains because Sequel is not in recognized multi-threaded mode")
88
- nil
89
- end
64
+ explainer = Proc.new do |*|
65
+ if THREAD_SAFE_CONNECTION_POOL_CLASSES.include?(self.pool.class)
66
+ self[ sql ].explain
67
+ else
68
+ NewRelic::Agent.logger.log_once(:info, :sequel_explain_skipped, "Not running SQL explains because Sequel is not in recognized multi-threaded mode")
69
+ nil
90
70
  end
91
- agent.transaction_sampler.notice_sql(sql, self.opts, duration, state, &explainer)
92
- agent.sql_sampler.notice_sql(sql, metric, self.opts, duration, state, &explainer)
93
- ensure
94
- stack.pop_frame(state, frame, metric, finish)
95
71
  end
96
- end
97
-
98
-
99
- # Derive a primary database metric for the specified +sql+.
100
- def primary_metric_for(sql, _)
101
- return metric_for_sql(NewRelic::Helper.correctly_encoded(sql))
72
+ NewRelic::Agent.instance.transaction_sampler.notice_sql(sql, self.opts, duration, state, &explainer)
73
+ NewRelic::Agent.instance.sql_sampler.notice_sql(sql, metric_name, self.opts, duration, state, &explainer)
102
74
  end
103
75
 
104
76
  end # module NewRelicInstrumentation
@@ -5,6 +5,8 @@
5
5
 
6
6
  require 'sequel' unless defined?( Sequel )
7
7
  require 'newrelic_rpm' unless defined?( NewRelic )
8
+ require 'new_relic/agent/instrumentation/sequel_helper'
9
+ require 'new_relic/agent/datastores/metric_helper'
8
10
 
9
11
  module Sequel
10
12
  module Plugins
@@ -13,68 +15,49 @@ module Sequel
13
15
  module NewrelicInstrumentation
14
16
 
15
17
  # Meta-programming for creating method tracers for the Sequel::Model plugin.
16
- module MethodTracer
17
-
18
- # Make a lambda for the method body of the traced method
19
- def make_tracer_method( opname, options )
20
- body = Proc.new do |*args, &block|
21
- classname = self.is_a?( Class ) ? self.name : self.class.name
22
- metric = "ActiveRecord/%s/%s" % [ classname, opname ]
23
- trace_execution_scoped( metric, options ) do
24
- super( *args, &block )
25
- end
26
- end
27
-
28
- return body
29
- end
30
-
18
+ module MethodWrapping
31
19
  # Install a method named +method_name+ that will trace execution
32
- # with a metric name derived from +metric+ (or +method_name+ if +metric+
33
- # isn't specified). The +options+ hash is passed as-is though to
34
- # NewRelic::Agent::MethodTracer#trace_execution_scoped; see the
35
- # docs for that method for valid settings.
36
- def add_method_tracer( method_name, metric=nil, options={} )
37
- # Shift options hash if metric is omitted
38
- if metric.is_a?( Hash )
39
- options = metric
40
- metric = nil
41
- end
20
+ # with a metric name derived from +operation_name+ (or +method_name+ if +operation_name+
21
+ # isn't specified).
22
+ def wrap_sequel_method(method_name, operation_name=method_name)
23
+ define_method(method_name) do |*args, &block|
24
+ klass = self.is_a?(Class) ? self : self.class
42
25
 
43
- metric ||= method_name.to_s
26
+ product = NewRelic::Agent::Instrumentation::SequelHelper.product_name_from_adapter(db.adapter_scheme)
27
+ metrics = ::NewRelic::Agent::Datastores::MetricHelper.metrics_for(product, operation_name, klass.name)
44
28
 
45
- body = make_tracer_method( metric, options )
46
- define_method( method_name, &body )
29
+ NewRelic::Agent::MethodTracer.trace_execution_scoped(metrics) do
30
+ NewRelic::Agent.disable_all_tracing { super(*args, &block) }
31
+ end
32
+ end
47
33
  end
48
34
 
49
35
  end # module MethodTracer
50
36
 
51
-
52
37
  # Methods to be added to Sequel::Model instances.
53
38
  module InstanceMethods
54
- include NewRelic::Agent::MethodTracer
55
- extend Sequel::Plugins::NewrelicInstrumentation::MethodTracer
39
+ extend Sequel::Plugins::NewrelicInstrumentation::MethodWrapping
56
40
 
57
- add_method_tracer :delete
58
- add_method_tracer :destroy
59
- add_method_tracer :update
60
- add_method_tracer :update_all
61
- add_method_tracer :update_except
62
- add_method_tracer :update_fields
63
- add_method_tracer :update_only
64
- add_method_tracer :save
41
+ wrap_sequel_method :delete
42
+ wrap_sequel_method :destroy
43
+ wrap_sequel_method :update
44
+ wrap_sequel_method :update_all
45
+ wrap_sequel_method :update_except
46
+ wrap_sequel_method :update_fields
47
+ wrap_sequel_method :update_only
48
+ wrap_sequel_method :save
65
49
 
66
50
  end # module InstanceMethods
67
51
 
68
52
 
69
53
  # Methods to be added to Sequel::Model classes.
70
54
  module ClassMethods
71
- include NewRelic::Agent::MethodTracer
72
- extend Sequel::Plugins::NewrelicInstrumentation::MethodTracer
55
+ extend Sequel::Plugins::NewrelicInstrumentation::MethodWrapping
73
56
 
74
- add_method_tracer :[], :get
75
- add_method_tracer :all
76
- add_method_tracer :first
77
- add_method_tracer :create
57
+ wrap_sequel_method :[], "get"
58
+ wrap_sequel_method :all
59
+ wrap_sequel_method :first
60
+ wrap_sequel_method :create
78
61
  end # module ClassMethods
79
62
 
80
63
  end # module NewRelicInstrumentation
data/newrelic_rpm.gemspec CHANGED
@@ -70,11 +70,4 @@ EOS
70
70
  s.add_development_dependency 'rubysl'
71
71
  s.add_development_dependency 'racc'
72
72
  end
73
-
74
- # Only sign with our private key if you can find it
75
- signing_key_path = File.expand_path('~/.ssh/newrelic_rpm-private_key.pem')
76
- if File.exists?(signing_key_path)
77
- s.signing_key = signing_key_path
78
- s.cert_chain = ['gem-public_cert.pem']
79
- end
80
73
  end
data/test/agent_helper.rb CHANGED
@@ -156,9 +156,9 @@ def assert_metrics_recorded(expected)
156
156
  expected = _normalize_metric_expectations(expected)
157
157
  expected.each do |specish, expected_attrs|
158
158
  expected_spec = metric_spec_from_specish(specish)
159
- actual_stats = NewRelic::Agent.instance.stats_engine.lookup_stats(*Array(specish))
159
+ actual_stats = NewRelic::Agent.instance.stats_engine.to_h[expected_spec]
160
160
  if !actual_stats
161
- all_specs = NewRelic::Agent.instance.stats_engine.metric_specs.sort
161
+ all_specs = NewRelic::Agent.instance.stats_engine.to_h.keys.sort
162
162
  matches = all_specs.select { |spec| spec.name == expected_spec.name }
163
163
  matches.map! { |m| " #{m.inspect}" }
164
164
 
@@ -187,7 +187,7 @@ def assert_metrics_recorded_exclusive(expected, options={})
187
187
  expected = _normalize_metric_expectations(expected)
188
188
  assert_metrics_recorded(expected)
189
189
 
190
- recorded_metrics = NewRelic::Agent.instance.stats_engine.metric_specs
190
+ recorded_metrics = NewRelic::Agent.instance.stats_engine.to_h.keys
191
191
 
192
192
  if options[:filter]
193
193
  recorded_metrics = recorded_metrics.select { |m| m.name.match(options[:filter]) }
@@ -209,7 +209,7 @@ def assert_metrics_not_recorded(not_expected)
209
209
  found_but_not_expected = []
210
210
  not_expected.each do |specish, _|
211
211
  spec = metric_spec_from_specish(specish)
212
- if NewRelic::Agent.instance.stats_engine.lookup_stats(*Array(specish))
212
+ if NewRelic::Agent.instance.stats_engine.to_h[spec]
213
213
  found_but_not_expected << spec
214
214
  end
215
215
  end
@@ -220,7 +220,7 @@ alias :refute_metrics_recorded :assert_metrics_not_recorded
220
220
 
221
221
  def assert_no_metrics_match(regex)
222
222
  matching_metrics = []
223
- NewRelic::Agent.instance.stats_engine.metrics.each do |metric|
223
+ NewRelic::Agent.instance.stats_engine.to_h.keys.map(&:to_s).each do |metric|
224
224
  matching_metrics << metric if metric.match regex
225
225
  end
226
226
 
@@ -327,6 +327,12 @@ def last_transaction_trace_request_params
327
327
  last_transaction_trace.params[:request_params]
328
328
  end
329
329
 
330
+ def find_sql_trace(metric_name)
331
+ NewRelic::Agent.agent.sql_sampler.sql_traces.values.detect do |trace|
332
+ trace.database_metric_name == metric_name
333
+ end
334
+ end
335
+
330
336
  def last_sql_trace
331
337
  NewRelic::Agent.agent.sql_sampler.sql_traces.values.last
332
338
  end
@@ -417,21 +423,29 @@ def with_transaction_renaming_rules(rule_specs)
417
423
  end
418
424
  end
419
425
 
426
+ # Need to guard against double-installing this patch because in 1.8.x the same
427
+ # file can be required multiple times under different non-canonicalized paths.
428
+ unless Time.respond_to?(:__original_now)
429
+ Time.instance_eval do
430
+ class << self
431
+ attr_accessor :__frozen_now
432
+ alias_method :__original_now, :now
420
433
 
421
- def freeze_time(now=Time.now)
422
- if block_given?
423
- begin
424
- Time.stubs(:now).returns(now)
425
- yield now
426
- ensure
427
- Time.unstub(:now)
434
+ def now
435
+ __frozen_now || __original_now
436
+ end
428
437
  end
429
- else
430
- Time.stubs(:now).returns(now)
431
- now
432
438
  end
433
439
  end
434
440
 
441
+ def freeze_time(now=Time.now)
442
+ Time.__frozen_now = now
443
+ end
444
+
445
+ def unfreeze_time
446
+ Time.__frozen_now = nil
447
+ end
448
+
435
449
  def advance_time(seconds)
436
450
  freeze_time(Time.now + seconds)
437
451
  end
@@ -508,7 +522,12 @@ def wait_for_backtrace_service_poll(opts={})
508
522
  until opts[:service].worker_loop.iterations > opts[:iterations]
509
523
  sleep(0.01)
510
524
  if Time.now > deadline
511
- raise "Timed out waiting #{opts[:timeout]} s for backtrace service poll"
525
+ raise "Timed out waiting #{opts[:timeout]} s for backtrace service poll\n" +
526
+ "Worker loop ran for #{opts[:service].worker_loop.iterations} iterations\n\n" +
527
+ Thread.list.map { |t|
528
+ "#{t.to_s}: newrelic_label: #{t[:newrelic_label].inspect}\n\n" +
529
+ (t.backtrace || []).join("\n\t")
530
+ }.join("\n\n")
512
531
  end
513
532
  end
514
533
  end
@@ -1,6 +1,7 @@
1
1
  source 'https://rubygems.org'
2
2
 
3
3
  gem 'rails', '~>3.1.12'
4
+ gem 'i18n', '0.6.11'
4
5
 
5
6
  gem 'rake', '~>10.1.1'
6
7
  gem 'minitest', '~>4.7.5'
@@ -1,6 +1,7 @@
1
1
  source 'https://rubygems.org'
2
2
 
3
3
  gem 'rails', '~>3.2.20'
4
+ gem 'i18n', '0.6.11'
4
5
 
5
6
  gem 'rake', '~>10.1.1'
6
7
  gem 'minitest', '~>4.7.5'
@@ -7,11 +7,10 @@ require 'new_relic/agent/datastores/mongo/metric_translator'
7
7
  module NewRelic
8
8
  module TestHelpers
9
9
  module MongoMetricBuilder
10
- def build_test_metrics(name, request_type = :web)
10
+ def build_test_metrics(name)
11
11
  NewRelic::Agent::Datastores::Mongo::MetricTranslator.build_metrics(
12
12
  name,
13
- @collection_name,
14
- request_type
13
+ @collection_name
15
14
  )
16
15
  end
17
16
 
@@ -17,7 +17,7 @@ module Multiverse
17
17
  @buffer_lock = Mutex.new
18
18
 
19
19
  def self.failing_output
20
- @failing ||= []
20
+ @failing_output ||= []
21
21
  end
22
22
 
23
23
  def self.buffer(suite, env)
@@ -30,8 +30,11 @@ module Multiverse
30
30
  end
31
31
 
32
32
  def self.failed(suite, env)
33
- @failing ||= []
34
- @failing << buffer(suite, env) + "\n"
33
+ @failing_suites ||= []
34
+ @failing_suites << [suite, env]
35
+
36
+ @failing_output ||= []
37
+ @failing_output << buffer(suite, env) + "\n"
35
38
  end
36
39
 
37
40
  def self.write(suite, env, msg)
@@ -47,15 +50,27 @@ module Multiverse
47
50
  if failing_output.empty?
48
51
  output(green("There were no test failures"))
49
52
  else
50
- output(
51
- red("*" * 80),
52
- red("There were failures in #{failing_output.size} test suites"),
53
- red("Here is their output"),
54
- red("*" * 80),
55
- *failing_output)
53
+ to_output = failing_output_header + failing_output + failing_output_footer
54
+ output(*to_output)
56
55
  end
57
56
  end
58
57
 
58
+ def self.failing_output_header
59
+ [red("*" * 80),
60
+ red("Repeating failed test output"),
61
+ red("*" * 80),
62
+ ""]
63
+ end
64
+
65
+ def self.failing_output_footer
66
+ ["",
67
+ red("*" * 80),
68
+ red("There were failures in #{failing_output.size} test suites"),
69
+ "",
70
+ @failing_suites.map { |suite, env| red("#{suite} failed in env #{env}") },
71
+ red("*" * 80)]
72
+ end
73
+
59
74
  # Because the various environments potentially run in separate threads to
60
75
  # start their processes, make sure we don't blatantly interleave output.
61
76
  def self.output(*args)