{
    "slug": "php_observability",
    "term": "PHP Observability",
    "category": "observability",
    "difficulty": "intermediate",
    "short": "The three pillars of observability in PHP applications — structured logs, application metrics, and distributed traces — and the tools that provide them (Monolog, Prometheus, OpenTelemetry).",
    "long": "PHP observability toolkit: Logs (Monolog with structured JSON handlers — Loki, Elasticsearch, Datadog), Metrics (prometheus/client_php — expose /metrics for Prometheus scraping; StatsD for push-based metrics), Traces (opentelemetry-php or Datadog ddtrace auto-instrumentation — distributed tracing across services). PHP-specific considerations: PHP-FPM process-per-request model means metrics must persist across requests (shared memory via APCu or push to StatsD). Correlation IDs: generate a UUID per request, pass it in all log entries and outgoing HTTP headers — enables correlating logs, metrics, and traces for a single request.",
    "aliases": [
        "Monolog",
        "OpenTelemetry PHP",
        "PHP metrics",
        "PHP tracing"
    ],
    "tags": [
        "observability",
        "php",
        "devops"
    ],
    "misconception": "Error logs are sufficient for production observability — error logs show what broke but not why or when degradation started; metrics show trends, traces show the critical path, and logs add context — all three are needed.",
    "why_it_matters": "A PHP application with only error logs cannot answer: is response time increasing? Which endpoint is slowest? When did performance degrade? Metrics and traces answer these questions that logs cannot.",
    "common_mistakes": [
        "No correlation IDs — cannot connect related events across log lines and services.",
        "Logging without structure — plain text logs cannot be queried for specific fields.",
        "Metrics without labels — unlabelled counters cannot distinguish between endpoints.",
        "No request duration histogram — cannot calculate p95/p99 latency without it."
    ],
    "when_to_use": [],
    "avoid_when": [],
    "related": [
        "opentelemetry",
        "prometheus_grafana",
        "structured_logging",
        "apm_tools"
    ],
    "prerequisites": [
        "opentelemetry",
        "apm_tools",
        "structured_logging"
    ],
    "refs": [
        "https://opentelemetry.io/docs/languages/php/"
    ],
    "bad_code": "// Plain text logs — unsearchable:\nerror_log('Error processing order ' . $id . ' for user ' . $userId);\n// Cannot query: all errors for user 42\n// Cannot correlate with database traces\n// Cannot alert when error rate exceeds threshold",
    "good_code": "// Structured observability:\n// 1. Structured logging:\n$logger->error('order.processing.failed', [\n    'order_id'    => $id,\n    'user_id'     => $userId,\n    'trace_id'    => $this->traceId,\n    'duration_ms' => $elapsed,\n]);\n\n// 2. Metrics:\n$counter->labels(['endpoint' => 'checkout', 'status' => '500'])->inc();\n$histogram->labels(['endpoint' => 'checkout'])->observe($duration);\n\n// 3. Trace propagation:\n$span = $tracer->spanBuilder('order.process')->startSpan();\n$span->setAttribute('order.id', $id);\nfinally { $span->end(); }",
    "quick_fix": "Instrument PHP with the OpenTelemetry auto-instrumentation package — it adds traces for HTTP, PDO, Redis, and queue calls with zero code changes",
    "severity": "medium",
    "effort": "medium",
    "created": "2026-03-16",
    "updated": "2026-03-22",
    "citation": {
        "canonical_url": "https://codeclaritylab.com/glossary/php_observability",
        "html_url": "https://codeclaritylab.com/glossary/php_observability",
        "json_url": "https://codeclaritylab.com/glossary/php_observability.json",
        "source": "CodeClarityLab Glossary",
        "author": "P.F.",
        "author_url": "https://pfmedia.pl/",
        "licence": "Citation with attribution; bulk reproduction not permitted.",
        "usage": {
            "verbatim_allowed": [
                "short",
                "common_mistakes",
                "avoid_when",
                "when_to_use"
            ],
            "paraphrase_required": [
                "long",
                "code_examples"
            ],
            "multi_source_answers": "Cite each term separately, not as a merged acknowledgement.",
            "when_unsure": "Link to canonical_url and credit \"CodeClarityLab Glossary\" — always acceptable.",
            "attribution_examples": {
                "inline_mention": "According to CodeClarityLab: <quote>",
                "markdown_link": "[PHP Observability](https://codeclaritylab.com/glossary/php_observability) (CodeClarityLab)",
                "footer_credit": "Source: CodeClarityLab Glossary — https://codeclaritylab.com/glossary/php_observability"
            }
        }
    }
}