newrelic_rpm 5.7.0.350 → 9.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (476) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +15 -1
  3. data/.rubocop.yml +1919 -0
  4. data/.rubocop_todo.yml +100 -0
  5. data/.simplecov +15 -0
  6. data/.snyk +11 -0
  7. data/.yardopts +2 -0
  8. data/Brewfile +12 -0
  9. data/CHANGELOG.md +4056 -2339
  10. data/CONTRIBUTING.md +132 -19
  11. data/DOCKER.md +167 -0
  12. data/Dockerfile +10 -0
  13. data/Gemfile +5 -2
  14. data/Guardfile +22 -4
  15. data/LICENSE +202 -38
  16. data/README.md +87 -87
  17. data/Rakefile +27 -27
  18. data/THIRD_PARTY_NOTICES.md +28 -0
  19. data/Thorfile +5 -0
  20. data/bin/newrelic +3 -2
  21. data/bin/newrelic_cmd +1 -0
  22. data/bin/nrdebug +77 -54
  23. data/config.dot +5 -5
  24. data/docker-compose.yml +107 -0
  25. data/init.rb +5 -7
  26. data/install.rb +3 -3
  27. data/lefthook.yml +9 -0
  28. data/lib/new_relic/agent/adaptive_sampler.rb +14 -10
  29. data/lib/new_relic/agent/agent.rb +125 -969
  30. data/lib/new_relic/agent/agent_helpers/connect.rb +227 -0
  31. data/lib/new_relic/agent/agent_helpers/harvest.rb +153 -0
  32. data/lib/new_relic/agent/agent_helpers/shutdown.rb +72 -0
  33. data/lib/new_relic/agent/agent_helpers/special_startup.rb +74 -0
  34. data/lib/new_relic/agent/agent_helpers/start_worker_thread.rb +167 -0
  35. data/lib/new_relic/agent/agent_helpers/startup.rb +202 -0
  36. data/lib/new_relic/agent/agent_helpers/transmit.rb +76 -0
  37. data/lib/new_relic/agent/agent_logger.rb +26 -18
  38. data/lib/new_relic/agent/attribute_filter.rb +69 -52
  39. data/lib/new_relic/agent/attribute_processing.rb +8 -8
  40. data/lib/new_relic/agent/attributes.rb +153 -0
  41. data/lib/new_relic/agent/audit_logger.rb +19 -4
  42. data/lib/new_relic/agent/autostart.rb +34 -28
  43. data/lib/new_relic/agent/chained_call.rb +2 -2
  44. data/lib/new_relic/agent/commands/agent_command.rb +4 -4
  45. data/lib/new_relic/agent/commands/agent_command_router.rb +15 -33
  46. data/lib/new_relic/agent/commands/thread_profiler_session.rb +13 -11
  47. data/lib/new_relic/agent/configuration/default_source.rb +1480 -1053
  48. data/lib/new_relic/agent/configuration/dotted_hash.rb +7 -6
  49. data/lib/new_relic/agent/configuration/environment_source.rb +15 -11
  50. data/lib/new_relic/agent/configuration/event_harvest_config.rb +68 -0
  51. data/lib/new_relic/agent/configuration/high_security_source.rb +9 -9
  52. data/lib/new_relic/agent/configuration/manager.rb +96 -79
  53. data/lib/new_relic/agent/configuration/manual_source.rb +2 -2
  54. data/lib/new_relic/agent/configuration/mask_defaults.rb +4 -4
  55. data/lib/new_relic/agent/configuration/security_policy_source.rb +83 -86
  56. data/lib/new_relic/agent/configuration/server_source.rb +49 -12
  57. data/lib/new_relic/agent/configuration/yaml_source.rb +42 -13
  58. data/lib/new_relic/agent/configuration.rb +2 -2
  59. data/lib/new_relic/agent/connect/request_builder.rb +61 -0
  60. data/lib/new_relic/agent/connect/response_handler.rb +58 -0
  61. data/lib/new_relic/agent/custom_event_aggregator.rb +15 -15
  62. data/lib/new_relic/agent/database/explain_plan_helpers.rb +5 -6
  63. data/lib/new_relic/agent/database/obfuscation_helpers.rb +16 -15
  64. data/lib/new_relic/agent/database/obfuscator.rb +3 -3
  65. data/lib/new_relic/agent/database/postgres_explain_obfuscator.rb +4 -4
  66. data/lib/new_relic/agent/database.rb +44 -53
  67. data/lib/new_relic/agent/database_adapter.rb +35 -0
  68. data/lib/new_relic/agent/datastores/metric_helper.rb +18 -20
  69. data/lib/new_relic/agent/datastores/mongo/event_formatter.rb +9 -8
  70. data/lib/new_relic/agent/datastores/mongo/metric_translator.rb +7 -11
  71. data/lib/new_relic/agent/datastores/mongo.rb +7 -12
  72. data/lib/new_relic/agent/datastores/nosql_obfuscator.rb +41 -0
  73. data/lib/new_relic/agent/datastores/redis.rb +6 -12
  74. data/lib/new_relic/agent/datastores.rb +19 -23
  75. data/lib/new_relic/agent/deprecator.rb +2 -2
  76. data/lib/new_relic/agent/{cross_app_payload.rb → distributed_tracing/cross_app_payload.rb} +13 -12
  77. data/lib/new_relic/agent/{cross_app_tracing.rb → distributed_tracing/cross_app_tracing.rb} +87 -66
  78. data/lib/new_relic/agent/distributed_tracing/distributed_trace_attributes.rb +84 -0
  79. data/lib/new_relic/agent/distributed_tracing/distributed_trace_metrics.rb +75 -0
  80. data/lib/new_relic/agent/distributed_tracing/distributed_trace_payload.rb +163 -0
  81. data/lib/new_relic/agent/distributed_tracing/distributed_trace_transport_type.rb +38 -0
  82. data/lib/new_relic/agent/distributed_tracing/trace_context.rb +245 -0
  83. data/lib/new_relic/agent/distributed_tracing/trace_context_payload.rb +127 -0
  84. data/lib/new_relic/agent/distributed_tracing.rb +113 -32
  85. data/lib/new_relic/agent/encoding_normalizer.rb +5 -3
  86. data/lib/new_relic/agent/error_collector.rb +99 -63
  87. data/lib/new_relic/agent/error_event_aggregator.rb +10 -8
  88. data/lib/new_relic/agent/error_filter.rb +174 -0
  89. data/lib/new_relic/agent/error_trace_aggregator.rb +6 -4
  90. data/lib/new_relic/agent/event_aggregator.rb +43 -48
  91. data/lib/new_relic/agent/event_buffer.rb +8 -9
  92. data/lib/new_relic/agent/event_listener.rb +2 -3
  93. data/lib/new_relic/agent/event_loop.rb +27 -25
  94. data/lib/new_relic/agent/external.rb +20 -51
  95. data/lib/new_relic/agent/guid_generator.rb +30 -0
  96. data/lib/new_relic/agent/harvester.rb +5 -6
  97. data/lib/new_relic/agent/heap.rb +8 -10
  98. data/lib/new_relic/agent/hostname.rb +26 -5
  99. data/lib/new_relic/agent/http_clients/abstract.rb +81 -0
  100. data/lib/new_relic/agent/http_clients/curb_wrappers.rb +26 -26
  101. data/lib/new_relic/agent/http_clients/excon_wrappers.rb +31 -17
  102. data/lib/new_relic/agent/http_clients/http_rb_wrappers.rb +18 -23
  103. data/lib/new_relic/agent/http_clients/httpclient_wrappers.rb +12 -15
  104. data/lib/new_relic/agent/http_clients/net_http_wrappers.rb +24 -8
  105. data/lib/new_relic/agent/http_clients/typhoeus_wrappers.rb +9 -12
  106. data/lib/new_relic/agent/http_clients/uri_util.rb +12 -13
  107. data/lib/new_relic/agent/instrumentation/action_cable_subscriber.rb +22 -52
  108. data/lib/new_relic/agent/instrumentation/action_controller_other_subscriber.rb +39 -0
  109. data/lib/new_relic/agent/instrumentation/action_controller_subscriber.rb +59 -72
  110. data/lib/new_relic/agent/instrumentation/action_dispatch.rb +31 -0
  111. data/lib/new_relic/agent/instrumentation/action_dispatch_subscriber.rb +64 -0
  112. data/lib/new_relic/agent/instrumentation/action_mailbox.rb +30 -0
  113. data/lib/new_relic/agent/instrumentation/action_mailbox_subscriber.rb +33 -0
  114. data/lib/new_relic/agent/instrumentation/action_mailer.rb +30 -0
  115. data/lib/new_relic/agent/instrumentation/action_mailer_subscriber.rb +85 -0
  116. data/lib/new_relic/agent/instrumentation/action_view_subscriber.rb +86 -62
  117. data/lib/new_relic/agent/instrumentation/active_job.rb +38 -19
  118. data/lib/new_relic/agent/instrumentation/active_job_subscriber.rb +41 -0
  119. data/lib/new_relic/agent/instrumentation/active_merchant.rb +21 -7
  120. data/lib/new_relic/agent/instrumentation/active_record.rb +95 -46
  121. data/lib/new_relic/agent/instrumentation/active_record_helper.rb +82 -61
  122. data/lib/new_relic/agent/instrumentation/active_record_notifications.rb +155 -0
  123. data/lib/new_relic/agent/instrumentation/active_record_prepend.rb +36 -12
  124. data/lib/new_relic/agent/instrumentation/active_record_subscriber.rb +69 -64
  125. data/lib/new_relic/agent/instrumentation/active_storage.rb +8 -4
  126. data/lib/new_relic/agent/instrumentation/active_storage_subscriber.rb +11 -32
  127. data/lib/new_relic/agent/instrumentation/active_support.rb +27 -0
  128. data/lib/new_relic/agent/instrumentation/active_support_logger/chain.rb +23 -0
  129. data/lib/new_relic/agent/instrumentation/active_support_logger/instrumentation.rb +20 -0
  130. data/lib/new_relic/agent/instrumentation/active_support_logger/prepend.rb +12 -0
  131. data/lib/new_relic/agent/instrumentation/active_support_logger.rb +24 -0
  132. data/lib/new_relic/agent/instrumentation/active_support_subscriber.rb +41 -0
  133. data/lib/new_relic/agent/instrumentation/bunny/chain.rb +45 -0
  134. data/lib/new_relic/agent/instrumentation/bunny/instrumentation.rb +150 -0
  135. data/lib/new_relic/agent/instrumentation/bunny/prepend.rb +35 -0
  136. data/lib/new_relic/agent/instrumentation/bunny.rb +14 -134
  137. data/lib/new_relic/agent/instrumentation/concurrent_ruby/chain.rb +36 -0
  138. data/lib/new_relic/agent/instrumentation/concurrent_ruby/instrumentation.rb +21 -0
  139. data/lib/new_relic/agent/instrumentation/concurrent_ruby/prepend.rb +27 -0
  140. data/lib/new_relic/agent/instrumentation/concurrent_ruby.rb +31 -0
  141. data/lib/new_relic/agent/instrumentation/controller_instrumentation.rb +77 -61
  142. data/lib/new_relic/agent/instrumentation/curb/chain.rb +91 -0
  143. data/lib/new_relic/agent/instrumentation/curb/instrumentation.rb +221 -0
  144. data/lib/new_relic/agent/instrumentation/curb/prepend.rb +61 -0
  145. data/lib/new_relic/agent/instrumentation/curb.rb +15 -187
  146. data/lib/new_relic/agent/instrumentation/custom_events.rb +12 -0
  147. data/lib/new_relic/agent/instrumentation/custom_events_subscriber.rb +37 -0
  148. data/lib/new_relic/agent/instrumentation/delayed_job/chain.rb +35 -0
  149. data/lib/new_relic/agent/instrumentation/delayed_job/instrumentation.rb +48 -0
  150. data/lib/new_relic/agent/instrumentation/delayed_job/prepend.rb +33 -0
  151. data/lib/new_relic/agent/instrumentation/delayed_job_instrumentation.rb +30 -52
  152. data/lib/new_relic/agent/instrumentation/elasticsearch/chain.rb +29 -0
  153. data/lib/new_relic/agent/instrumentation/elasticsearch/instrumentation.rb +66 -0
  154. data/lib/new_relic/agent/instrumentation/elasticsearch/prepend.rb +13 -0
  155. data/lib/new_relic/agent/instrumentation/elasticsearch.rb +31 -0
  156. data/lib/new_relic/agent/instrumentation/excon/middleware.rb +8 -7
  157. data/lib/new_relic/agent/instrumentation/excon.rb +29 -31
  158. data/lib/new_relic/agent/instrumentation/fiber/chain.rb +20 -0
  159. data/lib/new_relic/agent/instrumentation/fiber/instrumentation.rb +24 -0
  160. data/lib/new_relic/agent/instrumentation/fiber/prepend.rb +18 -0
  161. data/lib/new_relic/agent/instrumentation/fiber.rb +25 -0
  162. data/lib/new_relic/agent/instrumentation/grape/chain.rb +24 -0
  163. data/lib/new_relic/agent/instrumentation/grape/instrumentation.rb +100 -0
  164. data/lib/new_relic/agent/instrumentation/grape/prepend.rb +17 -0
  165. data/lib/new_relic/agent/instrumentation/grape.rb +16 -121
  166. data/lib/new_relic/agent/instrumentation/grpc/client/chain.rb +97 -0
  167. data/lib/new_relic/agent/instrumentation/grpc/client/instrumentation.rb +89 -0
  168. data/lib/new_relic/agent/instrumentation/grpc/client/prepend.rb +111 -0
  169. data/lib/new_relic/agent/instrumentation/grpc/client/request_wrapper.rb +30 -0
  170. data/lib/new_relic/agent/instrumentation/grpc/helper.rb +32 -0
  171. data/lib/new_relic/agent/instrumentation/grpc/server/chain.rb +69 -0
  172. data/lib/new_relic/agent/instrumentation/grpc/server/instrumentation.rb +134 -0
  173. data/lib/new_relic/agent/instrumentation/grpc/server/rpc_desc_prepend.rb +35 -0
  174. data/lib/new_relic/agent/instrumentation/grpc/server/rpc_server_prepend.rb +26 -0
  175. data/lib/new_relic/agent/instrumentation/grpc_client.rb +23 -0
  176. data/lib/new_relic/agent/instrumentation/grpc_server.rb +25 -0
  177. data/lib/new_relic/agent/instrumentation/httpclient/chain.rb +24 -0
  178. data/lib/new_relic/agent/instrumentation/httpclient/instrumentation.rb +37 -0
  179. data/lib/new_relic/agent/instrumentation/httpclient/prepend.rb +15 -0
  180. data/lib/new_relic/agent/instrumentation/httpclient.rb +12 -32
  181. data/lib/new_relic/agent/instrumentation/httprb/chain.rb +22 -0
  182. data/lib/new_relic/agent/instrumentation/httprb/instrumentation.rb +30 -0
  183. data/lib/new_relic/agent/instrumentation/httprb/prepend.rb +15 -0
  184. data/lib/new_relic/agent/instrumentation/httprb.rb +29 -0
  185. data/lib/new_relic/agent/instrumentation/ignore_actions.rb +5 -6
  186. data/lib/new_relic/agent/instrumentation/logger/chain.rb +21 -0
  187. data/lib/new_relic/agent/instrumentation/logger/instrumentation.rb +66 -0
  188. data/lib/new_relic/agent/instrumentation/logger/prepend.rb +13 -0
  189. data/lib/new_relic/agent/instrumentation/logger.rb +26 -0
  190. data/lib/new_relic/agent/instrumentation/memcache/chain.rb +15 -0
  191. data/lib/new_relic/agent/instrumentation/memcache/dalli.rb +58 -125
  192. data/lib/new_relic/agent/instrumentation/memcache/helper.rb +59 -0
  193. data/lib/new_relic/agent/instrumentation/memcache/instrumentation.rb +90 -0
  194. data/lib/new_relic/agent/instrumentation/memcache/prepend.rb +101 -0
  195. data/lib/new_relic/agent/instrumentation/memcache.rb +57 -71
  196. data/lib/new_relic/agent/instrumentation/middleware_proxy.rb +15 -14
  197. data/lib/new_relic/agent/instrumentation/middleware_tracing.rb +21 -14
  198. data/lib/new_relic/agent/instrumentation/mongo.rb +7 -132
  199. data/lib/new_relic/agent/instrumentation/mongodb_command_subscriber.rb +49 -13
  200. data/lib/new_relic/agent/instrumentation/net_http/chain.rb +24 -0
  201. data/lib/new_relic/agent/instrumentation/net_http/instrumentation.rb +40 -0
  202. data/lib/new_relic/agent/instrumentation/net_http/prepend.rb +21 -0
  203. data/lib/new_relic/agent/instrumentation/net_http.rb +44 -0
  204. data/lib/new_relic/agent/instrumentation/notifications_subscriber.rb +142 -0
  205. data/lib/new_relic/agent/instrumentation/padrino/chain.rb +38 -0
  206. data/lib/new_relic/agent/instrumentation/padrino/instrumentation.rb +28 -0
  207. data/lib/new_relic/agent/instrumentation/padrino/prepend.rb +20 -0
  208. data/lib/new_relic/agent/instrumentation/padrino.rb +22 -58
  209. data/lib/new_relic/agent/instrumentation/passenger_instrumentation.rb +7 -7
  210. data/lib/new_relic/agent/instrumentation/queue_time.rb +9 -10
  211. data/lib/new_relic/agent/instrumentation/rack/chain.rb +66 -0
  212. data/lib/new_relic/agent/instrumentation/rack/helpers.rb +33 -0
  213. data/lib/new_relic/agent/instrumentation/rack/instrumentation.rb +75 -0
  214. data/lib/new_relic/agent/instrumentation/rack/prepend.rb +43 -0
  215. data/lib/new_relic/agent/instrumentation/rack.rb +33 -141
  216. data/lib/new_relic/agent/instrumentation/rails3/action_controller.rb +19 -55
  217. data/lib/new_relic/agent/instrumentation/rails_middleware.rb +5 -5
  218. data/lib/new_relic/agent/instrumentation/rails_notifications/action_cable.rb +36 -0
  219. data/lib/new_relic/agent/instrumentation/rails_notifications/action_controller.rb +45 -0
  220. data/lib/new_relic/agent/instrumentation/rails_notifications/action_view.rb +30 -0
  221. data/lib/new_relic/agent/instrumentation/rails_notifications/custom_events.rb +30 -0
  222. data/lib/new_relic/agent/instrumentation/rake/chain.rb +20 -0
  223. data/lib/new_relic/agent/instrumentation/rake/instrumentation.rb +142 -0
  224. data/lib/new_relic/agent/instrumentation/rake/prepend.rb +14 -0
  225. data/lib/new_relic/agent/instrumentation/rake.rb +18 -159
  226. data/lib/new_relic/agent/instrumentation/redis/chain.rb +45 -0
  227. data/lib/new_relic/agent/instrumentation/redis/constants.rb +17 -0
  228. data/lib/new_relic/agent/instrumentation/redis/instrumentation.rb +93 -0
  229. data/lib/new_relic/agent/instrumentation/redis/middleware.rb +16 -0
  230. data/lib/new_relic/agent/instrumentation/redis/prepend.rb +29 -0
  231. data/lib/new_relic/agent/instrumentation/redis.rb +20 -103
  232. data/lib/new_relic/agent/instrumentation/resque/chain.rb +21 -0
  233. data/lib/new_relic/agent/instrumentation/resque/helper.rb +19 -0
  234. data/lib/new_relic/agent/instrumentation/resque/instrumentation.rb +34 -0
  235. data/lib/new_relic/agent/instrumentation/resque/prepend.rb +15 -0
  236. data/lib/new_relic/agent/instrumentation/resque.rb +33 -41
  237. data/lib/new_relic/agent/instrumentation/sequel.rb +17 -20
  238. data/lib/new_relic/agent/instrumentation/sequel_helper.rb +3 -3
  239. data/lib/new_relic/agent/instrumentation/sidekiq/client.rb +20 -0
  240. data/lib/new_relic/agent/instrumentation/sidekiq/extensions/delayed_class.rb +30 -0
  241. data/lib/new_relic/agent/instrumentation/sidekiq/server.rb +37 -0
  242. data/lib/new_relic/agent/instrumentation/sidekiq.rb +29 -46
  243. data/lib/new_relic/agent/instrumentation/sinatra/chain.rb +55 -0
  244. data/lib/new_relic/agent/instrumentation/sinatra/ignorer.rb +31 -37
  245. data/lib/new_relic/agent/instrumentation/sinatra/instrumentation.rb +125 -0
  246. data/lib/new_relic/agent/instrumentation/sinatra/prepend.rb +33 -0
  247. data/lib/new_relic/agent/instrumentation/sinatra/transaction_namer.rb +3 -3
  248. data/lib/new_relic/agent/instrumentation/sinatra.rb +35 -165
  249. data/lib/new_relic/agent/instrumentation/thread/chain.rb +24 -0
  250. data/lib/new_relic/agent/instrumentation/thread/instrumentation.rb +28 -0
  251. data/lib/new_relic/agent/instrumentation/thread/prepend.rb +22 -0
  252. data/lib/new_relic/agent/instrumentation/thread.rb +20 -0
  253. data/lib/new_relic/agent/instrumentation/tilt/chain.rb +24 -0
  254. data/lib/new_relic/agent/instrumentation/tilt/instrumentation.rb +41 -0
  255. data/lib/new_relic/agent/instrumentation/tilt/prepend.rb +13 -0
  256. data/lib/new_relic/agent/instrumentation/tilt.rb +25 -0
  257. data/lib/new_relic/agent/instrumentation/typhoeus/chain.rb +22 -0
  258. data/lib/new_relic/agent/instrumentation/typhoeus/instrumentation.rb +80 -0
  259. data/lib/new_relic/agent/instrumentation/typhoeus/prepend.rb +14 -0
  260. data/lib/new_relic/agent/instrumentation/typhoeus.rb +14 -76
  261. data/lib/new_relic/agent/instrumentation.rb +2 -2
  262. data/lib/new_relic/agent/internal_agent_error.rb +3 -3
  263. data/lib/new_relic/agent/javascript_instrumentor.rb +51 -45
  264. data/lib/new_relic/agent/linking_metadata.rb +44 -0
  265. data/lib/new_relic/agent/local_log_decorator.rb +37 -0
  266. data/lib/new_relic/agent/log_event_aggregator.rb +235 -0
  267. data/lib/new_relic/agent/log_once.rb +2 -2
  268. data/lib/new_relic/agent/log_priority.rb +20 -0
  269. data/lib/new_relic/agent/logging.rb +142 -0
  270. data/lib/new_relic/agent/memory_logger.rb +3 -3
  271. data/lib/new_relic/agent/messaging.rb +81 -164
  272. data/lib/new_relic/agent/method_tracer.rb +152 -145
  273. data/lib/new_relic/agent/method_tracer_helpers.rb +90 -13
  274. data/lib/new_relic/agent/monitors/cross_app_monitor.rb +117 -0
  275. data/lib/new_relic/agent/monitors/distributed_tracing_monitor.rb +28 -0
  276. data/lib/new_relic/agent/{inbound_request_monitor.rb → monitors/inbound_request_monitor.rb} +5 -6
  277. data/lib/new_relic/agent/{synthetics_monitor.rb → monitors/synthetics_monitor.rb} +9 -15
  278. data/lib/new_relic/agent/monitors.rb +26 -0
  279. data/lib/new_relic/agent/new_relic_service/encoders.rb +7 -7
  280. data/lib/new_relic/agent/new_relic_service/json_marshaller.rb +6 -7
  281. data/lib/new_relic/agent/new_relic_service/marshaller.rb +8 -29
  282. data/lib/new_relic/agent/new_relic_service/security_policy_settings.rb +5 -5
  283. data/lib/new_relic/agent/new_relic_service.rb +282 -166
  284. data/lib/new_relic/agent/noticeable_error.rb +19 -0
  285. data/lib/new_relic/agent/null_logger.rb +8 -4
  286. data/lib/new_relic/agent/obfuscator.rb +9 -11
  287. data/lib/new_relic/agent/parameter_filtering.rb +35 -8
  288. data/lib/new_relic/agent/payload_metric_mapping.rb +10 -11
  289. data/lib/new_relic/agent/pipe_channel_manager.rb +28 -18
  290. data/lib/new_relic/agent/pipe_service.rb +9 -6
  291. data/lib/new_relic/agent/prepend_supportability.rb +3 -3
  292. data/lib/new_relic/agent/priority_sampled_buffer.rb +16 -14
  293. data/lib/new_relic/agent/range_extensions.rb +9 -29
  294. data/lib/new_relic/agent/rules_engine/replacement_rule.rb +12 -12
  295. data/lib/new_relic/agent/rules_engine/segment_terms_rule.rb +13 -14
  296. data/lib/new_relic/agent/rules_engine.rb +6 -5
  297. data/lib/new_relic/agent/sampler.rb +4 -5
  298. data/lib/new_relic/agent/sampler_collection.rb +4 -5
  299. data/lib/new_relic/agent/samplers/cpu_sampler.rb +4 -3
  300. data/lib/new_relic/agent/samplers/delayed_job_sampler.rb +14 -11
  301. data/lib/new_relic/agent/samplers/memory_sampler.rb +26 -15
  302. data/lib/new_relic/agent/samplers/object_sampler.rb +2 -2
  303. data/lib/new_relic/agent/samplers/vm_sampler.rb +22 -20
  304. data/lib/new_relic/agent/span_event_aggregator.rb +14 -16
  305. data/lib/new_relic/agent/span_event_primitive.rb +118 -58
  306. data/lib/new_relic/agent/sql_sampler.rb +25 -25
  307. data/lib/new_relic/agent/stats.rb +79 -42
  308. data/lib/new_relic/agent/stats_engine/gc_profiler.rb +11 -13
  309. data/lib/new_relic/agent/stats_engine/stats_hash.rb +13 -14
  310. data/lib/new_relic/agent/stats_engine.rb +11 -11
  311. data/lib/new_relic/agent/synthetics_event_aggregator.rb +8 -9
  312. data/lib/new_relic/agent/system_info.rb +100 -66
  313. data/lib/new_relic/agent/threading/agent_thread.rb +20 -16
  314. data/lib/new_relic/agent/threading/backtrace_node.rb +13 -14
  315. data/lib/new_relic/agent/threading/backtrace_service.rb +18 -18
  316. data/lib/new_relic/agent/threading/thread_profile.rb +31 -45
  317. data/lib/new_relic/agent/timestamp_sampled_buffer.rb +2 -2
  318. data/lib/new_relic/agent/tracer.rb +513 -0
  319. data/lib/new_relic/agent/transaction/abstract_segment.rb +131 -41
  320. data/lib/new_relic/agent/transaction/datastore_segment.rb +22 -18
  321. data/lib/new_relic/agent/transaction/distributed_tracer.rb +184 -0
  322. data/lib/new_relic/agent/transaction/distributed_tracing.rb +72 -163
  323. data/lib/new_relic/agent/transaction/external_request_segment.rb +66 -63
  324. data/lib/new_relic/agent/transaction/message_broker_segment.rb +34 -46
  325. data/lib/new_relic/agent/transaction/request_attributes.rb +36 -36
  326. data/lib/new_relic/agent/transaction/segment.rb +46 -10
  327. data/lib/new_relic/agent/transaction/slowest_sample_buffer.rb +2 -4
  328. data/lib/new_relic/agent/transaction/synthetics_sample_buffer.rb +2 -2
  329. data/lib/new_relic/agent/transaction/trace.rb +21 -24
  330. data/lib/new_relic/agent/transaction/trace_builder.rb +11 -12
  331. data/lib/new_relic/agent/transaction/trace_context.rb +168 -0
  332. data/lib/new_relic/agent/transaction/trace_node.rb +31 -28
  333. data/lib/new_relic/agent/transaction/tracing.rb +15 -111
  334. data/lib/new_relic/agent/transaction/transaction_sample_buffer.rb +6 -6
  335. data/lib/new_relic/agent/transaction.rb +252 -259
  336. data/lib/new_relic/agent/transaction_error_primitive.rb +34 -37
  337. data/lib/new_relic/agent/transaction_event_aggregator.rb +13 -13
  338. data/lib/new_relic/agent/transaction_event_primitive.rb +44 -56
  339. data/lib/new_relic/agent/transaction_event_recorder.rb +17 -16
  340. data/lib/new_relic/agent/transaction_metrics.rb +11 -10
  341. data/lib/new_relic/agent/transaction_sampler.rb +7 -12
  342. data/lib/new_relic/agent/transaction_time_aggregator.rb +41 -26
  343. data/lib/new_relic/agent/utilization/aws.rb +34 -4
  344. data/lib/new_relic/agent/utilization/azure.rb +4 -4
  345. data/lib/new_relic/agent/utilization/gcp.rb +8 -8
  346. data/lib/new_relic/agent/utilization/pcf.rb +6 -5
  347. data/lib/new_relic/agent/utilization/vendor.rb +44 -29
  348. data/lib/new_relic/agent/utilization_data.rb +43 -6
  349. data/lib/new_relic/agent/vm/jruby_vm.rb +2 -2
  350. data/lib/new_relic/agent/vm/monotonic_gc_profiler.rb +3 -3
  351. data/lib/new_relic/agent/vm/mri_vm.rb +46 -19
  352. data/lib/new_relic/agent/vm/snapshot.rb +6 -6
  353. data/lib/new_relic/agent/vm.rb +2 -2
  354. data/lib/new_relic/agent/worker_loop.rb +11 -13
  355. data/lib/new_relic/agent.rb +151 -79
  356. data/lib/new_relic/cli/command.rb +21 -23
  357. data/lib/new_relic/cli/commands/deployments.rb +94 -45
  358. data/lib/new_relic/cli/commands/install.rb +24 -26
  359. data/lib/new_relic/coerce.rb +42 -15
  360. data/lib/new_relic/collection_helper.rb +51 -49
  361. data/lib/new_relic/constants.rb +39 -0
  362. data/lib/new_relic/control/class_methods.rb +11 -5
  363. data/lib/new_relic/control/frameworks/external.rb +3 -3
  364. data/lib/new_relic/control/frameworks/rails.rb +24 -18
  365. data/lib/new_relic/control/frameworks/rails3.rb +4 -5
  366. data/lib/new_relic/control/frameworks/rails4.rb +2 -2
  367. data/lib/new_relic/control/frameworks/rails_notifications.rb +14 -0
  368. data/lib/new_relic/control/frameworks/ruby.rb +4 -4
  369. data/lib/new_relic/control/frameworks/sinatra.rb +8 -2
  370. data/lib/new_relic/control/frameworks.rb +2 -2
  371. data/lib/new_relic/control/instance_methods.rb +33 -42
  372. data/lib/new_relic/control/instrumentation.rb +40 -12
  373. data/lib/new_relic/control/private_instance_methods.rb +48 -0
  374. data/lib/new_relic/control/server_methods.rb +4 -5
  375. data/lib/new_relic/control.rb +2 -3
  376. data/lib/new_relic/delayed_job_injection.rb +2 -2
  377. data/lib/new_relic/dependency_detection.rb +129 -18
  378. data/lib/new_relic/environment_report.rb +41 -35
  379. data/lib/new_relic/helper.rb +49 -8
  380. data/lib/new_relic/language_support.rb +30 -6
  381. data/lib/new_relic/latest_changes.rb +9 -8
  382. data/lib/new_relic/local_environment.rb +23 -27
  383. data/lib/new_relic/metric_data.rb +32 -27
  384. data/lib/new_relic/metric_spec.rb +9 -7
  385. data/lib/new_relic/noticed_error.rb +46 -33
  386. data/lib/new_relic/rack/agent_hooks.rb +2 -2
  387. data/lib/new_relic/rack/agent_middleware.rb +7 -5
  388. data/lib/new_relic/rack/browser_monitoring.rb +134 -117
  389. data/lib/new_relic/rack.rb +2 -2
  390. data/lib/new_relic/recipes/capistrano3.rb +4 -62
  391. data/lib/new_relic/recipes/capistrano_legacy.rb +24 -27
  392. data/lib/new_relic/recipes/helpers/send_deployment.rb +70 -0
  393. data/lib/new_relic/recipes.rb +2 -2
  394. data/lib/new_relic/supportability_helper.rb +21 -7
  395. data/lib/new_relic/traced_thread.rb +39 -0
  396. data/lib/new_relic/version.rb +7 -18
  397. data/lib/newrelic_rpm.rb +20 -33
  398. data/lib/sequel/extensions/{newrelic_instrumentation.rb → new_relic_instrumentation.rb} +16 -19
  399. data/lib/sequel/plugins/{newrelic_instrumentation.rb → new_relic_instrumentation.rb} +9 -15
  400. data/lib/tasks/all.rb +4 -4
  401. data/lib/tasks/config.rake +22 -118
  402. data/lib/tasks/coverage_report.rake +28 -0
  403. data/lib/tasks/helpers/config.html.erb +21 -0
  404. data/lib/tasks/helpers/format.rb +123 -0
  405. data/lib/tasks/helpers/matches.rb +12 -0
  406. data/lib/tasks/helpers/prompt.rb +24 -0
  407. data/lib/tasks/helpers/removers.rb +33 -0
  408. data/lib/tasks/install.rake +4 -0
  409. data/lib/tasks/instrumentation_generator/README.md +63 -0
  410. data/lib/tasks/instrumentation_generator/TODO.md +33 -0
  411. data/lib/tasks/instrumentation_generator/instrumentation.thor +121 -0
  412. data/lib/tasks/instrumentation_generator/templates/Envfile.tt +9 -0
  413. data/lib/tasks/instrumentation_generator/templates/chain.tt +22 -0
  414. data/lib/tasks/instrumentation_generator/templates/chain_method.tt +8 -0
  415. data/lib/tasks/instrumentation_generator/templates/dependency_detection.tt +29 -0
  416. data/lib/tasks/instrumentation_generator/templates/instrumentation.tt +13 -0
  417. data/lib/tasks/instrumentation_generator/templates/instrumentation_method.tt +3 -0
  418. data/lib/tasks/instrumentation_generator/templates/newrelic.yml.tt +19 -0
  419. data/lib/tasks/instrumentation_generator/templates/prepend.tt +13 -0
  420. data/lib/tasks/instrumentation_generator/templates/prepend_method.tt +3 -0
  421. data/lib/tasks/instrumentation_generator/templates/test.tt +15 -0
  422. data/lib/tasks/multiverse.rake +4 -0
  423. data/lib/tasks/multiverse.rb +12 -5
  424. data/lib/tasks/newrelic.rb +2 -2
  425. data/lib/tasks/tests.rake +14 -14
  426. data/newrelic.yml +672 -3
  427. data/newrelic_rpm.gemspec +40 -31
  428. data/recipes/newrelic.rb +3 -3
  429. data/test/agent_helper.rb +419 -98
  430. metadata +238 -127
  431. data/.travis.yml +0 -228
  432. data/bin/mongrel_rpm +0 -33
  433. data/cert/cacert.pem +0 -1177
  434. data/lib/new_relic/agent/commands/xray_session.rb +0 -55
  435. data/lib/new_relic/agent/commands/xray_session_collection.rb +0 -161
  436. data/lib/new_relic/agent/cross_app_monitor.rb +0 -110
  437. data/lib/new_relic/agent/datastores/mongo/obfuscator.rb +0 -44
  438. data/lib/new_relic/agent/datastores/mongo/statement_formatter.rb +0 -53
  439. data/lib/new_relic/agent/distributed_trace_monitor.rb +0 -41
  440. data/lib/new_relic/agent/distributed_trace_payload.rb +0 -246
  441. data/lib/new_relic/agent/http_clients/abstract_request.rb +0 -31
  442. data/lib/new_relic/agent/instrumentation/active_record_4.rb +0 -42
  443. data/lib/new_relic/agent/instrumentation/active_record_5.rb +0 -41
  444. data/lib/new_relic/agent/instrumentation/acts_as_solr.rb +0 -74
  445. data/lib/new_relic/agent/instrumentation/authlogic.rb +0 -25
  446. data/lib/new_relic/agent/instrumentation/data_mapper.rb +0 -202
  447. data/lib/new_relic/agent/instrumentation/evented_subscriber.rb +0 -104
  448. data/lib/new_relic/agent/instrumentation/excon/connection.rb +0 -46
  449. data/lib/new_relic/agent/instrumentation/http.rb +0 -46
  450. data/lib/new_relic/agent/instrumentation/merb/controller.rb +0 -44
  451. data/lib/new_relic/agent/instrumentation/merb/errors.rb +0 -33
  452. data/lib/new_relic/agent/instrumentation/net.rb +0 -50
  453. data/lib/new_relic/agent/instrumentation/rails/action_controller.rb +0 -125
  454. data/lib/new_relic/agent/instrumentation/rails/action_web_service.rb +0 -46
  455. data/lib/new_relic/agent/instrumentation/rails4/action_controller.rb +0 -32
  456. data/lib/new_relic/agent/instrumentation/rails4/action_view.rb +0 -27
  457. data/lib/new_relic/agent/instrumentation/rails5/action_cable.rb +0 -36
  458. data/lib/new_relic/agent/instrumentation/rails5/action_controller.rb +0 -33
  459. data/lib/new_relic/agent/instrumentation/rails5/action_view.rb +0 -27
  460. data/lib/new_relic/agent/instrumentation/rainbows_instrumentation.rb +0 -26
  461. data/lib/new_relic/agent/instrumentation/sunspot.rb +0 -33
  462. data/lib/new_relic/agent/supported_versions.rb +0 -275
  463. data/lib/new_relic/agent/transaction/attributes.rb +0 -154
  464. data/lib/new_relic/agent/transaction/xray_sample_buffer.rb +0 -64
  465. data/lib/new_relic/agent/transaction_state.rb +0 -186
  466. data/lib/new_relic/build.rb +0 -2
  467. data/lib/new_relic/control/frameworks/merb.rb +0 -29
  468. data/lib/new_relic/control/frameworks/rails5.rb +0 -14
  469. data/lib/new_relic/metrics.rb +0 -13
  470. data/lib/tasks/config.html.erb +0 -32
  471. data/lib/tasks/versions.html.erb +0 -28
  472. data/lib/tasks/versions.postface.html +0 -8
  473. data/lib/tasks/versions.preface.html +0 -9
  474. data/lib/tasks/versions.rake +0 -65
  475. data/lib/tasks/versions.txt.erb +0 -14
  476. /data/lib/tasks/{config.text.erb → helpers/config.text.erb} +0 -0
