datadog 2.7.1 → 2.17.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (417) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +310 -1
  3. data/ext/datadog_profiling_native_extension/clock_id.h +2 -2
  4. data/ext/datadog_profiling_native_extension/collectors_cpu_and_wall_time_worker.c +66 -56
  5. data/ext/datadog_profiling_native_extension/collectors_discrete_dynamic_sampler.c +1 -1
  6. data/ext/datadog_profiling_native_extension/collectors_discrete_dynamic_sampler.h +1 -1
  7. data/ext/datadog_profiling_native_extension/collectors_idle_sampling_helper.c +16 -16
  8. data/ext/datadog_profiling_native_extension/collectors_stack.c +10 -10
  9. data/ext/datadog_profiling_native_extension/collectors_stack.h +2 -2
  10. data/ext/datadog_profiling_native_extension/collectors_thread_context.c +314 -145
  11. data/ext/datadog_profiling_native_extension/datadog_ruby_common.c +1 -4
  12. data/ext/datadog_profiling_native_extension/datadog_ruby_common.h +10 -0
  13. data/ext/datadog_profiling_native_extension/encoded_profile.c +79 -0
  14. data/ext/datadog_profiling_native_extension/encoded_profile.h +8 -0
  15. data/ext/datadog_profiling_native_extension/extconf.rb +7 -8
  16. data/ext/datadog_profiling_native_extension/gvl_profiling_helper.c +2 -0
  17. data/ext/datadog_profiling_native_extension/gvl_profiling_helper.h +0 -8
  18. data/ext/datadog_profiling_native_extension/heap_recorder.c +61 -174
  19. data/ext/datadog_profiling_native_extension/heap_recorder.h +2 -2
  20. data/ext/datadog_profiling_native_extension/http_transport.c +64 -98
  21. data/ext/datadog_profiling_native_extension/private_vm_api_access.c +68 -1
  22. data/ext/datadog_profiling_native_extension/private_vm_api_access.h +10 -1
  23. data/ext/datadog_profiling_native_extension/profiling.c +19 -8
  24. data/ext/datadog_profiling_native_extension/ruby_helpers.c +8 -8
  25. data/ext/datadog_profiling_native_extension/stack_recorder.c +84 -131
  26. data/ext/datadog_profiling_native_extension/stack_recorder.h +2 -2
  27. data/ext/datadog_profiling_native_extension/time_helpers.h +1 -1
  28. data/ext/datadog_profiling_native_extension/unsafe_api_calls_check.c +47 -0
  29. data/ext/datadog_profiling_native_extension/unsafe_api_calls_check.h +31 -0
  30. data/ext/libdatadog_api/crashtracker.c +17 -15
  31. data/ext/libdatadog_api/crashtracker.h +5 -0
  32. data/ext/libdatadog_api/datadog_ruby_common.c +1 -4
  33. data/ext/libdatadog_api/datadog_ruby_common.h +10 -0
  34. data/ext/libdatadog_api/init.c +15 -0
  35. data/ext/libdatadog_api/library_config.c +122 -0
  36. data/ext/libdatadog_api/library_config.h +19 -0
  37. data/ext/libdatadog_api/macos_development.md +3 -3
  38. data/ext/libdatadog_api/process_discovery.c +117 -0
  39. data/ext/libdatadog_api/process_discovery.h +5 -0
  40. data/ext/libdatadog_extconf_helpers.rb +1 -1
  41. data/lib/datadog/appsec/actions_handler/serializable_backtrace.rb +89 -0
  42. data/lib/datadog/appsec/actions_handler.rb +49 -0
  43. data/lib/datadog/appsec/anonymizer.rb +16 -0
  44. data/lib/datadog/appsec/api_security/lru_cache.rb +49 -0
  45. data/lib/datadog/appsec/api_security.rb +9 -0
  46. data/lib/datadog/appsec/assets/waf_rules/README.md +50 -5
  47. data/lib/datadog/appsec/assets/waf_rules/processors.json +239 -10
  48. data/lib/datadog/appsec/assets/waf_rules/recommended.json +355 -157
  49. data/lib/datadog/appsec/assets/waf_rules/scanners.json +926 -17
  50. data/lib/datadog/appsec/assets/waf_rules/strict.json +62 -32
  51. data/lib/datadog/appsec/autoload.rb +1 -1
  52. data/lib/datadog/appsec/component.rb +41 -33
  53. data/lib/datadog/appsec/compressed_json.rb +40 -0
  54. data/lib/datadog/appsec/configuration/settings.rb +152 -25
  55. data/lib/datadog/appsec/context.rb +74 -0
  56. data/lib/datadog/appsec/contrib/active_record/instrumentation.rb +92 -0
  57. data/lib/datadog/appsec/contrib/active_record/integration.rb +41 -0
  58. data/lib/datadog/appsec/contrib/active_record/patcher.rb +101 -0
  59. data/lib/datadog/appsec/contrib/auto_instrument.rb +1 -1
  60. data/lib/datadog/appsec/contrib/devise/configuration.rb +52 -0
  61. data/lib/datadog/appsec/contrib/devise/data_extractor.rb +78 -0
  62. data/lib/datadog/appsec/contrib/devise/ext.rb +22 -0
  63. data/lib/datadog/appsec/contrib/devise/integration.rb +1 -2
  64. data/lib/datadog/appsec/contrib/devise/patcher.rb +33 -25
  65. data/lib/datadog/appsec/contrib/devise/patches/signin_tracking_patch.rb +102 -0
  66. data/lib/datadog/appsec/contrib/devise/patches/signup_tracking_patch.rb +69 -0
  67. data/lib/datadog/appsec/contrib/devise/{patcher/rememberable_patch.rb → patches/skip_signin_tracking_patch.rb} +3 -3
  68. data/lib/datadog/appsec/contrib/devise/tracking_middleware.rb +106 -0
  69. data/lib/datadog/appsec/contrib/excon/integration.rb +41 -0
  70. data/lib/datadog/appsec/contrib/excon/patcher.rb +28 -0
  71. data/lib/datadog/appsec/contrib/excon/ssrf_detection_middleware.rb +42 -0
  72. data/lib/datadog/appsec/contrib/faraday/connection_patch.rb +22 -0
  73. data/lib/datadog/appsec/contrib/faraday/integration.rb +42 -0
  74. data/lib/datadog/appsec/contrib/faraday/patcher.rb +53 -0
  75. data/lib/datadog/appsec/contrib/faraday/rack_builder_patch.rb +22 -0
  76. data/lib/datadog/appsec/contrib/faraday/ssrf_detection_middleware.rb +41 -0
  77. data/lib/datadog/appsec/contrib/graphql/appsec_trace.rb +1 -7
  78. data/lib/datadog/appsec/contrib/graphql/gateway/watcher.rb +17 -30
  79. data/lib/datadog/appsec/contrib/graphql/integration.rb +1 -1
  80. data/lib/datadog/appsec/contrib/graphql/patcher.rb +0 -3
  81. data/lib/datadog/appsec/contrib/rack/ext.rb +34 -0
  82. data/lib/datadog/appsec/contrib/rack/gateway/response.rb +3 -3
  83. data/lib/datadog/appsec/contrib/rack/gateway/watcher.rb +78 -98
  84. data/lib/datadog/appsec/contrib/rack/integration.rb +1 -1
  85. data/lib/datadog/appsec/contrib/rack/patcher.rb +0 -3
  86. data/lib/datadog/appsec/contrib/rack/request_body_middleware.rb +10 -11
  87. data/lib/datadog/appsec/contrib/rack/request_middleware.rb +52 -68
  88. data/lib/datadog/appsec/contrib/rails/gateway/watcher.rb +16 -33
  89. data/lib/datadog/appsec/contrib/rails/integration.rb +1 -1
  90. data/lib/datadog/appsec/contrib/rails/patcher.rb +25 -38
  91. data/lib/datadog/appsec/contrib/rest_client/integration.rb +45 -0
  92. data/lib/datadog/appsec/contrib/rest_client/patcher.rb +28 -0
  93. data/lib/datadog/appsec/contrib/rest_client/request_ssrf_detection_patch.rb +38 -0
  94. data/lib/datadog/appsec/contrib/sinatra/gateway/watcher.rb +31 -68
  95. data/lib/datadog/appsec/contrib/sinatra/integration.rb +1 -1
  96. data/lib/datadog/appsec/contrib/sinatra/patcher.rb +5 -31
  97. data/lib/datadog/appsec/event.rb +96 -135
  98. data/lib/datadog/appsec/ext.rb +12 -3
  99. data/lib/datadog/appsec/instrumentation/gateway/argument.rb +7 -2
  100. data/lib/datadog/appsec/instrumentation/gateway/middleware.rb +24 -0
  101. data/lib/datadog/appsec/instrumentation/gateway.rb +17 -22
  102. data/lib/datadog/appsec/metrics/collector.rb +38 -0
  103. data/lib/datadog/appsec/metrics/exporter.rb +35 -0
  104. data/lib/datadog/appsec/metrics/telemetry.rb +23 -0
  105. data/lib/datadog/appsec/metrics.rb +13 -0
  106. data/lib/datadog/appsec/monitor/gateway/watcher.rb +52 -32
  107. data/lib/datadog/appsec/processor/rule_loader.rb +26 -31
  108. data/lib/datadog/appsec/processor/rule_merger.rb +7 -6
  109. data/lib/datadog/appsec/processor.rb +5 -4
  110. data/lib/datadog/appsec/remote.rb +26 -12
  111. data/lib/datadog/appsec/response.rb +19 -85
  112. data/lib/datadog/appsec/security_engine/result.rb +67 -0
  113. data/lib/datadog/appsec/security_engine/runner.rb +88 -0
  114. data/lib/datadog/appsec/security_engine.rb +9 -0
  115. data/lib/datadog/appsec/security_event.rb +39 -0
  116. data/lib/datadog/appsec/utils.rb +0 -2
  117. data/lib/datadog/appsec.rb +23 -10
  118. data/lib/datadog/auto_instrument.rb +3 -0
  119. data/lib/datadog/core/buffer/random.rb +18 -2
  120. data/lib/datadog/core/configuration/agent_settings_resolver.rb +42 -14
  121. data/lib/datadog/core/configuration/agentless_settings_resolver.rb +176 -0
  122. data/lib/datadog/core/configuration/components.rb +76 -32
  123. data/lib/datadog/core/configuration/components_state.rb +23 -0
  124. data/lib/datadog/core/configuration/ext.rb +5 -1
  125. data/lib/datadog/core/configuration/option.rb +79 -43
  126. data/lib/datadog/core/configuration/option_definition.rb +6 -4
  127. data/lib/datadog/core/configuration/options.rb +3 -3
  128. data/lib/datadog/core/configuration/settings.rb +100 -41
  129. data/lib/datadog/core/configuration/stable_config.rb +23 -0
  130. data/lib/datadog/core/configuration.rb +43 -11
  131. data/lib/datadog/{tracing → core}/contrib/rails/utils.rb +1 -3
  132. data/lib/datadog/core/crashtracking/component.rb +4 -13
  133. data/lib/datadog/core/diagnostics/environment_logger.rb +1 -1
  134. data/lib/datadog/core/encoding.rb +17 -1
  135. data/lib/datadog/core/environment/agent_info.rb +78 -0
  136. data/lib/datadog/core/environment/cgroup.rb +10 -12
  137. data/lib/datadog/core/environment/container.rb +38 -40
  138. data/lib/datadog/core/environment/ext.rb +6 -6
  139. data/lib/datadog/core/environment/git.rb +1 -0
  140. data/lib/datadog/core/environment/identity.rb +3 -3
  141. data/lib/datadog/core/environment/platform.rb +3 -3
  142. data/lib/datadog/core/environment/variable_helpers.rb +1 -1
  143. data/lib/datadog/core/error.rb +11 -9
  144. data/lib/datadog/core/logger.rb +2 -2
  145. data/lib/datadog/core/metrics/client.rb +27 -27
  146. data/lib/datadog/core/metrics/logging.rb +5 -5
  147. data/lib/datadog/core/process_discovery.rb +32 -0
  148. data/lib/datadog/core/rate_limiter.rb +4 -2
  149. data/lib/datadog/core/remote/client/capabilities.rb +6 -0
  150. data/lib/datadog/core/remote/client.rb +107 -92
  151. data/lib/datadog/core/remote/component.rb +18 -19
  152. data/lib/datadog/core/remote/configuration/digest.rb +7 -7
  153. data/lib/datadog/core/remote/configuration/path.rb +1 -1
  154. data/lib/datadog/core/remote/configuration/repository.rb +2 -1
  155. data/lib/datadog/core/remote/negotiation.rb +9 -9
  156. data/lib/datadog/core/remote/transport/config.rb +4 -3
  157. data/lib/datadog/core/remote/transport/http/api.rb +13 -18
  158. data/lib/datadog/core/remote/transport/http/client.rb +5 -4
  159. data/lib/datadog/core/remote/transport/http/config.rb +27 -55
  160. data/lib/datadog/core/remote/transport/http/negotiation.rb +8 -51
  161. data/lib/datadog/core/remote/transport/http.rb +25 -94
  162. data/lib/datadog/core/remote/transport/negotiation.rb +17 -4
  163. data/lib/datadog/core/remote/worker.rb +10 -7
  164. data/lib/datadog/core/runtime/metrics.rb +12 -5
  165. data/lib/datadog/core/telemetry/component.rb +84 -49
  166. data/lib/datadog/core/telemetry/emitter.rb +23 -11
  167. data/lib/datadog/core/telemetry/event/app_client_configuration_change.rb +65 -0
  168. data/lib/datadog/core/telemetry/event/app_closing.rb +18 -0
  169. data/lib/datadog/core/telemetry/event/app_dependencies_loaded.rb +33 -0
  170. data/lib/datadog/core/telemetry/event/app_heartbeat.rb +18 -0
  171. data/lib/datadog/core/telemetry/event/app_integrations_change.rb +58 -0
  172. data/lib/datadog/core/telemetry/event/app_started.rb +179 -0
  173. data/lib/datadog/core/telemetry/event/base.rb +40 -0
  174. data/lib/datadog/core/telemetry/event/distributions.rb +18 -0
  175. data/lib/datadog/core/telemetry/event/generate_metrics.rb +43 -0
  176. data/lib/datadog/core/telemetry/event/log.rb +76 -0
  177. data/lib/datadog/core/telemetry/event/message_batch.rb +42 -0
  178. data/lib/datadog/core/telemetry/event/synth_app_client_configuration_change.rb +43 -0
  179. data/lib/datadog/core/telemetry/event.rb +17 -383
  180. data/lib/datadog/core/telemetry/ext.rb +1 -0
  181. data/lib/datadog/core/telemetry/http/adapters/net.rb +12 -97
  182. data/lib/datadog/core/telemetry/logger.rb +1 -1
  183. data/lib/datadog/core/telemetry/logging.rb +2 -2
  184. data/lib/datadog/core/telemetry/metric.rb +28 -6
  185. data/lib/datadog/core/telemetry/request.rb +4 -4
  186. data/lib/datadog/core/telemetry/transport/http/api.rb +43 -0
  187. data/lib/datadog/core/telemetry/transport/http/client.rb +49 -0
  188. data/lib/datadog/core/telemetry/transport/http/telemetry.rb +92 -0
  189. data/lib/datadog/core/telemetry/transport/http.rb +63 -0
  190. data/lib/datadog/core/telemetry/transport/telemetry.rb +51 -0
  191. data/lib/datadog/core/telemetry/worker.rb +128 -25
  192. data/lib/datadog/core/transport/http/adapters/test.rb +2 -1
  193. data/lib/datadog/core/transport/http/adapters/unix_socket.rb +1 -1
  194. data/lib/datadog/{tracing → core}/transport/http/api/instance.rb +18 -1
  195. data/lib/datadog/core/transport/http/api/spec.rb +36 -0
  196. data/lib/datadog/{tracing → core}/transport/http/builder.rb +53 -31
  197. data/lib/datadog/core/transport/http.rb +75 -0
  198. data/lib/datadog/core/transport/response.rb +4 -0
  199. data/lib/datadog/core/utils/at_fork_monkey_patch.rb +6 -6
  200. data/lib/datadog/core/utils/duration.rb +32 -32
  201. data/lib/datadog/core/utils/forking.rb +2 -2
  202. data/lib/datadog/core/utils/network.rb +6 -6
  203. data/lib/datadog/core/utils/only_once_successful.rb +16 -5
  204. data/lib/datadog/core/utils/time.rb +20 -0
  205. data/lib/datadog/core/utils/truncation.rb +21 -0
  206. data/lib/datadog/core/vendor/multipart-post/multipart/post/composite_read_io.rb +1 -1
  207. data/lib/datadog/core/vendor/multipart-post/multipart/post/multipartable.rb +8 -8
  208. data/lib/datadog/core/vendor/multipart-post/multipart/post/parts.rb +7 -7
  209. data/lib/datadog/core/worker.rb +1 -1
  210. data/lib/datadog/core/workers/async.rb +29 -12
  211. data/lib/datadog/core/workers/interval_loop.rb +12 -1
  212. data/lib/datadog/core/workers/runtime_metrics.rb +2 -2
  213. data/lib/datadog/core.rb +8 -0
  214. data/lib/datadog/di/base.rb +115 -0
  215. data/lib/datadog/di/boot.rb +34 -0
  216. data/lib/datadog/di/code_tracker.rb +26 -15
  217. data/lib/datadog/di/component.rb +23 -14
  218. data/lib/datadog/di/configuration/settings.rb +25 -1
  219. data/lib/datadog/di/contrib/active_record.rb +1 -0
  220. data/lib/datadog/di/contrib/railtie.rb +15 -0
  221. data/lib/datadog/di/contrib.rb +28 -0
  222. data/lib/datadog/di/error.rb +5 -0
  223. data/lib/datadog/di/instrumenter.rb +111 -20
  224. data/lib/datadog/di/logger.rb +30 -0
  225. data/lib/datadog/di/preload.rb +18 -0
  226. data/lib/datadog/di/probe.rb +14 -7
  227. data/lib/datadog/di/probe_builder.rb +1 -0
  228. data/lib/datadog/di/probe_manager.rb +11 -5
  229. data/lib/datadog/di/probe_notification_builder.rb +34 -8
  230. data/lib/datadog/di/probe_notifier_worker.rb +52 -26
  231. data/lib/datadog/di/redactor.rb +0 -1
  232. data/lib/datadog/di/remote.rb +147 -0
  233. data/lib/datadog/di/serializer.rb +14 -7
  234. data/lib/datadog/di/transport/diagnostics.rb +62 -0
  235. data/lib/datadog/di/transport/http/api.rb +42 -0
  236. data/lib/datadog/di/transport/http/client.rb +47 -0
  237. data/lib/datadog/di/transport/http/diagnostics.rb +65 -0
  238. data/lib/datadog/di/transport/http/input.rb +67 -0
  239. data/lib/datadog/di/transport/http.rb +57 -0
  240. data/lib/datadog/di/transport/input.rb +62 -0
  241. data/lib/datadog/di/utils.rb +103 -0
  242. data/lib/datadog/di.rb +14 -76
  243. data/lib/datadog/error_tracking/collector.rb +87 -0
  244. data/lib/datadog/error_tracking/component.rb +167 -0
  245. data/lib/datadog/error_tracking/configuration/settings.rb +63 -0
  246. data/lib/datadog/error_tracking/configuration.rb +11 -0
  247. data/lib/datadog/error_tracking/ext.rb +18 -0
  248. data/lib/datadog/error_tracking/extensions.rb +16 -0
  249. data/lib/datadog/error_tracking/filters.rb +77 -0
  250. data/lib/datadog/error_tracking.rb +18 -0
  251. data/lib/datadog/kit/appsec/events.rb +15 -3
  252. data/lib/datadog/kit/identity.rb +9 -5
  253. data/lib/datadog/opentelemetry/api/baggage.rb +90 -0
  254. data/lib/datadog/opentelemetry/api/baggage.rbs +26 -0
  255. data/lib/datadog/opentelemetry/api/context.rb +16 -2
  256. data/lib/datadog/opentelemetry/sdk/trace/span.rb +1 -1
  257. data/lib/datadog/opentelemetry.rb +2 -1
  258. data/lib/datadog/profiling/collectors/code_provenance.rb +1 -1
  259. data/lib/datadog/profiling/collectors/info.rb +3 -0
  260. data/lib/datadog/profiling/collectors/thread_context.rb +1 -1
  261. data/lib/datadog/profiling/component.rb +60 -76
  262. data/lib/datadog/profiling/encoded_profile.rb +11 -0
  263. data/lib/datadog/profiling/exporter.rb +3 -4
  264. data/lib/datadog/profiling/ext.rb +0 -2
  265. data/lib/datadog/profiling/flush.rb +5 -8
  266. data/lib/datadog/profiling/http_transport.rb +6 -85
  267. data/lib/datadog/profiling/load_native_extension.rb +1 -33
  268. data/lib/datadog/profiling/scheduler.rb +8 -1
  269. data/lib/datadog/profiling/stack_recorder.rb +4 -4
  270. data/lib/datadog/profiling/tag_builder.rb +1 -5
  271. data/lib/datadog/profiling.rb +6 -2
  272. data/lib/datadog/tracing/analytics.rb +1 -1
  273. data/lib/datadog/tracing/component.rb +16 -12
  274. data/lib/datadog/tracing/configuration/ext.rb +8 -1
  275. data/lib/datadog/tracing/configuration/settings.rb +22 -10
  276. data/lib/datadog/tracing/context_provider.rb +1 -1
  277. data/lib/datadog/tracing/contrib/action_cable/integration.rb +5 -2
  278. data/lib/datadog/tracing/contrib/action_mailer/integration.rb +6 -2
  279. data/lib/datadog/tracing/contrib/action_pack/integration.rb +5 -2
  280. data/lib/datadog/tracing/contrib/action_view/integration.rb +5 -2
  281. data/lib/datadog/tracing/contrib/active_job/integration.rb +5 -2
  282. data/lib/datadog/tracing/contrib/active_record/integration.rb +7 -3
  283. data/lib/datadog/tracing/contrib/active_support/cache/events/cache.rb +7 -2
  284. data/lib/datadog/tracing/contrib/active_support/cache/instrumentation.rb +36 -1
  285. data/lib/datadog/tracing/contrib/active_support/cache/patcher.rb +4 -0
  286. data/lib/datadog/tracing/contrib/active_support/cache/redis.rb +14 -4
  287. data/lib/datadog/tracing/contrib/active_support/configuration/settings.rb +10 -0
  288. data/lib/datadog/tracing/contrib/active_support/integration.rb +5 -2
  289. data/lib/datadog/tracing/contrib/auto_instrument.rb +2 -2
  290. data/lib/datadog/tracing/contrib/aws/instrumentation.rb +10 -0
  291. data/lib/datadog/tracing/contrib/aws/integration.rb +3 -0
  292. data/lib/datadog/tracing/contrib/aws/parsed_context.rb +5 -1
  293. data/lib/datadog/tracing/contrib/concurrent_ruby/integration.rb +3 -0
  294. data/lib/datadog/tracing/contrib/configuration/settings.rb +1 -1
  295. data/lib/datadog/tracing/contrib/elasticsearch/configuration/settings.rb +4 -0
  296. data/lib/datadog/tracing/contrib/elasticsearch/patcher.rb +6 -1
  297. data/lib/datadog/tracing/contrib/ethon/easy_patch.rb +4 -5
  298. data/lib/datadog/tracing/contrib/excon/middleware.rb +5 -3
  299. data/lib/datadog/tracing/contrib/ext.rb +1 -0
  300. data/lib/datadog/tracing/contrib/extensions.rb +29 -3
  301. data/lib/datadog/tracing/contrib/faraday/middleware.rb +5 -3
  302. data/lib/datadog/tracing/contrib/graphql/configuration/error_extension_env_parser.rb +21 -0
  303. data/lib/datadog/tracing/contrib/graphql/configuration/settings.rb +11 -0
  304. data/lib/datadog/tracing/contrib/graphql/ext.rb +5 -0
  305. data/lib/datadog/tracing/contrib/graphql/unified_trace.rb +102 -11
  306. data/lib/datadog/tracing/contrib/grpc/datadog_interceptor/client.rb +7 -1
  307. data/lib/datadog/tracing/contrib/grpc/distributed/propagation.rb +3 -0
  308. data/lib/datadog/tracing/contrib/http/circuit_breaker.rb +0 -15
  309. data/lib/datadog/tracing/contrib/http/distributed/propagation.rb +4 -1
  310. data/lib/datadog/tracing/contrib/http/instrumentation.rb +6 -10
  311. data/lib/datadog/tracing/contrib/http/integration.rb +3 -0
  312. data/lib/datadog/tracing/contrib/httpclient/instrumentation.rb +6 -16
  313. data/lib/datadog/tracing/contrib/httprb/instrumentation.rb +7 -15
  314. data/lib/datadog/tracing/contrib/httprb/integration.rb +3 -0
  315. data/lib/datadog/tracing/contrib/kafka/integration.rb +3 -0
  316. data/lib/datadog/tracing/contrib/karafka/configuration/settings.rb +27 -0
  317. data/lib/datadog/tracing/contrib/karafka/distributed/propagation.rb +48 -0
  318. data/lib/datadog/tracing/contrib/karafka/ext.rb +27 -0
  319. data/lib/datadog/tracing/contrib/karafka/integration.rb +45 -0
  320. data/lib/datadog/tracing/contrib/karafka/monitor.rb +66 -0
  321. data/lib/datadog/tracing/contrib/karafka/patcher.rb +71 -0
  322. data/lib/datadog/tracing/contrib/karafka.rb +37 -0
  323. data/lib/datadog/tracing/contrib/mongodb/configuration/settings.rb +8 -0
  324. data/lib/datadog/tracing/contrib/mongodb/ext.rb +1 -0
  325. data/lib/datadog/tracing/contrib/mongodb/integration.rb +3 -0
  326. data/lib/datadog/tracing/contrib/mongodb/subscribers.rb +18 -1
  327. data/lib/datadog/tracing/contrib/opensearch/configuration/settings.rb +17 -0
  328. data/lib/datadog/tracing/contrib/opensearch/ext.rb +9 -0
  329. data/lib/datadog/tracing/contrib/opensearch/integration.rb +3 -0
  330. data/lib/datadog/tracing/contrib/opensearch/patcher.rb +5 -1
  331. data/lib/datadog/tracing/contrib/patcher.rb +5 -2
  332. data/lib/datadog/tracing/contrib/presto/integration.rb +3 -0
  333. data/lib/datadog/tracing/contrib/rack/header_collection.rb +11 -1
  334. data/lib/datadog/tracing/contrib/rack/integration.rb +2 -2
  335. data/lib/datadog/tracing/contrib/rack/middlewares.rb +1 -1
  336. data/lib/datadog/tracing/contrib/rack/request_queue.rb +1 -1
  337. data/lib/datadog/tracing/contrib/rails/framework.rb +2 -2
  338. data/lib/datadog/tracing/contrib/rails/patcher.rb +1 -1
  339. data/lib/datadog/tracing/contrib/rest_client/integration.rb +3 -0
  340. data/lib/datadog/tracing/contrib/rest_client/request_patch.rb +5 -3
  341. data/lib/datadog/tracing/contrib/sidekiq/client_tracer.rb +6 -1
  342. data/lib/datadog/tracing/contrib/sidekiq/distributed/propagation.rb +3 -0
  343. data/lib/datadog/tracing/contrib/sidekiq/server_tracer.rb +1 -1
  344. data/lib/datadog/tracing/contrib/span_attribute_schema.rb +6 -1
  345. data/lib/datadog/tracing/contrib/support.rb +28 -0
  346. data/lib/datadog/tracing/contrib.rb +1 -0
  347. data/lib/datadog/tracing/correlation.rb +9 -2
  348. data/lib/datadog/tracing/distributed/b3_multi.rb +1 -1
  349. data/lib/datadog/tracing/distributed/b3_single.rb +1 -1
  350. data/lib/datadog/tracing/distributed/baggage.rb +131 -0
  351. data/lib/datadog/tracing/distributed/datadog.rb +4 -2
  352. data/lib/datadog/tracing/distributed/propagation.rb +25 -4
  353. data/lib/datadog/tracing/distributed/propagation_policy.rb +42 -0
  354. data/lib/datadog/tracing/metadata/errors.rb +4 -4
  355. data/lib/datadog/tracing/metadata/ext.rb +5 -0
  356. data/lib/datadog/tracing/metadata/metastruct.rb +36 -0
  357. data/lib/datadog/tracing/metadata/metastruct_tagging.rb +42 -0
  358. data/lib/datadog/tracing/metadata.rb +2 -0
  359. data/lib/datadog/tracing/sampling/rate_sampler.rb +2 -1
  360. data/lib/datadog/tracing/sampling/span/rule.rb +0 -1
  361. data/lib/datadog/tracing/span.rb +22 -5
  362. data/lib/datadog/tracing/span_event.rb +124 -4
  363. data/lib/datadog/tracing/span_operation.rb +52 -16
  364. data/lib/datadog/tracing/sync_writer.rb +9 -5
  365. data/lib/datadog/tracing/trace_digest.rb +9 -2
  366. data/lib/datadog/tracing/trace_operation.rb +44 -24
  367. data/lib/datadog/tracing/trace_segment.rb +6 -4
  368. data/lib/datadog/tracing/tracer.rb +60 -12
  369. data/lib/datadog/tracing/transport/http/api.rb +5 -4
  370. data/lib/datadog/tracing/transport/http/client.rb +5 -4
  371. data/lib/datadog/tracing/transport/http/traces.rb +13 -44
  372. data/lib/datadog/tracing/transport/http.rb +13 -70
  373. data/lib/datadog/tracing/transport/serializable_trace.rb +31 -7
  374. data/lib/datadog/tracing/transport/trace_formatter.rb +7 -0
  375. data/lib/datadog/tracing/transport/traces.rb +47 -13
  376. data/lib/datadog/tracing/utils.rb +1 -1
  377. data/lib/datadog/tracing/workers/trace_writer.rb +8 -5
  378. data/lib/datadog/tracing/workers.rb +5 -4
  379. data/lib/datadog/tracing/writer.rb +10 -6
  380. data/lib/datadog/tracing.rb +16 -3
  381. data/lib/datadog/version.rb +2 -2
  382. data/lib/datadog.rb +2 -0
  383. metadata +143 -50
  384. data/ext/datadog_profiling_loader/datadog_profiling_loader.c +0 -142
  385. data/ext/datadog_profiling_loader/extconf.rb +0 -60
  386. data/lib/datadog/appsec/contrib/devise/event.rb +0 -57
  387. data/lib/datadog/appsec/contrib/devise/patcher/authenticatable_patch.rb +0 -77
  388. data/lib/datadog/appsec/contrib/devise/patcher/registration_controller_patch.rb +0 -54
  389. data/lib/datadog/appsec/contrib/devise/resource.rb +0 -35
  390. data/lib/datadog/appsec/contrib/devise/tracking.rb +0 -57
  391. data/lib/datadog/appsec/contrib/graphql/reactive/multiplex.rb +0 -46
  392. data/lib/datadog/appsec/contrib/patcher.rb +0 -12
  393. data/lib/datadog/appsec/contrib/rack/reactive/request.rb +0 -69
  394. data/lib/datadog/appsec/contrib/rack/reactive/request_body.rb +0 -47
  395. data/lib/datadog/appsec/contrib/rack/reactive/response.rb +0 -53
  396. data/lib/datadog/appsec/contrib/rails/reactive/action.rb +0 -53
  397. data/lib/datadog/appsec/contrib/sinatra/ext.rb +0 -14
  398. data/lib/datadog/appsec/contrib/sinatra/reactive/routed.rb +0 -48
  399. data/lib/datadog/appsec/monitor/reactive/set_user.rb +0 -45
  400. data/lib/datadog/appsec/processor/actions.rb +0 -49
  401. data/lib/datadog/appsec/processor/context.rb +0 -107
  402. data/lib/datadog/appsec/reactive/address_hash.rb +0 -22
  403. data/lib/datadog/appsec/reactive/engine.rb +0 -47
  404. data/lib/datadog/appsec/reactive/operation.rb +0 -68
  405. data/lib/datadog/appsec/reactive/subscriber.rb +0 -19
  406. data/lib/datadog/appsec/scope.rb +0 -58
  407. data/lib/datadog/appsec/utils/trace_operation.rb +0 -15
  408. data/lib/datadog/core/crashtracking/agent_base_url.rb +0 -21
  409. data/lib/datadog/core/remote/transport/http/api/instance.rb +0 -39
  410. data/lib/datadog/core/remote/transport/http/api/spec.rb +0 -21
  411. data/lib/datadog/core/remote/transport/http/builder.rb +0 -219
  412. data/lib/datadog/core/telemetry/http/env.rb +0 -20
  413. data/lib/datadog/core/telemetry/http/ext.rb +0 -28
  414. data/lib/datadog/core/telemetry/http/response.rb +0 -70
  415. data/lib/datadog/core/telemetry/http/transport.rb +0 -90
  416. data/lib/datadog/di/transport.rb +0 -81
  417. data/lib/datadog/tracing/transport/http/api/spec.rb +0 -19
