newrelic_rpm 9.1.0 → 9.21.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 (360) hide show
  1. checksums.yaml +4 -4
  2. data/.build_ignore +27 -0
  3. data/CHANGELOG.md +841 -7
  4. data/CONTRIBUTING.md +2 -9
  5. data/README.md +25 -22
  6. data/Rakefile +2 -2
  7. data/bin/newrelic +3 -9
  8. data/bin/newrelic_rpm +15 -0
  9. data/init.rb +2 -2
  10. data/lib/boot/strap.rb +102 -0
  11. data/lib/new_relic/agent/agent.rb +11 -2
  12. data/lib/new_relic/agent/agent_helpers/connect.rb +13 -8
  13. data/lib/new_relic/agent/agent_helpers/harvest.rb +3 -0
  14. data/lib/new_relic/agent/agent_helpers/shutdown.rb +4 -1
  15. data/lib/new_relic/agent/agent_helpers/special_startup.rb +1 -1
  16. data/lib/new_relic/agent/agent_helpers/start_worker_thread.rb +4 -3
  17. data/lib/new_relic/agent/agent_helpers/startup.rb +11 -3
  18. data/lib/new_relic/agent/agent_logger.rb +3 -1
  19. data/lib/new_relic/agent/attribute_filter.rb +3 -3
  20. data/lib/new_relic/agent/attribute_pre_filtering.rb +109 -0
  21. data/lib/new_relic/agent/aws.rb +68 -0
  22. data/lib/new_relic/agent/configuration/default_source.rb +918 -166
  23. data/lib/new_relic/agent/configuration/environment_source.rb +15 -3
  24. data/lib/new_relic/agent/configuration/high_security_source.rb +1 -0
  25. data/lib/new_relic/agent/configuration/manager.rb +72 -11
  26. data/lib/new_relic/agent/configuration/security_policy_source.rb +11 -0
  27. data/lib/new_relic/agent/configuration/yaml_source.rb +22 -2
  28. data/lib/new_relic/agent/connect/request_builder.rb +1 -1
  29. data/lib/new_relic/agent/custom_event_aggregator.rb +27 -1
  30. data/lib/new_relic/agent/database/obfuscation_helpers.rb +11 -11
  31. data/lib/new_relic/agent/database/obfuscator.rb +1 -0
  32. data/lib/new_relic/agent/database.rb +41 -1
  33. data/lib/new_relic/agent/database_adapter.rb +1 -1
  34. data/lib/new_relic/agent/datastores/mongo/metric_translator.rb +1 -1
  35. data/lib/new_relic/agent/datastores/redis.rb +1 -1
  36. data/lib/new_relic/agent/distributed_tracing/cross_app_tracing.rb +1 -1
  37. data/lib/new_relic/agent/distributed_tracing/distributed_trace_payload.rb +4 -8
  38. data/lib/new_relic/agent/distributed_tracing.rb +5 -3
  39. data/lib/new_relic/agent/error_collector.rb +40 -11
  40. data/lib/new_relic/agent/event_loop.rb +1 -1
  41. data/lib/new_relic/agent/external.rb +2 -0
  42. data/lib/new_relic/agent/harvester.rb +1 -1
  43. data/lib/new_relic/agent/health_check.rb +136 -0
  44. data/lib/new_relic/agent/http_clients/abstract.rb +4 -0
  45. data/lib/new_relic/agent/http_clients/async_http_wrappers.rb +80 -0
  46. data/lib/new_relic/agent/http_clients/curb_wrappers.rb +1 -3
  47. data/lib/new_relic/agent/http_clients/ethon_wrappers.rb +109 -0
  48. data/lib/new_relic/agent/http_clients/excon_wrappers.rb +0 -3
  49. data/lib/new_relic/agent/http_clients/http_rb_wrappers.rb +1 -3
  50. data/lib/new_relic/agent/http_clients/httpclient_wrappers.rb +0 -3
  51. data/lib/new_relic/agent/http_clients/httpx_wrappers.rb +91 -0
  52. data/lib/new_relic/agent/http_clients/net_http_wrappers.rb +1 -4
  53. data/lib/new_relic/agent/http_clients/typhoeus_wrappers.rb +0 -3
  54. data/lib/new_relic/agent/http_clients/uri_util.rb +1 -1
  55. data/lib/new_relic/agent/instrumentation/action_controller_other_subscriber.rb +1 -1
  56. data/lib/new_relic/agent/instrumentation/action_dispatch.rb +1 -1
  57. data/lib/new_relic/agent/instrumentation/action_dispatch_subscriber.rb +1 -1
  58. data/lib/new_relic/agent/instrumentation/action_mailbox.rb +1 -1
  59. data/lib/new_relic/agent/instrumentation/action_mailer.rb +1 -1
  60. data/lib/new_relic/agent/instrumentation/active_job.rb +1 -1
  61. data/lib/new_relic/agent/instrumentation/active_job_subscriber.rb +6 -2
  62. data/lib/new_relic/agent/instrumentation/active_merchant.rb +3 -16
  63. data/lib/new_relic/agent/instrumentation/active_record.rb +8 -13
  64. data/lib/new_relic/agent/instrumentation/active_record_helper.rb +8 -5
  65. data/lib/new_relic/agent/instrumentation/active_record_notifications.rb +13 -10
  66. data/lib/new_relic/agent/instrumentation/active_record_prepend.rb +2 -2
  67. data/lib/new_relic/agent/instrumentation/active_record_subscriber.rb +9 -16
  68. data/lib/new_relic/agent/instrumentation/active_support_broadcast_logger/chain.rb +69 -0
  69. data/lib/new_relic/agent/instrumentation/active_support_broadcast_logger/instrumentation.rb +17 -0
  70. data/lib/new_relic/agent/instrumentation/active_support_broadcast_logger/prepend.rb +37 -0
  71. data/lib/new_relic/agent/instrumentation/active_support_broadcast_logger.rb +21 -0
  72. data/lib/new_relic/agent/instrumentation/active_support_logger/instrumentation.rb +4 -0
  73. data/lib/new_relic/agent/instrumentation/active_support_logger.rb +3 -3
  74. data/lib/new_relic/agent/instrumentation/async_http/chain.rb +23 -0
  75. data/lib/new_relic/agent/instrumentation/async_http/instrumentation.rb +37 -0
  76. data/lib/new_relic/agent/instrumentation/async_http/prepend.rb +15 -0
  77. data/lib/new_relic/agent/instrumentation/async_http.rb +27 -0
  78. data/lib/new_relic/agent/instrumentation/aws_sdk_firehose/chain.rb +21 -0
  79. data/lib/new_relic/agent/instrumentation/aws_sdk_firehose/instrumentation.rb +66 -0
  80. data/lib/new_relic/agent/instrumentation/aws_sdk_firehose/prepend.rb +15 -0
  81. data/lib/new_relic/agent/instrumentation/aws_sdk_firehose.rb +22 -0
  82. data/lib/new_relic/agent/instrumentation/aws_sdk_kinesis/chain.rb +21 -0
  83. data/lib/new_relic/agent/instrumentation/aws_sdk_kinesis/instrumentation.rb +91 -0
  84. data/lib/new_relic/agent/instrumentation/aws_sdk_kinesis/prepend.rb +15 -0
  85. data/lib/new_relic/agent/instrumentation/aws_sdk_kinesis.rb +22 -0
  86. data/lib/new_relic/agent/instrumentation/aws_sdk_lambda/chain.rb +33 -0
  87. data/lib/new_relic/agent/instrumentation/aws_sdk_lambda/instrumentation.rb +93 -0
  88. data/lib/new_relic/agent/instrumentation/aws_sdk_lambda/prepend.rb +23 -0
  89. data/lib/new_relic/agent/instrumentation/aws_sdk_lambda.rb +23 -0
  90. data/lib/new_relic/agent/instrumentation/aws_sqs/chain.rb +37 -0
  91. data/lib/new_relic/agent/instrumentation/aws_sqs/instrumentation.rb +67 -0
  92. data/lib/new_relic/agent/instrumentation/aws_sqs/prepend.rb +21 -0
  93. data/lib/new_relic/agent/instrumentation/aws_sqs.rb +23 -0
  94. data/lib/new_relic/agent/instrumentation/bunny/chain.rb +1 -1
  95. data/lib/new_relic/agent/instrumentation/bunny/instrumentation.rb +23 -0
  96. data/lib/new_relic/agent/instrumentation/bunny.rb +4 -5
  97. data/lib/new_relic/agent/instrumentation/concurrent_ruby/chain.rb +1 -1
  98. data/lib/new_relic/agent/instrumentation/concurrent_ruby/instrumentation.rb +3 -4
  99. data/lib/new_relic/agent/instrumentation/concurrent_ruby/prepend.rb +1 -1
  100. data/lib/new_relic/agent/instrumentation/concurrent_ruby.rb +2 -3
  101. data/lib/new_relic/agent/instrumentation/controller_instrumentation.rb +5 -2
  102. data/lib/new_relic/agent/instrumentation/curb/instrumentation.rb +4 -0
  103. data/lib/new_relic/agent/instrumentation/curb.rb +4 -5
  104. data/lib/new_relic/agent/instrumentation/delayed_job/chain.rb +1 -0
  105. data/lib/new_relic/agent/instrumentation/delayed_job/instrumentation.rb +3 -0
  106. data/lib/new_relic/agent/instrumentation/delayed_job_instrumentation.rb +0 -23
  107. data/lib/new_relic/agent/instrumentation/dynamodb/chain.rb +27 -0
  108. data/lib/new_relic/agent/instrumentation/dynamodb/instrumentation.rb +64 -0
  109. data/lib/new_relic/agent/instrumentation/dynamodb/prepend.rb +19 -0
  110. data/lib/new_relic/agent/instrumentation/dynamodb.rb +23 -0
  111. data/lib/new_relic/agent/instrumentation/elasticsearch/chain.rb +2 -3
  112. data/lib/new_relic/agent/instrumentation/elasticsearch/instrumentation.rb +65 -10
  113. data/lib/new_relic/agent/instrumentation/elasticsearch.rb +2 -4
  114. data/lib/new_relic/agent/instrumentation/ethon/chain.rb +39 -0
  115. data/lib/new_relic/agent/instrumentation/ethon/instrumentation.rb +105 -0
  116. data/lib/new_relic/agent/instrumentation/ethon/prepend.rb +35 -0
  117. data/lib/new_relic/agent/instrumentation/ethon.rb +35 -0
  118. data/lib/new_relic/agent/instrumentation/excon/middleware.rb +3 -0
  119. data/lib/new_relic/agent/instrumentation/excon.rb +1 -17
  120. data/lib/new_relic/agent/instrumentation/fiber/chain.rb +11 -4
  121. data/lib/new_relic/agent/instrumentation/fiber/instrumentation.rb +2 -6
  122. data/lib/new_relic/agent/instrumentation/fiber/prepend.rb +10 -3
  123. data/lib/new_relic/agent/instrumentation/fiber.rb +1 -3
  124. data/lib/new_relic/agent/instrumentation/grape/instrumentation.rb +4 -3
  125. data/lib/new_relic/agent/instrumentation/grape.rb +1 -1
  126. data/lib/new_relic/agent/instrumentation/grpc/client/chain.rb +1 -1
  127. data/lib/new_relic/agent/instrumentation/grpc/client/instrumentation.rb +5 -2
  128. data/lib/new_relic/agent/instrumentation/grpc/client/prepend.rb +1 -1
  129. data/lib/new_relic/agent/instrumentation/grpc/client/request_wrapper.rb +1 -1
  130. data/lib/new_relic/agent/instrumentation/grpc/server/instrumentation.rb +5 -1
  131. data/lib/new_relic/agent/instrumentation/grpc_client.rb +2 -2
  132. data/lib/new_relic/agent/instrumentation/grpc_server.rb +2 -2
  133. data/lib/new_relic/agent/instrumentation/httpclient/instrumentation.rb +4 -0
  134. data/lib/new_relic/agent/instrumentation/httpclient.rb +1 -5
  135. data/lib/new_relic/agent/instrumentation/httprb/instrumentation.rb +4 -0
  136. data/lib/new_relic/agent/instrumentation/httprb.rb +0 -1
  137. data/lib/new_relic/agent/instrumentation/httpx/chain.rb +20 -0
  138. data/lib/new_relic/agent/instrumentation/httpx/instrumentation.rb +51 -0
  139. data/lib/new_relic/agent/instrumentation/httpx/prepend.rb +15 -0
  140. data/lib/new_relic/agent/instrumentation/httpx.rb +23 -0
  141. data/lib/new_relic/agent/instrumentation/logger/instrumentation.rb +3 -0
  142. data/lib/new_relic/agent/instrumentation/logger.rb +1 -3
  143. data/lib/new_relic/agent/instrumentation/logstasher/chain.rb +21 -0
  144. data/lib/new_relic/agent/instrumentation/logstasher/instrumentation.rb +24 -0
  145. data/lib/new_relic/agent/instrumentation/logstasher/prepend.rb +13 -0
  146. data/lib/new_relic/agent/instrumentation/logstasher.rb +25 -0
  147. data/lib/new_relic/agent/instrumentation/memcache/dalli.rb +4 -2
  148. data/lib/new_relic/agent/instrumentation/memcache/helper.rb +2 -2
  149. data/lib/new_relic/agent/instrumentation/memcache/instrumentation.rb +13 -4
  150. data/lib/new_relic/agent/instrumentation/memcache/prepend.rb +4 -2
  151. data/lib/new_relic/agent/instrumentation/memcache.rb +4 -5
  152. data/lib/new_relic/agent/instrumentation/mongodb_command_subscriber.rb +3 -5
  153. data/lib/new_relic/agent/instrumentation/net_http/instrumentation.rb +13 -3
  154. data/lib/new_relic/agent/instrumentation/net_http.rb +2 -1
  155. data/lib/new_relic/agent/instrumentation/notifications_subscriber.rb +4 -2
  156. data/lib/new_relic/agent/instrumentation/opensearch/chain.rb +21 -0
  157. data/lib/new_relic/agent/instrumentation/opensearch/instrumentation.rb +66 -0
  158. data/lib/new_relic/agent/instrumentation/opensearch/prepend.rb +13 -0
  159. data/lib/new_relic/agent/instrumentation/opensearch.rb +23 -0
  160. data/lib/new_relic/agent/instrumentation/padrino/instrumentation.rb +4 -0
  161. data/lib/new_relic/agent/instrumentation/padrino.rb +3 -3
  162. data/lib/new_relic/agent/instrumentation/queue_time.rb +1 -1
  163. data/lib/new_relic/agent/instrumentation/rack/instrumentation.rb +9 -0
  164. data/lib/new_relic/agent/instrumentation/rails3/action_controller.rb +4 -0
  165. data/lib/new_relic/agent/instrumentation/rails_notifications/action_cable.rb +1 -1
  166. data/lib/new_relic/agent/instrumentation/rails_notifications/action_controller.rb +10 -5
  167. data/lib/new_relic/agent/instrumentation/rake/instrumentation.rb +4 -0
  168. data/lib/new_relic/agent/instrumentation/rake.rb +1 -2
  169. data/lib/new_relic/agent/instrumentation/rdkafka/chain.rb +72 -0
  170. data/lib/new_relic/agent/instrumentation/rdkafka/instrumentation.rb +70 -0
  171. data/lib/new_relic/agent/instrumentation/rdkafka/prepend.rb +67 -0
  172. data/lib/new_relic/agent/instrumentation/rdkafka.rb +25 -0
  173. data/lib/new_relic/agent/instrumentation/redis/cluster_middleware.rb +26 -0
  174. data/lib/new_relic/agent/instrumentation/redis/constants.rb +2 -2
  175. data/lib/new_relic/agent/instrumentation/redis/instrumentation.rb +18 -11
  176. data/lib/new_relic/agent/instrumentation/redis/middleware.rb +3 -0
  177. data/lib/new_relic/agent/instrumentation/redis.rb +11 -5
  178. data/lib/new_relic/agent/instrumentation/resque/instrumentation.rb +4 -0
  179. data/lib/new_relic/agent/instrumentation/resque.rb +8 -6
  180. data/lib/new_relic/agent/instrumentation/roda/chain.rb +43 -0
  181. data/lib/new_relic/agent/instrumentation/roda/ignorer.rb +45 -0
  182. data/lib/new_relic/agent/instrumentation/roda/instrumentation.rb +68 -0
  183. data/lib/new_relic/agent/instrumentation/roda/prepend.rb +24 -0
  184. data/lib/new_relic/agent/instrumentation/roda/roda_transaction_namer.rb +29 -0
  185. data/lib/new_relic/agent/instrumentation/roda.rb +36 -0
  186. data/lib/new_relic/agent/instrumentation/ruby_kafka/chain.rb +55 -0
  187. data/lib/new_relic/agent/instrumentation/ruby_kafka/instrumentation.rb +67 -0
  188. data/lib/new_relic/agent/instrumentation/ruby_kafka/prepend.rb +60 -0
  189. data/lib/new_relic/agent/instrumentation/ruby_kafka.rb +25 -0
  190. data/lib/new_relic/agent/instrumentation/ruby_openai/chain.rb +36 -0
  191. data/lib/new_relic/agent/instrumentation/ruby_openai/instrumentation.rb +196 -0
  192. data/lib/new_relic/agent/instrumentation/ruby_openai/prepend.rb +20 -0
  193. data/lib/new_relic/agent/instrumentation/ruby_openai.rb +35 -0
  194. data/lib/new_relic/agent/instrumentation/sequel.rb +1 -1
  195. data/lib/new_relic/agent/instrumentation/sidekiq/client.rb +4 -0
  196. data/lib/new_relic/agent/instrumentation/sidekiq/extensions/delay_extensions.rb +24 -0
  197. data/lib/new_relic/agent/instrumentation/sidekiq/extensions/delayed_class.rb +2 -2
  198. data/lib/new_relic/agent/instrumentation/sidekiq/server.rb +26 -3
  199. data/lib/new_relic/agent/instrumentation/sidekiq.rb +13 -16
  200. data/lib/new_relic/agent/instrumentation/sinatra/ignorer.rb +1 -1
  201. data/lib/new_relic/agent/instrumentation/sinatra/instrumentation.rb +4 -0
  202. data/lib/new_relic/agent/instrumentation/sinatra/transaction_namer.rb +1 -3
  203. data/lib/new_relic/agent/instrumentation/sinatra.rb +3 -19
  204. data/lib/new_relic/agent/instrumentation/stripe.rb +28 -0
  205. data/lib/new_relic/agent/instrumentation/stripe_subscriber.rb +98 -0
  206. data/lib/new_relic/agent/instrumentation/thread/chain.rb +1 -1
  207. data/lib/new_relic/agent/instrumentation/thread/instrumentation.rb +1 -5
  208. data/lib/new_relic/agent/instrumentation/thread/prepend.rb +1 -1
  209. data/lib/new_relic/agent/instrumentation/thread.rb +0 -2
  210. data/lib/new_relic/agent/instrumentation/tilt/instrumentation.rb +4 -0
  211. data/lib/new_relic/agent/instrumentation/tilt.rb +0 -4
  212. data/lib/new_relic/agent/instrumentation/typhoeus/instrumentation.rb +7 -3
  213. data/lib/new_relic/agent/instrumentation/typhoeus.rb +0 -1
  214. data/lib/new_relic/agent/instrumentation/view_component/chain.rb +21 -0
  215. data/lib/new_relic/agent/instrumentation/view_component/instrumentation.rb +45 -0
  216. data/lib/{tasks/instrumentation_generator/templates/instrumentation.tt → new_relic/agent/instrumentation/view_component/prepend.rb} +4 -4
  217. data/lib/new_relic/agent/instrumentation/view_component.rb +24 -0
  218. data/lib/new_relic/agent/javascript_instrumentor.rb +2 -4
  219. data/lib/new_relic/agent/llm/chat_completion_message.rb +25 -0
  220. data/lib/new_relic/agent/llm/chat_completion_summary.rb +66 -0
  221. data/lib/new_relic/agent/llm/embedding.rb +60 -0
  222. data/lib/new_relic/agent/llm/llm_event.rb +95 -0
  223. data/lib/new_relic/agent/llm/response_headers.rb +80 -0
  224. data/lib/new_relic/agent/llm.rb +49 -0
  225. data/lib/new_relic/agent/local_log_decorator.rb +20 -3
  226. data/lib/new_relic/agent/log_event_aggregator.rb +149 -26
  227. data/lib/new_relic/agent/log_event_attributes.rb +115 -0
  228. data/lib/new_relic/agent/logging.rb +5 -5
  229. data/lib/new_relic/agent/messaging.rb +18 -7
  230. data/lib/new_relic/agent/method_tracer.rb +4 -1
  231. data/lib/new_relic/agent/method_tracer_helpers.rb +26 -5
  232. data/lib/new_relic/agent/monitors/inbound_request_monitor.rb +1 -1
  233. data/lib/new_relic/agent/monitors/synthetics_monitor.rb +12 -1
  234. data/lib/new_relic/agent/new_relic_service/encoders.rb +2 -2
  235. data/lib/new_relic/agent/new_relic_service/json_marshaller.rb +2 -2
  236. data/lib/new_relic/agent/new_relic_service.rb +61 -28
  237. data/lib/new_relic/agent/obfuscator.rb +0 -2
  238. data/lib/new_relic/agent/opentelemetry/context/propagation/trace_propagator.rb +66 -0
  239. data/lib/new_relic/agent/opentelemetry/context/propagation.rb +15 -0
  240. data/lib/{tasks/instrumentation_generator/templates/Envfile.tt → new_relic/agent/opentelemetry/context.rb} +9 -5
  241. data/lib/new_relic/agent/opentelemetry/trace/span.rb +31 -0
  242. data/lib/new_relic/agent/opentelemetry/trace/tracer.rb +129 -0
  243. data/lib/new_relic/agent/opentelemetry/trace/tracer_provider.rb +18 -0
  244. data/lib/new_relic/agent/opentelemetry/trace.rb +15 -0
  245. data/lib/new_relic/agent/opentelemetry/transaction_patch.rb +69 -0
  246. data/lib/new_relic/agent/opentelemetry_bridge.rb +32 -0
  247. data/lib/new_relic/agent/parameter_filtering.rb +1 -1
  248. data/lib/new_relic/agent/pipe_channel_manager.rb +2 -2
  249. data/lib/new_relic/agent/pipe_service.rb +1 -1
  250. data/lib/new_relic/agent/rules_engine/segment_terms_rule.rb +1 -2
  251. data/lib/new_relic/agent/rules_engine.rb +1 -1
  252. data/lib/new_relic/agent/sampler.rb +1 -0
  253. data/lib/new_relic/agent/samplers/cpu_sampler.rb +1 -1
  254. data/lib/new_relic/agent/samplers/memory_sampler.rb +1 -1
  255. data/lib/new_relic/agent/serverless_handler.rb +406 -0
  256. data/lib/new_relic/agent/serverless_handler_event_sources.json +155 -0
  257. data/lib/new_relic/agent/serverless_handler_event_sources.rb +49 -0
  258. data/lib/new_relic/agent/span_event_primitive.rb +32 -15
  259. data/lib/new_relic/agent/sql_sampler.rb +0 -1
  260. data/lib/new_relic/agent/system_info.rb +40 -0
  261. data/lib/new_relic/agent/threading/agent_thread.rb +1 -2
  262. data/lib/new_relic/agent/threading/backtrace_node.rb +10 -1
  263. data/lib/new_relic/agent/tracer.rb +16 -16
  264. data/lib/new_relic/agent/transaction/abstract_segment.rb +103 -41
  265. data/lib/new_relic/agent/transaction/datastore_segment.rb +1 -1
  266. data/lib/new_relic/agent/transaction/distributed_tracer.rb +3 -3
  267. data/lib/new_relic/agent/transaction/distributed_tracing.rb +7 -8
  268. data/lib/new_relic/agent/transaction/external_request_segment.rb +5 -12
  269. data/lib/new_relic/agent/transaction/message_broker_segment.rb +5 -3
  270. data/lib/new_relic/agent/transaction/request_attributes.rb +54 -11
  271. data/lib/new_relic/agent/transaction/trace_context.rb +34 -5
  272. data/lib/new_relic/agent/transaction/tracing.rb +20 -4
  273. data/lib/new_relic/agent/transaction.rb +38 -13
  274. data/lib/new_relic/agent/transaction_error_primitive.rb +39 -19
  275. data/lib/new_relic/agent/transaction_event_primitive.rb +19 -0
  276. data/lib/new_relic/agent/transaction_time_aggregator.rb +1 -1
  277. data/lib/new_relic/agent/utilization/ecs.rb +22 -0
  278. data/lib/new_relic/agent/utilization/ecs_v4.rb +22 -0
  279. data/lib/new_relic/agent/utilization/gcp.rb +1 -3
  280. data/lib/new_relic/agent/utilization/vendor.rb +5 -7
  281. data/lib/new_relic/agent/utilization_data.rb +40 -5
  282. data/lib/new_relic/agent/vm/{mri_vm.rb → c_ruby_vm.rb} +10 -18
  283. data/lib/new_relic/agent/vm.rb +2 -2
  284. data/lib/new_relic/agent/worker_loop.rb +1 -1
  285. data/lib/new_relic/agent.rb +286 -17
  286. data/lib/new_relic/base64.rb +25 -0
  287. data/lib/new_relic/cli/command.rb +6 -3
  288. data/lib/new_relic/constants.rb +8 -0
  289. data/lib/new_relic/control/class_methods.rb +1 -7
  290. data/lib/new_relic/control/frameworks/grape.rb +14 -0
  291. data/lib/new_relic/control/frameworks/padrino.rb +14 -0
  292. data/lib/new_relic/control/frameworks/rails.rb +17 -5
  293. data/lib/new_relic/control/frameworks/rails4.rb +1 -3
  294. data/lib/new_relic/control/frameworks/roda.rb +20 -0
  295. data/lib/new_relic/control/instance_methods.rb +13 -0
  296. data/lib/new_relic/control/instrumentation.rb +2 -16
  297. data/lib/new_relic/control/private_instance_methods.rb +4 -0
  298. data/lib/new_relic/control/security_interface.rb +57 -0
  299. data/lib/new_relic/control.rb +1 -1
  300. data/lib/new_relic/dependency_detection.rb +25 -13
  301. data/lib/new_relic/environment_report.rb +2 -2
  302. data/lib/new_relic/helper.rb +22 -0
  303. data/lib/new_relic/language_support.rb +12 -1
  304. data/lib/new_relic/latest_changes.rb +1 -1
  305. data/lib/new_relic/local_environment.rb +31 -18
  306. data/lib/new_relic/noticed_error.rb +5 -2
  307. data/lib/new_relic/rack/agent_hooks.rb +1 -1
  308. data/lib/new_relic/rack/agent_middleware.rb +0 -16
  309. data/lib/new_relic/rack/browser_monitoring.rb +29 -13
  310. data/lib/new_relic/supportability_helper.rb +5 -1
  311. data/lib/new_relic/thread_local_storage.rb +31 -0
  312. data/lib/new_relic/traced_thread.rb +2 -3
  313. data/lib/new_relic/version.rb +1 -1
  314. data/lib/sequel/extensions/new_relic_instrumentation.rb +4 -3
  315. data/lib/tasks/bump_version.rake +21 -0
  316. data/lib/tasks/config.rake +11 -5
  317. data/lib/tasks/coverage_report.rake +1 -1
  318. data/lib/tasks/gha.rake +31 -0
  319. data/lib/tasks/helpers/config.html.erb +94 -0
  320. data/lib/tasks/helpers/format.rb +11 -7
  321. data/lib/tasks/helpers/newrelicyml.rb +211 -0
  322. data/lib/tasks/helpers/version_bump.rb +62 -0
  323. data/lib/tasks/newrelic.rb +1 -0
  324. data/lib/tasks/newrelicyml.rake +13 -0
  325. data/lib/tasks/tests.rake +71 -0
  326. data/newrelic.yml +657 -251
  327. data/newrelic_rpm.gemspec +17 -10
  328. data/test/agent_helper.rb +38 -4
  329. metadata +230 -44
  330. data/.gitignore +0 -43
  331. data/.project +0 -23
  332. data/.rubocop.yml +0 -1909
  333. data/.rubocop_todo.yml +0 -61
  334. data/.simplecov +0 -15
  335. data/.snyk +0 -11
  336. data/.yardopts +0 -27
  337. data/Brewfile +0 -12
  338. data/DOCKER.md +0 -167
  339. data/Dockerfile +0 -10
  340. data/Guardfile +0 -26
  341. data/bin/newrelic_cmd +0 -6
  342. data/config/database.yml +0 -5
  343. data/config.dot +0 -278
  344. data/docker-compose.yml +0 -107
  345. data/lefthook.yml +0 -9
  346. data/lib/new_relic/agent/range_extensions.rb +0 -27
  347. data/lib/tasks/helpers/removers.rb +0 -33
  348. data/lib/tasks/instrumentation_generator/README.md +0 -63
  349. data/lib/tasks/instrumentation_generator/TODO.md +0 -33
  350. data/lib/tasks/instrumentation_generator/instrumentation.thor +0 -121
  351. data/lib/tasks/instrumentation_generator/templates/chain.tt +0 -22
  352. data/lib/tasks/instrumentation_generator/templates/chain_method.tt +0 -8
  353. data/lib/tasks/instrumentation_generator/templates/dependency_detection.tt +0 -29
  354. data/lib/tasks/instrumentation_generator/templates/instrumentation_method.tt +0 -3
  355. data/lib/tasks/instrumentation_generator/templates/newrelic.yml.tt +0 -19
  356. data/lib/tasks/instrumentation_generator/templates/prepend.tt +0 -13
  357. data/lib/tasks/instrumentation_generator/templates/prepend_method.tt +0 -3
  358. data/lib/tasks/instrumentation_generator/templates/test.tt +0 -15
  359. data/lib/tasks/multiverse.rake +0 -6
  360. data/lib/tasks/multiverse.rb +0 -83