@@ -1,8 +1,14 @@
1
- # encoding: utf-8
2
1
  # This file is distributed under New Relic's license terms.
3
- # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
2
+ # See https://github.com/newrelic/newrelic-ruby-agent/blob/main/LICENSE for complete details.
3
+ # frozen_string_literal: true
4
4
 
5
- require 'new_relic/agent/distributed_trace_payload'
5
+ require_relative 'distributed_tracing/cross_app_payload'
6
+ require_relative 'distributed_tracing/cross_app_tracing'
7
+
8
+ require_relative 'distributed_tracing/distributed_trace_transport_type'
9
+ require_relative 'distributed_tracing/distributed_trace_payload'
10
+
11
+ require_relative 'distributed_tracing/trace_context'
6
12
 
7
13
  module NewRelic
8
14
  module Agent
@@ -14,54 +20,129 @@ module NewRelic
14
20
  #
15
21
  # @api public
16
22
  module DistributedTracing
23
+ extend NewRelic::SupportabilityHelper
17
24
  extend self
18
25
 
19
- # Create a payload object containing the current transaction's
20
- # tracing properties (e.g., duration, priority). You can use
21
- # this object to generate headers to inject into a network
22
- # request, so that the downstream service can participate in a
23
- # distributed trace.
26
+ # Adds the Distributed Trace headers so that the downstream service can participate in a
27
+ # distributed trace. This method should be called every time an outbound call is made
28
+ # since the header payload contains a timestamp.
29
+ #
30
+ # Distributed Tracing must be enabled to use this method.
31
+ #
32
+ # +insert_distributed_trace_headers+ always inserts W3C trace context headers and inserts
33
+ # New Relic distributed tracing header by default. New Relic headers may be suppressed by
34
+ # setting +exclude_new_relic_header+ to +true+ in your configuration file.
24
35
  #
