datadog 2.23.0 → 2.28.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/CHANGELOG.md +132 -2
- data/ext/datadog_profiling_native_extension/clock_id_from_pthread.c +2 -1
- data/ext/datadog_profiling_native_extension/collectors_cpu_and_wall_time_worker.c +100 -29
- data/ext/datadog_profiling_native_extension/collectors_discrete_dynamic_sampler.c +2 -2
- data/ext/datadog_profiling_native_extension/collectors_gc_profiling_helper.c +3 -2
- data/ext/datadog_profiling_native_extension/collectors_stack.c +23 -10
- data/ext/datadog_profiling_native_extension/collectors_thread_context.c +16 -12
- data/ext/datadog_profiling_native_extension/crashtracking_runtime_stacks.c +239 -0
- data/ext/datadog_profiling_native_extension/datadog_ruby_common.c +48 -1
- data/ext/datadog_profiling_native_extension/datadog_ruby_common.h +41 -0
- data/ext/datadog_profiling_native_extension/encoded_profile.c +2 -1
- data/ext/datadog_profiling_native_extension/extconf.rb +4 -1
- data/ext/datadog_profiling_native_extension/heap_recorder.c +24 -24
- data/ext/datadog_profiling_native_extension/http_transport.c +10 -4
- data/ext/datadog_profiling_native_extension/libdatadog_helpers.c +3 -22
- data/ext/datadog_profiling_native_extension/libdatadog_helpers.h +0 -5
- data/ext/datadog_profiling_native_extension/private_vm_api_access.c +21 -8
- data/ext/datadog_profiling_native_extension/private_vm_api_access.h +4 -0
- data/ext/datadog_profiling_native_extension/profiling.c +22 -15
- data/ext/datadog_profiling_native_extension/ruby_helpers.c +55 -44
- data/ext/datadog_profiling_native_extension/ruby_helpers.h +17 -5
- data/ext/datadog_profiling_native_extension/setup_signal_handler.c +8 -2
- data/ext/datadog_profiling_native_extension/setup_signal_handler.h +3 -0
- data/ext/datadog_profiling_native_extension/stack_recorder.c +16 -16
- data/ext/datadog_profiling_native_extension/unsafe_api_calls_check.c +2 -1
- data/ext/datadog_profiling_native_extension/unsafe_api_calls_check.h +5 -2
- data/ext/libdatadog_api/crashtracker.c +5 -8
- data/ext/libdatadog_api/datadog_ruby_common.c +48 -1
- data/ext/libdatadog_api/datadog_ruby_common.h +41 -0
- data/ext/libdatadog_api/ddsketch.c +4 -8
- data/ext/libdatadog_api/feature_flags.c +5 -5
- data/ext/libdatadog_api/helpers.h +27 -0
- data/ext/libdatadog_api/init.c +4 -0
- data/ext/libdatadog_extconf_helpers.rb +1 -1
- data/lib/datadog/ai_guard/api_client.rb +82 -0
- data/lib/datadog/ai_guard/component.rb +42 -0
- data/lib/datadog/ai_guard/configuration/ext.rb +17 -0
- data/lib/datadog/ai_guard/configuration/settings.rb +110 -0
- data/lib/datadog/ai_guard/configuration.rb +11 -0
- data/lib/datadog/ai_guard/contrib/integration.rb +37 -0
- data/lib/datadog/ai_guard/contrib/ruby_llm/chat_instrumentation.rb +42 -0
- data/lib/datadog/ai_guard/contrib/ruby_llm/integration.rb +41 -0
- data/lib/datadog/ai_guard/contrib/ruby_llm/patcher.rb +30 -0
- data/lib/datadog/ai_guard/evaluation/message.rb +25 -0
- data/lib/datadog/ai_guard/evaluation/no_op_result.rb +34 -0
- data/lib/datadog/ai_guard/evaluation/request.rb +81 -0
- data/lib/datadog/ai_guard/evaluation/result.rb +43 -0
- data/lib/datadog/ai_guard/evaluation/tool_call.rb +18 -0
- data/lib/datadog/ai_guard/evaluation.rb +72 -0
- data/lib/datadog/ai_guard/ext.rb +16 -0
- data/lib/datadog/ai_guard.rb +155 -0
- data/lib/datadog/appsec/api_security/endpoint_collection/rails_collector.rb +8 -1
- data/lib/datadog/appsec/api_security/endpoint_collection/rails_route_serializer.rb +9 -2
- data/lib/datadog/appsec/component.rb +1 -1
- data/lib/datadog/appsec/context.rb +5 -4
- data/lib/datadog/appsec/contrib/active_record/integration.rb +1 -1
- data/lib/datadog/appsec/contrib/active_record/patcher.rb +1 -1
- data/lib/datadog/appsec/contrib/excon/integration.rb +1 -1
- data/lib/datadog/appsec/contrib/excon/patcher.rb +1 -1
- data/lib/datadog/appsec/contrib/excon/ssrf_detection_middleware.rb +47 -12
- data/lib/datadog/appsec/contrib/faraday/ssrf_detection_middleware.rb +32 -15
- data/lib/datadog/appsec/contrib/rails/patcher.rb +10 -2
- data/lib/datadog/appsec/contrib/rest_client/integration.rb +1 -1
- data/lib/datadog/appsec/contrib/rest_client/patcher.rb +1 -1
- data/lib/datadog/appsec/contrib/rest_client/request_ssrf_detection_patch.rb +50 -14
- data/lib/datadog/appsec/contrib/sinatra/gateway/watcher.rb +5 -4
- data/lib/datadog/appsec/contrib/sinatra/integration.rb +1 -1
- data/lib/datadog/appsec/contrib/sinatra/patcher.rb +4 -4
- data/lib/datadog/appsec/contrib/sinatra/patches/json_patch.rb +1 -1
- data/lib/datadog/appsec/ext.rb +2 -0
- data/lib/datadog/appsec/metrics/collector.rb +8 -3
- data/lib/datadog/appsec/metrics/exporter.rb +7 -0
- data/lib/datadog/appsec/metrics/telemetry.rb +7 -2
- data/lib/datadog/appsec/metrics.rb +5 -5
- data/lib/datadog/appsec/remote.rb +7 -14
- data/lib/datadog/appsec/security_engine/engine.rb +3 -3
- data/lib/datadog/appsec/security_engine/result.rb +2 -1
- data/lib/datadog/appsec/security_engine/runner.rb +2 -2
- data/lib/datadog/appsec/utils/http/media_type.rb +37 -23
- data/lib/datadog/appsec.rb +7 -1
- data/lib/datadog/core/configuration/components.rb +7 -0
- data/lib/datadog/core/configuration/config_helper.rb +1 -1
- data/lib/datadog/core/configuration/deprecations.rb +2 -2
- data/lib/datadog/core/configuration/option_definition.rb +4 -2
- data/lib/datadog/core/configuration/options.rb +8 -5
- data/lib/datadog/core/configuration/settings.rb +31 -3
- data/lib/datadog/core/configuration/supported_configurations.rb +10 -1
- data/lib/datadog/core/crashtracking/tag_builder.rb +6 -0
- data/lib/datadog/core/environment/cgroup.rb +52 -25
- data/lib/datadog/core/environment/container.rb +140 -46
- data/lib/datadog/core/environment/ext.rb +1 -0
- data/lib/datadog/core/environment/process.rb +9 -1
- data/lib/datadog/core/error.rb +6 -6
- data/lib/datadog/core/knuth_sampler.rb +57 -0
- data/lib/datadog/core/pin.rb +4 -0
- data/lib/datadog/core/rate_limiter.rb +9 -1
- data/lib/datadog/core/remote/client.rb +14 -6
- data/lib/datadog/core/remote/component.rb +6 -4
- data/lib/datadog/core/remote/configuration/content.rb +15 -2
- data/lib/datadog/core/remote/configuration/digest.rb +14 -7
- data/lib/datadog/core/remote/configuration/repository.rb +1 -1
- data/lib/datadog/core/remote/configuration/target.rb +13 -6
- data/lib/datadog/core/remote/transport/config.rb +3 -16
- data/lib/datadog/core/remote/transport/http/config.rb +4 -44
- data/lib/datadog/core/remote/transport/http/negotiation.rb +0 -39
- data/lib/datadog/core/remote/transport/http.rb +13 -24
- data/lib/datadog/core/remote/transport/negotiation.rb +7 -16
- data/lib/datadog/core/runtime/metrics.rb +11 -1
- data/lib/datadog/core/semaphore.rb +1 -4
- data/lib/datadog/core/telemetry/component.rb +52 -13
- data/lib/datadog/core/telemetry/event/app_started.rb +36 -1
- data/lib/datadog/core/telemetry/event/synth_app_client_configuration_change.rb +27 -4
- data/lib/datadog/core/telemetry/logger.rb +2 -0
- data/lib/datadog/core/telemetry/logging.rb +20 -2
- data/lib/datadog/core/telemetry/metrics_manager.rb +9 -0
- data/lib/datadog/core/telemetry/request.rb +17 -3
- data/lib/datadog/core/telemetry/transport/http/telemetry.rb +2 -32
- data/lib/datadog/core/telemetry/transport/http.rb +21 -16
- data/lib/datadog/core/telemetry/transport/telemetry.rb +3 -10
- data/lib/datadog/core/telemetry/worker.rb +88 -32
- data/lib/datadog/core/transport/ext.rb +2 -0
- data/lib/datadog/core/transport/http/api/endpoint.rb +9 -4
- data/lib/datadog/core/transport/http/api/instance.rb +4 -21
- data/lib/datadog/core/transport/http/builder.rb +9 -5
- data/lib/datadog/core/transport/http/client.rb +19 -8
- data/lib/datadog/core/transport/http.rb +22 -19
- data/lib/datadog/core/transport/response.rb +12 -1
- data/lib/datadog/core/transport/transport.rb +90 -0
- data/lib/datadog/core/utils/only_once_successful.rb +2 -0
- data/lib/datadog/core/utils/safe_dup.rb +2 -2
- data/lib/datadog/core/utils/sequence.rb +2 -0
- data/lib/datadog/core/utils/time.rb +1 -1
- data/lib/datadog/core/workers/async.rb +10 -1
- data/lib/datadog/core/workers/interval_loop.rb +44 -3
- data/lib/datadog/core/workers/polling.rb +2 -0
- data/lib/datadog/core/workers/queue.rb +100 -1
- data/lib/datadog/data_streams/processor.rb +1 -1
- data/lib/datadog/data_streams/transport/http/stats.rb +1 -36
- data/lib/datadog/data_streams/transport/http.rb +5 -6
- data/lib/datadog/data_streams/transport/stats.rb +3 -17
- data/lib/datadog/di/boot.rb +4 -2
- data/lib/datadog/di/configuration/settings.rb +22 -0
- data/lib/datadog/di/contrib/active_record.rb +30 -5
- data/lib/datadog/di/el/compiler.rb +8 -4
- data/lib/datadog/di/error.rb +5 -0
- data/lib/datadog/di/instrumenter.rb +26 -7
- data/lib/datadog/di/logger.rb +2 -2
- data/lib/datadog/di/probe_builder.rb +2 -1
- data/lib/datadog/di/probe_file_loader/railtie.rb +1 -1
- data/lib/datadog/di/probe_manager.rb +37 -31
- data/lib/datadog/di/probe_notification_builder.rb +15 -2
- data/lib/datadog/di/probe_notifier_worker.rb +5 -5
- data/lib/datadog/di/redactor.rb +8 -1
- data/lib/datadog/di/remote.rb +89 -84
- data/lib/datadog/di/transport/diagnostics.rb +7 -35
- data/lib/datadog/di/transport/http/diagnostics.rb +1 -31
- data/lib/datadog/di/transport/http/input.rb +1 -31
- data/lib/datadog/di/transport/http.rb +28 -17
- data/lib/datadog/di/transport/input.rb +7 -34
- data/lib/datadog/di.rb +61 -5
- data/lib/datadog/error_tracking/filters.rb +2 -2
- data/lib/datadog/kit/appsec/events/v2.rb +2 -3
- data/lib/datadog/open_feature/evaluation_engine.rb +2 -1
- data/lib/datadog/open_feature/remote.rb +3 -10
- data/lib/datadog/open_feature/transport.rb +9 -11
- data/lib/datadog/opentelemetry/api/baggage.rb +1 -1
- data/lib/datadog/opentelemetry/configuration/settings.rb +2 -2
- data/lib/datadog/opentelemetry/metrics.rb +21 -14
- data/lib/datadog/opentelemetry/sdk/metrics_exporter.rb +5 -8
- data/lib/datadog/profiling/collectors/code_provenance.rb +27 -2
- data/lib/datadog/profiling/collectors/cpu_and_wall_time_worker.rb +3 -2
- data/lib/datadog/profiling/collectors/info.rb +5 -4
- data/lib/datadog/profiling/component.rb +25 -11
- data/lib/datadog/profiling/exporter.rb +4 -0
- data/lib/datadog/profiling/ext/dir_monkey_patches.rb +18 -0
- data/lib/datadog/profiling/ext/exec_monkey_patch.rb +32 -0
- data/lib/datadog/profiling/flush.rb +3 -0
- data/lib/datadog/profiling/http_transport.rb +4 -1
- data/lib/datadog/profiling/profiler.rb +3 -5
- data/lib/datadog/profiling/scheduler.rb +8 -7
- data/lib/datadog/profiling/tag_builder.rb +1 -0
- data/lib/datadog/tracing/contrib/extensions.rb +10 -2
- data/lib/datadog/tracing/contrib/karafka/patcher.rb +31 -32
- data/lib/datadog/tracing/contrib/status_range_matcher.rb +2 -1
- data/lib/datadog/tracing/contrib/utils/quantization/hash.rb +3 -1
- data/lib/datadog/tracing/contrib/waterdrop/patcher.rb +6 -3
- data/lib/datadog/tracing/contrib/waterdrop.rb +4 -0
- data/lib/datadog/tracing/diagnostics/environment_logger.rb +1 -1
- data/lib/datadog/tracing/distributed/baggage.rb +3 -2
- data/lib/datadog/tracing/remote.rb +1 -9
- data/lib/datadog/tracing/sampling/priority_sampler.rb +3 -1
- data/lib/datadog/tracing/sampling/rate_sampler.rb +8 -19
- data/lib/datadog/tracing/span.rb +1 -1
- data/lib/datadog/tracing/span_event.rb +2 -2
- data/lib/datadog/tracing/span_operation.rb +20 -9
- data/lib/datadog/tracing/trace_operation.rb +44 -6
- data/lib/datadog/tracing/tracer.rb +42 -16
- data/lib/datadog/tracing/transport/http/traces.rb +2 -50
- data/lib/datadog/tracing/transport/http.rb +15 -9
- data/lib/datadog/tracing/transport/io/client.rb +1 -1
- data/lib/datadog/tracing/transport/traces.rb +6 -66
- data/lib/datadog/tracing/workers/trace_writer.rb +5 -0
- data/lib/datadog/tracing/writer.rb +1 -0
- data/lib/datadog/version.rb +2 -2
- data/lib/datadog.rb +1 -0
- metadata +33 -19
- data/lib/datadog/core/remote/transport/http/api.rb +0 -53
- data/lib/datadog/core/telemetry/transport/http/api.rb +0 -43
- data/lib/datadog/core/transport/http/api/spec.rb +0 -36
- data/lib/datadog/data_streams/transport/http/api.rb +0 -33
- data/lib/datadog/data_streams/transport/http/client.rb +0 -21
- data/lib/datadog/di/transport/http/api.rb +0 -42
- data/lib/datadog/opentelemetry/api/baggage.rbs +0 -26
- data/lib/datadog/tracing/transport/http/api.rb +0 -44
|
@@ -4,9 +4,6 @@ module Datadog
|
|
|
4
4
|
module Profiling
|
|
5
5
|
# Responsible for wiring up the Profiler for execution
|
|
6
6
|
module Component
|
|
7
|
-
ALLOCATION_WITH_RACTORS_ONLY_ONCE = Datadog::Core::Utils::OnlyOnce.new
|
|
8
|
-
private_constant :ALLOCATION_WITH_RACTORS_ONLY_ONCE
|
|
9
|
-
|
|
10
7
|
# Passing in a `nil` tracer is supported and will disable the following profiling features:
|
|
11
8
|
# * Profiling in the trace viewer, as well as scoping a profile down to a span
|
|
12
9
|
# * Endpoint aggregation in the profiler UX, including normalization (resource per endpoint call)
|
|
@@ -85,6 +82,10 @@ module Datadog
|
|
|
85
82
|
Datadog::Profiling::Ext::DirMonkeyPatches.apply!
|
|
86
83
|
end
|
|
87
84
|
|
|
85
|
+
if can_apply_exec_monkey_patch?(settings)
|
|
86
|
+
Datadog::Profiling::Ext::ExecMonkeyPatch.apply!
|
|
87
|
+
end
|
|
88
|
+
|
|
88
89
|
[profiler, {profiling_enabled: true}]
|
|
89
90
|
end
|
|
90
91
|
|
|
@@ -145,7 +146,7 @@ module Datadog
|
|
|
145
146
|
logger.debug(
|
|
146
147
|
"Using Ractors may result in GC profiling unexpectedly " \
|
|
147
148
|
"stopping (https://bugs.ruby-lang.org/issues/19112). Note that this stop has no impact in your " \
|
|
148
|
-
"application stability or performance. This
|
|
149
|
+
"application stability or performance. This issue is fixed on Ruby 4."
|
|
149
150
|
)
|
|
150
151
|
end
|
|
151
152
|
|
|
@@ -195,13 +196,11 @@ module Datadog
|
|
|
195
196
|
# On all known versions of Ruby 3.x, due to https://bugs.ruby-lang.org/issues/19112, when a ractor gets
|
|
196
197
|
# garbage collected, Ruby will disable all active tracepoints, which this feature internally relies on.
|
|
197
198
|
elsif RUBY_VERSION.start_with?("3.")
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
)
|
|
204
|
-
end
|
|
199
|
+
logger.debug(
|
|
200
|
+
"Using Ractors may result in allocation profiling " \
|
|
201
|
+
"stopping (https://bugs.ruby-lang.org/issues/19112). Note that this stop has no impact in your " \
|
|
202
|
+
"application stability or performance. This issue is fixed on Ruby 4."
|
|
203
|
+
)
|
|
205
204
|
end
|
|
206
205
|
|
|
207
206
|
logger.debug("Enabled allocation profiling")
|
|
@@ -220,6 +219,12 @@ module Datadog
|
|
|
220
219
|
"Please upgrade to Ruby >= 3.1 in order to use this feature. Heap profiling has been disabled."
|
|
221
220
|
)
|
|
222
221
|
return false
|
|
222
|
+
elsif RUBY_VERSION.start_with?("4.")
|
|
223
|
+
logger.warn(
|
|
224
|
+
"Datadog Ruby heap profiler is currently incompatible with Ruby 4. " \
|
|
225
|
+
"Heap profiling has been disabled."
|
|
226
|
+
)
|
|
227
|
+
return false
|
|
223
228
|
end
|
|
224
229
|
|
|
225
230
|
unless allocation_profiling_enabled
|
|
@@ -433,6 +438,15 @@ module Datadog
|
|
|
433
438
|
settings.profiling.advanced.dir_interruption_workaround_enabled
|
|
434
439
|
end
|
|
435
440
|
|
|
441
|
+
private_class_method def self.can_apply_exec_monkey_patch?(settings)
|
|
442
|
+
return false if RUBY_VERSION < "2.7"
|
|
443
|
+
|
|
444
|
+
# This file is 2.7+ only so we only require it here once we've checked the Ruby version
|
|
445
|
+
require "datadog/profiling/ext/exec_monkey_patch"
|
|
446
|
+
|
|
447
|
+
settings.profiling.advanced.shutdown_on_exec_enabled
|
|
448
|
+
end
|
|
449
|
+
|
|
436
450
|
private_class_method def self.enable_gvl_profiling?(settings, logger)
|
|
437
451
|
return false if RUBY_VERSION < "3.2"
|
|
438
452
|
|
|
@@ -70,6 +70,9 @@ module Datadog
|
|
|
70
70
|
|
|
71
71
|
uncompressed_code_provenance = code_provenance_collector.refresh.generate_json if code_provenance_collector
|
|
72
72
|
|
|
73
|
+
process_tags = Datadog.configuration.experimental_propagate_process_tags_enabled ?
|
|
74
|
+
Core::Environment::Process.serialized : ''
|
|
75
|
+
|
|
73
76
|
Flush.new(
|
|
74
77
|
start: start,
|
|
75
78
|
finish: finish,
|
|
@@ -80,6 +83,7 @@ module Datadog
|
|
|
80
83
|
settings: Datadog.configuration,
|
|
81
84
|
profile_seq: sequence_tracker.get_next,
|
|
82
85
|
).to_a,
|
|
86
|
+
process_tags: process_tags,
|
|
83
87
|
internal_metadata: internal_metadata.merge(
|
|
84
88
|
{
|
|
85
89
|
worker_stats: worker_stats,
|
|
@@ -30,6 +30,10 @@ module Datadog
|
|
|
30
30
|
if RUBY_VERSION.start_with?("2.")
|
|
31
31
|
# Monkey patches for Dir.singleton_class (Ruby 2 version). See DirMonkeyPatches above for more details.
|
|
32
32
|
module DirClassMonkeyPatches
|
|
33
|
+
# Steep: Workaround that defines args and block only for Ruby 2.x.
|
|
34
|
+
# @type var args: ::Array[any]
|
|
35
|
+
# @type var block: ^(?) -> any | nil
|
|
36
|
+
|
|
33
37
|
def [](*args, &block)
|
|
34
38
|
Datadog::Profiling::Collectors::CpuAndWallTimeWorker._native_hold_signals
|
|
35
39
|
super
|
|
@@ -148,6 +152,11 @@ module Datadog
|
|
|
148
152
|
else
|
|
149
153
|
# Monkey patches for Dir.singleton_class (Ruby 3 version). See DirMonkeyPatches above for more details.
|
|
150
154
|
module DirClassMonkeyPatches
|
|
155
|
+
# Steep: Workaround that defines args, kwargs and block only for Ruby 3.x.
|
|
156
|
+
# @type var args: ::Array[any]
|
|
157
|
+
# @type var kwargs: ::Hash[::Symbol, any]
|
|
158
|
+
# @type var block: ^(?) -> any | nil
|
|
159
|
+
|
|
151
160
|
def [](*args, **kwargs, &block)
|
|
152
161
|
Datadog::Profiling::Collectors::CpuAndWallTimeWorker._native_hold_signals
|
|
153
162
|
super
|
|
@@ -263,6 +272,10 @@ module Datadog
|
|
|
263
272
|
if RUBY_VERSION.start_with?("2.")
|
|
264
273
|
# Monkey patches for Dir (Ruby 2 version). See DirMonkeyPatches above for more details.
|
|
265
274
|
module DirInstanceMonkeyPatches
|
|
275
|
+
# Steep: Workaround that defines args and block only for Ruby 2.x.
|
|
276
|
+
# @type var args: ::Array[any]
|
|
277
|
+
# @type var block: ^(?) -> any | nil
|
|
278
|
+
|
|
266
279
|
# See note on methods that yield above.
|
|
267
280
|
def each(*args, &block)
|
|
268
281
|
if block
|
|
@@ -336,6 +349,11 @@ module Datadog
|
|
|
336
349
|
else
|
|
337
350
|
# Monkey patches for Dir (Ruby 3 version). See DirMonkeyPatches above for more details.
|
|
338
351
|
module DirInstanceMonkeyPatches
|
|
352
|
+
# Steep: Workaround that defines args, kwargs and block only for Ruby 3.x.
|
|
353
|
+
# @type var args: ::Array[any]
|
|
354
|
+
# @type var kwargs: ::Hash[::Symbol, any]
|
|
355
|
+
# @type var block: ^(?) -> any | nil
|
|
356
|
+
|
|
339
357
|
# See note on methods that yield above.
|
|
340
358
|
def each(*args, **kwargs, &block)
|
|
341
359
|
if block
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Datadog
|
|
4
|
+
module Profiling
|
|
5
|
+
module Ext
|
|
6
|
+
# The profiler gathers data by sending `SIGPROF` unix signals to Ruby application threads.
|
|
7
|
+
#
|
|
8
|
+
# When using `Kernel#exec` on Linux, it can happen that a signal sent before calling `exec` arrives after
|
|
9
|
+
# the new process is running, causing it to fail with the `Profiling timer expired` error message.
|
|
10
|
+
# To avoid this, the profiler installs a monkey patch on `Kernel#exec` to stop profiling before actually
|
|
11
|
+
# calling `exec`.
|
|
12
|
+
# This monkey patch is available for Ruby 2.7+; let us know if you need it on earlier Rubies.
|
|
13
|
+
# For more details see https://github.com/DataDog/dd-trace-rb/issues/5101 .
|
|
14
|
+
module ExecMonkeyPatch
|
|
15
|
+
def self.apply!
|
|
16
|
+
::Object.prepend(ObjectMonkeyPatch)
|
|
17
|
+
|
|
18
|
+
true
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
module ObjectMonkeyPatch
|
|
22
|
+
private
|
|
23
|
+
|
|
24
|
+
def exec(...)
|
|
25
|
+
Datadog.send(:components, allow_initialization: false)&.profiler&.shutdown!(report_last_profile: false)
|
|
26
|
+
super
|
|
27
|
+
end
|
|
28
|
+
end
|
|
29
|
+
end
|
|
30
|
+
end
|
|
31
|
+
end
|
|
32
|
+
end
|
|
@@ -13,6 +13,7 @@ module Datadog
|
|
|
13
13
|
:code_provenance_file_name,
|
|
14
14
|
:code_provenance_data,
|
|
15
15
|
:tags_as_array,
|
|
16
|
+
:process_tags,
|
|
16
17
|
:internal_metadata_json,
|
|
17
18
|
:info_json
|
|
18
19
|
|
|
@@ -23,6 +24,7 @@ module Datadog
|
|
|
23
24
|
code_provenance_file_name:,
|
|
24
25
|
code_provenance_data:,
|
|
25
26
|
tags_as_array:,
|
|
27
|
+
process_tags:,
|
|
26
28
|
internal_metadata:,
|
|
27
29
|
info_json:
|
|
28
30
|
)
|
|
@@ -32,6 +34,7 @@ module Datadog
|
|
|
32
34
|
@code_provenance_file_name = code_provenance_file_name
|
|
33
35
|
@code_provenance_data = code_provenance_data
|
|
34
36
|
@tags_as_array = tags_as_array
|
|
37
|
+
@process_tags = process_tags
|
|
35
38
|
@internal_metadata_json = JSON.generate(internal_metadata)
|
|
36
39
|
@info_json = info_json
|
|
37
40
|
end
|
|
@@ -13,7 +13,10 @@ module Datadog
|
|
|
13
13
|
def initialize(agent_settings:, site:, api_key:, upload_timeout_seconds:)
|
|
14
14
|
@upload_timeout_milliseconds = (upload_timeout_seconds * 1_000).to_i
|
|
15
15
|
|
|
16
|
-
|
|
16
|
+
# Steep: multiple issues here
|
|
17
|
+
# first https://github.com/soutaro/steep/issues/363
|
|
18
|
+
# then https://github.com/soutaro/steep/issues/1603 (remove the .freeze to see it)
|
|
19
|
+
@exporter_configuration = # steep:ignore IncompatibleAssignment
|
|
17
20
|
if agentless?(site, api_key)
|
|
18
21
|
[:agentless, site, api_key].freeze
|
|
19
22
|
else
|
|
@@ -31,10 +31,11 @@ module Datadog
|
|
|
31
31
|
scheduler.start(on_failure_proc: proc { component_failed(:scheduler) })
|
|
32
32
|
end
|
|
33
33
|
|
|
34
|
-
def shutdown!
|
|
34
|
+
def shutdown!(report_last_profile: true)
|
|
35
35
|
Datadog.logger.debug("Shutting down profiler")
|
|
36
36
|
|
|
37
37
|
stop_worker
|
|
38
|
+
scheduler.disable_reporting unless report_last_profile
|
|
38
39
|
stop_scheduler
|
|
39
40
|
end
|
|
40
41
|
|
|
@@ -57,11 +58,8 @@ module Datadog
|
|
|
57
58
|
Datadog::Core::Telemetry::Logger
|
|
58
59
|
.error("Detected issue with profiler (#{failed_component} component), stopping profiling")
|
|
59
60
|
|
|
60
|
-
# We explicitly not stop the crash tracker in this situation, under the assumption that, if a component failed,
|
|
61
|
-
# we're operating in a degraded state and crash tracking may still be helpful.
|
|
62
|
-
|
|
63
61
|
if failed_component == :worker
|
|
64
|
-
scheduler.
|
|
62
|
+
scheduler.disable_reporting
|
|
65
63
|
stop_scheduler
|
|
66
64
|
elsif failed_component == :scheduler
|
|
67
65
|
stop_worker
|
|
@@ -24,7 +24,7 @@ module Datadog
|
|
|
24
24
|
attr_reader \
|
|
25
25
|
:exporter,
|
|
26
26
|
:transport,
|
|
27
|
-
:
|
|
27
|
+
:reporting_disabled
|
|
28
28
|
|
|
29
29
|
public
|
|
30
30
|
|
|
@@ -36,7 +36,7 @@ module Datadog
|
|
|
36
36
|
)
|
|
37
37
|
@exporter = exporter
|
|
38
38
|
@transport = transport
|
|
39
|
-
@
|
|
39
|
+
@reporting_disabled = false
|
|
40
40
|
@stop_requested = false
|
|
41
41
|
|
|
42
42
|
# Workers::Async::Thread settings
|
|
@@ -83,14 +83,15 @@ module Datadog
|
|
|
83
83
|
true
|
|
84
84
|
end
|
|
85
85
|
|
|
86
|
-
#
|
|
87
|
-
# if there is data to be flushed
|
|
88
|
-
|
|
89
|
-
|
|
86
|
+
# Called by the Profiler when it wants to prevent any further reporting,
|
|
87
|
+
# even if there is data to be flushed.
|
|
88
|
+
# Used when the profiler failed or we're otherwise in a hurry to shut down.
|
|
89
|
+
def disable_reporting
|
|
90
|
+
@reporting_disabled = true
|
|
90
91
|
end
|
|
91
92
|
|
|
92
93
|
def work_pending?
|
|
93
|
-
!
|
|
94
|
+
!reporting_disabled && exporter.can_flush? && (run_loop? || !stop_requested?)
|
|
94
95
|
end
|
|
95
96
|
|
|
96
97
|
def reset_after_fork
|
|
@@ -50,6 +50,7 @@ module Datadog
|
|
|
50
50
|
FORM_FIELD_TAG_PROFILER_VERSION => profiler_version,
|
|
51
51
|
'profile_seq' => profile_seq.to_s,
|
|
52
52
|
)
|
|
53
|
+
|
|
53
54
|
user_tag_keys = settings.tags.keys
|
|
54
55
|
hash.keep_if { |tag| user_tag_keys.include?(tag) || ALLOWED_TAGS.include?(tag) }
|
|
55
56
|
Core::Utils.encode_tags(hash)
|
|
@@ -220,12 +220,20 @@ module Datadog
|
|
|
220
220
|
# `@instrumented_integrations` hash.
|
|
221
221
|
# @!visibility private
|
|
222
222
|
def instrumented_integrations
|
|
223
|
-
INSTRUMENTED_INTEGRATIONS_LOCK.synchronize
|
|
223
|
+
INSTRUMENTED_INTEGRATIONS_LOCK.synchronize do
|
|
224
|
+
(if defined?(@instrumented_integrations)
|
|
225
|
+
@instrumented_integrations&.dup
|
|
226
|
+
end || {}).freeze
|
|
227
|
+
end
|
|
224
228
|
end
|
|
225
229
|
|
|
226
230
|
# @!visibility private
|
|
227
231
|
def reset!
|
|
228
|
-
INSTRUMENTED_INTEGRATIONS_LOCK.synchronize
|
|
232
|
+
INSTRUMENTED_INTEGRATIONS_LOCK.synchronize do
|
|
233
|
+
if defined?(@instrumented_integrations)
|
|
234
|
+
@instrumented_integrations&.clear
|
|
235
|
+
end
|
|
236
|
+
end
|
|
229
237
|
super
|
|
230
238
|
end
|
|
231
239
|
|
|
@@ -25,35 +25,34 @@ module Datadog
|
|
|
25
25
|
# @see https://github.com/karafka/karafka/blob/b06d1f7c17818e1605f80c2bb573454a33376b40/README.md?plain=1#L29-L35
|
|
26
26
|
def each(&block)
|
|
27
27
|
@messages_array.each do |message|
|
|
28
|
-
if configuration[:distributed_tracing]
|
|
28
|
+
trace_digest = if configuration[:distributed_tracing]
|
|
29
29
|
headers = if message.metadata.respond_to?(:raw_headers)
|
|
30
30
|
message.metadata.raw_headers
|
|
31
31
|
else
|
|
32
32
|
message.metadata.headers
|
|
33
33
|
end
|
|
34
|
-
|
|
35
|
-
Datadog::Tracing.continue_trace!(trace_digest) if trace_digest
|
|
34
|
+
Karafka.extract(headers)
|
|
36
35
|
end
|
|
37
36
|
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
message.metadata.raw_headers
|
|
42
|
-
|
|
43
|
-
|
|
37
|
+
Tracing.trace(Ext::SPAN_MESSAGE_CONSUME, continue_from: trace_digest) do |span, trace|
|
|
38
|
+
if Datadog::DataStreams.enabled?
|
|
39
|
+
begin
|
|
40
|
+
headers = if message.metadata.respond_to?(:raw_headers)
|
|
41
|
+
message.metadata.raw_headers
|
|
42
|
+
else
|
|
43
|
+
message.metadata.headers
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
Datadog::DataStreams.set_consume_checkpoint(
|
|
47
|
+
type: 'kafka',
|
|
48
|
+
source: message.topic,
|
|
49
|
+
auto_instrumentation: true
|
|
50
|
+
) { |key| headers[key] }
|
|
51
|
+
rescue => e
|
|
52
|
+
Datadog.logger.debug("Error setting DSM checkpoint: #{e.class}: #{e}")
|
|
44
53
|
end
|
|
45
|
-
|
|
46
|
-
Datadog::DataStreams.set_consume_checkpoint(
|
|
47
|
-
type: 'kafka',
|
|
48
|
-
source: message.topic,
|
|
49
|
-
auto_instrumentation: true
|
|
50
|
-
) { |key| headers[key] }
|
|
51
|
-
rescue => e
|
|
52
|
-
Datadog.logger.debug("Error setting DSM checkpoint: #{e.class}: #{e}")
|
|
53
54
|
end
|
|
54
|
-
end
|
|
55
55
|
|
|
56
|
-
Tracing.trace(Ext::SPAN_MESSAGE_CONSUME) do |span|
|
|
57
56
|
span.set_tag(Ext::TAG_OFFSET, message.metadata.offset)
|
|
58
57
|
span.set_tag(Contrib::Ext::Messaging::TAG_DESTINATION, message.topic)
|
|
59
58
|
span.set_tag(Contrib::Ext::Messaging::TAG_SYSTEM, Ext::TAG_SYSTEM)
|
|
@@ -66,22 +65,12 @@ module Datadog
|
|
|
66
65
|
end
|
|
67
66
|
end
|
|
68
67
|
|
|
69
|
-
module AppPatch
|
|
70
|
-
ONLY_ONCE_PER_APP = Hash.new { |h, key| h[key] = Core::Utils::OnlyOnce.new }
|
|
71
|
-
|
|
72
|
-
def initialized!
|
|
73
|
-
ONLY_ONCE_PER_APP[self].run do
|
|
74
|
-
# Activate tracing on components related to Karafka (e.g. WaterDrop)
|
|
75
|
-
Contrib::Karafka::Framework.setup
|
|
76
|
-
end
|
|
77
|
-
super
|
|
78
|
-
end
|
|
79
|
-
end
|
|
80
|
-
|
|
81
68
|
# Patcher enables patching of 'karafka' module.
|
|
82
69
|
module Patcher
|
|
83
70
|
include Contrib::Patcher
|
|
84
71
|
|
|
72
|
+
ACTIVATE_FRAMEWORK_ONLY_ONCE = Core::Utils::OnlyOnce.new
|
|
73
|
+
|
|
85
74
|
module_function
|
|
86
75
|
|
|
87
76
|
def target_version
|
|
@@ -91,10 +80,20 @@ module Datadog
|
|
|
91
80
|
def patch
|
|
92
81
|
require_relative 'monitor'
|
|
93
82
|
require_relative 'framework'
|
|
83
|
+
require_relative '../waterdrop'
|
|
94
84
|
|
|
95
85
|
::Karafka::Instrumentation::Monitor.prepend(Monitor)
|
|
96
86
|
::Karafka::Messages::Messages.prepend(MessagesPatch)
|
|
97
|
-
|
|
87
|
+
|
|
88
|
+
if Contrib::WaterDrop::Integration.compatible?
|
|
89
|
+
::Karafka.monitor.subscribe('app.initialized') do |event|
|
|
90
|
+
ACTIVATE_FRAMEWORK_ONLY_ONCE.run do
|
|
91
|
+
Contrib::Karafka::Framework.setup
|
|
92
|
+
end
|
|
93
|
+
|
|
94
|
+
Contrib::WaterDrop::Patcher.add_middleware(::Karafka.producer)
|
|
95
|
+
end
|
|
96
|
+
end
|
|
98
97
|
end
|
|
99
98
|
end
|
|
100
99
|
end
|
|
@@ -10,7 +10,9 @@ module Datadog
|
|
|
10
10
|
PLACEHOLDER = '?'
|
|
11
11
|
EXCLUDE_KEYS = [].freeze
|
|
12
12
|
SHOW_KEYS = [].freeze
|
|
13
|
-
|
|
13
|
+
|
|
14
|
+
# Steep: https://github.com/soutaro/steep/issues/363
|
|
15
|
+
DEFAULT_OPTIONS = { # steep:ignore IncompatibleAssignment
|
|
14
16
|
exclude: EXCLUDE_KEYS,
|
|
15
17
|
show: SHOW_KEYS,
|
|
16
18
|
placeholder: PLACEHOLDER
|
|
@@ -25,9 +25,7 @@ module Datadog
|
|
|
25
25
|
::WaterDrop::Producer.prepend(Producer)
|
|
26
26
|
::WaterDrop.instrumentation.subscribe('producer.configured') do |event|
|
|
27
27
|
producer = event[:producer]
|
|
28
|
-
|
|
29
|
-
included_middlewares = producer.middleware.instance_variable_get(:@steps)
|
|
30
|
-
producer.middleware.append(Middleware) unless included_middlewares.include?(Middleware)
|
|
28
|
+
add_middleware(producer)
|
|
31
29
|
|
|
32
30
|
if Datadog.configuration.data_streams.enabled
|
|
33
31
|
producer.monitor.subscribe('message.acknowledged') do |ack_event|
|
|
@@ -39,6 +37,11 @@ module Datadog
|
|
|
39
37
|
end
|
|
40
38
|
end
|
|
41
39
|
end
|
|
40
|
+
|
|
41
|
+
def add_middleware(producer)
|
|
42
|
+
included_middlewares = producer.middleware.instance_variable_get(:@steps)
|
|
43
|
+
producer.middleware.append(Middleware) unless included_middlewares.include?(Middleware)
|
|
44
|
+
end
|
|
42
45
|
end
|
|
43
46
|
end
|
|
44
47
|
end
|
|
@@ -12,12 +12,16 @@ module Datadog
|
|
|
12
12
|
def self.inject(digest, data)
|
|
13
13
|
raise 'Please invoke Datadog.configure at least once before calling this method' unless @propagation
|
|
14
14
|
|
|
15
|
+
# Steep: https://github.com/soutaro/steep/issues/477
|
|
16
|
+
# @type ivar @propagation: WaterDrop::Distributed::Propagation
|
|
15
17
|
@propagation.inject!(digest, data)
|
|
16
18
|
end
|
|
17
19
|
|
|
18
20
|
def self.extract(data)
|
|
19
21
|
raise 'Please invoke Datadog.configure at least once before calling this method' unless @propagation
|
|
20
22
|
|
|
23
|
+
# Steep: https://github.com/soutaro/steep/issues/477
|
|
24
|
+
# @type ivar @propagation: WaterDrop::Distributed::Propagation
|
|
21
25
|
@propagation.extract(data)
|
|
22
26
|
end
|
|
23
27
|
|
|
@@ -175,8 +175,9 @@ module Datadog
|
|
|
175
175
|
|
|
176
176
|
tags = {}
|
|
177
177
|
|
|
178
|
-
baggage_tag_keys.each do |key, _|
|
|
179
|
-
|
|
178
|
+
baggage_tag_keys.each do |key, _|
|
|
179
|
+
# Steep: https://github.com/soutaro/steep/issues/2031
|
|
180
|
+
value = baggage[key] # steep:ignore ArgumentTypeMismatch
|
|
180
181
|
next if value.nil? || value.empty?
|
|
181
182
|
|
|
182
183
|
tags["baggage.#{key}"] = value
|
|
@@ -7,8 +7,6 @@ module Datadog
|
|
|
7
7
|
module Tracing
|
|
8
8
|
# Remote configuration declaration
|
|
9
9
|
module Remote
|
|
10
|
-
class ReadError < StandardError; end
|
|
11
|
-
|
|
12
10
|
class << self
|
|
13
11
|
PRODUCT = 'APM_TRACING'
|
|
14
12
|
|
|
@@ -71,13 +69,7 @@ module Datadog
|
|
|
71
69
|
private
|
|
72
70
|
|
|
73
71
|
def parse_content(content)
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
content.data.rewind
|
|
77
|
-
|
|
78
|
-
raise ReadError, 'EOF reached' if data.nil?
|
|
79
|
-
|
|
80
|
-
JSON.parse(data)
|
|
72
|
+
JSON.parse(content.data)
|
|
81
73
|
end
|
|
82
74
|
end
|
|
83
75
|
end
|
|
@@ -60,7 +60,9 @@ module Datadog
|
|
|
60
60
|
ensure
|
|
61
61
|
if trace.sampling_priority && trace.sampling_priority > 0
|
|
62
62
|
# Don't modify decision if priority was set upstream.
|
|
63
|
-
|
|
63
|
+
# Steep: https://github.com/soutaro/steep/issues/1971
|
|
64
|
+
if !distributed_sampling_priority && # steep:ignore FallbackAny
|
|
65
|
+
!trace.has_tag?(Tracing::Metadata::Ext::Distributed::TAG_DECISION_MAKER)
|
|
64
66
|
# If no sampling priority being assigned at this point, a custom
|
|
65
67
|
# sampler implementation is configured: this means the user has
|
|
66
68
|
# full control over the sampling decision.
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
3
|
require_relative 'sampler'
|
|
4
|
-
require_relative '
|
|
4
|
+
require_relative '../../core/knuth_sampler'
|
|
5
5
|
|
|
6
6
|
module Datadog
|
|
7
7
|
module Tracing
|
|
@@ -9,46 +9,35 @@ module Datadog
|
|
|
9
9
|
# {Datadog::Tracing::Sampling::RateSampler} is based on a sample rate.
|
|
10
10
|
class RateSampler < Sampler
|
|
11
11
|
KNUTH_FACTOR = 1111111111111111111
|
|
12
|
-
UINT64_MODULO = (1 << 64)
|
|
13
12
|
|
|
14
13
|
# Initialize a {Datadog::Tracing::Sampling::RateSampler}.
|
|
15
14
|
# This sampler keeps a random subset of the traces. Its main purpose is to
|
|
16
15
|
# reduce the instrumentation footprint.
|
|
17
16
|
#
|
|
18
17
|
# @param sample_rate [Numeric] the sample rate between 0.0 and 1.0, inclusive.
|
|
19
|
-
# 0.0 means that no trace will be sampled; 1.0 means that all traces will be
|
|
18
|
+
# 0.0 means that no trace will be sampled; 1.0 means that all traces will be sampled.
|
|
20
19
|
def initialize(sample_rate = 1.0, decision: nil)
|
|
21
20
|
super()
|
|
22
|
-
|
|
23
|
-
unless sample_rate >= 0.0 && sample_rate <= 1.0
|
|
24
|
-
Datadog.logger.warn('sample rate is not between 0 and 1, falling back to 1')
|
|
25
|
-
sample_rate = 1.0
|
|
26
|
-
end
|
|
27
|
-
|
|
28
|
-
self.sample_rate = sample_rate
|
|
29
|
-
|
|
21
|
+
@sampler = Core::KnuthSampler.new(sample_rate, knuth_factor: KNUTH_FACTOR)
|
|
30
22
|
@decision = decision
|
|
31
23
|
end
|
|
32
24
|
|
|
33
25
|
def sample_rate(*_)
|
|
34
|
-
@
|
|
26
|
+
@sampler.rate
|
|
35
27
|
end
|
|
36
28
|
|
|
37
29
|
def sample_rate=(sample_rate)
|
|
38
|
-
@
|
|
39
|
-
@sampling_id_threshold = sample_rate * Tracing::Utils::EXTERNAL_MAX_ID
|
|
30
|
+
@sampler = Core::KnuthSampler.new(sample_rate, knuth_factor: KNUTH_FACTOR)
|
|
40
31
|
end
|
|
41
32
|
|
|
42
33
|
def sample?(trace)
|
|
43
|
-
(
|
|
34
|
+
@sampler.sample?(trace.id)
|
|
44
35
|
end
|
|
45
36
|
|
|
46
37
|
def sample!(trace)
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
return false unless sampled
|
|
38
|
+
return false unless sample?(trace)
|
|
50
39
|
|
|
51
|
-
trace.sample_rate =
|
|
40
|
+
trace.sample_rate = sample_rate
|
|
52
41
|
trace.set_tag(Tracing::Metadata::Ext::Distributed::TAG_DECISION_MAKER, @decision) if @decision
|
|
53
42
|
|
|
54
43
|
true
|
data/lib/datadog/tracing/span.rb
CHANGED
|
@@ -69,8 +69,8 @@ module Datadog
|
|
|
69
69
|
|
|
70
70
|
private
|
|
71
71
|
|
|
72
|
-
MIN_INT64_SIGNED = -2
|
|
73
|
-
MAX_INT64_SIGNED = 2 <<
|
|
72
|
+
MIN_INT64_SIGNED = -2 << 62
|
|
73
|
+
MAX_INT64_SIGNED = (2 << 62) - 1
|
|
74
74
|
|
|
75
75
|
# Checks the attributes hash to ensure it only contains serializable values.
|
|
76
76
|
# Invalid values are removed from the hash.
|