@@ -8,7 +8,7 @@ require 'new_relic/agent/vm/snapshot'
8
8
  module NewRelic
9
9
  module Agent
10
10
  module VM
11
- class MriVM
11
+ class CRubyVM
12
12
  def snapshot
13
13
  snap = Snapshot.new
14
14
  gather_stats(snap)
@@ -24,7 +24,7 @@ module NewRelic
24
24
 
25
25
  def gather_gc_stats(snap)
26
26
  gather_gc_runs(snap) if supports?(:gc_runs)
27
- gather_derived_stats(snap) if GC.respond_to?(:stat)
27
+ gather_derived_stats(snap)
28
28
  end
29
29
 
30
30
  def gather_gc_runs(snap)
@@ -33,19 +33,11 @@ module NewRelic
33
33
 
34
34
  def gather_derived_stats(snap)
35
35
  stat = GC.stat
36
- snap.total_allocated_object = derive_from_gc_stats(%i[total_allocated_objects total_allocated_object], stat)
37
- snap.major_gc_count = derive_from_gc_stats(:major_gc_count, stat)
38
- snap.minor_gc_count = derive_from_gc_stats(:minor_gc_count, stat)
39
- snap.heap_live = derive_from_gc_stats(%i[heap_live_slots heap_live_slot heap_live_num], stat)
40
- snap.heap_free = derive_from_gc_stats(%i[heap_free_slots heap_free_slot heap_free_num], stat)
41
- end
42
-
43
- def derive_from_gc_stats(keys, stat)
44
- Array(keys).each do |key|
45
- value = stat[key]
46
- return value if value
47
- end
48
- nil
36
+ snap.total_allocated_object = stat.fetch(:total_allocated_objects, nil)
37
+ snap.major_gc_count = stat.fetch(:major_gc_count, nil)
38
+ snap.minor_gc_count = stat.fetch(:minor_gc_count, nil)
39
+ snap.heap_live = stat.fetch(:heap_live_slots, nil)
40
+ snap.heap_free = stat.fetch(:heap_free_slots, nil)
49
41
  end