@@ -32,7 +32,7 @@ module Datadog
32
32
  def stripped_ip_from_request_headers(headers, ip_headers_to_check: DEFAULT_IP_HEADERS_NAMES)
33
33
  ip = ip_header(headers, ip_headers_to_check)
34
34
 
35
- ip ? ip.to_s : nil
35
+ ip&.to_s
36
36
  end
37
37
 
38
38
  # @param [String] IP value.
@@ -40,7 +40,7 @@ module Datadog
40
40
  # @return [nil] when no valid IP value found.
41
41
  def stripped_ip(ip)
42
42
  ip = ip_to_ipaddr(ip)
43
- ip ? ip.to_s : nil
43
+ ip&.to_s
44
44
  end
45
45
 
46
46
  private
@@ -52,10 +52,10 @@ module Datadog
52
52
  return unless ip
53
53
 
54
54
  clean_ip = if likely_ipv4?(ip)
55
- strip_ipv4_port(ip)
56
- else
57
- strip_zone_specifier(strip_ipv6_port(ip))
58
- end
55
+ strip_ipv4_port(ip)
56
+ else
57
+ strip_zone_specifier(strip_ipv6_port(ip))
58
+ end
59
59
 
60
60
  begin
61
61
  IPAddr.new(clean_ip)
@@ -5,14 +5,25 @@ require_relative 'only_once'
5
5
  module Datadog