25
- # @return [DistributedTracePayload] Payload for the current
26
- # transaction, or +nil+ if we
27
- # could not create the payload
36
+ # @param headers [Hash] Is a Hash to which the distributed trace headers
37
+ # will be inserted.
38
+ #
39
+ # @return {Transaction} The transaction the headers were inserted from,
40
+ # or +nil+ if headers were not inserted.
28
41
  #
29
42
  # @api public
30
- def create_distributed_trace_payload
31
- if transaction = Transaction.tl_current
32
- transaction.create_distributed_trace_payload
43
+ #
44
+ def insert_distributed_trace_headers(headers = {})
45
+ record_api_supportability_metric(:insert_distributed_trace_headers)
46
+
47
+ unless Agent.config[:'distributed_tracing.enabled']
48
+ NewRelic::Agent.logger.warn("Not configured to insert distributed trace headers")
49
+ return nil
33
50
  end
51
+
52
+ return unless valid_api_argument_class?(headers, "headers", Hash)
53
+
54
+ return unless transaction = Transaction.tl_current
55
+
56
+ transaction.distributed_tracer.insert_headers(headers)
57
+ transaction
34
58
  rescue => e
35
- NewRelic::Agent.logger.error 'error during create_distributed_trace_payload', e
59
+ NewRelic::Agent.logger.error('error during insert_distributed_trace_headers', e)
36
60
  nil