50
42
 
51
43
  def gather_gc_time(snap)
@@ -69,7 +61,7 @@ module NewRelic
69
61
  end
70
62
 
71
63
  def gather_constant_cache_invalidations
72
- RubyVM.stat[RUBY_VERSION >= '3.2.0' ? :constant_cache_invalidations : :global_constant_state]
64
+ RubyVM.stat[NewRelic::Helper.version_satisfied?(RUBY_VERSION, '>=', '3.2.0') ? :constant_cache_invalidations : :global_constant_state]
73
65
  end
74
66
 
75
67
  def gather_constant_cache_misses
@@ -94,9 +86,9 @@ module NewRelic
94
86
  when :gc_total_time
95
87
  NewRelic::LanguageSupport.gc_profiler_enabled?
96
88
  when :method_cache_invalidations
97
- RUBY_VERSION < '3.0.0'
89
+ NewRelic::Helper.version_satisfied?(RUBY_VERSION, '<', '3.0.0')
98
90
  when :constant_cache_misses
99
- RUBY_VERSION >= '3.2.0'
91
+ NewRelic::Helper.version_satisfied?(RUBY_VERSION, '>=', '3.2.0')
100
92
  else
101
93
  false
102
94
  end
@@ -3,7 +3,7 @@
3
3
  # frozen_string_literal: true