6
6
  module Core
7
7
  module Utils
8
- # Helper class to execute something with only one success.
8
+ # Helper class to execute something with only one successful execution.
9
9
  #
10
- # This is useful for cases where we want to ensure that a block of code is only executed once, and only if it
11
- # succeeds. One such example is sending app-started telemetry event.
10
+ # If limit is not provided to the constructor, +run+ will execute the
11
+ # block an unlimited number of times until the block indicates that it
12
+ # executed successfully by returning a truthy value. After a block
13
+ # executes successfully, subsequent +run+ calls will not invoke the
14
+ # block.
12
15
  #
13
- # Successful execution is determined by the return value of the block: any truthy value is considered success.
16
+ # If a non-zero limit is provided to the constructor, +run+ will
17
+ # execute the block up to that many times, and will mark the instance
18
+ # of OnlyOneSuccessful as failed if none of the executions succeeded.
14
19
  #
15
- # Thread-safe when used correctly (e.g. be careful of races when lazily initializing instances of this class).
20
+ # One consumer of this class is sending the app-started telemetry event.
21
+ #
22
+ # Successful execution is determined by the return value of the block:
23
+ # any truthy value is considered success.
24
+ #
25
+ # This class is thread-safe (however, instances of it must also be
26
+ # created in a thread-safe manner).
16
27
  #
