opentelemetry-api 0.13.0 → 1.0.0.rc1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +40 -0
- data/README.md +2 -2
- data/lib/opentelemetry.rb +24 -20
- data/lib/opentelemetry/baggage.rb +4 -1
- data/lib/opentelemetry/baggage/builder.rb +30 -4
- data/lib/opentelemetry/baggage/entry.rb +20 -0
- data/lib/opentelemetry/baggage/manager.rb +76 -13
- data/lib/opentelemetry/baggage/noop_builder.rb +18 -0
- data/lib/opentelemetry/baggage/noop_manager.rb +45 -0
- data/lib/opentelemetry/baggage/propagation.rb +9 -38
- data/lib/opentelemetry/baggage/propagation/text_map_propagator.rb +109 -0
- data/lib/opentelemetry/context/propagation.rb +62 -7
- data/lib/opentelemetry/context/propagation/composite_text_map_propagator.rb +105 -0
- data/lib/opentelemetry/context/propagation/noop_text_map_propagator.rb +51 -0
- data/lib/opentelemetry/context/propagation/rack_env_getter.rb +48 -0
- data/lib/opentelemetry/context/propagation/text_map_getter.rb +27 -0
- data/lib/opentelemetry/context/propagation/text_map_propagator.rb +71 -0
- data/lib/opentelemetry/context/propagation/text_map_setter.rb +21 -0
- data/lib/opentelemetry/internal.rb +17 -0
- data/lib/opentelemetry/internal/proxy_tracer.rb +38 -0
- data/lib/opentelemetry/internal/proxy_tracer_provider.rb +59 -0
- data/lib/opentelemetry/trace/propagation/trace_context.rb +7 -37
- data/lib/opentelemetry/trace/propagation/trace_context/text_map_propagator.rb +73 -0
- data/lib/opentelemetry/trace/span.rb +20 -0
- data/lib/opentelemetry/trace/tracer.rb +2 -2
- data/lib/opentelemetry/version.rb +1 -1
- metadata +21 -26
- data/lib/opentelemetry/baggage/propagation/text_map_extractor.rb +0 -60
- data/lib/opentelemetry/baggage/propagation/text_map_injector.rb +0 -55
- data/lib/opentelemetry/context/propagation/composite_propagator.rb +0 -73
- data/lib/opentelemetry/context/propagation/default_getter.rb +0 -26
- data/lib/opentelemetry/context/propagation/default_setter.rb +0 -26
- data/lib/opentelemetry/context/propagation/noop_extractor.rb +0 -26
- data/lib/opentelemetry/context/propagation/noop_injector.rb +0 -26
- data/lib/opentelemetry/context/propagation/propagation.rb +0 -27
- data/lib/opentelemetry/context/propagation/propagator.rb +0 -64
- data/lib/opentelemetry/instrumentation.rb +0 -15
- data/lib/opentelemetry/instrumentation/base.rb +0 -245
- data/lib/opentelemetry/instrumentation/registry.rb +0 -86
- data/lib/opentelemetry/metrics.rb +0 -16
- data/lib/opentelemetry/metrics/handles.rb +0 -44
- data/lib/opentelemetry/metrics/instruments.rb +0 -105
- data/lib/opentelemetry/metrics/meter.rb +0 -72
- data/lib/opentelemetry/metrics/meter_provider.rb +0 -22
- data/lib/opentelemetry/trace/propagation/trace_context/text_map_extractor.rb +0 -57
- data/lib/opentelemetry/trace/propagation/trace_context/text_map_injector.rb +0 -54
@@ -1,55 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
# Copyright The OpenTelemetry Authors
|
4
|
-
#
|
5
|
-
# SPDX-License-Identifier: Apache-2.0
|
6
|
-
|
7
|
-
require 'cgi'
|
8
|
-
|
9
|
-
module OpenTelemetry
|
10
|
-
module Baggage
|
11
|
-
module Propagation
|
12
|
-
# Injects baggage using the W3C Baggage format
|
13
|
-
class TextMapInjector
|
14
|
-
include Context::Propagation::DefaultSetter
|
15
|
-
|
16
|
-
# Returns a new TextMapInjector that injects context using the specified
|
17
|
-
# header key
|
18
|
-
#
|
19
|
-
# @param [String] baggage_key The baggage header
|
20
|
-
# key used in the carrier
|
21
|
-
# @return [TextMapInjector]
|
22
|
-
def initialize(baggage_key: 'baggage')
|
23
|
-
@baggage_key = baggage_key
|
24
|
-
end
|
25
|
-
|
26
|
-
# Inject in-process baggage into the supplied carrier.
|
27
|
-
#
|
28
|
-
# @param [Carrier] carrier The carrier to inject baggage into
|
29
|
-
# @param [Context] context The context to read baggage from
|
30
|
-
# @param [optional Callable] getter An optional callable that takes a carrier and a key and
|
31
|
-
# returns the value associated with the key. If omitted the default getter will be used
|
32
|
-
# which expects the carrier to respond to [] and []=.
|
33
|
-
# @yield [Carrier, String] if an optional getter is provided, inject will yield the carrier
|
34
|
-
# and the header key to the getter.
|
35
|
-
# @return [Object] carrier with injected baggage
|
36
|
-
def inject(carrier, context, &setter)
|
37
|
-
return carrier unless (baggage = context[ContextKeys.baggage_key]) && !baggage.empty?
|
38
|
-
|
39
|
-
setter ||= default_setter
|
40
|
-
setter.call(carrier, @baggage_key, encode(baggage))
|
41
|
-
|
42
|
-
carrier
|
43
|
-
end
|
44
|
-
|
45
|
-
private
|
46
|
-
|
47
|
-
def encode(baggage)
|
48
|
-
baggage.inject(+'') do |memo, (k, v)|
|
49
|
-
memo << CGI.escape(k.to_s) << '=' << CGI.escape(v.to_s) << ','
|
50
|
-
end.chop!
|
51
|
-
end
|
52
|
-
end
|
53
|
-
end
|
54
|
-
end
|
55
|
-
end
|
@@ -1,73 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
# Copyright The OpenTelemetry Authors
|
4
|
-
#
|
5
|
-
# SPDX-License-Identifier: Apache-2.0
|
6
|
-
|
7
|
-
module OpenTelemetry
|
8
|
-
class Context
|
9
|
-
module Propagation
|
10
|
-
# A composite propagator composes a list of injectors and extractors into
|
11
|
-
# single interface exposing inject and extract methods. Injection and
|
12
|
-
# extraction will preserve the order of the injectors and extractors
|
13
|
-
# passed in during initialization.
|
14
|
-
class CompositePropagator
|
15
|
-
# Returns a Propagator that extracts using the provided extractors
|
16
|
-
# and injectors.
|
17
|
-
#
|
18
|
-
# @param [Array<#inject>] injectors
|
19
|
-
# @param [Array<#extract>] extractors
|
20
|
-
def initialize(injectors, extractors)
|
21
|
-
@injectors = injectors
|
22
|
-
@extractors = extractors
|
23
|
-
end
|
24
|
-
|
25
|
-
# Runs injectors in order and returns a carrier. If an injection fails
|
26
|
-
# a warning will be logged and remaining injectors will be executed.
|
27
|
-
# Always returns a valid carrier.
|
28
|
-
#
|
29
|
-
# @param [Object] carrier A carrier to inject context into
|
30
|
-
# context into
|
31
|
-
# @param [optional Context] context Context to be injected into carrier.
|
32
|
-
# Defaults to +Context.current+
|
33
|
-
# @param [optional Callable] setter An optional callable that takes a
|
34
|
-
# carrier, a key and a value and assigns the key-value pair in the
|
35
|
-
# carrier. If omitted the default setter will be used which expects
|
36
|
-
# the carrier to respond to [] and []=.
|
37
|
-
#
|
38
|
-
# @return [Object] carrier
|
39
|
-
def inject(carrier, context = Context.current, &setter)
|
40
|
-
@injectors.inject(carrier) do |memo, injector|
|
41
|
-
injector.inject(memo, context, &setter)
|
42
|
-
rescue => e # rubocop:disable Style/RescueStandardError
|
43
|
-
OpenTelemetry.logger.warn "Error in CompositePropagator#inject #{e.message}"
|
44
|
-
carrier
|
45
|
-
end
|
46
|
-
end
|
47
|
-
|
48
|
-
# Runs extractors in order and returns a Context updated with the
|
49
|
-
# results of each extraction. If an extraction fails, a warning will be
|
50
|
-
# logged and remaining extractors will continue to be executed. Always
|
51
|
-
# returns a valid context.
|
52
|
-
#
|
53
|
-
# @param [Object] carrier The carrier to extract context from
|
54
|
-
# @param [optional Context] context Context to be updated with the state
|
55
|
-
# extracted from the carrier. Defaults to +Context.current+
|
56
|
-
# @param [optional Callable] getter An optional callable that takes a carrier and a key and
|
57
|
-
# returns the value associated with the key. If omitted the default getter will be used
|
58
|
-
# which expects the carrier to respond to [] and []=.
|
59
|
-
#
|
60
|
-
# @return [Context] a new context updated with state extracted from the
|
61
|
-
# carrier
|
62
|
-
def extract(carrier, context = Context.current, &getter)
|
63
|
-
@extractors.inject(context) do |ctx, extractor|
|
64
|
-
extractor.extract(carrier, ctx, &getter)
|
65
|
-
rescue => e # rubocop:disable Style/RescueStandardError
|
66
|
-
OpenTelemetry.logger.warn "Error in CompositePropagator#extract #{e.message}"
|
67
|
-
ctx
|
68
|
-
end
|
69
|
-
end
|
70
|
-
end
|
71
|
-
end
|
72
|
-
end
|
73
|
-
end
|
@@ -1,26 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
# Copyright The OpenTelemetry Authors
|
4
|
-
#
|
5
|
-
# SPDX-License-Identifier: Apache-2.0
|
6
|
-
|
7
|
-
module OpenTelemetry
|
8
|
-
class Context
|
9
|
-
module Propagation
|
10
|
-
# The default getter module provides a common method for reading
|
11
|
-
# a key from a carrier that implements +[]+
|
12
|
-
module DefaultGetter
|
13
|
-
DEFAULT_GETTER = ->(carrier, key) { carrier[key] }
|
14
|
-
private_constant :DEFAULT_GETTER
|
15
|
-
|
16
|
-
# Returns a callable that can read a key from a carrier that implements
|
17
|
-
# +[]+. Useful for extract operations.
|
18
|
-
#
|
19
|
-
# @return [Callable]
|
20
|
-
def default_getter
|
21
|
-
DEFAULT_GETTER
|
22
|
-
end
|
23
|
-
end
|
24
|
-
end
|
25
|
-
end
|
26
|
-
end
|
@@ -1,26 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
# Copyright The OpenTelemetry Authors
|
4
|
-
#
|
5
|
-
# SPDX-License-Identifier: Apache-2.0
|
6
|
-
|
7
|
-
module OpenTelemetry
|
8
|
-
class Context
|
9
|
-
module Propagation
|
10
|
-
# The default setter module provides a common method for writing
|
11
|
-
# a key into a carrier that implements +[]=+
|
12
|
-
module DefaultSetter
|
13
|
-
DEFAULT_SETTER = ->(carrier, key, value) { carrier[key] = value }
|
14
|
-
private_constant :DEFAULT_SETTER
|
15
|
-
|
16
|
-
# Returns a callable that can write a key into a carrier that implements
|
17
|
-
# +[]=+. Useful for inject operations.
|
18
|
-
#
|
19
|
-
# @return [Callable]
|
20
|
-
def default_setter
|
21
|
-
DEFAULT_SETTER
|
22
|
-
end
|
23
|
-
end
|
24
|
-
end
|
25
|
-
end
|
26
|
-
end
|
@@ -1,26 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
# Copyright The OpenTelemetry Authors
|
4
|
-
#
|
5
|
-
# SPDX-License-Identifier: Apache-2.0
|
6
|
-
|
7
|
-
module OpenTelemetry
|
8
|
-
class Context
|
9
|
-
module Propagation
|
10
|
-
# A no-op extractor implementation
|
11
|
-
class NoopExtractor
|
12
|
-
# Extract a context from the given carrier
|
13
|
-
#
|
14
|
-
# @param [Object] carrier The carrier to extract the context from
|
15
|
-
# @param [Context] context The context to be upated with the extracted
|
16
|
-
# context
|
17
|
-
# @param [optional Callable] getter An optional callable that takes a carrier and a key and
|
18
|
-
# and returns the value associated with the key
|
19
|
-
# @return [Context]
|
20
|
-
def extract(carrier, context, &getter)
|
21
|
-
context
|
22
|
-
end
|
23
|
-
end
|
24
|
-
end
|
25
|
-
end
|
26
|
-
end
|
@@ -1,26 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
# Copyright The OpenTelemetry Authors
|
4
|
-
#
|
5
|
-
# SPDX-License-Identifier: Apache-2.0
|
6
|
-
|
7
|
-
module OpenTelemetry
|
8
|
-
class Context
|
9
|
-
module Propagation
|
10
|
-
# A no-op injector implementation
|
11
|
-
class NoopInjector
|
12
|
-
# Inject the given context into the specified carrier
|
13
|
-
#
|
14
|
-
# @param [Object] carrier The carrier to inject the provided context
|
15
|
-
# into
|
16
|
-
# @param [Context] context The context to be injected
|
17
|
-
# @param [optional Callable] setter An optional callable that takes a carrier and a key and
|
18
|
-
# a value and assigns the key-value pair in the carrier
|
19
|
-
# @return [Object] carrier
|
20
|
-
def inject(carrier, context, &setter)
|
21
|
-
carrier
|
22
|
-
end
|
23
|
-
end
|
24
|
-
end
|
25
|
-
end
|
26
|
-
end
|
@@ -1,27 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
# Copyright The OpenTelemetry Authors
|
4
|
-
#
|
5
|
-
# SPDX-License-Identifier: Apache-2.0
|
6
|
-
|
7
|
-
module OpenTelemetry
|
8
|
-
class Context
|
9
|
-
module Propagation
|
10
|
-
# The Propagation class provides methods to inject and extract context
|
11
|
-
# to pass across process boundaries
|
12
|
-
class Propagation
|
13
|
-
# Get or set the global http propagator. Use a CompositePropagator
|
14
|
-
# to propagate multiple formats.
|
15
|
-
attr_accessor :http
|
16
|
-
|
17
|
-
# Get or set the global text propagator. Use a CompositePropagator
|
18
|
-
# to propagate multiple formats.
|
19
|
-
attr_accessor :text
|
20
|
-
|
21
|
-
def initialize
|
22
|
-
@http = @text = Propagator.new(NoopInjector.new, NoopExtractor.new)
|
23
|
-
end
|
24
|
-
end
|
25
|
-
end
|
26
|
-
end
|
27
|
-
end
|
@@ -1,64 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
# Copyright The OpenTelemetry Authors
|
4
|
-
#
|
5
|
-
# SPDX-License-Identifier: Apache-2.0
|
6
|
-
|
7
|
-
module OpenTelemetry
|
8
|
-
class Context
|
9
|
-
module Propagation
|
10
|
-
# A propagator composes an extractor and injector into a single interface
|
11
|
-
# exposing inject and extract methods
|
12
|
-
class Propagator
|
13
|
-
# Returns a Propagator that delegates inject and extract to the provided
|
14
|
-
# injector and extractor
|
15
|
-
#
|
16
|
-
# @param [#inject] injector
|
17
|
-
# @param [#extract] extractor
|
18
|
-
def initialize(injector, extractor)
|
19
|
-
@injector = injector
|
20
|
-
@extractor = extractor
|
21
|
-
end
|
22
|
-
|
23
|
-
# Returns a carrier with the provided context injected according the
|
24
|
-
# underlying injector. Returns the carrier and logs a warning if
|
25
|
-
# injection fails.
|
26
|
-
#
|
27
|
-
# @param [Object] carrier A carrier to inject context into
|
28
|
-
# context into
|
29
|
-
# @param [optional Context] context Context to be injected into carrier. Defaults
|
30
|
-
# to +Context.current+
|
31
|
-
# @param [optional Callable] setter An optional callable that takes a carrier, a key and
|
32
|
-
# a value and assigns the key-value pair in the carrier. If omitted the default setter
|
33
|
-
# will be used which expects the carrier to respond to [] and []=.
|
34
|
-
#
|
35
|
-
# @return [Object] carrier
|
36
|
-
def inject(carrier, context = Context.current, &setter)
|
37
|
-
@injector.inject(carrier, context, &setter)
|
38
|
-
rescue => e # rubocop:disable Style/RescueStandardError
|
39
|
-
OpenTelemetry.logger.warn "Error in Propagator#inject #{e.message}"
|
40
|
-
carrier
|
41
|
-
end
|
42
|
-
|
43
|
-
# Extracts and returns context from a carrier. Returns the provided
|
44
|
-
# context and logs a warning if an error if extraction fails.
|
45
|
-
#
|
46
|
-
# @param [Object] carrier The carrier to extract context from
|
47
|
-
# @param [optional Context] context Context to be updated with the state
|
48
|
-
# extracted from the carrier. Defaults to +Context.current+
|
49
|
-
# @param [optional Callable] getter An optional callable that takes a carrier and a key and
|
50
|
-
# returns the value associated with the key. If omitted the default getter will be used
|
51
|
-
# which expects the carrier to respond to [] and []=.
|
52
|
-
#
|
53
|
-
# @return [Context] a new context updated with state extracted from the
|
54
|
-
# carrier
|
55
|
-
def extract(carrier, context = Context.current, &getter)
|
56
|
-
@extractor.extract(carrier, context, &getter)
|
57
|
-
rescue => e # rubocop:disable Style/RescueStandardError
|
58
|
-
OpenTelemetry.logger.warn "Error in Propagator#extract #{e.message}"
|
59
|
-
context
|
60
|
-
end
|
61
|
-
end
|
62
|
-
end
|
63
|
-
end
|
64
|
-
end
|
@@ -1,15 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
# Copyright The OpenTelemetry Authors
|
4
|
-
#
|
5
|
-
# SPDX-License-Identifier: Apache-2.0
|
6
|
-
|
7
|
-
require 'opentelemetry/instrumentation/registry'
|
8
|
-
require 'opentelemetry/instrumentation/base'
|
9
|
-
|
10
|
-
module OpenTelemetry
|
11
|
-
# The instrumentation module contains functionality to register and install
|
12
|
-
# instrumentation
|
13
|
-
module Instrumentation
|
14
|
-
end
|
15
|
-
end
|
@@ -1,245 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
# Copyright The OpenTelemetry Authors
|
4
|
-
#
|
5
|
-
# SPDX-License-Identifier: Apache-2.0
|
6
|
-
|
7
|
-
module OpenTelemetry
|
8
|
-
module Instrumentation
|
9
|
-
# The Base class holds all metadata and configuration for an
|
10
|
-
# instrumentation. All instrumentation packages should
|
11
|
-
# include a subclass of +Instrumentation::Base+ that will register
|
12
|
-
# it with +OpenTelemetry.instrumentation_registry+ and make it available for
|
13
|
-
# discovery and installation by an SDK.
|
14
|
-
#
|
15
|
-
# A typical subclass of Base will provide an install block, a present
|
16
|
-
# block, and possibly a compatible block. Below is an
|
17
|
-
# example:
|
18
|
-
#
|
19
|
-
# module OpenTelemetry
|
20
|
-
# module Instrumentation
|
21
|
-
# module Sinatra
|
22
|
-
# class Instrumentation < OpenTelemetry::Instrumentation::Base
|
23
|
-
# install do |config|
|
24
|
-
# # install instrumentation, either by library hook or applying
|
25
|
-
# # a monkey patch
|
26
|
-
# end
|
27
|
-
#
|
28
|
-
# # determine if the target library is present
|
29
|
-
# present do
|
30
|
-
# defined?(::Sinatra)
|
31
|
-
# end
|
32
|
-
#
|
33
|
-
# # if the target library is present, is it compatible?
|
34
|
-
# compatible do
|
35
|
-
# Gem.loaded_specs['sinatra'].version > MIN_VERSION
|
36
|
-
# end
|
37
|
-
# end
|
38
|
-
# end
|
39
|
-
# end
|
40
|
-
# end
|
41
|
-
#
|
42
|
-
# The instrumentation name and version will be inferred from the namespace of the
|
43
|
-
# class. In this example, they'd be 'OpenTelemetry::Instrumentation::Sinatra' and
|
44
|
-
# OpenTelemetry::Instrumentation::Sinatra::VERSION, but can be explicitly set using
|
45
|
-
# the +instrumentation_name+ and +instrumetation_version+ methods if necessary.
|
46
|
-
#
|
47
|
-
# All subclasses of OpenTelemetry::Instrumentation::Base are automatically
|
48
|
-
# registered with OpenTelemetry.instrumentation_registry which is used by
|
49
|
-
# SDKs for instrumentation discovery and installation.
|
50
|
-
#
|
51
|
-
# Instrumentation libraries can use the instrumentation subclass to easily gain
|
52
|
-
# a reference to its named tracer. For example:
|
53
|
-
#
|
54
|
-
# OpenTelemetry::Instrumentation::Sinatra.instance.tracer
|
55
|
-
#
|
56
|
-
# The instrumention class establishes a convention for disabling an instrumentation
|
57
|
-
# by environment variable and local configuration. An instrumentation disabled
|
58
|
-
# by environment variable will take precedence over local config. The
|
59
|
-
# convention for environment variable name is the library name, upcased with
|
60
|
-
# '::' replaced by underscores, OPENTELEMETRY shortened to OTEL_{LANG}, and '_ENABLED' appended.
|
61
|
-
# For example: OTEL_RUBY_INSTRUMENTATION_SINATRA_ENABLED = false.
|
62
|
-
class Base
|
63
|
-
class << self
|
64
|
-
NAME_REGEX = /^(?:(?<namespace>[a-zA-Z0-9_:]+):{2})?(?<classname>[a-zA-Z0-9_]+)$/.freeze
|
65
|
-
private_constant :NAME_REGEX
|
66
|
-
|
67
|
-
private :new # rubocop:disable Style/AccessModifierDeclarations
|
68
|
-
|
69
|
-
def inherited(subclass)
|
70
|
-
OpenTelemetry.instrumentation_registry.register(subclass)
|
71
|
-
end
|
72
|
-
|
73
|
-
# Optionally set the name of this instrumentation. If not
|
74
|
-
# explicitly set, the name will default to the namespace of the class,
|
75
|
-
# or the class name if it does not have a namespace. If there is not
|
76
|
-
# a namespace, or a class name, it will default to 'unknown'.
|
77
|
-
#
|
78
|
-
# @param [String] instrumentation_name The full name of the instrumentation package
|
79
|
-
def instrumentation_name(instrumentation_name = nil)
|
80
|
-
if instrumentation_name
|
81
|
-
@instrumentation_name = instrumentation_name
|
82
|
-
else
|
83
|
-
@instrumentation_name ||= infer_name || 'unknown'
|
84
|
-
end
|
85
|
-
end
|
86
|
-
|
87
|
-
# Optionally set the version of this instrumentation. If not explicitly set,
|
88
|
-
# the version will default to the VERSION constant under namespace of
|
89
|
-
# the class, or the VERSION constant under the class name if it does not
|
90
|
-
# have a namespace. If a VERSION constant cannot be found, it defaults
|
91
|
-
# to '0.0.0'.
|
92
|
-
#
|
93
|
-
# @param [String] instrumentation_version The version of the instrumentation package
|
94
|
-
def instrumentation_version(instrumentation_version = nil)
|
95
|
-
if instrumentation_version
|
96
|
-
@instrumentation_version = instrumentation_version
|
97
|
-
else
|
98
|
-
@instrumentation_version ||= infer_version || '0.0.0'
|
99
|
-
end
|
100
|
-
end
|
101
|
-
|
102
|
-
# The install block for this instrumentation. This will be where you install
|
103
|
-
# instrumentation, either by framework hook or applying a monkey patch.
|
104
|
-
#
|
105
|
-
# @param [Callable] blk The install block for this instrumentation
|
106
|
-
# @yieldparam [Hash] config The instrumentation config will be yielded to the
|
107
|
-
# install block
|
108
|
-
def install(&blk)
|
109
|
-
@install_blk = blk
|
110
|
-
end
|
111
|
-
|
112
|
-
# The present block for this instrumentation. This block is used to detect if
|
113
|
-
# target library is present on the system. Typically this will involve
|
114
|
-
# checking to see if the target gem spec was loaded or if expected
|
115
|
-
# constants from the target library are present.
|
116
|
-
#
|
117
|
-
# @param [Callable] blk The present block for this instrumentation
|
118
|
-
def present(&blk)
|
119
|
-
@present_blk = blk
|
120
|
-
end
|
121
|
-
|
122
|
-
# The compatible block for this instrumentation. This check will be run if the
|
123
|
-
# target library is present to determine if it's compatible. It's not
|
124
|
-
# required, but a common use case will be to check to target library
|
125
|
-
# version for compatibility.
|
126
|
-
#
|
127
|
-
# @param [Callable] blk The compatibility block for this instrumentation
|
128
|
-
def compatible(&blk)
|
129
|
-
@compatible_blk = blk
|
130
|
-
end
|
131
|
-
|
132
|
-
def instance
|
133
|
-
@instance ||= new(instrumentation_name, instrumentation_version, install_blk,
|
134
|
-
present_blk, compatible_blk)
|
135
|
-
end
|
136
|
-
|
137
|
-
private
|
138
|
-
|
139
|
-
attr_reader :install_blk, :present_blk, :compatible_blk
|
140
|
-
|
141
|
-
def infer_name
|
142
|
-
@inferred_name ||= if (md = name.match(NAME_REGEX)) # rubocop:disable Naming/MemoizedInstanceVariableName
|
143
|
-
md['namespace'] || md['classname']
|
144
|
-
end
|
145
|
-
end
|
146
|
-
|
147
|
-
def infer_version
|
148
|
-
return unless (inferred_name = infer_name)
|
149
|
-
|
150
|
-
mod = inferred_name.split('::').map(&:to_sym).inject(Object) do |object, const|
|
151
|
-
object.const_get(const)
|
152
|
-
end
|
153
|
-
mod.const_get(:VERSION)
|
154
|
-
rescue NameError
|
155
|
-
nil
|
156
|
-
end
|
157
|
-
end
|
158
|
-
|
159
|
-
attr_reader :name, :version, :config, :installed, :tracer
|
160
|
-
|
161
|
-
alias installed? installed
|
162
|
-
|
163
|
-
def initialize(name, version, install_blk, present_blk,
|
164
|
-
compatible_blk)
|
165
|
-
@name = name
|
166
|
-
@version = version
|
167
|
-
@install_blk = install_blk
|
168
|
-
@present_blk = present_blk
|
169
|
-
@compatible_blk = compatible_blk
|
170
|
-
@config = {}
|
171
|
-
@installed = false
|
172
|
-
end
|
173
|
-
|
174
|
-
# Install instrumentation with the given config. The present? and compatible?
|
175
|
-
# will be run first, and install will return false if either fail. Will
|
176
|
-
# return true if install was completed successfully.
|
177
|
-
#
|
178
|
-
# @param [Hash] config The config for this instrumentation
|
179
|
-
def install(config = {})
|
180
|
-
return true if installed?
|
181
|
-
return false unless installable?(config)
|
182
|
-
|
183
|
-
@config = config unless config.nil?
|
184
|
-
instance_exec(@config, &@install_blk)
|
185
|
-
@tracer ||= OpenTelemetry.tracer_provider.tracer(name, version)
|
186
|
-
@installed = true
|
187
|
-
end
|
188
|
-
|
189
|
-
# Whether or not this instrumentation is installable in the current process. Will
|
190
|
-
# be true when the instrumentation defines an install block, is not disabled
|
191
|
-
# by environment or config, and the target library present and compatible.
|
192
|
-
#
|
193
|
-
# @param [Hash] config The config for this instrumentation
|
194
|
-
def installable?(config = {})
|
195
|
-
@install_blk && enabled?(config) && present? && compatible?
|
196
|
-
end
|
197
|
-
|
198
|
-
# Calls the present block of the Instrumentation subclasses, if no block is provided
|
199
|
-
# it's assumed the instrumentation is not present
|
200
|
-
def present?
|
201
|
-
return false unless @present_blk
|
202
|
-
|
203
|
-
instance_exec(&@present_blk)
|
204
|
-
end
|
205
|
-
|
206
|
-
# Calls the compatible block of the Instrumentation subclasses, if no block is provided
|
207
|
-
# it's assumed to be compatible
|
208
|
-
def compatible?
|
209
|
-
return true unless @compatible_blk
|
210
|
-
|
211
|
-
instance_exec(&@compatible_blk)
|
212
|
-
end
|
213
|
-
|
214
|
-
# Whether this instrumentation is enabled. It first checks to see if it's enabled
|
215
|
-
# by an environment variable and will proceed to check if it's enabled
|
216
|
-
# by local config, if given.
|
217
|
-
#
|
218
|
-
# @param [optional Hash] config The local config
|
219
|
-
def enabled?(config = nil)
|
220
|
-
return false unless enabled_by_env_var?
|
221
|
-
return config[:enabled] if config&.key?(:enabled)
|
222
|
-
|
223
|
-
true
|
224
|
-
end
|
225
|
-
|
226
|
-
private
|
227
|
-
|
228
|
-
# Checks to see if this instrumentation is enabled by env var. By convention, the
|
229
|
-
# environment variable will be the instrumentation name upper cased, with '::'
|
230
|
-
# replaced by underscores, OPENTELEMETRY shortened to OTEL_{LANG} and _ENABLED appended.
|
231
|
-
# For example, the, environment variable name for OpenTelemetry::Instrumentation::Sinatra
|
232
|
-
# will be OTEL_RUBY_INSTRUMENTATION_SINATRA_ENABLED. A value of 'false' will disable
|
233
|
-
# the instrumentation, all other values will enable it.
|
234
|
-
def enabled_by_env_var?
|
235
|
-
var_name = name.dup.tap do |n|
|
236
|
-
n.upcase!
|
237
|
-
n.gsub!('::', '_')
|
238
|
-
n.gsub!('OPENTELEMETRY_', 'OTEL_RUBY_')
|
239
|
-
n << '_ENABLED'
|
240
|
-
end
|
241
|
-
ENV[var_name] != 'false'
|
242
|
-
end
|
243
|
-
end
|
244
|
-
end
|
245
|
-
end
|