datadog 2.22.0 → 2.23.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 +59 -2
- data/ext/LIBDATADOG_DEVELOPMENT.md +1 -58
- data/ext/datadog_profiling_native_extension/collectors_stack.c +4 -0
- data/ext/datadog_profiling_native_extension/datadog_ruby_common.h +1 -1
- data/ext/datadog_profiling_native_extension/extconf.rb +6 -4
- data/ext/datadog_profiling_native_extension/heap_recorder.c +1 -1
- data/ext/libdatadog_api/datadog_ruby_common.h +1 -1
- data/ext/libdatadog_api/feature_flags.c +554 -0
- data/ext/libdatadog_api/feature_flags.h +5 -0
- data/ext/libdatadog_api/init.c +2 -0
- data/ext/libdatadog_api/library_config.c +12 -11
- data/ext/libdatadog_extconf_helpers.rb +1 -1
- data/lib/datadog/appsec/api_security/route_extractor.rb +23 -6
- data/lib/datadog/appsec/api_security/sampler.rb +7 -4
- data/lib/datadog/appsec/assets/blocked.html +8 -0
- data/lib/datadog/appsec/assets/blocked.json +1 -1
- data/lib/datadog/appsec/assets/blocked.text +3 -1
- data/lib/datadog/appsec/assets.rb +1 -1
- data/lib/datadog/appsec/remote.rb +4 -0
- data/lib/datadog/appsec/response.rb +18 -4
- data/lib/datadog/core/configuration/components.rb +30 -3
- data/lib/datadog/core/configuration/config_helper.rb +1 -1
- data/lib/datadog/core/configuration/settings.rb +14 -0
- data/lib/datadog/core/configuration/supported_configurations.rb +330 -301
- data/lib/datadog/core/ddsketch.rb +0 -2
- data/lib/datadog/core/environment/ext.rb +6 -0
- data/lib/datadog/core/environment/process.rb +79 -0
- data/lib/datadog/core/feature_flags.rb +61 -0
- data/lib/datadog/core/remote/client/capabilities.rb +7 -0
- data/lib/datadog/core/remote/transport/config.rb +2 -10
- data/lib/datadog/core/remote/transport/http/config.rb +9 -9
- data/lib/datadog/core/remote/transport/http/negotiation.rb +17 -8
- data/lib/datadog/core/remote/transport/http.rb +2 -0
- data/lib/datadog/core/remote/transport/negotiation.rb +2 -18
- data/lib/datadog/core/remote/worker.rb +25 -37
- data/lib/datadog/core/tag_builder.rb +0 -4
- data/lib/datadog/core/tag_normalizer.rb +84 -0
- data/lib/datadog/core/telemetry/component.rb +7 -3
- data/lib/datadog/core/telemetry/event/app_started.rb +52 -49
- data/lib/datadog/core/telemetry/event/synth_app_client_configuration_change.rb +1 -1
- data/lib/datadog/core/telemetry/logger.rb +2 -2
- data/lib/datadog/core/telemetry/logging.rb +2 -8
- data/lib/datadog/core/telemetry/transport/http/telemetry.rb +5 -6
- data/lib/datadog/core/telemetry/transport/telemetry.rb +1 -2
- data/lib/datadog/core/transport/http/client.rb +69 -0
- data/lib/datadog/core/utils/array.rb +29 -0
- data/lib/datadog/{appsec/api_security → core/utils}/lru_cache.rb +10 -21
- data/lib/datadog/core/utils/network.rb +3 -1
- data/lib/datadog/core/utils/only_once_successful.rb +6 -2
- data/lib/datadog/core/utils.rb +2 -0
- data/lib/datadog/data_streams/configuration/settings.rb +49 -0
- data/lib/datadog/data_streams/configuration.rb +11 -0
- data/lib/datadog/data_streams/ext.rb +11 -0
- data/lib/datadog/data_streams/extensions.rb +16 -0
- data/lib/datadog/data_streams/pathway_context.rb +169 -0
- data/lib/datadog/data_streams/processor.rb +509 -0
- data/lib/datadog/data_streams/transport/http/api.rb +33 -0
- data/lib/datadog/data_streams/transport/http/client.rb +21 -0
- data/lib/datadog/data_streams/transport/http/stats.rb +87 -0
- data/lib/datadog/data_streams/transport/http.rb +41 -0
- data/lib/datadog/data_streams/transport/stats.rb +60 -0
- data/lib/datadog/data_streams.rb +100 -0
- data/lib/datadog/di/component.rb +0 -16
- data/lib/datadog/di/el/evaluator.rb +1 -1
- data/lib/datadog/di/error.rb +4 -0
- data/lib/datadog/di/instrumenter.rb +76 -30
- data/lib/datadog/di/probe.rb +20 -0
- data/lib/datadog/di/probe_manager.rb +10 -2
- data/lib/datadog/di/probe_notification_builder.rb +62 -23
- data/lib/datadog/di/proc_responder.rb +32 -0
- data/lib/datadog/di/transport/diagnostics.rb +2 -2
- data/lib/datadog/di/transport/http/diagnostics.rb +2 -4
- data/lib/datadog/di/transport/http/input.rb +2 -4
- data/lib/datadog/di/transport/http.rb +6 -2
- data/lib/datadog/di/transport/input.rb +64 -4
- data/lib/datadog/open_feature/component.rb +60 -0
- data/lib/datadog/open_feature/configuration.rb +27 -0
- data/lib/datadog/open_feature/evaluation_engine.rb +69 -0
- data/lib/datadog/open_feature/exposures/batch_builder.rb +32 -0
- data/lib/datadog/open_feature/exposures/buffer.rb +43 -0
- data/lib/datadog/open_feature/exposures/deduplicator.rb +30 -0
- data/lib/datadog/open_feature/exposures/event.rb +60 -0
- data/lib/datadog/open_feature/exposures/reporter.rb +40 -0
- data/lib/datadog/open_feature/exposures/worker.rb +116 -0
- data/lib/datadog/open_feature/ext.rb +14 -0
- data/lib/datadog/open_feature/native_evaluator.rb +38 -0
- data/lib/datadog/open_feature/noop_evaluator.rb +26 -0
- data/lib/datadog/open_feature/provider.rb +141 -0
- data/lib/datadog/open_feature/remote.rb +74 -0
- data/lib/datadog/open_feature/resolution_details.rb +35 -0
- data/lib/datadog/open_feature/transport.rb +72 -0
- data/lib/datadog/open_feature.rb +19 -0
- data/lib/datadog/opentelemetry/configuration/settings.rb +159 -0
- data/lib/datadog/opentelemetry/metrics.rb +110 -0
- data/lib/datadog/opentelemetry/sdk/configurator.rb +25 -1
- data/lib/datadog/opentelemetry/sdk/metrics_exporter.rb +38 -0
- data/lib/datadog/opentelemetry.rb +3 -0
- data/lib/datadog/profiling/collectors/code_provenance.rb +15 -6
- data/lib/datadog/profiling/collectors/cpu_and_wall_time_worker.rb +1 -1
- data/lib/datadog/profiling/collectors/idle_sampling_helper.rb +1 -1
- data/lib/datadog/profiling/profiler.rb +4 -0
- data/lib/datadog/profiling/tag_builder.rb +36 -3
- data/lib/datadog/profiling.rb +1 -2
- data/lib/datadog/single_step_instrument.rb +1 -1
- data/lib/datadog/tracing/configuration/ext.rb +9 -0
- data/lib/datadog/tracing/configuration/settings.rb +74 -0
- data/lib/datadog/tracing/contrib/action_pack/action_controller/instrumentation.rb +4 -4
- data/lib/datadog/tracing/contrib/action_pack/utils.rb +1 -2
- data/lib/datadog/tracing/contrib/active_job/log_injection.rb +21 -7
- data/lib/datadog/tracing/contrib/active_job/patcher.rb +5 -1
- data/lib/datadog/tracing/contrib/aws/instrumentation.rb +4 -2
- data/lib/datadog/tracing/contrib/ethon/easy_patch.rb +4 -1
- data/lib/datadog/tracing/contrib/excon/configuration/settings.rb +11 -3
- data/lib/datadog/tracing/contrib/faraday/configuration/settings.rb +11 -7
- data/lib/datadog/tracing/contrib/grape/configuration/settings.rb +7 -3
- data/lib/datadog/tracing/contrib/graphql/unified_trace.rb +22 -17
- data/lib/datadog/tracing/contrib/http/configuration/settings.rb +11 -3
- data/lib/datadog/tracing/contrib/httpclient/configuration/settings.rb +11 -3
- data/lib/datadog/tracing/contrib/httprb/configuration/settings.rb +11 -3
- data/lib/datadog/tracing/contrib/kafka/instrumentation/consumer.rb +66 -0
- data/lib/datadog/tracing/contrib/kafka/instrumentation/producer.rb +66 -0
- data/lib/datadog/tracing/contrib/kafka/patcher.rb +14 -0
- data/lib/datadog/tracing/contrib/karafka/framework.rb +30 -0
- data/lib/datadog/tracing/contrib/karafka/monitor.rb +11 -0
- data/lib/datadog/tracing/contrib/karafka/patcher.rb +32 -0
- data/lib/datadog/tracing/contrib/rack/middlewares.rb +59 -27
- data/lib/datadog/tracing/contrib/rack/route_inference.rb +53 -0
- data/lib/datadog/tracing/contrib/rails/middlewares.rb +2 -2
- data/lib/datadog/tracing/contrib/rest_client/request_patch.rb +4 -1
- data/lib/datadog/tracing/contrib/roda/instrumentation.rb +3 -1
- data/lib/datadog/tracing/contrib/sinatra/tracer_middleware.rb +3 -1
- data/lib/datadog/tracing/contrib/status_range_matcher.rb +7 -0
- data/lib/datadog/tracing/contrib/waterdrop/configuration/settings.rb +27 -0
- data/lib/datadog/tracing/contrib/waterdrop/distributed/propagation.rb +48 -0
- data/lib/datadog/tracing/contrib/waterdrop/ext.rb +17 -0
- data/lib/datadog/tracing/contrib/waterdrop/integration.rb +43 -0
- data/lib/datadog/tracing/contrib/waterdrop/middleware.rb +46 -0
- data/lib/datadog/tracing/contrib/waterdrop/patcher.rb +46 -0
- data/lib/datadog/tracing/contrib/waterdrop/producer.rb +50 -0
- data/lib/datadog/tracing/contrib/waterdrop.rb +37 -0
- data/lib/datadog/tracing/contrib.rb +1 -0
- data/lib/datadog/tracing/metadata/ext.rb +1 -1
- data/lib/datadog/tracing/transport/http/client.rb +12 -26
- data/lib/datadog/tracing/transport/trace_formatter.rb +11 -0
- data/lib/datadog/tracing/transport/traces.rb +3 -5
- data/lib/datadog/version.rb +2 -2
- data/lib/datadog.rb +2 -0
- metadata +78 -15
- data/lib/datadog/core/remote/transport/http/client.rb +0 -49
- data/lib/datadog/core/telemetry/transport/http/client.rb +0 -49
- data/lib/datadog/di/transport/http/client.rb +0 -47
|
@@ -8,8 +8,12 @@ module Datadog
|
|
|
8
8
|
module Event
|
|
9
9
|
# Telemetry class for the 'app-started' event
|
|
10
10
|
class AppStarted < Base
|
|
11
|
-
def initialize(
|
|
12
|
-
|
|
11
|
+
def initialize(components:)
|
|
12
|
+
# To not hold a reference to the component tree, generate
|
|
13
|
+
# the event payload here in the constructor.
|
|
14
|
+
@configuration = configuration(components.settings, components.agent_settings)
|
|
15
|
+
@install_signature = install_signature(components.settings)
|
|
16
|
+
@products = products(components)
|
|
13
17
|
end
|
|
14
18
|
|
|
15
19
|
def type
|
|
@@ -18,9 +22,9 @@ module Datadog
|
|
|
18
22
|
|
|
19
23
|
def payload
|
|
20
24
|
{
|
|
21
|
-
products: products,
|
|
22
|
-
configuration: configuration,
|
|
23
|
-
install_signature: install_signature,
|
|
25
|
+
products: @products,
|
|
26
|
+
configuration: @configuration,
|
|
27
|
+
install_signature: @install_signature,
|
|
24
28
|
# DEV: Not implemented yet
|
|
25
29
|
# error: error, # Start-up errors
|
|
26
30
|
}
|
|
@@ -28,17 +32,18 @@ module Datadog
|
|
|
28
32
|
|
|
29
33
|
private
|
|
30
34
|
|
|
31
|
-
def products
|
|
35
|
+
def products(components)
|
|
32
36
|
# @type var products: Hash[Symbol, Hash[Symbol, Hash[Symbol, String | Integer] | bool | nil]]
|
|
33
37
|
products = {
|
|
34
38
|
appsec: {
|
|
35
|
-
|
|
39
|
+
# TODO take appsec status out of component tree?
|
|
40
|
+
enabled: components.settings.appsec.enabled,
|
|
36
41
|
},
|
|
37
42
|
profiler: {
|
|
38
|
-
enabled:
|
|
43
|
+
enabled: !!components.profiler&.enabled?,
|
|
39
44
|
},
|
|
40
45
|
dynamic_instrumentation: {
|
|
41
|
-
enabled:
|
|
46
|
+
enabled: !!components.dynamic_instrumentation,
|
|
42
47
|
}
|
|
43
48
|
}
|
|
44
49
|
|
|
@@ -73,12 +78,11 @@ module Datadog
|
|
|
73
78
|
|
|
74
79
|
# standard:disable Metrics/AbcSize
|
|
75
80
|
# standard:disable Metrics/MethodLength
|
|
76
|
-
def configuration
|
|
77
|
-
config = Datadog.configuration
|
|
81
|
+
def configuration(settings, agent_settings)
|
|
78
82
|
seq_id = Event.configuration_sequence.next
|
|
79
83
|
|
|
80
84
|
# tracing.writer_options.buffer_size and tracing.writer_options.flush_interval have the same origin.
|
|
81
|
-
writer_option_origin = get_telemetry_origin(
|
|
85
|
+
writer_option_origin = get_telemetry_origin(settings, 'tracing.writer_options')
|
|
82
86
|
|
|
83
87
|
list = [
|
|
84
88
|
# Only set using env var as of June 2025
|
|
@@ -100,59 +104,59 @@ module Datadog
|
|
|
100
104
|
),
|
|
101
105
|
|
|
102
106
|
# Mix of env var, programmatic and default config, so we use unknown
|
|
103
|
-
conf_value('DD_AGENT_TRANSPORT', agent_transport, seq_id, 'unknown'), # rubocop:disable CustomCops/EnvStringValidationCop
|
|
107
|
+
conf_value('DD_AGENT_TRANSPORT', agent_transport(agent_settings), seq_id, 'unknown'), # rubocop:disable CustomCops/EnvStringValidationCop
|
|
104
108
|
|
|
105
109
|
# writer_options is defined as an option that has a Hash value.
|
|
106
110
|
conf_value(
|
|
107
111
|
'tracing.writer_options.buffer_size',
|
|
108
|
-
to_value(
|
|
112
|
+
to_value(settings.tracing.writer_options[:buffer_size]),
|
|
109
113
|
seq_id,
|
|
110
114
|
writer_option_origin
|
|
111
115
|
),
|
|
112
116
|
conf_value(
|
|
113
117
|
'tracing.writer_options.flush_interval',
|
|
114
|
-
to_value(
|
|
118
|
+
to_value(settings.tracing.writer_options[:flush_interval]),
|
|
115
119
|
seq_id,
|
|
116
120
|
writer_option_origin
|
|
117
121
|
),
|
|
118
122
|
|
|
119
|
-
conf_value('DD_AGENT_HOST',
|
|
123
|
+
conf_value('DD_AGENT_HOST', settings.agent.host, seq_id, get_telemetry_origin(settings, 'agent.host')),
|
|
120
124
|
conf_value(
|
|
121
125
|
'DD_TRACE_SAMPLE_RATE',
|
|
122
|
-
to_value(
|
|
126
|
+
to_value(settings.tracing.sampling.default_rate),
|
|
123
127
|
seq_id,
|
|
124
|
-
get_telemetry_origin(
|
|
128
|
+
get_telemetry_origin(settings, 'tracing.sampling.default_rate')
|
|
125
129
|
),
|
|
126
130
|
conf_value(
|
|
127
131
|
'DD_TRACE_REMOVE_INTEGRATION_SERVICE_NAMES_ENABLED',
|
|
128
|
-
|
|
132
|
+
settings.tracing.contrib.global_default_service_name.enabled,
|
|
129
133
|
seq_id,
|
|
130
|
-
get_telemetry_origin(
|
|
134
|
+
get_telemetry_origin(settings, 'tracing.contrib.global_default_service_name.enabled')
|
|
131
135
|
),
|
|
132
136
|
conf_value(
|
|
133
137
|
'DD_TRACE_PEER_SERVICE_DEFAULTS_ENABLED',
|
|
134
|
-
|
|
138
|
+
settings.tracing.contrib.peer_service_defaults,
|
|
135
139
|
seq_id,
|
|
136
|
-
get_telemetry_origin(
|
|
140
|
+
get_telemetry_origin(settings, 'tracing.contrib.peer_service_defaults')
|
|
137
141
|
),
|
|
138
142
|
conf_value(
|
|
139
143
|
'DD_TRACE_DEBUG',
|
|
140
|
-
|
|
144
|
+
settings.diagnostics.debug,
|
|
141
145
|
seq_id,
|
|
142
|
-
get_telemetry_origin(
|
|
146
|
+
get_telemetry_origin(settings, 'diagnostics.debug')
|
|
143
147
|
)
|
|
144
148
|
]
|
|
145
149
|
|
|
146
150
|
peer_service_mapping_str = ''
|
|
147
|
-
unless
|
|
148
|
-
peer_service_mapping =
|
|
151
|
+
unless settings.tracing.contrib.peer_service_mapping.empty?
|
|
152
|
+
peer_service_mapping = settings.tracing.contrib.peer_service_mapping
|
|
149
153
|
peer_service_mapping_str = peer_service_mapping.map { |key, value| "#{key}:#{value}" }.join(',')
|
|
150
154
|
end
|
|
151
155
|
list << conf_value(
|
|
152
156
|
'DD_TRACE_PEER_SERVICE_MAPPING',
|
|
153
157
|
peer_service_mapping_str,
|
|
154
158
|
seq_id,
|
|
155
|
-
get_telemetry_origin(
|
|
159
|
+
get_telemetry_origin(settings, 'tracing.contrib.peer_service_mapping')
|
|
156
160
|
)
|
|
157
161
|
|
|
158
162
|
# Whitelist of configuration options to send in additional payload object
|
|
@@ -160,9 +164,9 @@ module Datadog
|
|
|
160
164
|
split_option = option_path.split('.')
|
|
161
165
|
list << conf_value(
|
|
162
166
|
option_path,
|
|
163
|
-
to_value(
|
|
167
|
+
to_value(settings.dig(*split_option)),
|
|
164
168
|
seq_id,
|
|
165
|
-
get_telemetry_origin(
|
|
169
|
+
get_telemetry_origin(settings, option_path)
|
|
166
170
|
)
|
|
167
171
|
end
|
|
168
172
|
|
|
@@ -181,34 +185,34 @@ module Datadog
|
|
|
181
185
|
)
|
|
182
186
|
|
|
183
187
|
# Add some more custom additional payload values here
|
|
184
|
-
if
|
|
188
|
+
if settings.logger.instance
|
|
185
189
|
list << conf_value(
|
|
186
190
|
'logger.instance',
|
|
187
|
-
|
|
191
|
+
settings.logger.instance.class.to_s,
|
|
188
192
|
seq_id,
|
|
189
|
-
get_telemetry_origin(
|
|
193
|
+
get_telemetry_origin(settings, 'logger.instance')
|
|
190
194
|
)
|
|
191
195
|
end
|
|
192
|
-
if
|
|
196
|
+
if settings.respond_to?('appsec')
|
|
193
197
|
list << conf_value(
|
|
194
198
|
'appsec.enabled',
|
|
195
|
-
|
|
199
|
+
settings.dig('appsec', 'enabled'),
|
|
196
200
|
seq_id,
|
|
197
|
-
get_telemetry_origin(
|
|
201
|
+
get_telemetry_origin(settings, 'appsec.enabled')
|
|
198
202
|
)
|
|
199
203
|
list << conf_value(
|
|
200
204
|
'appsec.sca_enabled',
|
|
201
|
-
|
|
205
|
+
settings.dig('appsec', 'sca_enabled'),
|
|
202
206
|
seq_id,
|
|
203
|
-
get_telemetry_origin(
|
|
207
|
+
get_telemetry_origin(settings, 'appsec.sca_enabled')
|
|
204
208
|
)
|
|
205
209
|
end
|
|
206
|
-
if
|
|
210
|
+
if settings.respond_to?('ci')
|
|
207
211
|
list << conf_value(
|
|
208
212
|
'ci.enabled',
|
|
209
|
-
|
|
213
|
+
settings.dig('ci', 'enabled'),
|
|
210
214
|
seq_id,
|
|
211
|
-
get_telemetry_origin(
|
|
215
|
+
get_telemetry_origin(settings, 'ci.enabled')
|
|
212
216
|
)
|
|
213
217
|
end
|
|
214
218
|
|
|
@@ -218,8 +222,8 @@ module Datadog
|
|
|
218
222
|
# standard:enable Metrics/AbcSize
|
|
219
223
|
# standard:enable Metrics/MethodLength
|
|
220
224
|
|
|
221
|
-
def agent_transport
|
|
222
|
-
adapter =
|
|
225
|
+
def agent_transport(agent_settings)
|
|
226
|
+
adapter = agent_settings.adapter
|
|
223
227
|
if adapter == Datadog::Core::Transport::Ext::UnixSocket::ADAPTER
|
|
224
228
|
'UDS'
|
|
225
229
|
else
|
|
@@ -260,23 +264,22 @@ module Datadog
|
|
|
260
264
|
end
|
|
261
265
|
end
|
|
262
266
|
|
|
263
|
-
def install_signature
|
|
264
|
-
config = Datadog.configuration
|
|
267
|
+
def install_signature(settings)
|
|
265
268
|
{
|
|
266
|
-
install_id:
|
|
267
|
-
install_type:
|
|
268
|
-
install_time:
|
|
269
|
+
install_id: settings.dig('telemetry', 'install_id'),
|
|
270
|
+
install_type: settings.dig('telemetry', 'install_type'),
|
|
271
|
+
install_time: settings.dig('telemetry', 'install_time'),
|
|
269
272
|
}
|
|
270
273
|
end
|
|
271
274
|
|
|
272
|
-
def get_telemetry_origin(
|
|
275
|
+
def get_telemetry_origin(settings, config_path)
|
|
273
276
|
split_option = config_path.split('.')
|
|
274
277
|
option_name = split_option.pop
|
|
275
278
|
return 'unknown' if option_name.nil?
|
|
276
279
|
|
|
277
280
|
# @type var parent_setting: Core::Configuration::Options
|
|
278
281
|
# @type var option: Core::Configuration::Option
|
|
279
|
-
parent_setting =
|
|
282
|
+
parent_setting = settings.dig(*split_option)
|
|
280
283
|
option = parent_setting.send(:resolve_option, option_name.to_sym)
|
|
281
284
|
option.precedence_set&.origin || 'unknown'
|
|
282
285
|
end
|
|
@@ -14,8 +14,8 @@ module Datadog
|
|
|
14
14
|
# read: lib/datadog/core/telemetry/logging.rb
|
|
15
15
|
module Logger
|
|
16
16
|
class << self
|
|
17
|
-
def report(exception, level: :error, description: nil
|
|
18
|
-
instance&.report(exception, level: level, description: description
|
|
17
|
+
def report(exception, level: :error, description: nil)
|
|
18
|
+
instance&.report(exception, level: level, description: description)
|
|
19
19
|
end
|
|
20
20
|
|
|
21
21
|
def error(description)
|
|
@@ -45,17 +45,11 @@ module Datadog
|
|
|
45
45
|
end
|
|
46
46
|
end
|
|
47
47
|
|
|
48
|
-
def report(exception, level: :error, description: nil
|
|
48
|
+
def report(exception, level: :error, description: nil)
|
|
49
49
|
# Anonymous exceptions to be logged as <Class:0x00007f8b1c0b3b40>
|
|
50
50
|
message = +"#{exception.class.name || exception.class.inspect}" # standard:disable Style/RedundantInterpolation
|
|
51
51
|
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
if description || exception_message
|
|
55
|
-
message << ':'
|
|
56
|
-
message << " #{description}" if description
|
|
57
|
-
message << " (#{exception.message})" if exception_message
|
|
58
|
-
end
|
|
52
|
+
message << ": #{description}" if description
|
|
59
53
|
|
|
60
54
|
event = Event::Log.new(
|
|
61
55
|
message: message,
|
|
@@ -3,8 +3,8 @@
|
|
|
3
3
|
require_relative '../../../transport/http/api/endpoint'
|
|
4
4
|
require_relative '../../../transport/http/api/instance'
|
|
5
5
|
require_relative '../../../transport/http/api/spec'
|
|
6
|
+
require_relative '../../../transport/http/client'
|
|
6
7
|
require_relative '../../../transport/request'
|
|
7
|
-
require_relative 'client'
|
|
8
8
|
|
|
9
9
|
module Datadog
|
|
10
10
|
module Core
|
|
@@ -12,10 +12,11 @@ module Datadog
|
|
|
12
12
|
module Transport
|
|
13
13
|
module HTTP
|
|
14
14
|
module Telemetry
|
|
15
|
-
|
|
15
|
+
class Client < Core::Transport::HTTP::Client
|
|
16
16
|
def send_telemetry_payload(request)
|
|
17
|
-
send_request(request) do |api, env|
|
|
18
|
-
api
|
|
17
|
+
send_request(request) do |api, env|
|
|
18
|
+
# TODO how to make api have the derived type for steep?
|
|
19
|
+
api.send_telemetry(env) # steep:ignore
|
|
19
20
|
end
|
|
20
21
|
end
|
|
21
22
|
end
|
|
@@ -83,8 +84,6 @@ module Datadog
|
|
|
83
84
|
end
|
|
84
85
|
end
|
|
85
86
|
end
|
|
86
|
-
|
|
87
|
-
HTTP::Client.include(Telemetry::Client)
|
|
88
87
|
end
|
|
89
88
|
end
|
|
90
89
|
end
|
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
3
|
require_relative '../../transport/parcel'
|
|
4
|
-
require_relative 'http/client'
|
|
5
4
|
require_relative 'http/telemetry'
|
|
6
5
|
|
|
7
6
|
module Datadog
|
|
@@ -32,7 +31,7 @@ module Datadog
|
|
|
32
31
|
@apis = apis
|
|
33
32
|
@logger = logger
|
|
34
33
|
|
|
35
|
-
@client = HTTP::Client.new(@apis[default_api], logger: logger)
|
|
34
|
+
@client = Core::Telemetry::Transport::HTTP::Telemetry::Client.new(@apis[default_api], logger: logger)
|
|
36
35
|
end
|
|
37
36
|
|
|
38
37
|
def send_telemetry(request_type:, payload:)
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require_relative 'env'
|
|
4
|
+
require_relative '../response'
|
|
5
|
+
|
|
6
|
+
module Datadog
|
|
7
|
+
module Core
|
|
8
|
+
module Transport
|
|
9
|
+
module HTTP
|
|
10
|
+
# Routes, encodes, and sends DI data to the trace agent via HTTP.
|
|
11
|
+
#
|
|
12
|
+
# @api private
|
|
13
|
+
class Client
|
|
14
|
+
attr_reader :api, :logger
|
|
15
|
+
|
|
16
|
+
def initialize(api, logger:)
|
|
17
|
+
@api = api
|
|
18
|
+
@logger = logger
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
private
|
|
22
|
+
|
|
23
|
+
def send_request(request, &block)
|
|
24
|
+
# Build request into env
|
|
25
|
+
env = build_env(request)
|
|
26
|
+
|
|
27
|
+
# Get responses from API
|
|
28
|
+
yield(api, env).tap do |response|
|
|
29
|
+
on_response(response)
|
|
30
|
+
end
|
|
31
|
+
rescue => exception
|
|
32
|
+
on_exception(exception)
|
|
33
|
+
|
|
34
|
+
Datadog::Core::Transport::InternalErrorResponse.new(exception)
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
def build_env(request)
|
|
38
|
+
Datadog::Core::Transport::HTTP::Env.new(request)
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
# Callback that is invoked if a request did not raise an exception
|
|
42
|
+
# (but did not necessarily complete successfully).
|
|
43
|
+
#
|
|
44
|
+
# Override in subclasses.
|
|
45
|
+
#
|
|
46
|
+
# Note that the client will return the original response -
|
|
47
|
+
# the return value of this method is ignored, and response should
|
|
48
|
+
# not be modified.
|
|
49
|
+
def on_response(response)
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
# Callback that is invoked if a request failed with an exception.
|
|
53
|
+
#
|
|
54
|
+
# Override in subclasses.
|
|
55
|
+
def on_exception(exception)
|
|
56
|
+
message = build_exception_message(exception)
|
|
57
|
+
|
|
58
|
+
logger.debug(message)
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
def build_exception_message(exception)
|
|
62
|
+
"Internal error during #{self.class.name} request. Cause: #{exception.class}: #{exception} " \
|
|
63
|
+
"Location: #{Array(exception.backtrace).first}"
|
|
64
|
+
end
|
|
65
|
+
end
|
|
66
|
+
end
|
|
67
|
+
end
|
|
68
|
+
end
|
|
69
|
+
end
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Datadog
|
|
4
|
+
module Core
|
|
5
|
+
module Utils
|
|
6
|
+
# Common array-related utility functions.
|
|
7
|
+
module Array
|
|
8
|
+
def self.filter_map(array, &block)
|
|
9
|
+
if array.respond_to?(:filter_map)
|
|
10
|
+
# DEV Supported since Ruby 2.7, saves an intermediate object creation
|
|
11
|
+
array.filter_map(&block)
|
|
12
|
+
elsif array.is_a?(Enumerator::Lazy)
|
|
13
|
+
# You would think that .compact would work here, but it does not:
|
|
14
|
+
# the result of .map could be an Enumerator::Lazy instance which
|
|
15
|
+
# does not implement #compact on Ruby 2.5/2.6.
|
|
16
|
+
array.map(&block).reject do |item|
|
|
17
|
+
item.nil?
|
|
18
|
+
end
|
|
19
|
+
else
|
|
20
|
+
array.each_with_object([]) do |item, memo|
|
|
21
|
+
new_item = block.call(item)
|
|
22
|
+
memo.push(new_item) unless new_item.nil?
|
|
23
|
+
end
|
|
24
|
+
end
|
|
25
|
+
end
|
|
26
|
+
end
|
|
27
|
+
end
|
|
28
|
+
end
|
|
29
|
+
end
|
|
@@ -3,13 +3,13 @@
|
|
|
3
3
|
require 'forwardable'
|
|
4
4
|
|
|
5
5
|
module Datadog
|
|
6
|
-
module
|
|
7
|
-
module
|
|
6
|
+
module Core
|
|
7
|
+
module Utils
|
|
8
8
|
# An LRU (Least Recently Used) cache implementation that relies on the
|
|
9
9
|
# Ruby 1.9+ `Hash` implementation that guarantees insertion order.
|
|
10
10
|
#
|
|
11
11
|
# WARNING: This implementation is NOT thread-safe and should be used
|
|
12
|
-
# in a single-threaded context.
|
|
12
|
+
# in a single-threaded context or guarded by Mutex.
|
|
13
13
|
class LRUCache
|
|
14
14
|
extend Forwardable
|
|
15
15
|
|
|
@@ -30,25 +30,14 @@ module Datadog
|
|
|
30
30
|
end
|
|
31
31
|
end
|
|
32
32
|
|
|
33
|
-
def
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
# NOTE: If the key exists, it's moved to the end of the list and
|
|
42
|
-
# if does not, the given block will be executed and the result
|
|
43
|
-
# will be stored (which will add it to the end of the list).
|
|
44
|
-
def fetch_or_store(key)
|
|
45
|
-
if (entry = @store.delete(key))
|
|
46
|
-
return @store[key] = entry
|
|
33
|
+
def []=(key, value)
|
|
34
|
+
if @store.delete(key)
|
|
35
|
+
@store[key] = value
|
|
36
|
+
else
|
|
37
|
+
# NOTE: evict the oldest entry if store reached the maximum allowed size
|
|
38
|
+
@store.shift if @store.size >= @max_size
|
|
39
|
+
@store[key] = value
|
|
47
40
|
end
|
|
48
|
-
|
|
49
|
-
# NOTE: evict the oldest entry if store reached the maximum allowed size
|
|
50
|
-
@store.shift if @store.size >= @max_size
|
|
51
|
-
@store[key] = yield
|
|
52
41
|
end
|
|
53
42
|
end
|
|
54
43
|
end
|
|
@@ -21,6 +21,8 @@ module Datadog
|
|
|
21
21
|
cf-connecting-ipv6
|
|
22
22
|
].freeze
|
|
23
23
|
|
|
24
|
+
CGNAT_IP_RANGE = IPAddr.new('100.64.0.0/10')
|
|
25
|
+
|
|
24
26
|
class << self
|
|
25
27
|
# Returns a client IP associated with the request if it was
|
|
26
28
|
# retrieved successfully.
|
|
@@ -131,7 +133,7 @@ module Datadog
|
|
|
131
133
|
end
|
|
132
134
|
|
|
133
135
|
def global_ip?(parsed_ip)
|
|
134
|
-
parsed_ip && !parsed_ip.private? && !parsed_ip.loopback? && !parsed_ip.link_local?
|
|
136
|
+
parsed_ip && !parsed_ip.private? && !parsed_ip.loopback? && !parsed_ip.link_local? && !CGNAT_IP_RANGE.include?(parsed_ip)
|
|
135
137
|
end
|
|
136
138
|
end
|
|
137
139
|
end
|
|
@@ -29,7 +29,11 @@ module Datadog
|
|
|
29
29
|
# In https://github.com/DataDog/dd-trace-rb/pull/1398#issuecomment-797378810 we have a discussion of alternatives,
|
|
30
30
|
# including an alternative implementation that is Ractor-safe once spent.
|
|
31
31
|
class OnlyOnceSuccessful < OnlyOnce
|
|
32
|
-
def initialize(limit =
|
|
32
|
+
def initialize(limit = nil)
|
|
33
|
+
if limit && limit <= 0
|
|
34
|
+
raise ArgumentError, "Limit must be a positive integer if provided: #{limit}"
|
|
35
|
+
end
|
|
36
|
+
|
|
33
37
|
super()
|
|
34
38
|
|
|
35
39
|
@limit = limit
|
|
@@ -71,7 +75,7 @@ module Datadog
|
|
|
71
75
|
end
|
|
72
76
|
|
|
73
77
|
def limited?
|
|
74
|
-
!@limit.nil?
|
|
78
|
+
!@limit.nil?
|
|
75
79
|
end
|
|
76
80
|
|
|
77
81
|
def reset_ran_once_state_for_tests
|
data/lib/datadog/core/utils.rb
CHANGED
|
@@ -38,6 +38,8 @@ module Datadog
|
|
|
38
38
|
|
|
39
39
|
# Ensure `str` is a valid UTF-8, ready to be
|
|
40
40
|
# sent through the tracer transport.
|
|
41
|
+
# DEV-3.0: This method should unconditionally handle invalid byte sequences
|
|
42
|
+
# DEV-3.0: and return a safe string to display.
|
|
41
43
|
#
|
|
42
44
|
# @param [String,#to_s] str object to be converted to a UTF-8 string
|
|
43
45
|
# @param [Boolean] binary whether to expect binary data in the `str` parameter
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require_relative '../../core/environment/variable_helpers'
|
|
4
|
+
require_relative '../ext'
|
|
5
|
+
|
|
6
|
+
module Datadog
|
|
7
|
+
module DataStreams
|
|
8
|
+
module Configuration
|
|
9
|
+
# Configuration settings for Data Streams Monitoring.
|
|
10
|
+
module Settings
|
|
11
|
+
def self.extended(base)
|
|
12
|
+
base = base.singleton_class unless base.is_a?(Class)
|
|
13
|
+
add_settings!(base)
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def self.add_settings!(base)
|
|
17
|
+
base.class_eval do
|
|
18
|
+
# Data Streams Monitoring configuration
|
|
19
|
+
# @public_api
|
|
20
|
+
settings :data_streams do
|
|
21
|
+
# Whether Data Streams Monitoring is enabled. When enabled, the library will
|
|
22
|
+
# collect and report data lineage information for messaging systems.
|
|
23
|
+
#
|
|
24
|
+
# @default `DD_DATA_STREAMS_ENABLED` environment variable, otherwise `false`.
|
|
25
|
+
# @return [Boolean]
|
|
26
|
+
option :enabled do |o|
|
|
27
|
+
o.type :bool
|
|
28
|
+
o.env Ext::ENV_ENABLED
|
|
29
|
+
o.default false
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
# The interval (in seconds) at which Data Streams Monitoring stats are flushed.
|
|
33
|
+
#
|
|
34
|
+
# @default 10.0
|
|
35
|
+
# @env '_DD_TRACE_STATS_WRITER_INTERVAL'
|
|
36
|
+
# @return [Float]
|
|
37
|
+
# @!visibility private
|
|
38
|
+
option :interval do |o|
|
|
39
|
+
o.type :float
|
|
40
|
+
o.env '_DD_TRACE_STATS_WRITER_INTERVAL'
|
|
41
|
+
o.default 10.0
|
|
42
|
+
end
|
|
43
|
+
end
|
|
44
|
+
end
|
|
45
|
+
end
|
|
46
|
+
end
|
|
47
|
+
end
|
|
48
|
+
end
|
|
49
|
+
end
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require_relative 'configuration'
|
|
4
|
+
require_relative '../core/configuration'
|
|
5
|
+
|
|
6
|
+
module Datadog
|
|
7
|
+
module DataStreams
|
|
8
|
+
# Extends Datadog with Data Streams Monitoring features
|
|
9
|
+
module Extensions
|
|
10
|
+
# Inject Data Streams settings into global configuration.
|
|
11
|
+
def self.activate!
|
|
12
|
+
Core::Configuration::Settings.extend(Configuration::Settings)
|
|
13
|
+
end
|
|
14
|
+
end
|
|
15
|
+
end
|
|
16
|
+
end
|