17
28
  # Note: In its current state, this class is not Ractor-safe.
18
29
  # In https://github.com/DataDog/dd-trace-rb/pull/1398#issuecomment-797378810 we have a discussion of alternatives,
@@ -31,6 +31,16 @@ module Datadog
31
31
  #
32
32
  # @param block [Proc] block that returns a `Time` object representing the current wall time
33
33
  def now_provider=(block)
34
+ class << self
35
+ # Avoid method redefinition warning.
36
+ # `rescue nil` is added in case customers remove the method
37
+ # themselves to squelch the warning.
38
+ begin
39
+ remove_method(:now)
40
+ rescue
41
+ nil
42
+ end
43
+ end
34
44
  define_singleton_method(:now, &block)
35
45
  end
36
46
 
@@ -43,6 +53,16 @@ module Datadog
43
53
  #
44
54
  # @param block [Proc] block that accepts unit and returns timestamp in the requested unit
45
55
  def get_time_provider=(block)
56
+ class << self
57
+ # Avoid method redefinition warning
58
+ # `rescue nil` is added in case customers remove the method
59
+ # themselves to squelch the warning.
60
+ begin
61
+ remove_method(:get_time)
62
+ rescue
63
+ nil
64
+ end
65
+ end
46
66
  define_singleton_method(:get_time, &block)
