newrelic_rpm 9.9.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.
- checksums.yaml +4 -4
- data/.build_ignore +1 -0
- data/CHANGELOG.md +463 -1
- data/CONTRIBUTING.md +2 -2
- data/README.md +16 -17
- data/Rakefile +1 -1
- data/lib/boot/strap.rb +102 -0
- data/lib/new_relic/agent/agent.rb +6 -0
- data/lib/new_relic/agent/agent_helpers/connect.rb +3 -0
- data/lib/new_relic/agent/agent_helpers/harvest.rb +3 -0
- data/lib/new_relic/agent/agent_helpers/shutdown.rb +3 -0
- data/lib/new_relic/agent/agent_helpers/start_worker_thread.rb +1 -0
- data/lib/new_relic/agent/agent_helpers/startup.rb +7 -0
- data/lib/new_relic/agent/agent_logger.rb +1 -0
- data/lib/new_relic/agent/aws.rb +68 -0
- data/lib/new_relic/agent/configuration/default_source.rb +603 -105
- data/lib/new_relic/agent/configuration/environment_source.rb +5 -1
- data/lib/new_relic/agent/configuration/manager.rb +28 -2
- data/lib/new_relic/agent/configuration/yaml_source.rb +7 -2
- data/lib/new_relic/agent/database/obfuscation_helpers.rb +11 -11
- data/lib/new_relic/agent/database/obfuscator.rb +1 -0
- data/lib/new_relic/agent/database.rb +41 -1
- data/lib/new_relic/agent/database_adapter.rb +1 -1
- data/lib/new_relic/agent/datastores/redis.rb +1 -1
- data/lib/new_relic/agent/distributed_tracing/cross_app_tracing.rb +1 -1
- data/lib/new_relic/agent/distributed_tracing.rb +4 -2
- data/lib/new_relic/agent/error_collector.rb +37 -10
- data/lib/new_relic/agent/external.rb +2 -0
- data/lib/new_relic/agent/health_check.rb +136 -0
- data/lib/new_relic/agent/http_clients/uri_util.rb +1 -1
- data/lib/new_relic/agent/instrumentation/action_dispatch.rb +1 -1
- data/lib/new_relic/agent/instrumentation/action_dispatch_subscriber.rb +1 -1
- data/lib/new_relic/agent/instrumentation/action_mailbox.rb +1 -1
- data/lib/new_relic/agent/instrumentation/action_mailer.rb +1 -1
- data/lib/new_relic/agent/instrumentation/active_job.rb +1 -1
- data/lib/new_relic/agent/instrumentation/active_job_subscriber.rb +6 -2
- data/lib/new_relic/agent/instrumentation/active_merchant.rb +0 -13
- data/lib/new_relic/agent/instrumentation/active_record.rb +7 -12
- data/lib/new_relic/agent/instrumentation/active_record_helper.rb +7 -3
- data/lib/new_relic/agent/instrumentation/active_record_notifications.rb +11 -9
- data/lib/new_relic/agent/instrumentation/active_record_prepend.rb +2 -2
- data/lib/new_relic/agent/instrumentation/active_record_subscriber.rb +9 -16
- data/lib/new_relic/agent/instrumentation/active_support_broadcast_logger.rb +0 -2
- data/lib/new_relic/agent/instrumentation/active_support_logger.rb +0 -2
- data/lib/new_relic/agent/instrumentation/async_http.rb +2 -3
- data/lib/new_relic/agent/instrumentation/aws_sdk_firehose/chain.rb +21 -0
- data/lib/new_relic/agent/instrumentation/aws_sdk_firehose/instrumentation.rb +66 -0
- data/lib/new_relic/agent/instrumentation/aws_sdk_firehose/prepend.rb +15 -0
- data/lib/new_relic/agent/instrumentation/aws_sdk_firehose.rb +22 -0
- data/lib/new_relic/agent/instrumentation/aws_sdk_kinesis/chain.rb +21 -0
- data/lib/new_relic/agent/instrumentation/aws_sdk_kinesis/instrumentation.rb +91 -0
- data/lib/new_relic/agent/instrumentation/aws_sdk_kinesis/prepend.rb +15 -0
- data/lib/new_relic/agent/instrumentation/aws_sdk_kinesis.rb +22 -0
- data/lib/new_relic/agent/instrumentation/aws_sdk_lambda/chain.rb +33 -0
- data/lib/new_relic/agent/instrumentation/aws_sdk_lambda/instrumentation.rb +93 -0
- data/lib/new_relic/agent/instrumentation/aws_sdk_lambda/prepend.rb +23 -0
- data/lib/new_relic/agent/instrumentation/aws_sdk_lambda.rb +23 -0
- data/lib/new_relic/agent/instrumentation/aws_sqs/chain.rb +37 -0
- data/lib/new_relic/agent/instrumentation/aws_sqs/instrumentation.rb +67 -0
- data/lib/new_relic/agent/instrumentation/aws_sqs/prepend.rb +21 -0
- data/lib/new_relic/agent/instrumentation/aws_sqs.rb +23 -0
- data/lib/new_relic/agent/instrumentation/bunny/instrumentation.rb +14 -0
- data/lib/new_relic/agent/instrumentation/bunny.rb +3 -4
- data/lib/new_relic/agent/instrumentation/concurrent_ruby.rb +1 -3
- data/lib/new_relic/agent/instrumentation/controller_instrumentation.rb +4 -0
- data/lib/new_relic/agent/instrumentation/curb.rb +4 -5
- data/lib/new_relic/agent/instrumentation/delayed_job_instrumentation.rb +0 -23
- data/lib/new_relic/agent/instrumentation/dynamodb/chain.rb +27 -0
- data/lib/new_relic/agent/instrumentation/dynamodb/instrumentation.rb +64 -0
- data/lib/new_relic/agent/instrumentation/dynamodb/prepend.rb +19 -0
- data/lib/new_relic/agent/instrumentation/dynamodb.rb +23 -0
- data/lib/new_relic/agent/instrumentation/elasticsearch/chain.rb +1 -2
- data/lib/new_relic/agent/instrumentation/elasticsearch/instrumentation.rb +53 -7
- data/lib/new_relic/agent/instrumentation/elasticsearch.rb +1 -3
- data/lib/new_relic/agent/instrumentation/ethon.rb +1 -5
- data/lib/new_relic/agent/instrumentation/excon.rb +1 -17
- data/lib/new_relic/agent/instrumentation/fiber/chain.rb +1 -1
- data/lib/new_relic/agent/instrumentation/fiber/prepend.rb +1 -1
- data/lib/new_relic/agent/instrumentation/fiber.rb +0 -2
- data/lib/new_relic/agent/instrumentation/grape/instrumentation.rb +0 -3
- data/lib/new_relic/agent/instrumentation/grape.rb +1 -1
- data/lib/new_relic/agent/instrumentation/grpc/client/instrumentation.rb +0 -1
- data/lib/new_relic/agent/instrumentation/httpclient.rb +1 -5
- data/lib/new_relic/agent/instrumentation/httprb.rb +0 -1
- data/lib/new_relic/agent/instrumentation/httpx/instrumentation.rb +1 -1
- data/lib/new_relic/agent/instrumentation/httpx.rb +1 -5
- data/lib/new_relic/agent/instrumentation/logger.rb +1 -3
- data/lib/new_relic/agent/instrumentation/logstasher/chain.rb +21 -0
- data/lib/new_relic/agent/instrumentation/logstasher/instrumentation.rb +24 -0
- data/lib/new_relic/agent/instrumentation/logstasher/prepend.rb +13 -0
- data/lib/new_relic/agent/instrumentation/logstasher.rb +25 -0
- data/lib/new_relic/agent/instrumentation/memcache/dalli.rb +1 -1
- data/lib/new_relic/agent/instrumentation/memcache/helper.rb +2 -2
- data/lib/new_relic/agent/instrumentation/memcache/instrumentation.rb +1 -1
- data/lib/new_relic/agent/instrumentation/memcache/prepend.rb +1 -1
- data/lib/new_relic/agent/instrumentation/memcache.rb +0 -1
- data/lib/new_relic/agent/instrumentation/mongodb_command_subscriber.rb +1 -1
- data/lib/new_relic/agent/instrumentation/net_http/instrumentation.rb +3 -3
- data/lib/new_relic/agent/instrumentation/net_http.rb +2 -1
- data/lib/new_relic/agent/instrumentation/notifications_subscriber.rb +0 -2
- data/lib/new_relic/agent/instrumentation/opensearch/chain.rb +21 -0
- data/lib/new_relic/agent/instrumentation/opensearch/instrumentation.rb +66 -0
- data/lib/{tasks/instrumentation_generator/templates/instrumentation.tt → new_relic/agent/instrumentation/opensearch/prepend.rb} +4 -4
- data/lib/new_relic/agent/instrumentation/opensearch.rb +23 -0
- data/lib/new_relic/agent/instrumentation/padrino.rb +3 -3
- data/lib/new_relic/agent/instrumentation/rack/instrumentation.rb +3 -0
- data/lib/new_relic/agent/instrumentation/rails_notifications/action_controller.rb +9 -5
- data/lib/new_relic/agent/instrumentation/rake.rb +1 -2
- data/lib/new_relic/agent/instrumentation/rdkafka/chain.rb +72 -0
- data/lib/new_relic/agent/instrumentation/rdkafka/instrumentation.rb +70 -0
- data/lib/new_relic/agent/instrumentation/rdkafka/prepend.rb +67 -0
- data/lib/new_relic/agent/instrumentation/rdkafka.rb +25 -0
- data/lib/new_relic/agent/instrumentation/redis/cluster_middleware.rb +26 -0
- data/lib/new_relic/agent/instrumentation/redis/constants.rb +2 -2
- data/lib/new_relic/agent/instrumentation/redis/instrumentation.rb +14 -11
- data/lib/new_relic/agent/instrumentation/redis/middleware.rb +3 -0
- data/lib/new_relic/agent/instrumentation/redis.rb +11 -5
- data/lib/new_relic/agent/instrumentation/resque.rb +8 -6
- data/lib/new_relic/agent/instrumentation/roda.rb +5 -5
- data/lib/new_relic/agent/instrumentation/ruby_kafka/chain.rb +55 -0
- data/lib/new_relic/agent/instrumentation/ruby_kafka/instrumentation.rb +67 -0
- data/lib/new_relic/agent/instrumentation/ruby_kafka/prepend.rb +60 -0
- data/lib/new_relic/agent/instrumentation/ruby_kafka.rb +25 -0
- data/lib/new_relic/agent/instrumentation/ruby_openai.rb +2 -2
- data/lib/new_relic/agent/instrumentation/sidekiq/extensions/delay_extensions.rb +24 -0
- data/lib/new_relic/agent/instrumentation/sidekiq/extensions/delayed_class.rb +2 -2
- data/lib/new_relic/agent/instrumentation/sidekiq.rb +9 -15
- data/lib/new_relic/agent/instrumentation/sinatra.rb +3 -19
- data/lib/new_relic/agent/instrumentation/stripe.rb +1 -1
- data/lib/new_relic/agent/instrumentation/stripe_subscriber.rb +22 -1
- data/lib/new_relic/agent/instrumentation/thread.rb +0 -2
- data/lib/new_relic/agent/instrumentation/tilt.rb +0 -4
- data/lib/new_relic/agent/instrumentation/typhoeus/instrumentation.rb +2 -2
- data/lib/new_relic/agent/instrumentation/typhoeus.rb +0 -1
- data/lib/new_relic/agent/instrumentation/view_component/instrumentation.rb +11 -5
- data/lib/new_relic/agent/instrumentation/view_component.rb +0 -2
- data/lib/new_relic/agent/javascript_instrumentor.rb +2 -3
- data/lib/new_relic/agent/llm/chat_completion_summary.rb +1 -1
- data/lib/new_relic/agent/llm/embedding.rb +1 -1
- data/lib/new_relic/agent/local_log_decorator.rb +20 -3
- data/lib/new_relic/agent/log_event_aggregator.rb +119 -28
- data/lib/new_relic/agent/logging.rb +1 -1
- data/lib/new_relic/agent/messaging.rb +16 -5
- data/lib/new_relic/agent/method_tracer.rb +3 -0
- data/lib/new_relic/agent/monitors/inbound_request_monitor.rb +1 -1
- data/lib/new_relic/agent/monitors/synthetics_monitor.rb +1 -1
- data/lib/new_relic/agent/new_relic_service/json_marshaller.rb +2 -2
- data/lib/new_relic/agent/new_relic_service.rb +8 -2
- data/lib/new_relic/agent/opentelemetry/context/propagation/trace_propagator.rb +66 -0
- data/lib/new_relic/agent/opentelemetry/context/propagation.rb +15 -0
- data/lib/{tasks/instrumentation_generator/templates/Envfile.tt → new_relic/agent/opentelemetry/context.rb} +9 -5
- data/lib/new_relic/agent/opentelemetry/trace/span.rb +31 -0
- data/lib/new_relic/agent/opentelemetry/trace/tracer.rb +129 -0
- data/lib/new_relic/agent/opentelemetry/trace/tracer_provider.rb +18 -0
- data/lib/new_relic/agent/opentelemetry/trace.rb +15 -0
- data/lib/new_relic/agent/opentelemetry/transaction_patch.rb +69 -0
- data/lib/new_relic/agent/opentelemetry_bridge.rb +32 -0
- data/lib/new_relic/agent/parameter_filtering.rb +1 -1
- data/lib/new_relic/agent/samplers/cpu_sampler.rb +1 -1
- data/lib/new_relic/agent/samplers/memory_sampler.rb +1 -1
- data/lib/new_relic/agent/serverless_handler.rb +247 -12
- data/lib/new_relic/agent/serverless_handler_event_sources.json +155 -0
- data/lib/new_relic/agent/serverless_handler_event_sources.rb +49 -0
- data/lib/new_relic/agent/span_event_primitive.rb +16 -11
- data/lib/new_relic/agent/system_info.rb +14 -0
- data/lib/new_relic/agent/threading/backtrace_node.rb +10 -1
- data/lib/new_relic/agent/tracer.rb +1 -1
- data/lib/new_relic/agent/transaction/abstract_segment.rb +2 -1
- data/lib/new_relic/agent/transaction/datastore_segment.rb +1 -1
- data/lib/new_relic/agent/transaction/distributed_tracer.rb +3 -3
- data/lib/new_relic/agent/transaction/external_request_segment.rb +0 -10
- data/lib/new_relic/agent/transaction/message_broker_segment.rb +4 -1
- data/lib/new_relic/agent/transaction/request_attributes.rb +14 -7
- data/lib/new_relic/agent/transaction/trace_context.rb +34 -5
- data/lib/new_relic/agent/transaction/tracing.rb +3 -3
- data/lib/new_relic/agent/transaction.rb +4 -7
- data/lib/new_relic/agent/transaction_time_aggregator.rb +1 -1
- data/lib/new_relic/agent/utilization/ecs.rb +22 -0
- data/lib/new_relic/agent/utilization/ecs_v4.rb +22 -0
- data/lib/new_relic/agent/utilization_data.rb +40 -5
- data/lib/new_relic/agent/vm/c_ruby_vm.rb +3 -3
- data/lib/new_relic/agent.rb +124 -2
- data/lib/new_relic/constants.rb +1 -0
- data/lib/new_relic/control/frameworks/grape.rb +14 -0
- data/lib/new_relic/control/frameworks/padrino.rb +14 -0
- data/lib/new_relic/control/frameworks/rails4.rb +1 -3
- data/lib/new_relic/control/instance_methods.rb +6 -0
- data/lib/new_relic/control/instrumentation.rb +1 -1
- data/lib/new_relic/control/private_instance_methods.rb +4 -0
- data/lib/new_relic/control/security_interface.rb +57 -0
- data/lib/new_relic/control.rb +1 -1
- data/lib/new_relic/dependency_detection.rb +11 -14
- data/lib/new_relic/environment_report.rb +2 -2
- data/lib/new_relic/helper.rb +22 -0
- data/lib/new_relic/language_support.rb +3 -1
- data/lib/new_relic/local_environment.rb +1 -4
- data/lib/new_relic/rack/browser_monitoring.rb +20 -8
- data/lib/new_relic/version.rb +1 -1
- data/lib/sequel/extensions/new_relic_instrumentation.rb +3 -2
- data/lib/tasks/config.rake +7 -3
- data/lib/tasks/gha.rake +31 -0
- data/lib/tasks/helpers/config.html.erb +3 -2
- data/lib/tasks/helpers/format.rb +1 -1
- data/lib/tasks/helpers/newrelicyml.rb +80 -13
- data/newrelic.yml +425 -162
- data/newrelic_rpm.gemspec +3 -1
- data/test/agent_helper.rb +24 -2
- metadata +91 -22
- data/lib/tasks/instrumentation_generator/README.md +0 -63
- data/lib/tasks/instrumentation_generator/TODO.md +0 -33
- data/lib/tasks/instrumentation_generator/instrumentation.thor +0 -121
- data/lib/tasks/instrumentation_generator/templates/chain.tt +0 -21
- data/lib/tasks/instrumentation_generator/templates/chain_method.tt +0 -7
- data/lib/tasks/instrumentation_generator/templates/dependency_detection.tt +0 -29
- data/lib/tasks/instrumentation_generator/templates/instrumentation_method.tt +0 -3
- data/lib/tasks/instrumentation_generator/templates/newrelic.yml.tt +0 -19
- data/lib/tasks/instrumentation_generator/templates/prepend.tt +0 -13
- data/lib/tasks/instrumentation_generator/templates/prepend_method.tt +0 -3
- data/lib/tasks/instrumentation_generator/templates/test.tt +0 -15
@@ -9,18 +9,12 @@ module NewRelic
|
|
9
9
|
module Instrumentation
|
10
10
|
module ActiveRecord
|
11
11
|
EXPLAINER = lambda do |statement|
|
12
|
-
|
13
|
-
::ActiveRecord::Base.send("#{statement.config[:adapter]}_connection",
|
14
|
-
statement.config)
|
15
|
-
end
|
16
|
-
# the following line needs else branch coverage
|
17
|
-
if connection && connection.respond_to?(:execute) # rubocop:disable Style/SafeNavigation
|
18
|
-
return connection.execute("EXPLAIN #{statement.sql}")
|
19
|
-
end
|
12
|
+
NewRelic::Agent::Database.explain_this(statement, true)
|
20
13
|
end
|
21
14
|
|
22
15
|
def self.insert_instrumentation
|
23
|
-
if defined?(::ActiveRecord::VERSION::MAJOR) &&
|
16
|
+
if defined?(::ActiveRecord::VERSION::MAJOR) &&
|
17
|
+
NewRelic::Helper.version_satisfied?(::ActiveRecord::VERSION::MAJOR, '>=', 3)
|
24
18
|
if ::NewRelic::Agent.config[:prepend_active_record_instrumentation]
|
25
19
|
::ActiveRecord::Base.prepend(::NewRelic::Agent::Instrumentation::ActiveRecordPrepend::BaseExtensions)
|
26
20
|
::ActiveRecord::Relation.prepend(::NewRelic::Agent::Instrumentation::ActiveRecordPrepend::RelationExtensions)
|
@@ -44,7 +38,7 @@ module NewRelic
|
|
44
38
|
end
|
45
39
|
end
|
46
40
|
|
47
|
-
if RUBY_VERSION < '2.7.0'
|
41
|
+
if NewRelic::Helper.version_satisfied?(RUBY_VERSION, '<', '2.7.0')
|
48
42
|
def log_with_newrelic_instrumentation(*args, &block)
|
49
43
|
state = NewRelic::Agent::Tracer.state
|
50
44
|
|
@@ -144,7 +138,7 @@ DependencyDetection.defer do
|
|
144
138
|
depends_on do
|
145
139
|
defined?(ActiveRecord) && defined?(ActiveRecord::Base) &&
|
146
140
|
(!defined?(ActiveRecord::VERSION) ||
|
147
|
-
ActiveRecord::VERSION::MAJOR
|
141
|
+
NewRelic::Helper.version_satisfied?(ActiveRecord::VERSION::MAJOR, '<=', 3))
|
148
142
|
end
|
149
143
|
|
150
144
|
depends_on do
|
@@ -158,7 +152,8 @@ DependencyDetection.defer do
|
|
158
152
|
executes do
|
159
153
|
require 'new_relic/agent/instrumentation/active_record_helper'
|
160
154
|
|
161
|
-
if defined?(Rails::VERSION::MAJOR) &&
|
155
|
+
if defined?(Rails::VERSION::MAJOR) &&
|
156
|
+
NewRelic::Helper.version_satisfied?(Rails::VERSION::MAJOR, '==', 3)
|
162
157
|
ActiveSupport.on_load(:active_record) do
|
163
158
|
NewRelic::Agent::Instrumentation::ActiveRecord.insert_instrumentation
|
164
159
|
end
|
@@ -49,7 +49,7 @@ module NewRelic
|
|
49
49
|
|
50
50
|
alias_method(:delete_all_without_newrelic, :delete_all)
|
51
51
|
|
52
|
-
if RUBY_VERSION < '2.7.0'
|
52
|
+
if NewRelic::Helper.version_satisfied?(RUBY_VERSION, '<', '2.7.0')
|
53
53
|
def delete_all(*args, &blk)
|
54
54
|
::NewRelic::Agent.with_database_metric_name(self.name, nil, ACTIVE_RECORD) do
|
55
55
|
delete_all_without_newrelic(*args, &blk)
|
@@ -170,6 +170,9 @@ module NewRelic
|
|
170
170
|
|
171
171
|
'sqlite3' => 'SQLite',
|
172
172
|
|
173
|
+
# https://rubygems.org/gems/trilogy
|
174
|
+
'trilogy' => 'MySQL',
|
175
|
+
|
173
176
|
# https://rubygems.org/gems/activerecord-jdbcpostgresql-adapter
|
174
177
|
'jdbcmysql' => 'MySQL',
|
175
178
|
|
@@ -222,7 +225,8 @@ module NewRelic
|
|
222
225
|
|
223
226
|
'postgresql' => :postgres,
|
224
227
|
'jdbcpostgresql' => :postgres,
|
225
|
-
'postgis' => :postgres
|
228
|
+
'postgis' => :postgres,
|
229
|
+
'redshift' => :postgres
|
226
230
|
}.freeze
|
227
231
|
|
228
232
|
DATASTORE_DEFAULT_PORTS = {
|
@@ -231,7 +235,7 @@ module NewRelic
|
|
231
235
|
}.freeze
|
232
236
|
|
233
237
|
DEFAULT = 'default'.freeze
|
234
|
-
UNKNOWN =
|
238
|
+
UNKNOWN = NewRelic::UNKNOWN_LOWER
|
235
239
|
LOCALHOST = 'localhost'.freeze
|
236
240
|
|
237
241
|
def adapter_from_config(config)
|
@@ -28,7 +28,7 @@ module NewRelic
|
|
28
28
|
) { yield }
|
29
29
|
rescue => e
|
30
30
|
# The translate_exception_class method got introduced in 4.1
|
31
|
-
if ::ActiveRecord::VERSION::MINOR == 0
|
31
|
+
if NewRelic::Helper.version_satisfied?(::ActiveRecord::VERSION::MINOR, '==', 0)
|
32
32
|
raise translate_exception(e, sql)
|
33
33
|
else
|
34
34
|
raise translate_exception_class(e, sql)
|
@@ -86,7 +86,7 @@ DependencyDetection.defer do
|
|
86
86
|
depends_on do
|
87
87
|
defined?(ActiveRecord) && defined?(ActiveRecord::Base) &&
|
88
88
|
defined?(ActiveRecord::VERSION) &&
|
89
|
-
ActiveRecord::VERSION::MAJOR
|
89
|
+
NewRelic::Helper.version_satisfied?(ActiveRecord::VERSION::MAJOR, '>=', 4)
|
90
90
|
end
|
91
91
|
|
92
92
|
depends_on do
|
@@ -113,7 +113,7 @@ DependencyDetection.defer do
|
|
113
113
|
|
114
114
|
# Default to .prepending, unless the ActiveRecord version is <=4
|
115
115
|
# **AND** the :prepend_active_record_instrumentation config is false
|
116
|
-
if ActiveRecord::VERSION::MAJOR > 4 \
|
116
|
+
if NewRelic::Helper.version_satisfied?(ActiveRecord::VERSION::MAJOR, '>', 4) \
|
117
117
|
|| NewRelic::Agent.config[:prepend_active_record_instrumentation]
|
118
118
|
|
119
119
|
ActiveRecord::Base.send(:prepend,
|
@@ -131,11 +131,13 @@ DependencyDetection.defer do
|
|
131
131
|
major_version = ActiveRecord::VERSION::MAJOR.to_i
|
132
132
|
minor_version = ActiveRecord::VERSION::MINOR.to_i
|
133
133
|
|
134
|
-
activerecord_extension = if major_version == 4
|
134
|
+
activerecord_extension = if NewRelic::Helper.version_satisfied?(major_version, '==', 4)
|
135
135
|
NewRelic::Agent::Instrumentation::ActiveRecordNotifications::BaseExtensions4x
|
136
|
-
elsif major_version == 5 &&
|
136
|
+
elsif NewRelic::Helper.version_satisfied?(major_version, '==', 5) &&
|
137
|
+
NewRelic::Helper.version_satisfied?(minor_version, '==', 0)
|
137
138
|
NewRelic::Agent::Instrumentation::ActiveRecordNotifications::BaseExtensions50
|
138
|
-
elsif major_version == 5 &&
|
139
|
+
elsif NewRelic::Helper.version_satisfied?(major_version, '==', 5) &&
|
140
|
+
NewRelic::Helper.version_satisfied?(minor_version, '==', 1)
|
139
141
|
NewRelic::Agent::Instrumentation::ActiveRecordNotifications::BaseExtensions51
|
140
142
|
end
|
141
143
|
|
@@ -146,9 +148,9 @@ DependencyDetection.defer do
|
|
146
148
|
end
|
147
149
|
|
148
150
|
executes do
|
149
|
-
if ActiveRecord::VERSION::MAJOR == 5 \
|
150
|
-
&& ActiveRecord::VERSION::MINOR
|
151
|
-
&& ActiveRecord::VERSION::TINY
|
151
|
+
if NewRelic::Helper.version_satisfied?(ActiveRecord::VERSION::MAJOR, '==', 5) \
|
152
|
+
&& NewRelic::Helper.version_satisfied?(ActiveRecord::VERSION::MINOR, '==', 1) \
|
153
|
+
&& NewRelic::Helper.version_satisfied?(ActiveRecord::VERSION::TINY, '>=', 6)
|
152
154
|
|
153
155
|
ActiveRecord::Base.prepend(NewRelic::Agent::Instrumentation::ActiveRecordPrepend::BaseExtensions516)
|
154
156
|
end
|
@@ -11,7 +11,7 @@ module NewRelic
|
|
11
11
|
ACTIVE_RECORD = 'ActiveRecord'.freeze
|
12
12
|
|
13
13
|
module BaseExtensions
|
14
|
-
if RUBY_VERSION < '2.7.0'
|
14
|
+
if NewRelic::Helper.version_satisfied?(RUBY_VERSION, '<', '2.7.0')
|
15
15
|
def save(*args, &blk)
|
16
16
|
::NewRelic::Agent.with_database_metric_name(self.class.name, nil, ACTIVE_RECORD) do
|
17
17
|
super
|
@@ -46,7 +46,7 @@ module NewRelic
|
|
46
46
|
# Starting in v5.1.6, this call no longer happens. We'll
|
47
47
|
# have to set the database metrics explicitly now.
|
48
48
|
#
|
49
|
-
if RUBY_VERSION < '2.7.0'
|
49
|
+
if NewRelic::Helper.version_satisfied?(RUBY_VERSION, '<', '2.7.0')
|
50
50
|
def touch(*args, **kwargs, &blk)
|
51
51
|
::NewRelic::Agent.with_database_metric_name(self.class.name, nil, ACTIVE_RECORD) do
|
52
52
|
super
|
@@ -70,18 +70,7 @@ module NewRelic
|
|
70
70
|
end
|
71
71
|
|
72
72
|
def get_explain_plan(statement)
|
73
|
-
|
74
|
-
::ActiveRecord::Base.send("#{statement.config[:adapter]}_connection",
|
75
|
-
statement.config)
|
76
|
-
end
|
77
|
-
# the following line needs else branch coverage
|
78
|
-
if connection && connection.respond_to?(:exec_query) # rubocop:disable Style/SafeNavigation
|
79
|
-
return connection.exec_query("EXPLAIN #{statement.sql}",
|
80
|
-
"Explain #{statement.name}",
|
81
|
-
statement.binds)
|
82
|
-
end
|
83
|
-
rescue => e
|
84
|
-
NewRelic::Agent.logger.debug("Couldn't fetch the explain plan for #{statement} due to #{e}")
|
73
|
+
NewRelic::Agent::Database.explain_this(statement)
|
85
74
|
end
|
86
75
|
|
87
76
|
def active_record_config(payload)
|
@@ -127,10 +116,14 @@ module NewRelic
|
|
127
116
|
port_path_or_id = nil
|
128
117
|
database = nil
|
129
118
|
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
|
119
|
+
begin
|
120
|
+
if ActiveRecordHelper::InstanceIdentification.supported_adapter?(config)
|
121
|
+
host = ActiveRecordHelper::InstanceIdentification.host(config)
|
122
|
+
port_path_or_id = ActiveRecordHelper::InstanceIdentification.port_path_or_id(config)
|
123
|
+
database = config && config[:database]
|
124
|
+
end
|
125
|
+
rescue
|
126
|
+
NewRelic::Agent.logger.debug("Failed to retrieve ActiveRecord host, port, and database details for adapter: #{config && config[:adapter]}")
|
134
127
|
end
|
135
128
|
|
136
129
|
segment = Tracer.start_datastore_segment(product: product,
|
@@ -12,8 +12,6 @@ DependencyDetection.defer do
|
|
12
12
|
depends_on { defined?(ActiveSupport::BroadcastLogger) }
|
13
13
|
|
14
14
|
executes do
|
15
|
-
NewRelic::Agent.logger.info('Installing ActiveSupport::BroadcastLogger instrumentation')
|
16
|
-
|
17
15
|
if use_prepend?
|
18
16
|
prepend_instrument ActiveSupport::BroadcastLogger, NewRelic::Agent::Instrumentation::ActiveSupportBroadcastLogger::Prepend
|
19
17
|
else
|
@@ -14,8 +14,6 @@ DependencyDetection.defer do
|
|
14
14
|
end
|
15
15
|
|
16
16
|
executes do
|
17
|
-
NewRelic::Agent.logger.info('Installing ActiveSupport::Logger instrumentation')
|
18
|
-
|
19
17
|
if use_prepend?
|
20
18
|
# the only method currently instrumented is a class method
|
21
19
|
prepend_instrument ActiveSupport::Logger.singleton_class, NewRelic::Agent::Instrumentation::ActiveSupportLogger::Prepend
|
@@ -11,14 +11,13 @@ DependencyDetection.defer do
|
|
11
11
|
|
12
12
|
depends_on do
|
13
13
|
defined?(Async::HTTP) &&
|
14
|
-
|
14
|
+
NewRelic::Helper.version_satisfied?(Async::HTTP::VERSION, '>=', '0.59.0') &&
|
15
15
|
!defined?(Traces::Backend::NewRelic) # defined in the traces-backend-newrelic gem
|
16
16
|
end
|
17
17
|
|
18
18
|
executes do
|
19
|
-
NewRelic::Agent.logger.info('Installing async_http instrumentation')
|
20
|
-
|
21
19
|
require 'async/http/internet'
|
20
|
+
|
22
21
|
if use_prepend?
|
23
22
|
prepend_instrument Async::HTTP::Internet, NewRelic::Agent::Instrumentation::AsyncHttp::Prepend
|
24
23
|
else
|
@@ -0,0 +1,21 @@
|
|
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::Agent::Instrumentation
|
6
|
+
module Firehose::Chain
|
7
|
+
def self.instrument!
|
8
|
+
::Aws::Firehose::Client.class_eval do
|
9
|
+
include NewRelic::Agent::Instrumentation::Firehose
|
10
|
+
|
11
|
+
NewRelic::Agent::Instrumentation::Firehose::INSTRUMENTED_METHODS.each do |method_name|
|
12
|
+
alias_method("#{method_name}_without_new_relic".to_sym, method_name.to_sym)
|
13
|
+
|
14
|
+
define_method(method_name) do |*args|
|
15
|
+
instrument_method_with_new_relic(method_name, *args) { send("#{method_name}_without_new_relic".to_sym, *args) }
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,66 @@
|
|
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::Agent::Instrumentation
|
6
|
+
module Firehose
|
7
|
+
INSTRUMENTED_METHODS = %w[
|
8
|
+
create_delivery_stream
|
9
|
+
delete_delivery_stream
|
10
|
+
describe_delivery_stream
|
11
|
+
list_delivery_streams
|
12
|
+
list_tags_for_delivery_stream
|
13
|
+
put_record
|
14
|
+
put_record_batch
|
15
|
+
start_delivery_stream_encryption
|
16
|
+
stop_delivery_stream_encryption
|
17
|
+
tag_delivery_stream
|
18
|
+
untag_delivery_stream
|
19
|
+
update_destination
|
20
|
+
].freeze
|
21
|
+
|
22
|
+
FIREHOSE = 'Firehose'
|
23
|
+
AWS_KINESIS_DELIVERY_STREAMS = 'aws_kinesis_delivery_streams'
|
24
|
+
|
25
|
+
def instrument_method_with_new_relic(method_name, *args)
|
26
|
+
return yield unless NewRelic::Agent::Tracer.tracing_enabled?
|
27
|
+
|
28
|
+
NewRelic::Agent.record_instrumentation_invocation(FIREHOSE)
|
29
|
+
|
30
|
+
params = args[0]
|
31
|
+
segment = NewRelic::Agent::Tracer.start_segment(name: get_segment_name(method_name, params))
|
32
|
+
arn = get_arn(params) if params
|
33
|
+
segment&.add_agent_attribute('cloud.resource_id', arn) if arn
|
34
|
+
|
35
|
+
begin
|
36
|
+
NewRelic::Agent::Tracer.capture_segment_error(segment) { yield }
|
37
|
+
ensure
|
38
|
+
segment&.add_agent_attribute('cloud.platform', AWS_KINESIS_DELIVERY_STREAMS)
|
39
|
+
segment&.finish
|
40
|
+
end
|
41
|
+
end
|
42
|
+
|
43
|
+
def get_segment_name(method_name, params)
|
44
|
+
stream_name = params&.dig(:delivery_stream_name)
|
45
|
+
return "#{FIREHOSE}/#{method_name}/#{stream_name}" if stream_name
|
46
|
+
|
47
|
+
"#{FIREHOSE}/#{method_name}"
|
48
|
+
rescue => e
|
49
|
+
NewRelic::Agent.logger.warn("Failed to create segment name: #{e}")
|
50
|
+
end
|
51
|
+
|
52
|
+
def nr_account_id
|
53
|
+
return @nr_account_id if defined?(@nr_account_id)
|
54
|
+
|
55
|
+
@nr_account_id = NewRelic::Agent::Aws.get_account_id(config)
|
56
|
+
end
|
57
|
+
|
58
|
+
def get_arn(params)
|
59
|
+
stream_arn = params&.dig(:delivery_stream_arn)
|
60
|
+
return stream_arn if stream_arn
|
61
|
+
|
62
|
+
stream_name = params&.dig(:delivery_stream_name)
|
63
|
+
NewRelic::Agent::Aws.create_arn(FIREHOSE.downcase, "deliverystream/#{stream_name}", config&.region, nr_account_id) if stream_name
|
64
|
+
end
|
65
|
+
end
|
66
|
+
end
|
@@ -0,0 +1,15 @@
|
|
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::Agent::Instrumentation
|
6
|
+
module Firehose::Prepend
|
7
|
+
include NewRelic::Agent::Instrumentation::Firehose
|
8
|
+
|
9
|
+
INSTRUMENTED_METHODS.each do |method_name|
|
10
|
+
define_method(method_name) do |*args|
|
11
|
+
instrument_method_with_new_relic(method_name, *args) { super(*args) }
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
@@ -0,0 +1,22 @@
|
|
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
|
+
require_relative 'aws_sdk_firehose/instrumentation'
|
6
|
+
require_relative 'aws_sdk_firehose/chain'
|
7
|
+
require_relative 'aws_sdk_firehose/prepend'
|
8
|
+
|
9
|
+
DependencyDetection.defer do
|
10
|
+
named :aws_sdk_firehose
|
11
|
+
|
12
|
+
depends_on do
|
13
|
+
defined?(Aws::Firehose::Client)
|
14
|
+
end
|
15
|
+
executes do
|
16
|
+
if use_prepend?
|
17
|
+
prepend_instrument Aws::Firehose::Client, NewRelic::Agent::Instrumentation::Firehose::Prepend
|
18
|
+
else
|
19
|
+
chain_instrument NewRelic::Agent::Instrumentation::Firehose::Chain
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,21 @@
|
|
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::Agent::Instrumentation
|
6
|
+
module Kinesis::Chain
|
7
|
+
def self.instrument!
|
8
|
+
::Aws::Kinesis::Client.class_eval do
|
9
|
+
include NewRelic::Agent::Instrumentation::Kinesis
|
10
|
+
|
11
|
+
NewRelic::Agent::Instrumentation::Kinesis::INSTRUMENTED_METHODS.each do |method_name|
|
12
|
+
alias_method("#{method_name}_without_new_relic".to_sym, method_name.to_sym)
|
13
|
+
|
14
|
+
define_method(method_name) do |*args|
|
15
|
+
instrument_method_with_new_relic(method_name, *args) { send("#{method_name}_without_new_relic".to_sym, *args) }
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,91 @@
|
|
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::Agent::Instrumentation
|
6
|
+
module Kinesis
|
7
|
+
INSTRUMENTED_METHODS = %w[
|
8
|
+
add_tags_to_stream
|
9
|
+
create_stream
|
10
|
+
decrease_stream_retention_period
|
11
|
+
delete_stream
|
12
|
+
describe_limits
|
13
|
+
describe_stream
|
14
|
+
disable_enhanced_monitoring
|
15
|
+
enable_enhanced_monitoring
|
16
|
+
get_records
|
17
|
+
get_shard_iterator
|
18
|
+
increase_stream_retention_period
|
19
|
+
list_streams
|
20
|
+
list_tags_for_stream
|
21
|
+
merge_shards
|
22
|
+
put_record
|
23
|
+
put_records
|
24
|
+
remove_tags_from_stream
|
25
|
+
split_shard
|
26
|
+
update_shard_count
|
27
|
+
].freeze
|
28
|
+
|
29
|
+
KINESIS = 'Kinesis'
|
30
|
+
AWS_KINESIS_DATA_STREAMS = 'aws_kinesis_data_streams'
|
31
|
+
MESSAGE_BROKER_SEGMENT_METHODS = %w[put_record put_records get_records].freeze
|
32
|
+
|
33
|
+
def instrument_method_with_new_relic(method_name, *args)
|
34
|
+
return yield unless NewRelic::Agent::Tracer.tracing_enabled?
|
35
|
+
|
36
|
+
NewRelic::Agent.record_instrumentation_invocation(KINESIS)
|
37
|
+
params = args[0]
|
38
|
+
arn = get_arn(params) if params
|
39
|
+
|
40
|
+
if MESSAGE_BROKER_SEGMENT_METHODS.include?(method_name)
|
41
|
+
stream_name = get_stream_name(params, arn)
|
42
|
+
segment = NewRelic::Agent::Tracer.start_message_broker_segment(
|
43
|
+
action: method_name == 'get_records' ? :consume : :produce,
|
44
|
+
library: KINESIS,
|
45
|
+
destination_type: :stream,
|
46
|
+
destination_name: stream_name
|
47
|
+
)
|
48
|
+
else
|
49
|
+
segment = NewRelic::Agent::Tracer.start_segment(name: get_segment_name(method_name, params))
|
50
|
+
end
|
51
|
+
|
52
|
+
segment&.add_agent_attribute('cloud.resource_id', arn) if arn
|
53
|
+
|
54
|
+
begin
|
55
|
+
NewRelic::Agent::Tracer.capture_segment_error(segment) { yield }
|
56
|
+
ensure
|
57
|
+
segment&.add_agent_attribute('cloud.platform', AWS_KINESIS_DATA_STREAMS)
|
58
|
+
segment&.finish
|
59
|
+
end
|
60
|
+
end
|
61
|
+
|
62
|
+
def get_segment_name(method_name, params)
|
63
|
+
stream_name = params&.dig(:stream_name)
|
64
|
+
return "#{KINESIS}/#{method_name}/#{stream_name}" if stream_name
|
65
|
+
|
66
|
+
"#{KINESIS}/#{method_name}"
|
67
|
+
rescue => e
|
68
|
+
NewRelic::Agent.logger.warn("Failed to create segment name: #{e}")
|
69
|
+
end
|
70
|
+
|
71
|
+
def get_stream_name(params, arn)
|
72
|
+
params&.dig(:stream_name) || arn.split('/').last || NewRelic::UNKNOWN_LOWER
|
73
|
+
rescue => e
|
74
|
+
NewRelic::Agent.logger.warn("Failed to get stream name: #{e}")
|
75
|
+
end
|
76
|
+
|
77
|
+
def nr_account_id
|
78
|
+
return @nr_account_id if defined?(@nr_account_id)
|
79
|
+
|
80
|
+
@nr_account_id = NewRelic::Agent::Aws.get_account_id(config)
|
81
|
+
end
|
82
|
+
|
83
|
+
def get_arn(params)
|
84
|
+
stream_arn = params&.dig(:stream_arn)
|
85
|
+
return stream_arn if stream_arn
|
86
|
+
|
87
|
+
stream_name = params&.dig(:stream_name)
|
88
|
+
NewRelic::Agent::Aws.create_arn(KINESIS.downcase, "stream/#{stream_name}", config&.region, nr_account_id) if stream_name
|
89
|
+
end
|
90
|
+
end
|
91
|
+
end
|
@@ -0,0 +1,15 @@
|
|
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::Agent::Instrumentation
|
6
|
+
module Kinesis::Prepend
|
7
|
+
include NewRelic::Agent::Instrumentation::Kinesis
|
8
|
+
|
9
|
+
INSTRUMENTED_METHODS.each do |method_name|
|
10
|
+
define_method(method_name) do |*args|
|
11
|
+
instrument_method_with_new_relic(method_name, *args) { super(*args) }
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
@@ -0,0 +1,22 @@
|
|
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
|
+
require_relative 'aws_sdk_kinesis/instrumentation'
|
6
|
+
require_relative 'aws_sdk_kinesis/chain'
|
7
|
+
require_relative 'aws_sdk_kinesis/prepend'
|
8
|
+
|
9
|
+
DependencyDetection.defer do
|
10
|
+
named :aws_sdk_kinesis
|
11
|
+
|
12
|
+
depends_on do
|
13
|
+
defined?(Aws::Kinesis::Client)
|
14
|
+
end
|
15
|
+
executes do
|
16
|
+
if use_prepend?
|
17
|
+
prepend_instrument Aws::Kinesis::Client, NewRelic::Agent::Instrumentation::Kinesis::Prepend
|
18
|
+
else
|
19
|
+
chain_instrument NewRelic::Agent::Instrumentation::Kinesis::Chain
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,33 @@
|
|
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
|
+
require_relative 'instrumentation'
|
6
|
+
|
7
|
+
module NewRelic::Agent::Instrumentation
|
8
|
+
module AwsSdkLambda::Chain
|
9
|
+
def self.instrument!
|
10
|
+
::Aws::Lambda::Client.class_eval do
|
11
|
+
include NewRelic::Agent::Instrumentation::AwsSdkLambda
|
12
|
+
|
13
|
+
alias_method(:invoke_without_new_relic, :invoke)
|
14
|
+
|
15
|
+
def invoke(*args)
|
16
|
+
invoke_with_new_relic(*args) { invoke_without_new_relic(*args) }
|
17
|
+
end
|
18
|
+
|
19
|
+
alias_method(:invoke_async_without_new_relic, :invoke_async)
|
20
|
+
|
21
|
+
def invoke_async(*args)
|
22
|
+
invoke_async_with_new_relic(*args) { invoke_async_without_new_relic(*args) }
|
23
|
+
end
|
24
|
+
|
25
|
+
alias_method(:invoke_with_response_stream_without_new_relic, :invoke_with_response_stream)
|
26
|
+
|
27
|
+
def invoke_with_response_stream(*args)
|
28
|
+
invoke_with_response_stream_with_new_relic(*args) { invoke_with_response_stream_without_new_relic(*args) }
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -0,0 +1,93 @@
|
|
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
|
+
require 'json'
|
6
|
+
|
7
|
+
module NewRelic::Agent::Instrumentation
|
8
|
+
module AwsSdkLambda
|
9
|
+
INSTRUMENTATION_NAME = 'aws_sdk_lambda'
|
10
|
+
AWS_SERVICE = 'lambda'
|
11
|
+
CLOUD_PLATFORM = 'aws_lambda'
|
12
|
+
WRAPPED_RESPONSE = Struct.new(:status_code, :has_status_code?)
|
13
|
+
|
14
|
+
def invoke_with_new_relic(*args)
|
15
|
+
with_tracing(:invoke, *args) { yield }
|
16
|
+
end
|
17
|
+
|
18
|
+
def invoke_async_with_new_relic(*args)
|
19
|
+
with_tracing(:invoke_async, *args) { yield }
|
20
|
+
end
|
21
|
+
|
22
|
+
def invoke_with_response_stream_with_new_relic(*args)
|
23
|
+
with_tracing(:invoke_with_response_stream, *args) { yield }
|
24
|
+
end
|
25
|
+
|
26
|
+
private
|
27
|
+
|
28
|
+
def with_tracing(action, *args)
|
29
|
+
segment = generate_segment(action, *args)
|
30
|
+
|
31
|
+
# prevent additional instrumentation for things like Net::HTTP from
|
32
|
+
# creating any segments that may appear as redundant / confusing
|
33
|
+
NewRelic::Agent.disable_all_tracing do
|
34
|
+
response = NewRelic::Agent::Tracer.capture_segment_error(segment) { yield }
|
35
|
+
process_response(response, segment)
|
36
|
+
response
|
37
|
+
end
|
38
|
+
ensure
|
39
|
+
segment&.finish
|
40
|
+
end
|
41
|
+
|
42
|
+
def process_response(response, segment)
|
43
|
+
process_function_error(response) if response.respond_to?(:function_error)
|
44
|
+
rescue => e
|
45
|
+
NewRelic::Agent.logger.error("Error processing aws-sdk-lambda invocation response: #{e}")
|
46
|
+
end
|
47
|
+
|
48
|
+
# notice error that was raised / unhandled by the function
|
49
|
+
def process_function_error(response)
|
50
|
+
function_error = response.function_error
|
51
|
+
return unless function_error
|
52
|
+
|
53
|
+
msg = "[#{function_error}]"
|
54
|
+
payload = response.payload&.string if response.respond_to?(:payload)
|
55
|
+
payload_hash = JSON.parse(payload) if payload
|
56
|
+
msg = "#{msg} #{payload_hash['errorType']} - #{payload_hash['errorMessage']}" if payload_hash
|
57
|
+
e = StandardError.new(msg)
|
58
|
+
e.set_backtrace(payload_hash['stackTrace']) if payload_hash
|
59
|
+
|
60
|
+
NewRelic::Agent.notice_error(e)
|
61
|
+
end
|
62
|
+
|
63
|
+
def generate_segment(action, options = {})
|
64
|
+
function = function_name(options)
|
65
|
+
region = aws_region
|
66
|
+
arn = aws_arn(function, region)
|
67
|
+
segment = NewRelic::Agent::Tracer.start_segment(name: "Lambda/#{action}/#{function}")
|
68
|
+
segment.add_agent_attribute('cloud.account.id', nr_account_id)
|
69
|
+
segment.add_agent_attribute('cloud.platform', CLOUD_PLATFORM)
|
70
|
+
segment.add_agent_attribute('cloud.region', region)
|
71
|
+
segment.add_agent_attribute('cloud.resource_id', arn) if arn
|
72
|
+
segment
|
73
|
+
end
|
74
|
+
|
75
|
+
def function_name(options = {})
|
76
|
+
(options.fetch(:function_name, nil) if options.respond_to?(:fetch)) || NewRelic::UNKNOWN
|
77
|
+
end
|
78
|
+
|
79
|
+
def aws_region
|
80
|
+
config&.region if self.respond_to?(:config)
|
81
|
+
end
|
82
|
+
|
83
|
+
def aws_arn(function, region)
|
84
|
+
NewRelic::Agent::Aws.create_arn(AWS_SERVICE, "function:#{function}", region, nr_account_id)
|
85
|
+
end
|
86
|
+
|
87
|
+
def nr_account_id
|
88
|
+
return @nr_account_id if defined?(@nr_account_id)
|
89
|
+
|
90
|
+
@nr_account_id = NewRelic::Agent::Aws.get_account_id(config)
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|