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
@@ -2,9 +2,7 @@
2
2
  # This file is distributed under New Relic's license terms.
3
3
  # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
4
4
 
5
- require File.join(File.dirname(__FILE__), '..', '..', '..', 'agent_helper')
6
5
  require 'fake_collector'
7
- require 'multiverse_helpers'
8
6
 
9
7
  class LabelsTest < Minitest::Test
10
8
  include MultiverseHelpers
@@ -9,7 +9,6 @@
9
9
  require 'logger'
10
10
  require 'newrelic_rpm'
11
11
  require 'fake_collector'
12
- require 'multiverse_helpers'
13
12
 
14
13
  class LoggingTest < Minitest::Test
15
14
 
@@ -5,7 +5,6 @@
5
5
  # https://newrelic.atlassian.net/wiki/display/eng/The+Terror+and+Glory+of+Transaction+Traces
6
6
  # https://newrelic.atlassian.net/browse/RUBY-914
7
7
  require 'ostruct'
8
- require 'multiverse_helpers'
9
8
 
10
9
  class MarshalingTest < Minitest::Test
11
10
  include MultiverseHelpers
@@ -4,8 +4,6 @@
4
4
 
5
5
  # https://newrelic.atlassian.net/browse/RUBY-669
6
6
 
7
- require 'multiverse_helpers'
8
-
9
7
  class PipeManagerTest < Minitest::Test
10
8
  include MultiverseHelpers
11
9
 
@@ -2,8 +2,6 @@
2
2
  # This file is distributed under New Relic's license terms.
3
3
  # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
4
4
 
5
- require 'multiverse_helpers'
6
-
7
5
  class RenameRuleTest < Minitest::Test
8
6
 
9
7
  include MultiverseHelpers
@@ -41,12 +39,12 @@ class RenameRuleTest < Minitest::Test
41
39
  def test_transaction_names_rules
42
40
  TestWidget.new.txn
43
41
 
44
- metric_names = NewRelic::Agent.instance.stats_engine.metrics
45
-
46
- assert_includes(metric_names, 'Controller/Class::TestWidget/txn')
47
- assert_includes(metric_names, 'Apdex/Class::TestWidget/txn')
42
+ assert_metrics_recorded([
43
+ 'Controller/Class::TestWidget/txn',
44
+ 'Apdex/Class::TestWidget/txn'
45
+ ])
48
46
 
49
- assert_not_includes(metric_names, 'Controller/RenameRuleTest::TestWidget/txn')
47
+ refute_metrics_recorded('Controller/RenameRuleTest::TestWidget/txn')
50
48
  end
51
49
 
52
50
  def test_metric_name_rules
@@ -5,7 +5,6 @@
5
5
  require 'rack/test'
6
6
  require 'new_relic/rack/browser_monitoring'
7
7
  require './testing_app'
8
- require 'multiverse_helpers'
9
8
 
10
9
  class RumAutoTest < Minitest::Test
11
10
 
@@ -2,8 +2,6 @@
2
2
  # This file is distributed under New Relic's license terms.
3
3
  # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
4
4
 
5
- require 'multiverse_helpers'
6
-
7
5
  class SetTransactionNameTest < Minitest::Test
8
6
  include NewRelic::Agent::MethodTracer
9
7
 
@@ -2,8 +2,6 @@
2
2
  # This file is distributed under New Relic's license terms.
3
3
  # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
4
4
 
5
- require 'multiverse_helpers'
6
-
7
5
  class SSLTest < Minitest::Test
8
6
 
9
7
  include MultiverseHelpers
@@ -3,7 +3,6 @@
3
3
  # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
4
4
 
5
5
  require 'rack/test'
6
- require 'multiverse_helpers'
7
6
  require 'new_relic/rack/agent_hooks'
8
7
  require './testing_app'
9
8
 
@@ -30,4 +30,25 @@ class TestingApp
30
30
  sleep(params['sleep'].to_f) if params['sleep']
31
31
  [200, headers, [response]]
32
32
  end