4
4
 
5
5
  require 'new_relic/language_support'
6
- require 'new_relic/agent/vm/mri_vm'
6
+ require 'new_relic/agent/vm/c_ruby_vm'
7
7
  require 'new_relic/agent/vm/jruby_vm'
8
8
 
9
9
  module NewRelic
@@ -21,7 +21,7 @@ module NewRelic
21
21
  if NewRelic::LanguageSupport.jruby?
22
22
  JRubyVM.new
23
23
  else
24
- MriVM.new
24
+ CRubyVM.new
25
25
  end
26
26
  end
27
27
  end
@@ -88,7 +88,7 @@ module NewRelic
88
88
  raise
89
89
  rescue => e
90
90
  # Don't blow out the stack for anything that hasn't already propagated
91
- ::NewRelic::Agent.logger.error('Error running task in Agent Worker Loop:', e)
91
+ ::NewRelic::Agent.logger.error('Error running task in agent worker loop:', e)
92
92
  end
93
93
  end
94
94
  end
@@ -31,6 +31,7 @@ module NewRelic
31
31
  require 'new_relic/noticed_error'
32
32
  require 'new_relic/agent/noticeable_error'
33
33
  require 'new_relic/supportability_helper'
34
+ require 'new_relic/thread_local_storage'
34
35
 
