Connecting PHP Logs and Traces
New announcements from Dash: Incident Management, Continuous Profiler, and more! New announcements from Dash!

Connecting PHP Logs and Traces

Automatically Inject Trace and Span IDs

Given the many different ways to implement logging in PHP, with some completely circumventing PHP’s built-in error-logging API, the Datadog PHP tracing library cannot reliably inject trace and span IDs into logs automatically. See the section below to learn how to connect your PHP Logs and traces manually.

Manually Inject Trace and Span IDs

To connect your logs and traces together, your logs must contain the dd.trace_id and dd.span_id attributes that respectively contain your trace ID and your span ID.

If you are not using a Datadog Log Integration to parse your logs, custom log parsing rules need to ensure that dd.trace_id and dd.span_id are being parsed as strings and remapped thanks to the Trace Remapper. More information can be found in the Why can’t I see my correlated logs in the Trace ID panel? FAQ.

For instance, you would append those two attributes to your logs with:

  <?php
  $span = \DDTrace\GlobalTracer::get()->getActiveSpan();
  $append = sprintf(
      ' [dd.trace_id=%d dd.span_id=%d]',
      $span->getTraceId(),
      $span->getSpanId()
  );
  my_error_logger('Error message.' . $append);
?>

If the logger implements the monolog/monolog library, use Logger::pushProcessor() to automatically append the identifiers to all log messages:

<?php
  $logger->pushProcessor(function ($record) {
      $span = \DDTrace\GlobalTracer::get()->getActiveSpan();
      if (null === $span) {
          return $record;
      }
      $record['message'] .= sprintf(
          ' [dd.trace_id=%d dd.span_id=%d]',
          $span->getTraceId(),
          $span->getSpanId()
      );
      return $record;
  });
?>

If your application uses json logs format instead of appending trace_id and span_id to the log message you can add first-level key “dd” containing these ids:

<?php
  $logger->pushProcessor(function ($record) {
      $span = \DDTrace\GlobalTracer::get()->getActiveSpan();
      if (null === $span) {
          return $record;
      }
      
      $record['dd'] = [
          'trace_id' => $span->getTraceId(),
          'span_id'  => $span->getSpanId(),
      ];
      
      return $record;
  });
?>

Further Reading