33
+
34
+ end
35
+
36
+ class TestingBackgroundJob
37
+ FIRST_NAME = "OtherTransaction/Custom/TestingBackgroundJob/first"
38
+ SECOND_NAME = "OtherTransaction/Custom/TestingBackgroundJob/second"
39
+
40
+ def first(awhile=nil)
41
+ job(FIRST_NAME, awhile)
42
+ end
43
+
44
+ def second(awhile=nil)
45
+ job(SECOND_NAME, awhile)
46
+ end
47
+
48
+ def job(name, awhile)
49
+ state = ::NewRelic::Agent::TransactionState.tl_get
50
+ ::NewRelic::Agent::Transaction.wrap(state, name, :other) do
51
+ sleep(awhile) if awhile
52
+ end
53
+ end
33
54
  end
@@ -8,7 +8,6 @@
8
8
  if RUBY_VERSION >= '1.9'
9
9
 
10
10
  require 'thread'
11
- require 'multiverse_helpers'
12
11
 
13
12
  class ThreadProfilingTest < Minitest::Test
14
13
 
@@ -131,7 +130,7 @@ class ThreadProfilingTest < Minitest::Test
131
130
  end
132
131
 
133
132
  def let_it_finish
134
- wait_for_backtrace_service_poll(:timeout => 10.0, :iterations => 10)
133
+ wait_for_backtrace_service_poll(:timeout => 10.0, :iterations => 1)
135
134
  harvest
136
135
  join_background_threads
137
136
  end
@@ -2,8 +2,6 @@
2
2
  # This file is distributed under New Relic's license terms.
3
3
  # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
4
4
 
5
- require File.join(File.dirname(__FILE__), '..', '..', '..', 'agent_helper')
6
- require 'multiverse_helpers'
7
5
  require 'transaction_ignoring_test_cases'
8
6
 
9
7
  class TransactionIgnoringTest < Minitest::Test
@@ -3,7 +3,6 @@
3
3
  # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
4
4
 
5
5
  require 'newrelic_rpm'
6
- require 'multiverse_helpers'
7
6
  require 'fake_instance_metadata_service'
8
7
 
9
8
  class UtilizationDataCollectionTest < Minitest::Test
@@ -8,7 +8,6 @@
8
8
  if RUBY_VERSION >= '1.9'
9
9
 
10
10
  require 'rack/test'
11
- require 'multiverse_helpers'
12
11
  require './testing_app'
13
12
 
14
13
  class XraySessionsTest < Minitest::Test
@@ -35,16 +34,9 @@ class XraySessionsTest < Minitest::Test
35
34
  session = build_xray_session('key_transaction_name' => 'Controller/Rack/A')
36
35
  with_xray_sessions(session) do
37
36
  5.times { get '/?transaction_name=A' }
38
- trigger_harvest
39
37
  end
40
38
 
41
- posts = $collector.calls_for('transaction_sample_data')
42
- assert_equal(1, posts.size, "Expected exactly one transaction_sample_data post")
43
-
44
- traces = posts.first.samples
45
- assert_equal(5, traces.size)
46
- assert traces.all? { |t| t.metric_name == 'Controller/Rack/A' }
47
- assert traces.all? { |t| t.xray_id == session['x_ray_id'] }
39
+ assert_traced_transactions('Controller/Rack/A' => [5, session])
48
40
  end
49
41
 
50
42
  def test_does_not_collect_traces_for_non_xrayed_transactions
@@ -52,14 +44,10 @@ class XraySessionsTest < Minitest::Test
52
44
  with_xray_sessions(session) do
53
45
  get '/?transaction_name=OtherThing'
54
46
  get '/?transaction_name=A'
55
- trigger_harvest
56
47
  end
57
48
 
58
- posts = $collector.calls_for('transaction_sample_data')
59
- assert_equal(1, posts.size, "Expected exactly one transaction_sample_data post")
60
-
61
49
  # We expect exactly one transaction trace, for A only
62
- assert_equal(1, posts.first.samples.size)
50
+ assert_traced_transactions('Controller/Rack/A' => [1, session])
63
51
  end
