Skip to content

Commit

Permalink
Changed: Separate global, profiling, tracing settings into their own …
Browse files Browse the repository at this point in the history
…configuration APIs.
  • Loading branch information
delner committed Jan 14, 2022
1 parent 943f0a4 commit 88d0e13
Show file tree
Hide file tree
Showing 9 changed files with 266 additions and 28 deletions.
1 change: 1 addition & 0 deletions .yardopts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
--markup markdown
--markup-provider redcarpet
--readme docs/GettingStarted.md
--tag configure_with:"Configure with"
--tag default:"Defaults to"
--tag 'public_api:Public API'
--hide-tag public_api
Expand Down
28 changes: 24 additions & 4 deletions lib/datadog/tracing.rb
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
require 'ddtrace/configuration/validation_proxy'

module Datadog
# Datadog APM tracing public API.
#
Expand Down Expand Up @@ -49,13 +51,17 @@ def logger

# Current tracer configuration.
#
# Access to non-tracer configuration will raise an error.
#
# To modify the configuration, use {.configure}.
#
# @return [Datadog::Configuration::Settings]
# @!attribute [r] configuration
# @public_api
def configuration
Datadog.configuration
Datadog::Configuration::ValidationProxy::Tracing.new(
Datadog.send(:internal_configuration)
)
end

# Apply configuration changes to `Datadog::Tracing`. An example of a {.configure} call:
Expand All @@ -65,9 +71,15 @@ def configuration
# c.use :aws
# c.use :rails
# c.use :sidekiq
# # c.diagnostics.debug = true # Enables debug output
# end
# ```
# See {Datadog::Configuration::Settings} for all available options, defaults, and
# available environment variables for configuration.
#
# Only permits access to tracing configuration settings; others will raise an error.
# If you wish to configure a global setting, use `Datadog.configure`` instead.
# If you wish to configure a setting for a specific Datadog component (e.g. Profiling),
# use the corresponding `Datadog::COMPONENT.configure` method instead.
#
# Because many configuration changes require restarting internal components,
# invoking {.configure} is the only safe way to change `ddtrace` configuration.
Expand All @@ -81,11 +93,19 @@ def configuration
# See {Datadog::Configuration::Settings} for all available options, defaults, and
# available environment variables for configuration.
#
# Will raise errors if invalid setting is accessed.
#
# @yieldparam [Datadog::Configuration::Settings] c the mutable configuration object
# @return [void]
# @public_api
def configure(&block)
Datadog.configure(&block)
def configure
# Wrap block with trace option validation
wrapped_block = proc do |c|
yield(Datadog::Configuration::ValidationProxy::Tracing.new(c))
end

# Configure application normally
Datadog.send(:internal_configure, &wrapped_block)
end

# Apply configuration changes only to a specific Ruby object. An example of a {.configure_onto} call:
Expand Down
1 change: 1 addition & 0 deletions lib/ddtrace.rb
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ module Datadog
extend Contrib::AutoInstrument
# Load Contrib extension to global Datadog objects
Configuration::Settings.include Contrib::Extensions::Configuration::Settings
Configuration::ValidationProxy::Tracing.include Contrib::Extensions::Configuration::ValidationProxy

# Load and extend OpenTelemetry compatibility by default
extend OpenTelemetry::Extensions
Expand Down
71 changes: 50 additions & 21 deletions lib/ddtrace/configuration.rb
Original file line number Diff line number Diff line change
Expand Up @@ -39,51 +39,58 @@ module Configuration # rubocop:disable Metrics/ModuleLength

attr_writer :configuration

# Current Datadog configuration.
#
# Access to non-global configuration will raise an error.
#
# To modify the configuration, use {.configure}.
#
# @return [Datadog::Configuration::Settings]
# @!attribute [r] configuration
# @public_api
def configuration
@configuration ||= Settings.new
Datadog::Configuration::ValidationProxy::Global.new(
internal_configuration
)
end

