123456789_123456789_123456789_123456789_123456789_

Class: Mongo::Tracing::OpenTelemetry::Tracer Private

Relationships & Source Files
Inherits: Object
Defined in: lib/mongo/tracing/open_telemetry/tracer.rb

Overview

::Mongo::Tracing::OpenTelemetry tracer for MongoDB operations and commands.

Class Method Summary

Instance Attribute Summary

Instance Method Summary

Constructor Details

.new(enabled: nil, query_text_max_length: nil, otel_tracer: nil) ⇒ Tracer

Initializes a new ::Mongo::Tracing::OpenTelemetry tracer.

Parameters:

  • enabled (Boolean | nil)

    whether ::Mongo::Tracing::OpenTelemetry is enabled or not. Defaults to nil, which means it will check the environment variable OTEL_RUBY_INSTRUMENTATION_MONGODB_ENABLED (values: true/1/yes). If the environment variable is not set, ::Mongo::Tracing::OpenTelemetry will be disabled by default.

  • query_text_max_length (Integer | nil)

    maximum length for captured query text. Defaults to nil, which means it will check the environment variable OTEL_RUBY_INSTRUMENTATION_MONGODB_QUERY_TEXT_MAX_LENGTH. If the environment variable is not set, the query text will not be captured.

  • otel_tracer (OpenTelemetry::Trace::Tracer | nil)

    the ::Mongo::Tracing::OpenTelemetry tracer implementation to use. Defaults to nil, which means it will use the default tracer from OpenTelemetry's tracer provider.

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 42

def initialize(enabled: nil, query_text_max_length: nil, otel_tracer: nil)
  @enabled = if enabled.nil?
               %w[true 1 yes].include?(ENV['OTEL_RUBY_INSTRUMENTATION_MONGODB_ENABLED']&.downcase)
             else
               enabled
             end
  check_opentelemetry_loaded
  @query_text_max_length = if query_text_max_length.nil?
                             ENV['OTEL_RUBY_INSTRUMENTATION_MONGODB_QUERY_TEXT_MAX_LENGTH'].to_i
                           else
                             query_text_max_length
                           end
  @otel_tracer = otel_tracer || initialize_tracer
  @operation_tracer = OperationTracer.new(@otel_tracer, self)
  @command_tracer = CommandTracer.new(@otel_tracer, self, query_text_max_length: @query_text_max_length)
end

Instance Attribute Details

#enabled?Boolean (readonly)

Whether OpenTelemetry is enabled or not.

Returns:

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 62

def enabled?
  @enabled
end

#otel_tracerOpenTelemetry::Trace::Tracer (readonly)

Returns:

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 27

attr_reader :otel_tracer

Instance Method Details

#check_opentelemetry_loaded (private)

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 215

def check_opentelemetry_loaded
  return unless @enabled
  return if defined?(::OpenTelemetry)

  Logger.logger.warn('OpenTelemetry tracing for MongoDB is enabled, ' \
                     'but the OpenTelemetry library is not loaded. ' \
                     'Disabling tracing.')
  @enabled = false
end

#cursor_context_mapHash

Returns the cursor context map for tracking cursor-related ::Mongo::Tracing::OpenTelemetry contexts.

Returns:

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 145

def cursor_context_map
  @cursor_context_map ||= {}
end

#cursor_map_key(session, cursor_id) ⇒ String | nil

Generates a unique key for cursor tracking in the context map.

Parameters:

  • session (Mongo::Session)

    the session associated with the cursor.

  • cursor_id (Integer)

    the cursor ID.

Returns:

  • (String | nil)

    unique key combining session ID and cursor ID, or nil if either is nil.

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 155

def cursor_map_key(session, cursor_id)
  return if cursor_id.nil? || session.nil?

  "#{session.session_id['id'].to_uuid}-#{cursor_id}"
end

#finish_transaction_span(session)

Finish a transaction span and deactivate its context.

Parameters:

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 123