64
52
 
65
53
  def test_gathers_transaction_traces_from_multiple_concurrent_xray_sessions
@@ -71,19 +59,10 @@ class XraySessionsTest < Minitest::Test
71
59
  get '/?transaction_name=A'
72
60
  get '/?transaction_name=B'
73
61
  end
74
- trigger_harvest
75
62
  end
76
63
 
77
- posts = $collector.calls_for('transaction_sample_data')
78
- assert_equal(1, posts.size, "Expected exactly one transaction_sample_data post")
79
-
80
- traces = posts.first.samples
81
- assert_equal(4, traces.size)
82
-
83
- tracesA = traces.select { |t| t.metric_name == 'Controller/Rack/A' }
84
- tracesB = traces.select { |t| t.metric_name == 'Controller/Rack/B' }
85
- assert_equal(2, tracesA.size, "Expected 2 traces for transaction A")
86
- assert_equal(2, tracesB.size, "Expected 2 traces for transaction B")
64
+ assert_traced_transactions('Controller/Rack/A' => [2, sessionA],
65
+ 'Controller/Rack/B' => [2, sessionB])
87
66
  end
88
67
 
89
68
  def test_gathers_thread_profiles
@@ -91,16 +70,42 @@ class XraySessionsTest < Minitest::Test
91
70
  with_xray_sessions(session) do
92
71
  wait_for_backtrace_service_poll
93
72
  get '/?transaction_name=A&sleep=1'
94
- trigger_harvest
95
73
  end
96
74
 
97
- # assert that a thread profile was submitted
98
- posts = $collector.calls_for('profile_data')
99
- assert_equal(1, posts.size, "Expected exactly one profile_data post")
75
+ assert_profile_submitted('REQUEST')
76
+ end
77
+
78
+ def test_tags_background_transaction_traces_with_xray_id
79
+ session = build_xray_session('key_transaction_name' => TestingBackgroundJob::FIRST_NAME)
80
+ with_xray_sessions(session) do
81
+ 5.times { TestingBackgroundJob.new.first }
82
+ end
83
+
84
+ assert_traced_transactions(TestingBackgroundJob::FIRST_NAME => [5, session])
85
+ end
86
+
87
+
88
+ def test_tags_background_transaction_traces_concurrently
89
+ session1 = build_xray_session('key_transaction_name' => TestingBackgroundJob::FIRST_NAME)
90
+ session2 = build_xray_session('key_transaction_name' => TestingBackgroundJob::SECOND_NAME)
91
+
92
+ with_xray_sessions(session1, session2) do
93
+ 2.times { TestingBackgroundJob.new.first }
94
+ 2.times { TestingBackgroundJob.new.second }
95
+ end
96
+
97
+ assert_traced_transactions(TestingBackgroundJob::FIRST_NAME => [2, session1],
98
+ TestingBackgroundJob::SECOND_NAME => [2, session2])
99
+ end
100
+
101
+ def test_gathers_thread_profiles_for_background
102
+ session = build_xray_session('key_transaction_name' => TestingBackgroundJob::FIRST_NAME)
103
+ with_xray_sessions(session) do
104
+ wait_for_backtrace_service_poll
105
+ TestingBackgroundJob.new.first(1)
106
+ end
100
107
 
101
- profile_data_post = posts.first
102
- assert(profile_data_post.sample_count > 1, "Expected at least one sample")
103
- assert_saw_traces(profile_data_post, 'REQUEST')
108
+ assert_profile_submitted('BACKGROUND')
104
109
  end
105
110
 
106
111
  ## Helpers
@@ -143,6 +148,8 @@ class XraySessionsTest < Minitest::Test
143
148
 
144
149
  yield
145
150
 
151
+ agent.send(:transmit_data)
152
+
146
153
  deactivate_cmd = build_active_xrays_command([])
147
154
  issue_command(deactivate_cmd)
148
155
  end
@@ -152,13 +159,41 @@ class XraySessionsTest < Minitest::Test
152
159
  agent.send(:check_for_and_handle_agent_commands)