47
67
  end
48
68
 
@@ -0,0 +1,21 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Datadog
4
+ module Core
5
+ module Utils
6
+ # Helper methods for truncating data
7
+ module Truncation
8
+ module_function
9
+
10
+ def truncate_in_middle(string, max_prefix_length, max_suffix_length)
11
+ max_length = max_prefix_length + 3 + max_suffix_length
12
+ if string.length > max_length
13
+ "#{string[0...max_prefix_length]}...#{string[-max_suffix_length..-1]}"
14
+ else
15
+ string
16
+ end
17
+ end
18
+ end
19
+ end
20
+ end
21
+ end
@@ -108,7 +108,7 @@ module Datadog
108
108
  end
109
109
 
110
110
  def respond_to?(meth, include_all = false)
111
- @io.respond_to?(meth, include_all) || super(meth, include_all)
111
+ @io.respond_to?(meth, include_all) || super
112
112
  end
113
113
  end
114
114
  end
@@ -28,29 +28,29 @@ module Datadog
28
28
  "--#{SecureRandom.uuid}"
29
29
  end
30
30
 
31
- def initialize(path, params, headers={}, boundary = Multipartable.secure_boundary)
31
+ def initialize(path, params, headers = {}, boundary = Multipartable.secure_boundary)
32
32
  headers = headers.clone # don't want to modify the original variable