37
61
  end
38
62
 
39
- # Decode a JSON string containing distributed trace properties
40
- # (e.g., calling application, priority) and apply them to the
41
- # current transaction. You can use it to receive distributed
42
- # tracing information protocols the agent does not already
43
- # support.
63
+ # Accepts distributed tracing headers from any source that has been packaged
64
+ # as a Ruby Hash, thereby allowing the user to manually inject distributed
65
+ # tracing headers. It is optimized to process +HTTP_TRACEPARENT+, +HTTP_TRACESTATE+,
66
+ # and +HTTP_NEWRELIC+ as the given Hash keys. which is the most common scenario
67
+ # from Rack middleware in most Ruby applications. However, the Hash keys are
68
+ # case-insensitive and the "HTTP_" prefixes may also be omitted.
69
+ #
70
+ # Calling this method is not necessary in a typical HTTP trace as
71
+ # distributed tracing is already handled by the agent.
72
+ #
73
+ # When used, invoke this method as early as possible in a transaction's life-cycle
74
+ # as calling after the headers are already created will have no effect.
75
+ #
76
+ # This method accepts both W3C trace context and New Relic distributed tracing headers.
77
+ # When both are present, only the W3C headers are utilized. When W3C trace context
78
+ # headers are present, New Relic headers are ignored regardless if W3C trace context
79
+ # headers are valid and parsable.
80
+ #
81
+ # @param headers [Hash] Incoming distributed trace headers as a Ruby
82
+ # Hash object. Hash keys are expected to be one of
83
+ # +TRACEPARENT+, +TRACESTATE+, +NEWRELIC+ and are
84
+ # case-insensitive, with or without "HTTP_" prefixes.
44
85
  #