153
160
  end
154
161
 
155
- def trigger_harvest
156
- agent.send(:transmit_data)
162
+ def single_transaction_sample_post
163
+ posts = $collector.calls_for('transaction_sample_data')
164
+ assert_equal(1, posts.size, "Expected exactly one transaction_sample_data post")
165
+
166
+ posts.first
167
+ end
168
+
169
+ def single_profile_post
170
+ posts = $collector.calls_for('profile_data')
171
+ assert_equal(1, posts.size, "Expected exactly one profile_data post")
172
+ posts.first
157
173
  end
158
174
 
159
175
  def assert_saw_traces(profile_data, type)
160
176
  assert !profile_data.traces[type].empty?, "Missing #{type} traces"
161
177
  end
162
178
 
179
+ def assert_profile_submitted(type)
180
+ assert(single_profile_post.sample_count > 1, "Expected at least one sample")
181
+ assert_saw_traces(single_profile_post, type)
182
+ end
183
+
184
+ def assert_traced_transactions(txns)
185
+ traces = single_transaction_sample_post.samples
186
+
187
+ total_count = txns.inject(0) { |prior, (_, (count, *_))| prior + count }
188
+
189
+ assert_equal(total_count, traces.size)
190
+
191
+ txns.each do |name, (count, session)|
192
+ check_traces = traces.select { |t| t.metric_name == name }
193
+ assert_equal(count, check_traces.size, "Transaction #{name}")
194
+ assert check_traces.all? { |t| t.xray_id == session['x_ray_id'] }
195
+ end
196
+ end
197
+
163
198
  end
164
199
  end
@@ -3,7 +3,6 @@
3
3
  # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
4
4
 
5
5
  require 'fake_rpm_site'
6
- require 'multiverse_helpers'
7
6
  require 'new_relic/cli/command'
8
7
 
9
8
  class DeploymentTest < Minitest::Test
@@ -3,7 +3,6 @@
3
3
  # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
4
4
 
5
5
  require 'fake_rpm_site'
6
- require 'multiverse_helpers'
7
6
 
8
7
  class DeploymentTest < Minitest::Test
9
8
  def setup
@@ -14,8 +14,6 @@
14
14
  # If this fails the agent will attempt to dial Lew Cirne's cell phone and ask
15
15
  # that he verbally describe how it should be configured.
16
16
 
17
- require 'multiverse_helpers'
18
-
19
17
  class ConfigFileLoadingTest < Minitest::Test
20
18
  include MultiverseHelpers
21
19
 
@@ -8,8 +8,6 @@ require 'newrelic_rpm'
8
8
  require 'http_client_test_cases'
9
9
  require 'new_relic/agent/http_clients/curb_wrappers'
10
10
 
11
- require File.join(File.dirname(__FILE__), "..", "..", "..", "agent_helper")
12
-
13
11
  class CurbTest < Minitest::Test
14
12
 
15
13
  #
@@ -1,7 +1,30 @@
1
- omit_collector!
1
+ adapter_gems = <<-RB
2
+ gem 'dm-sqlite-adapter'
3
+
4
+ # Pin this version as the adapter breaks with later ones
5
+ gem 'jdbc-sqlite3', '~> 3.7.2.1', :platforms => [:jruby]
6
+
7
+ # Needed for the fake collector
8
+ gem 'rack'
9
+ RB
2
10
 
3
11
  gemfile <<-RB
4
12
  gem 'json', '>= 1.8.1'
5
- gem 'datamapper'
6
- gem 'dm-sqlite-adapter'
13
+ gem 'datamapper', '~> 1.2.0', :require => 'data_mapper'
14
+ gem 'dm-ar-finders', '~> 1.2.0'
15
+ #{adapter_gems}
16
+ RB
17
+
18
+ if RUBY_VERSION < '2.0.0'
19
+ gemfile <<-RB
20
+ gem 'datamapper', '~> 1.1.0'
21
+ gem 'dm-ar-finders', '~> 1.1.0'
22
+ #{adapter_gems}
23
+ RB
24
+
25
+ gemfile <<-RB
26
+ gem 'datamapper', '~> 1.0.2'
27
+ gem 'dm-ar-finders', '~> 1.0.2'
28
+ #{adapter_gems}
7
29
  RB