35
36
  require 'new_relic/agent/encoding_normalizer'
36
37
  require 'new_relic/agent/stats'
@@ -58,9 +59,12 @@ module NewRelic
58
59
  require 'new_relic/agent/deprecator'
59
60
  require 'new_relic/agent/logging'
60
61
  require 'new_relic/agent/distributed_tracing'
62
+ require 'new_relic/agent/attribute_pre_filtering'
61
63
  require 'new_relic/agent/attribute_processing'
62
64
  require 'new_relic/agent/linking_metadata'
63
65
  require 'new_relic/agent/local_log_decorator'
66
+ require 'new_relic/agent/llm'
67
+ require 'new_relic/agent/aws'
64
68
 
65
69
  require 'new_relic/agent/instrumentation/controller_instrumentation'
66
70
 
@@ -81,6 +85,10 @@ module NewRelic
81
85
  # An exception that forces an agent to stop reporting until its mongrel is restarted.
82
86
  class ForceDisconnectException < StandardError; end
83
87
 
88
+ # Error handling for the automated custom instrumentation tracer logic
89
+ class AutomaticTracerParseException < StandardError; end
90
+ class AutomaticTracerTraceException < StandardError; end
91
+
84
92
  # An exception that forces an agent to restart.
85
93
  class ForceRestartException < StandardError
86
94
  def message
@@ -104,11 +112,17 @@ module NewRelic
104
112
 
105
113
  # placeholder name used when we cannot determine a transaction's name
106
114
  UNKNOWN_METRIC = '(unknown)'.freeze
115
+ LLM_FEEDBACK_MESSAGE = 'LlmFeedbackMessage'
116
+ # give the observed app time to load the code that automatic tracers have
117
+ # been configured for
118
+ AUTOMATIC_TRACER_MAX_ATTEMPTS = 60 # 60 = try about twice a second for 30 seconds
107
119
 
108
120
  attr_reader :error_group_callback
121
+ attr_reader :llm_token_count_callback
109
122
 
110
123
  @agent = nil
111
124
  @error_group_callback = nil
125
+ @llm_token_count_callback = nil
112
126
  @logger = nil
113
127
  @tracer_lock = Mutex.new
114
128
  @tracer_queue = []