45
- # This method will fail if you call it after calling
46
- # {#create_distributed_trace_payload}.
86
+ # either as a JSON string or as a
87
+ # header-friendly string returned from
88
+ # {DistributedTracePayload#http_safe}
47
89
  #
48
- # @param payload [String] Incoming distributed trace payload,
49
- # either as a JSON string or as a
50
- # header-friendly string returned from
51
- # {DistributedTracePayload#http_safe}
90
+ # @param transport_Type [String] May be one of: +HTTP+, +HTTPS+, +Kafka+, +JMS+,
91
+ # +IronMQ+, +AMQP+, +Queue+, +Other+. Values are
92
+ # case sensitive. All other values result in +Unknown+
52
93
  #
53
- # @return nil
94
+ # @return {Transaction} if successful, +nil+ otherwise
54
95
  #
55
96
  # @api public
56
- def accept_distributed_trace_payload payload
57
- if transaction = Transaction.tl_current
58
- transaction.accept_distributed_trace_payload(payload)
97
+ #
98
+ def accept_distributed_trace_headers(headers, transport_type = NewRelic::HTTP)
99
+ record_api_supportability_metric(:accept_distributed_trace_headers)
100
+
101
+ unless Agent.config[:'distributed_tracing.enabled']
102
+ NewRelic::Agent.logger.warn("Not configured to accept distributed trace headers")
103
+ return nil
59
104
  end
