Skip to content
advanced Phase 83 · Observability Basics

Correlation IDs

Correlation IDs for request tracing, distributed tracing, and trace propagation across services

45m
0 problems
Topic Progress 0%

Request Tracing with Correlation IDs

Correlation ID Flow

Client Request
    │
    â–¼ X-Request-ID: req-abc-123
┌────────────────┐
│ API Gateway    │──▶ Log: req-abc-123 received
└───────┬────────┘
        │
        â–¼ X-Request-ID: req-abc-123
┌────────────────┐
│ Order Service  │──▶ Log: req-abc-123 processing order
└───────┬────────┘
        │
        â–¼ X-Request-ID: req-abc-123
┌────────────────┐
│ Payment Svc    │──▶ Log: req-abc-123 charging payment
└────────────────┘

All logs correlated by req-abc-123

Magento Correlation ID Middleware

class CorrelationIdPlugin {
    public function beforeExecute(
        $subject,
        RequestInterface $request
    ) {
        $requestId = $request->getHeader('X-Request-ID')
            ?? $this->generateRequestId();

        // Store in registry for logging
        $registry = $this->registry;
        $registry->register('request_id', $requestId);

        // Add to response header
        $this->responseHeader->addHeader(
            'X-Request-ID', $requestId
        );

        // Set in MDC for log context
        $this->logger->pushProcessor(function ($record) use ($requestId) {
            $record['extra']['request_id'] = $requestId;
            return $record;
        });
    }

    private function generateRequestId(): string {
        return 'req-' . bin2hex(random_bytes(8));
    }
}

HTTP Header Propagation

// Forward correlation ID to downstream services
function callExternalService($url, $data) {
    $requestId = $this->registry->registry('request_id');

    $response = $this->httpClient->post($url, [
        'headers' => [
            'X-Request-ID' => $requestId,
            'X-Forwarded-For' => $_SERVER['REMOTE_ADDR']
        ],
        'json' => $data
    ]);

    return $response;
}

Trace Context Propagation

W3C Trace Context

Header: traceparent
Format: 00-TRACE_ID-SPAN_ID-FLAGS

Example:
00-4bf92f3577b34da6a3ce929d0e0e4736-00f067aa0ba902b7-01
│   │                        │                │    │
│   │                        │                │    └─ Flags
│   │                        │                └────── Parent span ID
│   │                        └─────────────────────── Span ID
│   └───────────────────────────────────────────────── Trace ID
└───────────────────────────────────────────────────── Version

Magento Trace Context Plugin

class TraceContextPlugin {
    public function beforeExecute(
        $subject,
        RequestInterface $request
    ) {
        $traceparent = $request->getHeader('traceparent');

        if ($traceparent) {
            // Parse and store trace context
            $parts = explode('-', $traceparent);
            $this->registry->register('trace_id', $parts[1]);
            $this->registry->register('span_id', $parts[2]);
        } else {
            // Generate new trace context
            $traceId = bin2hex(random_bytes(16));
            $spanId = bin2hex(random_bytes(8));
            $this->registry->register('trace_id', $traceId);
            $this->registry->register('span_id', $spanId);
        }
    }
}

Trace Context in Logs

// Include trace context in all logs
$logger->pushProcessor(function ($record) {
    $record['extra']['trace_id'] = $this->registry->registry('trace_id');
    $record['extra']['span_id'] = $this->registry->registry('span_id');
    return $record;
});

// Log output includes trace context
// {"trace_id": "4bf92f35...", "span_id": "00f067aa...", "message": "..."}

Debugging with Correlation IDs

Debugging Workflow

1. Customer reports issue
2. Get request ID from response header
3. Query logs by request ID
4. See full request flow across services
5. Identify failure point

Log Query Examples

# Kibana query
request_id: "req-abc-123"

# Elasticsearch API
GET /magento-logs-*/_search
{
  "query": {
    "term": { "request_id": "req-abc-123" }
  },
  "sort": [{ "timestamp": "asc" }]
}

# Results show complete request lifecycle:
# 10:30:00 INFO  - API Gateway: Received request
# 10:30:01 INFO  - Order Service: Processing order 12345
# 10:30:01 DEBUG - Order Service: SQL query executed (15ms)
# 10:30:02 INFO  - Payment Service: Charging $99.99
# 10:30:03 ERROR - Payment Service: Gateway timeout
# 10:30:03 INFO  - Order Service: Retrying payment
# 10:30:04 INFO  - Payment Service: Payment successful

Debug Endpoints

// Debug endpoint for support team
if ($request->getParam('debug') && $this->auth->isAdmin()) {
    return [
        'request_id' => $this->registry->registry('request_id'),
        'trace_id' => $this->registry->registry('trace_id'),
        'service' => 'magento',
        'environment' => getenv('APP_ENV'),
        'server' => gethostname()
    ];
}

Integration with Tracing Systems

OpenTelemetry Correlation

use OpenTelemetry\Context\Context;
use OpenTelemetry\Context\Propagation\TraceContextPropagator;

// Inject trace context into outgoing requests
$propagator = new TraceContextPropagator();
$context = Context::getCurrent();

$headers = [];
$propagator->inject($headers, $context);

// $headers now contains traceparent header
$httpClient->post($url, ['headers' => $headers]);

Jaeger Integration

// Send trace data to Jaeger
$tracer = new JaegerTracer('magento', 'http://jaeger:14268/api/traces');

$span = $tracer->startSpan('process_order');
$span->setTag('order.id', $orderId);
$span->log(['event' => 'payment_started']);

try {
    $this->paymentService->charge($order);
    $span->setTag('payment.status', 'success');
} catch (Exception $e) {
    $span->setTag('error', true);
    $span->log(['event' => 'payment_failed', 'error' => $e->getMessage()]);
} finally {
    $span->finish();
}

Quiz

1. What header carries the correlation ID?

Question 1 options

2. What is the W3C trace context format?

Question 2 options

3. Why propagate correlation IDs to downstream services?

Question 3 options

Flashcards

Question

Correlation ID header?

Answer

X-Request-ID carries the unique request identifier

Question

W3C trace context header?

Answer

traceparent: 00-TRACE_ID-SPAN_ID-FLAGS

Question

Correlation ID purpose?

Answer

Link all logs from a single request across services

Question

Debugging workflow?

Answer

Get request ID → Query logs → See full request flow

Revision Notes

Key Takeaways

  • 1. Correlation IDs link all logs from a single request
  • 2. X-Request-ID is the standard header for correlation
  • 3. W3C traceparent header carries trace context (00-TRACE_ID-SPAN_ID-FLAGS)
  • 4. Always propagate correlation IDs to downstream services
  • 5. Include correlation IDs in all structured log output

Interview Tips

  • Explain how correlation IDs enable distributed debugging
  • Discuss W3C trace context propagation
  • Describe the debugging workflow with correlation IDs

Cheat Sheet

Correlation IDs:
  Header: X-Request-ID
  Format: req-<random-hex>
  Propagate to all downstream services

W3C Trace Context:
  Header: traceparent
  Format: 00-TRACE_ID-SPAN_ID-FLAGS
  Use OpenTelemetry for propagation

Debugging:
  1. Get request ID from response
  2. Query logs by request_id
  3. See full request lifecycle
  4. Identify failure point