30
+ end
@@ -10,6 +10,7 @@ development:
10
10
  app_name: test
11
11
  host: 127.0.0.1
12
12
  api_host: 127.0.0.1
13
+ port: <%= $collector && $collector.port %>
13
14
  transaction_tracer:
14
15
  record_sql: obfuscated
15
16
  enabled: true
@@ -2,11 +2,6 @@
2
2
  # This file is distributed under New Relic's license terms.
3
3
  # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
4
4
 
5
- require 'data_mapper'
6
-
7
- require File.join(File.dirname(__FILE__), '..', '..', '..', 'agent_helper')
8
- require 'multiverse_helpers'
9
-
10
5
  DataMapper::Logger.new("/dev/null", :debug)
11
6
  DataMapper.setup(:default, 'sqlite::memory:')
12
7
  class Post
@@ -32,55 +27,272 @@ class DataMapperTest < Minitest::Test
32
27
 
33
28
  setup_and_teardown_agent
34
29
 
35
- def test_basic_metrics
36
- post = Post.create(:title => "Dummy post", :body => "whatever, man")
37
- post = Post.get(post.id)
38
- post.update(:title => 'other title')
39
- post.destroy
30
+ def test_create
31
+ # DM 1.0 generates a create method on inclusion of a module that internally
32
+ # calls the instance #save method, so that's all we see on that version.
33
+ expected_metric = DataMapper::VERSION < "1.1" ? :save : :create
34
+ assert_basic_metrics(expected_metric) do
35
+ Post.create(:title => "Dummy post", :body => "whatever, man")
36
+ end
37
+ end
38
+
39
+ def test_create!
40
+ assert_basic_metrics(:create) do
41
+ Post.create!(:title => "Dummy post", :body => "whatever, man")
42
+ end
43
+ end
44
+
45
+ def test_get
46
+ assert_against_record(:get) do |post|
47
+ Post.get(post.id)
48
+ end
49
+ end
50
+
51
+ def test_get!
52
+ assert_against_record(:get) do |post|
53
+ Post.get!(post.id)
54
+ end
55
+ end
56
+
57
+ def test_first
58
+ assert_against_record(:first) do
59
+ Post.first
60
+ end
61
+ end
62
+
63
+ def test_all
64
+ assert_against_record(:all) do
65
+ Post.all
66
+ end
67
+ end
68
+
69
+ def test_last
70
+ assert_against_record(:last) do
71
+ Post.last
72
+ end
73
+ end
74
+
75
+ def test_bulk_update
76
+ assert_against_record(:update) do
77
+ Post.update(:title => 'other title')
78
+ end
79
+ end
80
+
81
+ def test_bulk_update!
82
+ assert_against_record(:update) do
83
+ Post.update!(:title => 'other title')
84
+ end
85
+ end
86
+
87
+ def test_instance_update
88
+ assert_against_record(:update) do |post|
89
+ post.update(:title => 'other title')
90
+ end
91
+ end
92
+
93
+ def test_bulk_update!
94
+ assert_against_record(:update) do |post|
95
+ post.update!(:title => 'other title')
96
+ end
97
+ end
98
+
99
+ def test_bulk_destroy
100
+ assert_against_record(:destroy) do
101
+ Post.destroy
102
+ end
103
+ end
104
+
105
+ def test_bulk_destroy!
106
+ assert_against_record(:destroy) do
107
+ Post.destroy!
108
+ end
109
+ end
110
+
111
+ def test_instance_destroy
112
+ assert_against_record(:destroy) do |post|
113
+ post.destroy
114
+ end
115
+ end
116
+
117
+ def test_instance_destroy!
118
+ assert_against_record(:destroy) do |post|
119
+ post.destroy!
120
+ end
121
+ end
122
+
123
+ def test_save
124
+ assert_against_record(:save) do |post|
125
+ post.save
126
+ end
127
+ end
128
+
129
+ def test_save!
130
+ assert_against_record(:save) do |post|
131
+ post.save!
132
+ end
133
+ end
134
+
135
+ def test_aggregate
136
+ assert_against_record(:aggregate) do
137
+ Post.aggregate(:title, :all.count)
138
+ end
139
+ end
140
+
141
+ def test_find
142
+ assert_against_record(:find) do
143
+ Post.find(1)
144
+ end
145
+ end
146
+
147
+ def test_find_by_sql
148
+ assert_against_record(:find_by_sql) do
149
+ Post.find_by_sql('select * from posts')
150
+ end
151
+ end
152
+
153
+ def test_in_web_transaction
154
+ in_web_transaction("dm4evr") do
155
+ Post.all
156
+ end
157
+
158
+ assert_metrics_recorded([
159
+ 'Datastore/all',
160
+ 'Datastore/allWeb',
161
+ 'Datastore/DataMapper/all',
162
+ 'Datastore/DataMapper/allWeb',
163
+ 'Datastore/operation/DataMapper/all',
164
+ 'Datastore/statement/DataMapper/Post/all',
165
+ ['Datastore/statement/DataMapper/Post/all', 'dm4evr']
166
+ ])
167
+ end
168
+
169
+ def test_collection_get
170
+ assert_against_record(:get) do
171
+ Post.all.get(1)
172
+ end
173
+ end
174
+
175
+ def test_collection_first
176
+ assert_against_record(:first) do
177
+ Post.all.first
178
+ end
179
+ end
180
+
181
+ def test_collection_last
182
+ assert_against_record(:last) do
183
+ Post.all.last
184
+ end
185
+ end
186
+
187
+ def test_collection_all
188
+ assert_against_record(:all) do
189
+ Post.all.all # sic
190
+ end
191
+
40
192
  assert_metrics_recorded(
41
- 'ActiveRecord/Post/save' => { :call_count => 2 },
42
- 'ActiveRecord/Post/get' => { :call_count => 1 },
43
- 'ActiveRecord/Post/update' => { :call_count => 1 },
44
- 'ActiveRecord/Post/destroy' => { :call_count => 1 }
193
+ 'Datastore/statement/DataMapper/Post/all' => { :call_count => 2 }
45
194
  )