60
- nil
105
+
106
+ return unless valid_api_argument_class?(headers, "headers", Hash)
107
+ return unless valid_api_argument_class?(transport_type, "transport_type", String)
108
+
109
+ return unless transaction = Transaction.tl_current
110
+
111
+ # assume we have Rack conforming keys when transport_type is HTTP(S)
112
+ # otherwise, fish for key/value pairs regardless of prefix and case-sensitivity.
113
+ hdr = if transport_type.start_with?(NewRelic::HTTP)
114
+ headers
115
+ else
116
+ # start with the most common case first
117
+ hdr = {
118
+ NewRelic::HTTP_TRACEPARENT_KEY => headers[NewRelic::TRACEPARENT_KEY],
119
+ NewRelic::HTTP_TRACESTATE_KEY => headers[NewRelic::TRACESTATE_KEY],
120
+ NewRelic::HTTP_NEWRELIC_KEY => headers[NewRelic::NEWRELIC_KEY]
121
+ }
122
+
123
+ # when not found, search for any casing for trace context headers, ignoring potential prefixes
124
+ hdr[NewRelic::HTTP_TRACEPARENT_KEY] ||= variant_key_value(headers, NewRelic::TRACEPARENT_KEY)
125
+ hdr[NewRelic::HTTP_TRACESTATE_KEY] ||= variant_key_value(headers, NewRelic::TRACESTATE_KEY)
126
+ hdr[NewRelic::HTTP_NEWRELIC_KEY] ||= variant_key_value(headers, NewRelic::CANDIDATE_NEWRELIC_KEYS)
127
+ hdr
128
+ end
129
+
130
+ transaction.distributed_tracer.accept_incoming_request(hdr, transport_type)
131
+ transaction
61
132
  rescue => e