# Apply configuration changes to `ddtrace`. An example of a {.configure} call:
# Apply global configuration changes to `Datadog`. An example of a {.configure} call:
#
# ```
# Datadog.configure do |c|
# c.sampling.default_rate = 1.0
# c.use :aws
# c.use :rails
# c.use :sidekiq
# c.service = 'my-service'
# c.env = 'staging'
# # c.diagnostics.debug = true # Enables debug output
# end
# ```
#
# See {Datadog::Configuration::Settings} for all available options, defaults, and
# available environment variables for configuration.
#
# Only permits access to global configuration settings; others will raise an error.
# If you wish to configure a setting for a specific Datadog component (e.g. Tracing),
# use the corresponding `Datadog::COMPONENT.configure` method instead.
#
# Because many configuration changes require restarting internal components,
# invoking {.configure} is the only safe way to change `ddtrace` configuration.
# invoking {.configure} is the only safe way to change `Datadog` configuration.
#
# Successive calls to {.configure} maintain the previous configuration values:
# configuration is additive between {.configure} calls.
#
# The yielded configuration `c` comes pre-populated from environment variables, if
# any are applicable.
#
# See {Datadog::Configuration::Settings} for all available options, defaults, and
# available environment variables for configuration.
#
# @param [Datadog::Configuration::Settings] configuration the base configuration object. Provide a custom instance
# if you are managing the configuration yourself. By default, the global configuration object is used.
# @yieldparam [Datadog::Configuration::Settings] c the mutable configuration object
def configure(configuration = self.configuration)
yield(configuration)

safely_synchronize do |write_components|
write_components.call(
if components?
replace_components!(configuration, @components)
else
build_components(configuration)
end
)
# Wrap block with global option validation
wrapped_block = proc do |c|
yield(Datadog::Configuration::ValidationProxy::Global.new(c))
end

configuration
# Configure application normally
internal_configure(&wrapped_block)
end

def_delegators \
Expand Down Expand Up @@ -214,5 +221,27 @@ def handle_interrupt_shutdown!

nil
end

private

def internal_configure(configuration = self.internal_configuration)
yield(configuration)

safely_synchronize do |write_components|
write_components.call(
if components?
replace_components!(configuration, @components)
else
build_components(configuration)
end
)
end

configuration
end

def internal_configuration
@configuration ||= Settings.new
end
end
end
21 changes: 19 additions & 2 deletions lib/ddtrace/configuration/settings.rb
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ def initialize(*_)

# Legacy [App Analytics](https://docs.datadoghq.com/tracing/legacy_app_analytics/) configuration.
#
# @configure_with Datadog::Tracing
# @deprecated Use [Trace Retention and Ingestion](https://docs.datadoghq.com/tracing/trace_retention_and_ingestion/)
# controls.
# @public_api
Expand All @@ -58,21 +59,23 @@ def initialize(*_)
end
end

# Profiler API key.
# Datadog API key.
#
# For internal use only.
#
# @configure_with Datadog
# @default `DD_API_KEY` environment variable, otherwise `nil`
# @return [String,nil]
option :api_key do |o|
o.default { ENV.fetch(Ext::Environment::ENV_API_KEY, nil) }
o.lazy
end

# Internal tracer diagnostic settings.
# Datadog diagnostic settings.
#
# Enabling these surfaces debug information that can be helpful to
# diagnose issues related to the tracer internals.
# @configure_with Datadog
# @public_api
settings :diagnostics do
# Outputs all spans created by the host application to `Datadog.logger`.
Expand Down Expand Up @@ -144,6 +147,7 @@ def initialize(*_)
# * `B3`: B3 Propagation using multiple headers, described by [openzipkin/b3-propagation](https://github.com/openzipkin/b3-propagation#multiple-headers).
# * `B3 single header`: B3 Propagation using a single header, described by [openzipkin/b3-propagation](https://github.com/openzipkin/b3-propagation#single-header).
#
# @configure_with Datadog::Tracing
# @public_api
settings :distributed_tracing do
# An ordered list of what data propagation styles the tracer will use to extract distributed tracing propagation
Expand Down Expand Up @@ -190,6 +194,7 @@ def initialize(*_)
# @see https://docs.datadoghq.com/getting_started/tagging/unified_service_tagging
# @default `DD_ENV` environment variable, otherwise `nil`
# @return [String,nil]
# @configure_with Datadog
option :env do |o|
# NOTE: env also gets set as a side effect of tags. See the WORKAROUND note in #initialize for details.
o.default { ENV.fetch(Ext::Environment::ENV_ENVIRONMENT, nil) }
Expand All @@ -199,6 +204,7 @@ def initialize(*_)
# Automatic correlation between tracing and logging.
# @see https://docs.datadoghq.com/tracing/setup_overview/setup/ruby/#trace-correlation
# @return [Boolean]
# @configure_with Datadog::Tracing
option :log_injection do |o|
o.default { env_to_bool(Ext::Correlation::ENV_LOGS_INJECTION_ENABLED, true) }
o.lazy
Expand All @@ -207,6 +213,7 @@ def initialize(*_)
# Internal `Datadog.logger` configuration.
#
# This logger instance is only used internally by the gem.
# @configure_with Datadog
# @public_api
settings :logger do
# The `Datadog.logger` object.
Expand All @@ -229,6 +236,7 @@ def initialize(*_)
# Datadog Profiler-specific configurations.
#
# @see https://docs.datadoghq.com/tracing/profiler/
# @configure_with Datadog::Profiling
# @public_api
settings :profiling do
# Enable profiling.
Expand Down Expand Up @@ -292,6 +300,7 @@ def initialize(*_)