46
195
  end
47
196
 
48
- def test_rollup_metrics_for_create
49
- post = Post.create(:title => 'foo', :body => 'bar')
50
- post.save
51
- assert_metrics_recorded(['ActiveRecord/save'])
197
+ def test_collection_lazy_load
198
+ assert_against_record(:lazy_load) do
199
+ Post.all.send(:lazy_load)
200
+ end
201
+ end
202
+
203
+ def test_collection_create
204
+ assert_against_record(:create) do
205
+ Post.all.create(:title => "The Title", :body => "Body")
206
+ end
207
+ end
208
+
209
+ def test_collection_create!
210
+ assert_against_record(:create) do
211
+ Post.all.create!(:title => "The Title", :body => "Body")
212
+ end
213
+ end
214
+
215
+ def test_collection_update
216
+ assert_against_record(:update) do
217
+ Post.all.update(:title => "Another")
218
+ end
219
+ end
220
+
221
+ def test_collection_update!
222
+ assert_against_record(:update) do
223
+ Post.all.update!(:title => "Another")
224
+ end
225
+ end
226
+
227
+ def test_collection_destroy
228
+ assert_against_record(:destroy) do
229
+ Post.all.destroy
230
+ end
52
231
  end
53
232
 
54
- def test_rollup_metrics_for_update
55
- post = Post.create(:title => 'foo', :body => 'bar')
56
- post.body = 'baz'
57
- post.save
58
- assert_metrics_recorded('ActiveRecord/save' => { :call_count => 2 })
233
+ def test_collection_destroy!
234
+ assert_against_record(:destroy) do
235
+ Post.all.destroy!
236
+ end
59
237
  end