def finish_transaction_span(session)
  return unless enabled?

  key = transaction_map_key(session)
  return unless key

  span = transaction_span_map.delete(key)
  token = transaction_token_map.delete(key)
  transaction_context_map.delete(key)

  return unless span && token

  begin
    span.finish
  ensure
    ::OpenTelemetry::Context.detach(token)
  end
end

#initialize_tracer (private)

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 225

def initialize_tracer
  return unless enabled?

  ::OpenTelemetry.tracer_provider.tracer(
    'mongo-ruby-driver',
    Mongo::VERSION
  )
end

#parent_context_for(operation_context, cursor_id) ⇒ OpenTelemetry::Context | nil

Determines the parent ::Mongo::Tracing::OpenTelemetry context for an operation.

Returns the transaction context if the operation is part of a transaction, otherwise returns nil. Cursor-based context nesting is not currently implemented.

Parameters:

  • operation_context (Mongo::Operation::Context)

    the operation context.

  • cursor_id (Integer)

    the cursor ID, if applicable.

Returns:

  • (OpenTelemetry::Context | nil)

    parent context or nil.

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 170

def parent_context_for(operation_context, cursor_id)
  if (key = transaction_map_key(operation_context.session))
    transaction_context_map[key]
  elsif (_key = cursor_map_key(operation_context.session, cursor_id))
    # We return nil here unless we decide how to nest cursor operations.
    nil
  end
end

#start_transaction_span(session)

Start a transaction span and activate its context.

Parameters:

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 95

def start_transaction_span(session)
  return unless enabled?

  key = transaction_map_key(session)
  return unless key

  # Create the transaction span with minimal attributes
  span = @otel_tracer.start_span(
    'transaction',
    attributes: { 'db.system.name' => 'mongodb' },
    kind: :client
  )

  # Create a context containing this span
  context = ::OpenTelemetry::Trace.context_with_span(span)

  # Activate the context and store the token for later detachment
  token = ::OpenTelemetry::Context.attach(context)

  # Store span, token, and context for later retrieval
  transaction_span_map[key] = span
  transaction_token_map[key] = token
  transaction_context_map[key] = context
end

#trace_command(message, operation_context, connection) { ... } ⇒ Object

Trace a MongoDB command.

Parameters:

Yields:

  • The block representing the command to be traced.

Returns:

  • (Object)

    The result of the command.

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 86

def trace_command(message, operation_context, connection, &block)
  return yield unless enabled?

  @command_tracer.trace_command(message, operation_context, connection, &block)
end

#trace_operation(operation, operation_context, op_name: nil) { ... } ⇒ Object

Trace a MongoDB operation.

Parameters:

  • operation (Mongo::Operation)

    The MongoDB operation to trace.

  • operation_context (Mongo::Operation::Context)

    The context of the operation.

  • op_name (String, nil)

    An optional name for the operation.

Yields:

  • The block representing the operation to be traced.

Returns:

  • (Object)

    The result of the operation.

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 73

def trace_operation(operation, operation_context, op_name: nil, &block)
  return yield unless enabled?

  @operation_tracer.trace_operation(operation, operation_context, op_name: op_name, &block)
end

#transaction_context_mapHash

Returns the transaction context map for tracking active transaction contexts.

Returns:

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 182

def transaction_context_map
  @transaction_context_map ||= {}
end

#transaction_map_key(session) ⇒ String | nil

Generates a unique key for transaction tracking.

Returns nil for implicit sessions or sessions not in a transaction.

Parameters:

Returns:

  • (String | nil)

    unique key combining session ID and transaction number, or nil.

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 207

def transaction_map_key(session)
  return if session.nil? || session.implicit? || !session.in_transaction?

  "#{session.session_id['id'].to_uuid}-#{session.txn_num}"
end

#transaction_span_mapHash

Returns the transaction span map for tracking active transaction spans.

Returns:

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 189

def transaction_span_map
  @transaction_span_map ||= {}
end

#transaction_token_mapHash

Returns the transaction token map for tracking context attachment tokens.

Returns:

[ GitHub ]

  
# File 'lib/mongo/tracing/open_telemetry/tracer.rb', line 196

def transaction_token_map
  @transaction_token_map ||= {}
end