@@ -118,8 +132,8 @@ module NewRelic
118
132
  def agent # :nodoc:
119
133
  return @agent if @agent
120
134
 
121
- NewRelic::Agent.logger.warn("Agent unavailable as it hasn't been started.")
122
- NewRelic::Agent.logger.warn(caller.join("\n"))
135
+ NewRelic::Agent.logger.debug("Agent unavailable as it hasn't been started.")
136
+ NewRelic::Agent.logger.debug(caller.join("\n"))
123
137
  nil
124
138
  end
125
139
 
@@ -156,6 +170,92 @@ module NewRelic
156
170
  end
157
171
  end
158
172
 
173
+ # @api private
174
+ def self.add_automatic_method_tracers(arr)
175
+ return unless arr
176
+ return arr if arr.respond_to?(:empty?) && arr.empty?
177
+
178
+ arr = arr.split(/\s*,\s*/) if arr.is_a?(String)
179
+
180
+ add_tracers_once_methods_are_defined(arr.dup)
181
+
182
+ arr
183
+ end
184
+
185
+ # spawn a thread that will attempt to establish a tracer for each of the
186
+ # configured methods. the thread will continue to keep trying with each
187
+ # tracer until one of the following happens:
188
+ # - the tracer is successfully established
189
+ # - the configured method string couldn't be parsed
190
+ # - establishing a tracer for a successfully parsed string failed
191
+ # - the maximum number of attempts has been reached
192
+ # the thread will only be spawned once per agent initialization, to account
193
+ # for configuration reloading scenarios.
194
+ #
195
+ # @api private
196
+ def self.add_tracers_once_methods_are_defined(notations)
197
+ # this class method can be invoked multiple times at agent startup, so
198
+ # we return asap here instead of using a traditional memoization of
199
+ # waiting for the method's body to finish being executed
200
+ if defined?(@add_tracers_once_methods_are_defined)
201
+ return
202
+ else
203
+ @add_tracers_once_methods_are_defined = true
204
+ end
205
+
206
+ Thread.new do
207
+ AUTOMATIC_TRACER_MAX_ATTEMPTS.times do
208
+ notations.delete_if { |notation| prep_tracer_for(notation) }
209
+
210
+ break if notations.empty?
211
+
212
+ sleep 0.5
213
+ end
214
+ end
215
+ end
216
+
217
+ # returns `true` if the notation string has either been successfully
218
+ # processed or raised an error during processing. returns `false` if the
219
+ # string seems good but the (customer) code to be traced has not yet been
220
+ # loaded into the Ruby VM
221
+ #
222
+ # @api private
223
+ def self.prep_tracer_for(fully_qualified_method_notation)
224
+ delimiters = fully_qualified_method_notation.scan(/\.|#/)
225
+ raise AutomaticTracerParseException.new("Expected exactly one '.' or '#' delimiter.") unless delimiters.size == 1
226
+
227
+ delimiter = delimiters.first
228
+ namespace, method_name = fully_qualified_method_notation.split(delimiter)
229
+ unless namespace && !namespace.empty?
230
+ raise AutomaticTracerParseException.new("Nothing found to the left of the #{delimiter} delimiter.")
231
+ end
232
+ unless method_name && !method_name.empty?
233
+ raise AutomaticTracerParseException.new("Nothing found to the right of the #{delimiter} delimiter.")
234
+ end
235
+
236
+ begin
237
+ klass = ::NewRelic::LanguageSupport.constantize(namespace)
238
+ return false unless klass
239
+
240
+ klass_to_trace = delimiter.eql?('.') ? klass.singleton_class : klass
241
+ add_or_defer_method_tracer(klass_to_trace, method_name, nil, {})
242
+ rescue StandardError => e
243
+ raise AutomaticTracerTraceException.new("#{e.class} - #{e.message}")
244
+ end
245
+
246
+ true
247
+ rescue AutomaticTracerParseException => e
248
+ NewRelic::Agent.logger.error('Unable to parse out a usable method name to trace. Expected a valid, fully ' \
249
+ "qualified method notation. Got: '#{fully_qualified_method_notation}'. " \
250
+ "Error: #{e.message}")
251
+ true
252
+ rescue AutomaticTracerTraceException => e
253
+ NewRelic::Agent.logger.error('Unable to automatically apply a tracer to method ' \
254
+ "'#{fully_qualified_method_notation}'. Error: #{e.message}")
255
+ true
256
+ end
257
+
258
+ # @api private
159
259
  def add_deferred_method_tracers_now
160
260
  @tracer_lock.synchronize do
161
261
  @tracer_queue.each do |receiver, method_name, metric_name, options|
@@ -193,6 +293,7 @@ module NewRelic
193
293
  #
194
294
  # This method is safe to use from any thread.
195
295
  #
296
+ # @!scope class
196
297
  # @api public
197
298
  def record_metric(metric_name, value) # THREAD_LOCAL_ACCESS
198
299
  record_api_supportability_metric(:record_metric)
@@ -213,6 +314,17 @@ module NewRelic
213
314
  record_metric(metric_name, value)
214
315
  end
215
316
 
317
+ def record_instrumentation_invocation(library)
318
+ record_metric_once("Supportability/#{library}/Invoked")
319
+ end
320
+
321
+ # see ActiveSupport::Inflector.demodulize
322
+ def base_name(klass_name)
323
+ return klass_name unless ridx = klass_name.rindex('::')
324
+
325
+ klass_name[(ridx + 2), klass_name.length]
326
+ end
327
+
216
328
  SUPPORTABILITY_INCREMENT_METRIC = 'Supportability/API/increment_metric'.freeze
217
329
 
218
330
  # Increment a simple counter metric.
@@ -222,6 +334,7 @@ module NewRelic
222
334
  #
223
335
  # This method is safe to use from any thread.
224
336
  #
337
+ # @!scope class
225
338
  # @api public
226
339
  #
227
340
  def increment_metric(metric_name, amount = 1) # THREAD_LOCAL_ACCESS
@@ -240,7 +353,7 @@ module NewRelic
240
353
 
241
354
  # @!group Recording custom errors
242
355
 
243
- # Set a filter to be applied to errors that the Ruby Agent will
356
+ # Set a filter to be applied to errors that the Ruby agent will
244
357
  # track. The block should evaluate to the exception to track
245
358
  # (which could be different from the original exception) or nil to
246
359
  # ignore this exception.
@@ -249,6 +362,7 @@ module NewRelic
249
362
  #
250
363
  # Return the new block or the existing filter Proc if no block is passed.
251
364
  #
365
+ # @!scope class
252
366
  # @api public
253
367
  #
254
368
  def ignore_error_filter(&block)
@@ -287,6 +401,7 @@ module NewRelic
287
401
  # them if you are calling <code>notice_error</code> outside a
288
402
  # transaction.
289
403
  #
404
+ # @!scope class
290
405
  # @api public
291
406
  #
292
407
  def notice_error(exception, options = {})
@@ -298,7 +413,7 @@ module NewRelic
298
413
 
299
414
  # Set a callback proc for determining an error's error group name
300
415
  #
301
- # @param [Proc] the callback proc
416
+ # @param callback_proc [Proc] the callback proc
302
417
  #
303
418
  # Typically this method should be called only once to set a callback for
304
419
  # use with all noticed errors. If it is called multiple times, each new
@@ -324,6 +439,7 @@ module NewRelic
324
439
  # :'error.expected' => Whether (true) or not (false) the error was expected
325
440
  # :options => The options hash passed to `NewRelic::Agent.notice_error`
326
441
  #
442
+ # @!scope class
327
443
  # @api public
328
444
  #
329
445
  def set_error_group_callback(callback_proc)
@@ -363,6 +479,7 @@ module NewRelic
363
479
  # may be strings, symbols, numeric values or
364
480
  # booleans.
365
481
  #
482
+ # @!scope class
366
483
  # @api public
367
484
  #
368
485
  def record_custom_event(event_type, event_attrs)
@@ -375,17 +492,105 @@ module NewRelic
375
492
  nil
376
493
  end
377
494
 
495
+ # Records user feedback events for LLM applications. This API must pass
496
+ # the current trace id as a parameter, which can be obtained using:
497
+ #
498
+ # NewRelic::Agent::Tracer.current_trace_id
499
+ #
500
+ # @param [String] ID of the trace where the chat completion(s) related
501
+ # to the feedback occurred.
502
+ #
503
+ # @param [String or Integer] Rating provided by an end user
504
+ # (ex: “Good", "Bad”, 1, 2, 5, 8, 10).
505
+ #
506
+ # @param [optional, String] Category of the feedback as provided by the
507
+ # end user (ex: “informative”, “inaccurate”).
508
+ #
509
+ # @param start_time [optional, String] Freeform text feedback from an
510
+ # end user.
511
+ #
512
+ # @param [optional, Hash] Set of key-value pairs to store any other
513
+ # desired data to submit with the feedback event.
514
+ #
515
+ # @!scope class
516
+ # @api public
517
+ #
518
+ def record_llm_feedback_event(trace_id:,
519
+ rating:,
520
+ category: nil,
521
+ message: nil,
522
+ metadata: NewRelic::EMPTY_HASH)
523
+
524
+ record_api_supportability_metric(:record_llm_feedback_event)
525
+ unless NewRelic::Agent.config[:'distributed_tracing.enabled']
526
+ return NewRelic::Agent.logger.error('Distributed tracing must be enabled to record LLM feedback')
527
+ end
528
+
529
+ feedback_message_event = {
530
+ 'trace_id': trace_id,
531
+ 'rating': rating,
532
+ 'category': category,
533
+ 'message': message,
534
+ 'id': NewRelic::Agent::GuidGenerator.generate_guid,
535
+ 'ingest_source': NewRelic::Agent::Llm::LlmEvent::INGEST_SOURCE
536
+ }
537
+ feedback_message_event.merge!(metadata) unless metadata.empty?
538
+
539
+ NewRelic::Agent.record_custom_event(LLM_FEEDBACK_MESSAGE, feedback_message_event)
540
+ rescue ArgumentError
541
+ raise
542
+ rescue => exception
543
+ NewRelic::Agent.logger.error('record_llm_feedback_event', exception)
544
+ end
545
+
546
+ # @!endgroup
547
+
548
+ # @!group LLM callbacks
549
+
550
+ # Set a callback proc for calculating `token_count` attributes for
551
+ # LlmEmbedding and LlmChatCompletionMessage events
552
+ #
553
+ # @param callback_proc [Proc] the callback proc
554
+ #
555
+ # This method should be called only once to set a callback for
556
+ # use with all LLM token calculations. If it is called multiple times, each
557
+ # new callback will replace the old one.
558
+ #
559
+ # The proc will be called with a single hash as its input argument and
560
+ # must return an Integer representing the number of tokens used for that
561
+ # particular prompt, completion message, or embedding. Values less than or
562
+ # equal to 0 will not be attached to an event.
563
+ #
564
+ # The hash has the following keys:
565
+ #
566
+ # :model => [String] The name of the LLM model
567
+ # :content => [String] The message content or prompt
568
+ #
569
+ # @!scope class
570
+ # @api public
571
+ #
572
+ def set_llm_token_count_callback(callback_proc)
573
+ unless callback_proc.is_a?(Proc)
574
+ NewRelic::Agent.logger.error("#{self}.#{__method__}: expected an argument of type Proc, " \
575
+ "got #{callback_proc.class}")
576
+ return
577
+ end
578
+
579
+ record_api_supportability_metric(:set_llm_token_count_callback)
580
+ @llm_token_count_callback = callback_proc
581
+ end
582
+
378
583
  # @!endgroup
379
584
 
380
585
  # @!group Manual agent configuration and startup/shutdown
381
586
 
382
- # Call this to manually start the Agent in situations where the Agent does
587
+ # Call this to manually start the agent in situations where the agent does
383
588
  # not auto-start.
384
589
  #
385
- # When the app environment loads, so does the Agent. However, the
386
- # Agent will only connect to the service if a web front-end is found. If
590
+ # When the app environment loads, so does the agent. However, the
591
+ # agent will only connect to the service if a web front-end is found. If
387
592
  # you want to selectively monitor ruby processes that don't use
388
- # web plugins, then call this method in your code and the Agent
593
+ # web plugins, then call this method in your code and the agent
389
594
  # will fire up and start reporting to the service.
390
595
  #
391
596
  # Options are passed in as overrides for values in the
@@ -394,6 +599,7 @@ module NewRelic
394
599
  # file logger. The setting for the newrelic.yml section to use
395
600
  # (ie, RAILS_ENV) can be overridden with an :env argument.
396
601
  #
602
+ # @!scope class
397
603
  # @api public
398
604
  #
399
605
  def manual_start(options = {})
@@ -426,6 +632,7 @@ module NewRelic
426
632
  # connection, this tells me to only try it once so this method returns
427
633
  # quickly if there is some kind of latency with the server.
428
634
  #
635
+ # @!scope class
429
636
  # @api public
430
637
  #
431
638
  def after_fork(options = {})
@@ -439,6 +646,7 @@ module NewRelic
439
646
  #
440
647
  # @param options [Hash] Unused options Hash, for back compatibility only
441
648
  #
649
+ # @!scope class
442
650
  # @api public
443
651
  #
444
652
  def shutdown(options = {})
@@ -449,6 +657,7 @@ module NewRelic
449
657
  # Clear out any data the agent has buffered but has not yet transmitted
450
658
  # to the collector.
451
659
  #
660
+ # @!scope class
452
661
  # @api public
453
662
  def drop_buffered_data
454
663
  # the following line needs else branch coverage
@@ -463,6 +672,7 @@ module NewRelic
463
672
  # register instrumentation than just loading the files directly,
464
673
  # although that probably also works.
465
674
  #
675
+ # @!scope class
466
676
  # @api public
467
677
  #
468
678
  def add_instrumentation(file_pattern)
@@ -472,6 +682,7 @@ module NewRelic
472
682
 
473
683
  # Require agent testing helper methods
474
684
  #
685
+ # @!scope class
475
686
  # @api public
476
687
  def require_test_helper
477
688
  record_api_supportability_metric(:require_test_helper)
@@ -492,6 +703,7 @@ module NewRelic
492
703
  # my_obfuscator(sql)
493
704
  # end
494
705
  #
706
+ # @!scope class
495
707
  # @api public
496
708
  #
497
709
  def set_sql_obfuscator(type = :replace, &block)
@@ -507,6 +719,7 @@ module NewRelic
507
719
  # traced errors, transaction traces, Insights events, slow SQL traces,
508
720
  # or RUM injection will happen for this transaction.
509
721
  #
722
+ # @!scope class
510
723
  # @api public
511
724
  #
512
725
  def ignore_transaction
@@ -517,6 +730,7 @@ module NewRelic
517
730
  # This method disables the recording of Apdex metrics in the current
518
731
  # transaction.
519
732
  #
733
+ # @!scope class
520
734
  # @api public
521
735
  #
522
736
  def ignore_apdex
@@ -527,6 +741,7 @@ module NewRelic
527
741
  # This method disables browser monitoring javascript injection in the
528
742
  # current transaction.
529
743
  #
744
+ # @!scope class
530
745
  # @api public
531
746
  #
532
747
  def ignore_enduser
@@ -539,6 +754,7 @@ module NewRelic
539
754
  # track of the first entry point and turn on tracing again after
540
755
  # leaving that block. This uses the thread local Tracer::State.
541
756
  #
757
+ # @!scope class
542
758
  # @api public
543
759
  #
544
760
  def disable_all_tracing
@@ -563,6 +779,7 @@ module NewRelic
563
779
  # ...
564
780
  # end
565
781
  #
782
+ # @!scope class
566
783
  # @api public
567
784
  #
568
785
  def disable_sql_recording
@@ -601,27 +818,33 @@ module NewRelic
601
818
  # may be strings, symbols, numeric values or
602
819
  # booleans.
603
820
  #
821
+ # @!scope class
604
822
  # @api public
605
823
  #
606
824
  def add_custom_attributes(params) # THREAD_LOCAL_ACCESS
607
825
  record_api_supportability_metric(:add_custom_attributes)
608
826
 
609
- if params.is_a?(Hash)
610
- Transaction.tl_current&.add_custom_attributes(params)
611
-
612
- segment = ::NewRelic::Agent::Tracer.current_segment
613
- if segment
614
- add_new_segment_attributes(params, segment)
615
- end
616
- else
827
+ unless params.is_a?(Hash)
617
828
  ::NewRelic::Agent.logger.warn("Bad argument passed to #add_custom_attributes. Expected Hash but got #{params.class}")
829
+ return
830
+ end
831
+
832
+ if NewRelic::Agent.agent&.serverless?
833
+ ::NewRelic::Agent.logger.warn('Custom attributes are not supported in serverless mode')
834
+ return
618
835
  end
836
+
837
+ Transaction.tl_current&.add_custom_attributes(params)
838
+ segment = ::NewRelic::Agent::Tracer.current_segment
839
+ add_new_segment_attributes(params, segment) if segment
619
840
  end
620
841
 
621
842
  def add_new_segment_attributes(params, segment)
622
843
  # Make sure not to override existing segment-level custom attributes
623
844
  segment_custom_keys = segment.attributes.custom_attributes.keys.map(&:to_sym)
624
- segment.add_custom_attributes(params.reject { |k, _v| segment_custom_keys.include?(k.to_sym) })
845
+ segment.add_custom_attributes(params.reject do |k, _v|
846
+ segment_custom_keys.include?(k.to_sym) if k.respond_to?(:to_sym) # param keys can be integers
847
+ end)
625
848
  end
626
849
 
627
850
  # Add custom attributes to the span event for the current span. Attributes will be visible on spans in the
@@ -636,6 +859,7 @@ module NewRelic
636
859
  # booleans.
637
860
  #
638
861
  # @see https://docs.newrelic.com/docs/using-new-relic/welcome-new-relic/get-started/glossary#span
862
+ # @!scope class
639
863
  # @api public
640
864
  def add_custom_span_attributes(params)
641
865
  record_api_supportability_metric(:add_custom_span_attributes)
@@ -649,10 +873,51 @@ module NewRelic
649
873
  end
650
874
  end
651
875
 
876
+ # Add global custom attributes to log events for the current agent instance. As these attributes are global to the
877
+ # agent instance, they will be attached to all log events generated by the agent, and this methods usage isn't
878
+ # suitable for setting dynamic values.
879
+ #
880
+ # @param [Hash] params A Hash of attributes to attach to log
881
+ # events. The agent accepts up to 240 custom
882
+ # log event attributes.
883
+ #
884
+ # Keys will be coerced into Strings and must
885
+ # be less than 256 characters. Keys longer
886
+ # than 255 characters will be truncated.
887
+ #
888
+ # Values may be Strings, Symbols, numeric
889
+ # values or Booleans and must be less than
890
+ # 4095 characters. If the value is a String
891
+ # or a Symbol, values longer than 4094
892
+ # characters will be truncated. If the value
893
+ # exceeds 4094 characters and is of a
894
+ # different class, the attribute pair will
895
+ # be dropped.
896
+ #
897
+ # This API can be called multiple times.
898
+ # If the same key is passed more than once,
899
+ # the value associated with the last call
900
+ # will be preserved.
901
+ #
902
+ # Attribute pairs with empty or nil contents
903
+ # will be dropped.
904
+ # @!scope class
905
+ # @api public
906
+ def add_custom_log_attributes(params)
907
+ record_api_supportability_metric(:add_custom_log_attributes)
908
+
909
+ if params.is_a?(Hash)
910
+ NewRelic::Agent.agent.log_event_aggregator.add_custom_attributes(params)
911
+ else
912
+ NewRelic::Agent.logger.warn("Bad argument passed to #add_custom_log_attributes. Expected Hash but got #{params.class}.")
913
+ end
914
+ end
915
+
652
916
  # Set the user id for the current transaction. When present, this value will be included in the agent attributes for transaction and error events as 'enduser.id'.
653
917
  #
654
918
  # @param [String] user_id The user id to add to the current transaction attributes
655
919
  #
920
+ # @!scope class
656
921
  # @api public
657
922
  def set_user_id(user_id)
658
923
  record_api_supportability_metric(:set_user_id)
@@ -696,6 +961,7 @@ module NewRelic
696
961
  #
697
962
  # The default category is the same as the running transaction.
698
963
  #
964
+ # @!scope class
699
965
  # @api public
700
966
  #
701
967
  def set_transaction_name(name, options = {})
@@ -706,6 +972,7 @@ module NewRelic
706
972
  # Get the name of the current running transaction. This is useful if you
707
973
  # want to modify the default name.
708
974
  #
975
+ # @!scope class
709
976
  # @api public
710
977
  #
711
978
  def get_transaction_name # THREAD_LOCAL_ACCESS
@@ -777,6 +1044,7 @@ module NewRelic
777
1044
  # * entity.guid - The guid of the current entity.
778
1045
  # * hostname - The fully qualified hostname.
779
1046
  #
1047
+ # @!scope class
780
1048
  # @api public
781
1049
  def linking_metadata
782
1050
  metadata = Hash.new
@@ -803,6 +1071,7 @@ module NewRelic
803
1071
  #
804
1072
  # @param [String] nonce The nonce to use in the javascript tag for browser instrumentation
805
1073
  #
1074
+ # @!scope class
806
1075
  # @api public
807
1076
  #
808
1077
  def browser_timing_header(nonce = nil)
@@ -0,0 +1,25 @@
1
+ # This file is distributed under New Relic's license terms.
2
+ # See https://github.com/newrelic/newrelic-ruby-agent/blob/main/LICENSE for complete details.
3
+ # frozen_string_literal: true
4
+
5
+ module NewRelic
6
+ module Base64
7
+ extend self
8
+
9
+ def encode64(bin)
10
+ [bin].pack('m')
11
+ end
12
+
13
+ def decode64(str)
14
+ str.unpack1('m')
15
+ end
16
+
17
+ def strict_encode64(bin)
18
+ [bin].pack('m0')
19
+ end
20
+
21
+ def strict_decode64(str)
22
+ str.unpack1('m0')
23
+ end
24
+ end
25
+ end