60
238
 
61
- def test_rollup_metrics_for_destroy
62
- post = Post.create(:title => 'foo', :body => 'bar')
63
- post.save
64
- post.destroy
65
- assert_metrics_recorded(['ActiveRecord/destroy'])
239
+ def test_collection_aggregate
240
+ assert_against_record(:aggregate) do
241
+ Post.all.aggregate(:title, :all.count)
242
+ end
66
243
  end
67
244
 
68
- def test_rollup_metrics_should_include_all_if_in_web_transaction
245
+ def test_notices_sql
69
246
  in_web_transaction do
70
- Post.create(:title => 'foo', :body => 'bar').save
247
+ Post.get(42)
248
+ end
249
+
250
+ sql_segment = find_last_transaction_segment(last_transaction_trace)
251
+ refute_nil sql_segment.obfuscated_sql
252
+ end
253
+
254
+ def test_direct_select_on_adapter
255
+ in_web_transaction('dm4evr') do
256
+ DataMapper.repository.adapter.select('select * from posts limit 1')
257
+ end
258
+
259
+ assert_metrics_recorded([
260
+ 'Datastore/all',
261
+ 'Datastore/allWeb',
262
+ 'Datastore/DataMapper/all',
263
+ 'Datastore/DataMapper/allWeb',
264
+ 'Datastore/operation/DataMapper/select',
265
+ ['Datastore/operation/DataMapper/select', 'dm4evr'],
266
+ ])
267
+ end
268
+
269
+ def test_direct_execute_on_adapter
270
+ in_transaction('background') do
271
+ DataMapper.repository.adapter.execute('update posts set title=title')
71
272
  end
273
+
72
274
  assert_metrics_recorded([
73
- 'ActiveRecord/save',
74
- 'ActiveRecord/all'
275
+ 'Datastore/all',
276
+ 'Datastore/allOther',
277
+ 'Datastore/DataMapper/all',
278
+ 'Datastore/DataMapper/allOther',
279
+ 'Datastore/operation/DataMapper/execute',
280
+ ['Datastore/operation/DataMapper/execute', 'background'],
75
281
  ])
76
282
  end
77
283
 
78
- def test_rollup_metrics_should_omit_all_if_not_in_web_transaction
79
- in_transaction do
80
- Post.create(:title => 'foo', :body => 'bar').save
284
+ def test_datamapper_transaction_commit
285
+ Post.transaction do |t|
286
+ Post.destroy!
81
287
  end
82
- assert_metrics_recorded(['ActiveRecord/save'])
83
- assert_metrics_not_recorded(['ActiveRecord/all'])
288
+
289
+ assert_metrics_recorded([
290
+ 'Datastore/all',
291
+ 'Datastore/allOther',
292
+ 'Datastore/DataMapper/all',
293
+ 'Datastore/DataMapper/allOther',
294
+ 'Datastore/operation/DataMapper/commit'
295
+ ])
84
296
  end
85
297
 
86
298
  # https://support.newrelic.com/tickets/2101
@@ -98,4 +310,26 @@ class DataMapperTest < Minitest::Test
98
310
  assert_equal false, msg.query.valid_encoding? if RUBY_VERSION >= '1.9'
99
311
  db.send(:log, msg)
100
312
  end
313
+
314
+ def assert_against_record(operation)
315
+ post = Post.create!(:title => "Dummy post", :body => "whatever, man")
316
+
317
+ # Want to ignore our default record's creation for these tests
318
+ NewRelic::Agent.drop_buffered_data
319
+
320
+ assert_basic_metrics(operation) do
321
+ yield(post)
322
+ end
323
+ end
324
+
325
+ def assert_basic_metrics(operation)
326
+ yield
327
+ assert_metrics_recorded([
328
+ "Datastore/all",
329
+ "Datastore/allOther",
330
+ "Datastore/operation/DataMapper/#{operation}",
331
+ "Datastore/statement/DataMapper/Post/#{operation}"
332
+ ])
333
+ end
334
+
101
335
  end