33
33
  parts_headers = headers.delete(:parts) || {}
34
34
  super(path, headers)
35
- parts = params.map do |k,v|
35
+ parts = params.map do |k, v|
36
36
  case v
37
37
  when Array
38
- v.map {|item| Parts::Part.new(boundary, "#{k}[]", item, parts_headers[k]) }
38
+ v.map { |item| Parts::Part.new(boundary, "#{k}[]", item, parts_headers[k]) }
39
39
  else
40
40
  Parts::Part.new(boundary, k, v, parts_headers[k])
41
41
  end
42
42
  end.flatten
43
43
  parts << Parts::EpiloguePart.new(boundary)
44
- ios = parts.map {|p| p.to_io }
45
- self.set_content_type(headers["Content-Type"] || "multipart/form-data",
46
- { "boundary" => boundary })
47
- self.content_length = parts.inject(0) {|sum,i| sum + i.length }
44
+ ios = parts.map { |p| p.to_io }
45
+ set_content_type(headers["Content-Type"] || "multipart/form-data",
46
+ {"boundary" => boundary})
47
+ self.content_length = parts.inject(0) { |sum, i| sum + i.length }
48
48
  self.body_stream = CompositeReadIO.new(*ios)
49
49
 
50
50
  @boundary = boundary
51
51
  end
52
52
 
53
- attr :boundary
53
+ attr_reader :boundary
54
54
  end
55
55
  end
56
56
  end
@@ -58,7 +58,7 @@ module Datadog
58
58
  part = ''
59
59
  part << "--#{boundary}\r\n"
60
60
  part << "Content-ID: #{headers["Content-ID"]}\r\n" if headers["Content-ID"]
61
- part << "Content-Disposition: form-data; name=\"#{name.to_s}\"\r\n"
61
+ part << "Content-Disposition: form-data; name=\"#{name}\"\r\n"
62
62
  part << "Content-Type: #{headers["Content-Type"]}\r\n" if headers["Content-Type"]
63
63
  part << "\r\n"
64
64
  part << "#{value}\r\n"
@@ -76,9 +76,9 @@ module Datadog
76
76
  # @param io [IO]
77
77
  # @param headers [Hash]
78
78
  def initialize(boundary, name, io, headers = {})
79
- file_length = io.respond_to?(:length) ? io.length : File.size(io.local_path)
79
+ file_length = io.respond_to?(:length) ? io.length : File.size(io.local_path)
80
80
  @head = build_head(boundary, name, io.original_filename, io.content_type, file_length,
81
- io.respond_to?(:opts) ? io.opts.merge(headers) : headers)
81
+ io.respond_to?(:opts) ? io.opts.merge(headers) : headers)
82
82
  @foot = "\r\n"
83
83
  @length = @head.bytesize + file_length + @foot.length
84
84
  @io = CompositeReadIO.new(StringIO.new(@head), io, StringIO.new(@foot))
@@ -98,16 +98,16 @@ module Datadog
98
98
 
99
99
  part = ''
100
100
  part << "--#{boundary}\r\n"
101
- part << "Content-Disposition: #{content_disposition}; name=\"#{name.to_s}\"; filename=\"#{filename}\"\r\n"
101
+ part << "Content-Disposition: #{content_disposition}; name=\"#{name}\"; filename=\"#{filename}\"\r\n"
102
102
  part << "Content-Length: #{content_len}\r\n"
103
103
  if content_id = opts.delete("Content-ID")
104
104
  part << "Content-ID: #{content_id}\r\n"