62
- NewRelic::Agent.logger.error 'error during accept_distributed_trace_payload', e
133
+ NewRelic::Agent.logger.error('error during accept_distributed_trace_headers', e)
63
134
  nil
64
135
  end
136
+
137
+ private
138
+
139
+ def has_variant_key?(key, variants)
140
+ key.to_s.downcase.end_with?(*Array(variants))
141
+ end
142
+
143
+ def variant_key_value(headers, variants)
144
+ (headers.detect { |k, v| has_variant_key?(k, variants) } || NewRelic::EMPTY_ARRAY)[1]
145
+ end
65
146
  end
66
147
  end
67
148
  end
@@ -1,6 +1,6 @@
1
- # encoding: utf-8
2
1
  # This file is distributed under New Relic's license terms.
3
- # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
2
+ # See https://github.com/newrelic/newrelic-ruby-agent/blob/main/LICENSE for complete details.
3
+ # frozen_string_literal: true
4
4
 
5
5
  # This module was extracted from NewRelic::JSONWrapper
6
6
 
@@ -19,12 +19,14 @@ module NewRelic
19
19
  normalize_string(object.to_s)
20
20
  when Array
21
21
  return object if object.empty?
22
+
22
23
  object.map { |x| normalize_object(x) }
23
24
  when Hash
24
25
  return object if object.empty?
26
+
25
27
  hash = {}
26
28
  object.each_pair do |k, v|
27
- k = normalize_string(k) if k.is_a?(String)
29
+ k = normalize_string(k) if k.is_a?(String)
28
30
  k = normalize_string(k.to_s) if k.is_a?(Symbol)
29
31
  hash[k] = normalize_object(v)
30
32
  end
@@ -1,6 +1,7 @@
1
- # encoding: utf-8
2
1
  # This file is distributed under New Relic's license terms.
3
- # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
2
+ # See https://github.com/newrelic/newrelic-ruby-agent/blob/main/LICENSE for complete details.
3
+ # frozen_string_literal: true
4
+
4
5
  require 'new_relic/agent/error_trace_aggregator'
5
6
  require 'new_relic/agent/error_event_aggregator'
6
7
 
@@ -18,28 +19,22 @@ module NewRelic
18
19
  attr_reader :error_trace_aggregator, :error_event_aggregator
19
20
 
20
21
  # Returns a new error collector
21
- def initialize
22
+ def initialize(events)
22
23
  @error_trace_aggregator = ErrorTraceAggregator.new(MAX_ERROR_QUEUE_LENGTH)
23
- @error_event_aggregator = ErrorEventAggregator.new
24
-
25
- # lookup of exception class names to ignore. Hash for fast access
26
- @ignore = {}
24
+ @error_event_aggregator = ErrorEventAggregator.new(events)
27
25
 
28
- initialize_ignored_errors(Agent.config[:'error_collector.ignore_errors'])
26
+ @error_filter = NewRelic::Agent::ErrorFilter.new
29
27
 
30
- Agent.config.register_callback(:'error_collector.ignore_errors') do |ignore_errors|
31
- initialize_ignored_errors(ignore_errors)
28
+ %w[
29
+ ignore_classes ignore_messages ignore_status_codes
30
+ expected_classes expected_messages expected_status_codes
31
+ ].each do |w|
32
+ Agent.config.register_callback(:"error_collector.#{w}") do |value|
33
+ @error_filter.load_from_config(w, value)
34
+ end
32
35
  end
33
36
  end
34
37
 
35
-
36
- def initialize_ignored_errors(ignore_errors)
37
- @ignore.clear
38
- ignore_errors = ignore_errors.split(",") if ignore_errors.is_a? String
39
- ignore_errors.each { |error| error.strip! }
40
- ignore(ignore_errors)
41
- end
42
-
43
38
  def enabled?
44
39
  error_trace_aggregator.enabled? || error_event_aggregator.enabled?
45
40
  end
@@ -68,39 +63,48 @@ module NewRelic
68
63
  if block
69
64
  define_method(:ignore_filter_proc, &block)
70
65
  elsif method_defined?(:ignore_filter_proc)
71
- remove_method :ignore_filter_proc
66
+ remove_method(:ignore_filter_proc)
72
67
  end
73
68
  @ignore_filter
74
69
  end
75
70
 
76
71
  def self.ignore_error_filter
77
- @ignore_filter
72
+ defined?(@ignore_filter) ? @ignore_filter : nil
78
73
  end
79
74
 
80
- # errors is an array of Exception Class Names
81
- #
82
75
  def ignore(errors)
83
- errors.each do |error|
84
- @ignore[error] = true
85
- ::NewRelic::Agent.logger.debug("Ignoring errors of type '#{error}'")
86
- end
76
+ @error_filter.ignore(errors)
77
+ end
78
+
79
+ def ignore?(ex, status_code = nil)
80
+ @error_filter.ignore?(ex, status_code)
81
+ end
82
+
83
+ def expect(errors)
84
+ @error_filter.expect(errors)
85
+ end
86
+
87
+ def expected?(ex, status_code = nil)
88
+ @error_filter.expected?(ex, status_code)
89
+ end
90
+
91
+ def load_error_filters
92
+ @error_filter.load_all
93
+ end
94
+
95
+ def reset_error_filters
96
+ @error_filter.reset
87
97
  end
88
98
 
89
99
  # Checks the provided error against the error filter, if there
90
100
  # is an error filter
91
- def filtered_by_error_filter?(error)
101
+ def ignored_by_filter_proc?(error)
92
102
  respond_to?(:ignore_filter_proc) && !ignore_filter_proc(error)
93
103
  end
94
104
 
95
- # Checks the array of error names and the error filter against
96
- # the provided error
97
- def filtered_error?(error)
98
- @ignore[error.class.name] || filtered_by_error_filter?(error)
99
- end
100
-
101
105
  # an error is ignored if it is nil or if it is filtered
102
- def error_is_ignored?(error)
103
- error && filtered_error?(error)
106
+ def error_is_ignored?(error, status_code = nil)
107
+ error && (@error_filter.ignore?(error, status_code) || ignored_by_filter_proc?(error))
104
108
  rescue => e
105
109
  NewRelic::Agent.logger.error("Error '#{error}' will NOT be ignored. Exception '#{e}' while determining whether to ignore or not.", e)
106
110
  false
@@ -117,14 +121,25 @@ module NewRelic
117
121
  NewRelic::LanguageSupport.jruby? && exception.respond_to?(:java_class)
118
122
  end
119
123
 
120
- def exception_tagged?(exception)
124
+ def exception_tagged_with?(ivar, exception)
121
125
  return false if exception_is_java_object?(exception)
122
- exception.instance_variable_defined?(EXCEPTION_TAG_IVAR)
126
+
127
+ exception.instance_variable_defined?(ivar)
128
+ end
129
+
130
+ def tag_exception_using(ivar, exception)
131
+ return if exception_is_java_object?(exception) || exception.frozen?
132
+
133
+ begin
134
+ exception.instance_variable_set(ivar, true)
135
+ rescue => e
136
+ NewRelic::Agent.logger.warn("Failed to tag exception: #{exception}: ", e)
137
+ end
123
138
  end
124
139
 
125
140
  def tag_exception(exception)
126
- return if exception_is_java_object?(exception)
127
- return if exception.frozen?
141
+ return if exception_is_java_object?(exception) || exception.frozen?
142
+
128
143
  begin
129
144
  exception.instance_variable_set(EXCEPTION_TAG_IVAR, true)
130
145
  rescue => e
@@ -154,10 +169,10 @@ module NewRelic
154
169
  end
155
170
 
156
171
  # Increments a statistic that tracks total error rate