# [Runtime Metrics](https://docs.datadoghq.com/tracing/runtime_metrics/)
# are StatsD metrics collected by the tracer to gain additional insights into an application's performance.
# @configure_with Datadog::Tracing
# @public_api
settings :runtime_metrics do
# Enable runtime metrics.
Expand All @@ -307,6 +316,7 @@ def initialize(*_)
end

# Client-side sampling configuration.
# @configure_with Datadog::Tracing
# @public_api
settings :sampling do
# Default sampling rate for the tracer.
Expand Down Expand Up @@ -339,6 +349,7 @@ def initialize(*_)
# @see https://docs.datadoghq.com/getting_started/tagging/unified_service_tagging
# @default `DD_SERVICE` environment variable, otherwise the program name (e.g. `'ruby'`, `'rails'`, `'pry'`)
# @return [String]
# @configure_with Datadog
option :service do |o|
# NOTE: service also gets set as a side effect of tags. See the WORKAROUND note in #initialize for details.
o.default { ENV.fetch(Ext::Environment::ENV_SERVICE, Ext::Environment::FALLBACK_SERVICE_NAME) }
Expand All @@ -361,6 +372,7 @@ def initialize(*_)
# @see https://docs.datadoghq.com/agent/troubleshooting/site/
# @default `DD_SITE` environment variable, otherwise `nil` which sends data to `app.datadoghq.com`
# @return [String,nil]
# @configure_with Datadog
option :site do |o|
o.default { ENV.fetch(Ext::Environment::ENV_SITE, nil) }
o.lazy
Expand All @@ -371,6 +383,7 @@ def initialize(*_)
# These tags are applied to every span.
# @default `DD_TAGS` environment variable (in the format `'tag1:value1,tag2:value2'`), otherwise `{}`
# @return [Hash<String,String>]
# @configure_with Datadog
option :tags do |o|
o.default do
tags = {}
Expand Down Expand Up @@ -412,6 +425,7 @@ def initialize(*_)
end

# [Continuous Integration Visibility](https://docs.datadoghq.com/continuous_integration/) configuration.
# @configure_with Datadog::Tracing
# @public_api
settings :test_mode do
# Enable test mode. This allows the tracer to collect spans from test runs.
Expand Down Expand Up @@ -449,6 +463,7 @@ def initialize(*_)
#
# @default `->{ Time.now }`
# @return [Proc<Time>]
# @configure_with Datadog
option :time_now_provider do |o|
o.default { ::Time.now }

Expand All @@ -466,6 +481,7 @@ def initialize(*_)
end

# Tracer specific configurations.
# @configure_with Datadog::Tracing
# @public_api
settings :tracer do
# Enable trace collection and span generation.
Expand Down Expand Up @@ -544,6 +560,7 @@ def initialize(*_)
# @see https://docs.datadoghq.com/getting_started/tagging/unified_service_tagging
# @default `DD_VERSION` environment variable, otherwise `nils`
# @return [String,nil]
# @configure_with Datadog
option :version do |o|
# NOTE: version also gets set as a side effect of tags. See the WORKAROUND note in #initialize for details.
o.default { ENV.fetch(Ext::Environment::ENV_VERSION, nil) }
Expand Down
Loading

0 comments on commit 88d0e13

Please sign in to comment.