105
105
  end
106
106
 
107
- if opts["Content-Type"] != nil
108
- part << "Content-Type: " + opts["Content-Type"] + "\r\n"
107
+ part << if !opts["Content-Type"].nil?
108
+ "Content-Type: " + opts["Content-Type"] + "\r\n"
109
109
  else
110
- part << "Content-Type: #{type}\r\n"
110
+ "Content-Type: #{type}\r\n"
111
111
  end
112
112
 
113
113
  part << "Content-Transfer-Encoding: #{trans_encoding}\r\n"
@@ -12,7 +12,7 @@ module Datadog
12
12
  end
13
13
 
14
14
  def perform(*args)
15
- task.call(*args) unless task.nil?
15
+ task&.call(*args)
16
16
  end
17
17
 
18
18
  protected
@@ -47,6 +47,14 @@ module Datadog
47
47
  @run_async = false
48
48
  Datadog.logger.debug { "Forcibly terminating worker thread for: #{self}" }
49
49
  worker.terminate
50
+ # Wait for the worker thread to end
51
+ begin
52
+ Timeout.timeout(SHUTDOWN_TIMEOUT) do
53
+ worker.join
54
+ end
55
+ rescue Timeout::Error
56
+ Datadog.logger.debug { "Worker thread did not end after #{SHUTDOWN_TIMEOUT} seconds: #{self}" }
57
+ end
50
58
  true
51
59
  end
52
60
 
@@ -112,23 +120,33 @@ module Datadog
112
120
  @worker ||= nil
113
121
  end
114
122
 
123
+ # Returns true if worker thread is successfully started,
124
+ # false if it is not started. Reasons for not starting the worker
125
+ # thread: it is already running, or the process forked and fork
126
+ # policy is to stop the workers on fork (which means they are
127
+ # not started in children, really).
115
128
  def start_async(&block)
116
129
  mutex.synchronize do
117
- return if running?
130
+ return false if running?
118
131
 
119
132
  if forked?
120
133
  case fork_policy
121
134
  when FORK_POLICY_STOP
122
135
  stop_fork
136
+ false
123
137
  when FORK_POLICY_RESTART
138
+ # restart_after_fork should return true
124
139
  restart_after_fork(&block)
125
140
  end
126
141
  elsif !run_async?
142
+ # start_worker should return true
127
143
  start_worker(&block)
128
144
  end
129
145
  end
130
146
  end
131
147
 
148
+ # Returns true if worker thread is successfully started,
149
+ # which should generally be always.
132
150
  def start_worker
133
151
  @run_async = true
134
152
  @pid = Process.pid
@@ -136,22 +154,21 @@ module Datadog
136
154
  Datadog.logger.debug { "Starting thread for: #{self}" }
137
155
 
138
156
  @worker = ::Thread.new do
139
- begin
140
- yield
141
- # rubocop:disable Lint/RescueException
142
- rescue Exception => e
143
- @error = e
144
- Datadog.logger.debug(
145
- "Worker thread error. Cause: #{e.class.name} #{e.message} Location: #{Array(e.backtrace).first}"
146
- )
147
- raise
148
- end
157
+ yield
158
+ # rubocop:disable Lint/RescueException
159
+ rescue Exception => e
160
+ @error = e
161
+ Datadog.logger.debug(
162
+ "Worker thread error. Cause: #{e.class.name} #{e.message} Location: #{Array(e.backtrace).first}"
163
+ )
164
+ raise
165
+
149
166
  # rubocop:enable Lint/RescueException
150
167
  end
151
168
  @worker.name = self.class.name
152
169
  @worker.thread_variable_set(:fork_safe, true)
153
170
 
154
- nil
171
+ true
155
172
  end
156
173
 
157
174
  def stop_fork
@@ -21,7 +21,18 @@ module Datadog
21
21
  # Methods that must be prepended
22
22
  module PrependedMethods
23
23
  def perform(*args)
24
- perform_loop { super(*args) }
24
+ perform_loop do
25
+ @in_iteration = true
26
+ begin
27
+ super(*args)
28
+ ensure
29
+ @in_iteration = false
30
+ end
31
+ end
32
+ end
33
+
34
+ def in_iteration?
35
+ defined?(@in_iteration) && @in_iteration
25
36
  end
26
37
  end
27
38
 
@@ -20,8 +20,8 @@ module Datadog
20
20
  attr_reader \
21
21
  :metrics
22
22
 
23
- def initialize(options = {})
24
- @metrics = options.fetch(:metrics) { Core::Runtime::Metrics.new }
23
+ def initialize(telemetry:, **options)
24
+ @metrics = options.fetch(:metrics) { Core::Runtime::Metrics.new(logger: options[:logger], telemetry: telemetry) }
25
25
 
26
26
  # Workers::Async::Thread settings
27
27
  self.fork_policy = options.fetch(:fork_policy, Workers::Async::Thread::FORK_POLICY_STOP)
data/lib/datadog/core.rb CHANGED
@@ -11,6 +11,14 @@ module Datadog
11
11
  # for higher-level features.
12
12
  module Core
13
13
  extend Core::Deprecations
14
+
15
+ LIBDATADOG_API_FAILURE =
16
+ begin
17
+ require "libdatadog_api.#{RUBY_VERSION[/\d+.\d+/]}_#{RUBY_PLATFORM}"
18
+ nil
19
+ rescue LoadError => e
20
+ e.message
21
+ end
14
22
  end
15
23
 
16
24
  extend Core::Extensions