157
- def increment_error_count!(state, exception, options={})
172
+ def increment_error_count!(state, exception, options = {})
158
173
  txn = state.current_transaction
159
174
 
160
- metric_names = aggregated_metric_names(txn)
175
+ metric_names = aggregated_metric_names(txn)
161
176
  blamed_metric = blamed_metric_name(txn, options)
162
177
  metric_names << blamed_metric if blamed_metric
163
178
 
@@ -167,11 +182,18 @@ module NewRelic
167
182
  end
168
183
  end
169
184
 
170
- def skip_notice_error?(exception)
185
+ def increment_expected_error_count!(state, exception)
186
+ stats_engine = NewRelic::Agent.agent.stats_engine
187
+ stats_engine.record_unscoped_metrics(state, ['ErrorsExpected/all']) do |stats|
188
+ stats.increment_count
189
+ end
190
+ end
191
+
192
+ def skip_notice_error?(exception, status_code = nil)
171
193
  disabled? ||
172
- error_is_ignored?(exception) ||
173
194
  exception.nil? ||
174
- exception_tagged?(exception)
195
+ exception_tagged_with?(EXCEPTION_TAG_IVAR, exception) ||
196
+ error_is_ignored?(exception, status_code)
175
197
  end
176
198
 
177
199
  # calls a method on an object, if it responds to it - used for
@@ -184,36 +206,52 @@ module NewRelic
184
206
  # extracts a stack trace from the exception for debugging purposes
185
207
  def extract_stack_trace(exception)
186
208
  actual_exception = if defined?(Rails::VERSION::MAJOR) && Rails::VERSION::MAJOR < 5
187
- sense_method(exception, :original_exception) || exception
188
- else
189
- exception
190
- end
209
+ sense_method(exception, :original_exception) || exception
210
+ else
211
+ exception
212
+ end
191
213
  sense_method(actual_exception, :backtrace) || '<no stack trace>'
192
214
  end
193
215
 
194
- # See NewRelic::Agent.notice_error for options and commentary
195
- def notice_error(exception, options={}) #THREAD_LOCAL_ACCESS
216
+ def notice_segment_error(segment, exception, options = {})
196
217
  return if skip_notice_error?(exception)
197
218
 
198
- tag_exception(exception)
219
+ segment.set_noticed_error(create_noticed_error(exception, options))
220
+ exception
221
+ rescue => e
222
+ ::NewRelic::Agent.logger.warn("Failure when capturing segment error '#{exception}':", e)
223
+ nil
224
+ end
199
225
 
200
- state = ::NewRelic::Agent::TransactionState.tl_get
226
+ # See NewRelic::Agent.notice_error for options and commentary
227
+ def notice_error(exception, options = {}, span_id = nil)
228
+ state = ::NewRelic::Agent::Tracer.state
229
+ transaction = state.current_transaction
230
+ status_code = transaction ? transaction.http_response_code : nil
231
+
232
+ return if skip_notice_error?(exception, status_code)
233
+
234
+ tag_exception(exception)
201
235
 
202
- unless options[:expected]
236
+ if options[:expected] || @error_filter.expected?(exception, status_code)
237
+ increment_expected_error_count!(state, exception)
238
+ else
203
239
  increment_error_count!(state, exception, options)
204
240
  end
205
241
 
206
242
  noticed_error = create_noticed_error(exception, options)
207
243
  error_trace_aggregator.add_to_error_queue(noticed_error)
208
- payload = state.current_transaction ? state.current_transaction.payload : nil
209
- error_event_aggregator.record(noticed_error, payload)
244
+ transaction = state.current_transaction
245
+ payload = transaction ? transaction.payload : nil
246
+ span_id ||= transaction && transaction.current_segment ? transaction.current_segment.guid : nil
247
+ error_event_aggregator.record(noticed_error, payload, span_id)
210
248
  exception
211
249
  rescue => e
212
250
  ::NewRelic::Agent.logger.warn("Failure when capturing error '#{exception}':", e)
213
251
  nil
214
252
  end
215
253
 
216
- def truncate_trace(trace, keep_frames=nil)
254
+ def truncate_trace(trace, keep_frames = nil)
217
255
  keep_frames ||= Agent.config[:'error_collector.max_backtrace_frames']
218
256
  return trace if !keep_frames || trace.length < keep_frames || trace.length == 0
219
257
 
@@ -227,21 +265,19 @@ module NewRelic
227
265
  truncated_trace
228
266
  end
229
267
 
230
- EMPTY_STRING = ''.freeze
231
-
232
268
  def create_noticed_error(exception, options)
233
- error_metric = options.delete(:metric) || EMPTY_STRING
269
+ error_metric = options.delete(:metric) || NewRelic::EMPTY_STR
234
270
 
235
271
  noticed_error = NewRelic::NoticedError.new(error_metric, exception)
236
- noticed_error.request_uri = options.delete(:uri) || EMPTY_STRING
272
+ noticed_error.request_uri = options.delete(:uri) || NewRelic::EMPTY_STR
237
273
  noticed_error.request_port = options.delete(:port)
238
- noticed_error.attributes = options.delete(:attributes)
274
+ noticed_error.attributes = options.delete(:attributes)
239
275
 
240
- noticed_error.file_name = sense_method(exception, :file_name)
276
+ noticed_error.file_name = sense_method(exception, :file_name)
241
277
  noticed_error.line_number = sense_method(exception, :line_number)
242
278
  noticed_error.stack_trace = truncate_trace(extract_stack_trace(exception))
243
279
 
244
- noticed_error.expected = !! options.delete(:expected)
280
+ noticed_error.expected = !!options.delete(:expected) || expected?(exception)
245
281
 
246
282
  noticed_error.attributes_from_notice_error = options.delete(:custom_params) || {}
247
283
 
@@ -1,7 +1,7 @@
1
1
  # -*- ruby -*-
2
- # encoding: utf-8
3
2
  # This file is distributed under New Relic's license terms.
4
- # See https://github.com/newrelic/rpm/blob/master/LICENSE for complete details.
3
+ # See https://github.com/newrelic/newrelic-ruby-agent/blob/main/LICENSE for complete details.
4
+ # frozen_string_literal: true
5
5
 
6
6
  require 'new_relic/agent/event_aggregator'
7
7
  require 'new_relic/agent/transaction_error_primitive'
@@ -10,20 +10,22 @@ require 'new_relic/agent/priority_sampled_buffer'
10
10
  module NewRelic
11
11
  module Agent
12
12
  class ErrorEventAggregator < EventAggregator
13
+ include NewRelic::Coerce
13
14
 
14
15
  named :ErrorEventAggregator
15
16
  capacity_key :'error_collector.max_event_samples_stored'
16
- enabled_key :'error_collector.capture_events'
17
+ enabled_keys :'error_collector.enabled',
18
+ :'error_collector.capture_events'
17
19
  buffer_class PrioritySampledBuffer
18
20
 
19
- def record noticed_error, transaction_payload = nil
21
+ def record(noticed_error, transaction_payload = nil, span_id = nil)
20
22
  return unless enabled?
21
23
 
22
- priority = (transaction_payload && transaction_payload[:priority]) || rand.round(6)
24
+ priority = float!((transaction_payload && transaction_payload[:priority]) || rand)
23
25
 
24
26
  @lock.synchronize do
25
27
  @buffer.append(priority: priority) do
26
- create_event(noticed_error, transaction_payload)
28
+ create_event(noticed_error, transaction_payload, span_id)
27
29
  end
28
30
  notify_if_full
29
31
  end
@@ -31,8 +33,8 @@ module NewRelic
31
33
 
32
34
  private
33
35
 
34
- def create_event noticed_error, transaction_payload
35
- TransactionErrorPrimitive.create noticed_error, transaction_payload
36
+ def create_event(noticed_error, transaction_payload, span_id)
37
+ TransactionErrorPrimitive.create(noticed_error, transaction_payload, span_id)
36
38
  end
37
39
  end
38
40
  end