@@ -0,0 +1,115 @@
1
+ # frozen_string_literal: true
2
+
3
+ # This file is loaded by datadog/di/preload.rb.
4
+ # It contains just the global DI reference to the (normally one and only)
5
+ # code tracker for the current process.
6
+ # This file should not require the rest of DI, specifically none of the
7
+ # contrib code that is meant to be loaded after third-party libraries
8
+ # are loaded, and also none of the rest of datadog library which also
9
+ # has contrib code in other products.
10
+
11
+ require_relative 'code_tracker'
12
+
13
+ module Datadog
14
+ # Namespace for Datadog dynamic instrumentation.
15
+ #
16
+ # @api private
17
+ module DI
18
+ LOCK = Mutex.new
19
+
20
+ class << self
21
+ attr_reader :code_tracker
22
+
23
+ # Activates code tracking. Normally this method should be called
24
+ # when the application starts. If instrumenting third-party code,
25
+ # code tracking needs to be enabled before the third-party libraries
26
+ # are loaded. Any third-party code loaded before code tracking is
27
+ # activated will NOT be instrumentable using dynamic instrumentation.
28
+ #
29
+ # TODO test that activating tracker multiple times preserves
30
+ # existing mappings in the registry
31
+ def activate_tracking!
32
+ (@code_tracker ||= CodeTracker.new).start
33
+ end
34
+
35
+ # Activates code tracking if possible.
36
+ #
37
+ # This method does nothing if invoked in an environment that does not
38
+ # implement required trace points for code tracking (MRI Ruby < 2.6,
39
+ # JRuby) and rescues any exceptions that may be raised by downstream
40
+ # DI code.
41
+ def activate_tracking
42
+ # :script_compiled trace point was added in Ruby 2.6.
43
+ return unless RUBY_VERSION >= '2.6'
44
+
45
+ begin
46
+ # Activate code tracking by default because line trace points will not work
47
+ # without it.
48
+ Datadog::DI.activate_tracking!
49
+ rescue => exc
50
+ if defined?(Datadog.logger)
51
+ Datadog.logger.warn { "di: Failed to activate code tracking for DI: #{exc.class}: #{exc}" }
52
+ else
53
+ # We do not have Datadog logger potentially because DI code tracker is
54
+ # being loaded early in application boot process and the rest of datadog
55
+ # wasn't loaded yet. Output to standard error.
56
+ warn("datadog: di: Failed to activate code tracking for DI: #{exc.class}: #{exc}")
57
+ end
58
+ end
59
+ end
60
+
61
+ # Deactivates code tracking. In normal usage of DI this method should
62
+ # never be called, however it is used by DI's test suite to reset
63
+ # state for individual tests.
64
+ #
65
+ # Note that deactivating tracking clears out the registry, losing
66
+ # the ability to look up files that have been loaded into the process
67
+ # already.
68
+ def deactivate_tracking!
69
+ code_tracker&.stop
70
+ end
71
+
72
+ # Returns whether code tracking is available.
73
+ # This method should be used instead of querying #code_tracker
74
+ # because the latter one may be nil.
75
+ def code_tracking_active?
76
+ code_tracker&.active? || false
77
+ end
78
+
79
+ # DI code tracker is instantiated globally before the regular set of
80
+ # components is created, but the code tracker needs to call out to the
81
+ # "current" DI component to perform instrumentation when application
82
+ # code is loaded. Because this call may happen prior to Datadog
83
+ # components having been initialized, we maintain the "current component"
84
+ # which contains a reference to the most recently instantiated
85
+ # DI::Component. This way, if a DI component hasn't been instantiated,
86
+ # we do not try to reference Datadog.components.
87
+ # In other words, this method exists so that we never attempt to call
88
+ # Datadog.components from the code tracker.
89
+ def current_component
90
+ LOCK.synchronize do
91
+ @current_components&.last
92
+ end
93
+ end
94
+
95
+ # To avoid potential races with DI::Component being added and removed,
96
+ # we maintain a list of the components. Normally the list should contain
97
+ # either zero or one component depending on whether DI is enabled in
98
+ # Datadog configuration. However, if a new instance of DI::Component
99
+ # is created while the previous instance is still running, we are
100
+ # guaranteed to not end up with no component when one is running.
101
+ def add_current_component(component)
102
+ LOCK.synchronize do
103
+ @current_components ||= []
104
+ @current_components << component
105
+ end
106
+ end
107
+
108
+ def remove_current_component(component)
109
+ LOCK.synchronize do
110
+ @current_components&.delete(component)
111
+ end
112
+ end
113
+ end
114
+ end
115
+ end
@@ -0,0 +1,34 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative 'logger'
4
+ require_relative 'base'
5
+ require_relative 'error'
6
+ require_relative 'code_tracker'
7
+ require_relative 'component'
8
+ require_relative 'instrumenter'
9
+ require_relative 'probe'
10
+ require_relative 'probe_builder'
11
+ require_relative 'probe_manager'
12
+ require_relative 'probe_notification_builder'
13
+ require_relative 'probe_notifier_worker'
14
+ require_relative 'redactor'
15
+ require_relative 'serializer'
16
+ require_relative 'transport/http'
17
+ require_relative 'utils'
18
+
19
+ if %w[1 true yes].include?(ENV['DD_DYNAMIC_INSTRUMENTATION_ENABLED']) # steep:ignore
20
+ # For initial release of Dynamic Instrumentation, activate code tracking
21
+ # only if DI is explicitly requested in the environment.
22
+ # Code tracking is required for line probes to work; see the comments
23
+ # above for the implementation of the method.
24
+ #
25
+ # If DI is enabled programmatically, the application can (and must,
26
+ # for line probes to work) activate tracking in an initializer.
27
+ # We seem to have Datadog.logger here already
28
+ Datadog.logger.debug("di: activating code tracking")
29
+ Datadog::DI.activate_tracking
30
+ end
31
+
32
+ require_relative 'contrib'
33
+
34
+ Datadog::DI::Contrib.load_now_or_later
@@ -2,6 +2,8 @@
2
2
 
3
3
  # rubocop:disable Lint/AssignmentInCondition
4
4
 
5
+ require_relative 'error'
6
+
5
7
  module Datadog
6
8
  module DI
7
9
  # Tracks loaded Ruby code by source file and maintains a map from
@@ -78,19 +80,21 @@ module Datadog
78
80
  registry_lock.synchronize do
79
81
  registry[path] = tp.instruction_sequence
80
82
  end
81
- end
82
-
83
- DI.component&.probe_manager&.install_pending_line_probes(path)
84
83
 
84
+ # Also, pending line probes should only be installed for
85
+ # non-eval'd code.
86
+ DI.current_component&.probe_manager&.install_pending_line_probes(path)
87
+ end
85
88
  # Since this method normally is called from customer applications,
86
89
  # rescue any exceptions that might not be handled to not break said
87
90
  # customer applications.
88
91
  rescue => exc
89
- # TODO we do not have DI.component defined yet, remove steep:ignore
90
- # before release.
91
- if component = DI.component # steep:ignore
92
+ # Code tracker may be loaded without the rest of DI,
93
+ # in which case DI.component will not yet be defined,
94
+ # but we will have DI.current_component (set to nil).
95
+ if component = DI.current_component
92
96
  raise if component.settings.dynamic_instrumentation.internal.propagate_all_exceptions
93
- component.logger.warn("Unhandled exception in script_compiled trace point: #{exc.class}: #{exc}")
97
+ component.logger.debug { "di: unhandled exception in script_compiled trace point: #{exc.class}: #{exc}" }
94
98
  component.telemetry&.report(exc, description: "Unhandled exception in script_compiled trace point")
95
99
  # TODO test this path
96
100
  else
@@ -136,16 +140,23 @@ module Datadog
136
140
  exact = registry[suffix]
137
141
  return [suffix, exact] if exact
138
142
 
139
- inexact = []
140
- registry.each do |path, iseq|
141
- if Utils.path_matches_suffix?(path, suffix)
142
- inexact << [path, iseq]
143
+ suffix = suffix.dup
144
+ loop do
145
+ inexact = []
146
+ registry.each do |path, iseq|
147
+ if Utils.path_matches_suffix?(path, suffix)
148
+ inexact << [path, iseq]
149
+ end
143
150
  end
151
+ if inexact.length > 1
152
+ raise Error::MultiplePathsMatch, "Multiple paths matched requested suffix"
153
+ end
154
+ if inexact.any?
155
+ return inexact.first
156
+ end
157
+ return nil unless suffix.include?('/')
158
+ suffix.sub!(%r{.*/+}, '')
144
159
  end
145
- if inexact.length > 1
146
- raise Error::MultiplePathsMatch, "Multiple paths matched requested suffix"
147
- end
148
- inexact.first
149
160
  end
150
161
  end
151
162