{"id":47298671,"url":"https://github.com/tracewayapp/opentelemetry-symfony-bundle","last_synced_at":"2026-04-06T10:00:57.850Z","repository":{"id":344872365,"uuid":"1181052877","full_name":"tracewayapp/opentelemetry-symfony-bundle","owner":"tracewayapp","description":"Pure-PHP OpenTelemetry instrumentation for Symfony - automatic HTTP, HttpClient, and Messenger tracing. No C extension required","archived":false,"fork":false,"pushed_at":"2026-04-03T10:22:57.000Z","size":120,"stargazers_count":57,"open_issues_count":2,"forks_count":1,"subscribers_count":2,"default_branch":"master","last_synced_at":"2026-04-03T15:47:20.441Z","etag":null,"topics":["instrumentation","observability","opentelemetry","otel","php","symfony","symfony-bundle","tracing"],"latest_commit_sha":null,"homepage":"https://packagist.org/packages/traceway/opentelemetry-symfony","language":"PHP","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/tracewayapp.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2026-03-13T17:40:57.000Z","updated_at":"2026-04-03T14:21:58.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/tracewayapp/opentelemetry-symfony-bundle","commit_stats":null,"previous_names":["tracewayapp/opentelemetry-symfony-bundle"],"tags_count":12,"template":false,"template_full_name":null,"purl":"pkg:github/tracewayapp/opentelemetry-symfony-bundle","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tracewayapp%2Fopentelemetry-symfony-bundle","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tracewayapp%2Fopentelemetry-symfony-bundle/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tracewayapp%2Fopentelemetry-symfony-bundle/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tracewayapp%2Fopentelemetry-symfony-bundle/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/tracewayapp","download_url":"https://codeload.github.com/tracewayapp/opentelemetry-symfony-bundle/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tracewayapp%2Fopentelemetry-symfony-bundle/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":31368157,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-04-03T17:53:18.093Z","status":"ssl_error","status_checked_at":"2026-04-03T17:53:17.617Z","response_time":107,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.6:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["instrumentation","observability","opentelemetry","otel","php","symfony","symfony-bundle","tracing"],"created_at":"2026-03-16T21:00:39.596Z","updated_at":"2026-04-06T10:00:57.844Z","avatar_url":"https://github.com/tracewayapp.png","language":"PHP","funding_links":[],"categories":[],"sub_categories":[],"readme":"# OpenTelemetry Symfony Bundle\n\n[![CI](https://github.com/tracewayapp/opentelemetry-symfony-bundle/actions/workflows/ci.yml/badge.svg)](https://github.com/tracewayapp/opentelemetry-symfony-bundle/actions/workflows/ci.yml)\n[![codecov](https://codecov.io/gh/tracewayapp/opentelemetry-symfony-bundle/graph/badge.svg)](https://codecov.io/gh/tracewayapp/opentelemetry-symfony-bundle)\n[![Packagist Version](https://img.shields.io/packagist/v/traceway/opentelemetry-symfony.svg)](https://packagist.org/packages/traceway/opentelemetry-symfony)\n[![Packagist Downloads](https://img.shields.io/packagist/dt/traceway/opentelemetry-symfony.svg)](https://packagist.org/packages/traceway/opentelemetry-symfony)\n[![PHP Version](https://img.shields.io/badge/php-%3E%3D8.1-8892BF.svg)](https://php.net)\n[![Symfony Version](https://img.shields.io/badge/symfony-%3E%3D6.4-000000.svg)](https://symfony.com)\n[![License](https://img.shields.io/badge/license-MIT-blue.svg)](LICENSE)\n\nPure-PHP OpenTelemetry instrumentation for Symfony — automatic tracing for HTTP, Console, HttpClient, Messenger, Doctrine DBAL, Cache, and Twig, plus Monolog log-trace correlation. No C extension required.\n\nWorks with any OpenTelemetry-compatible backend: [Traceway](https://tracewayapp.com), [Jaeger](https://www.jaegertracing.io/), [Zipkin](https://zipkin.io/), [Datadog](https://www.datadoghq.com/), [Grafana Tempo](https://grafana.com/oss/tempo/), [Honeycomb](https://www.honeycomb.io/), and more.\n\n## Quick Start\n\n```bash\ncomposer require traceway/opentelemetry-symfony\n```\n\n```env\nOTEL_PHP_AUTOLOAD_ENABLED=true\nOTEL_SERVICE_NAME=my-symfony-app\nOTEL_TRACES_EXPORTER=otlp\nOTEL_EXPORTER_OTLP_ENDPOINT=http://localhost:4318\nOTEL_EXPORTER_OTLP_PROTOCOL=http/json\n```\n\n\u003e Use `http/json` by default. Switch to `http/protobuf` only if you have `ext-protobuf` installed — see [Performance](#performance).\n\nOptionally, it is possible to also provide a version identifier using e.g.:\n\n```env\nOTEL_RESOURCE_ATTRIBUTES=service.version=1.0\n```\n\nThat's it — every HTTP request, console command, outgoing HTTP call, Messenger job, DB query, cache operation, and Twig render is now traced automatically.\n\n## What Gets Traced\n\n| Component | Span Kind | What's captured |\n|---|---|---|\n| **HTTP requests** | SERVER | Route templates (`GET /api/items/{id}`), status codes, body sizes, client IP, exceptions, sub-requests |\n| **Console commands** | SERVER | Command name, arguments, exit code, exceptions |\n| **HttpClient** | CLIENT | Outgoing requests with W3C context propagation, OTLP endpoint auto-excluded, re-entrance guard |\n| **Messenger** | PRODUCER/CONSUMER | Message class, transport, W3C context propagation across async boundaries |\n| **Doctrine DBAL** | CLIENT | SQL queries (parameterized), transactions, db system/namespace auto-detection. Requires `doctrine/dbal` ^4.0 |\n| **Cache** | INTERNAL | `get` (hit/miss), `delete`, `invalidateTags` with pool name. Requires `symfony/cache` |\n| **Twig** | INTERNAL | Template name, nested includes. Requires `twig/twig` |\n| **Monolog** | — | Injects `trace_id` + `span_id` into every log record. Requires `monolog/monolog` |\n\nAdditional: response propagation (Server-Timing headers), `Tracing` helper for manual spans, full [OTel semantic conventions](https://opentelemetry.io/docs/specs/semconv/http/).\n\n## Requirements\n\n- PHP \u003e= 8.1, Symfony \u003e= 6.4, OpenTelemetry PHP SDK \u003e= 1.0\n- Doctrine DBAL \u003e= 4.0 *(optional)*, Twig \u003e= 3.0 *(optional)*\n\n## Configuration\n\nAll options are optional — the bundle works out of the box with zero configuration. Create `config/packages/open_telemetry.yaml` to customize:\n\n```yaml\nopen_telemetry:\n    traces_enabled: true\n    tracer_name: 'opentelemetry-symfony'\n\n    excluded_paths: [/health, /_profiler, /_wdt]\n    record_client_ip: true           # disable for GDPR\n    error_status_threshold: 500      # 400-599\n\n    console_enabled: true\n    console_excluded_commands: [cache:clear, assets:install]\n\n    http_client_enabled: true\n    http_client_excluded_hosts: []   # OTLP endpoint is auto-excluded\n\n    messenger_enabled: true\n    messenger_root_spans: false      # true = standalone traces per consumed message\n\n    doctrine_enabled: true\n    doctrine_record_statements: true # false = hide SQL from spans\n\n    cache_enabled: true\n    cache_excluded_pools: [cache.system, cache.validator, cache.serializer]\n\n    twig_enabled: true\n    twig_excluded_templates: ['@WebProfiler/', '@Debug/']\n\n    monolog_enabled: true\n```\n\n### Environment Variables\n\n| Variable | Example | Description |\n|---|---|---|\n| `OTEL_PHP_AUTOLOAD_ENABLED` | `true` | Enable SDK auto-initialization |\n| `OTEL_SERVICE_NAME` | `my-symfony-app` | Service name shown in your backend |\n| `OTEL_TRACES_EXPORTER` | `otlp` | Exporter type (`otlp`, `zipkin`, `console`, `none`) |\n| `OTEL_EXPORTER_OTLP_ENDPOINT` | `http://localhost:4318` | Collector/backend endpoint |\n| `OTEL_EXPORTER_OTLP_PROTOCOL` | `http/json` | Protocol (`http/json`, `http/protobuf`, `grpc`) |\n\nSee the [OpenTelemetry SDK docs](https://opentelemetry.io/docs/languages/php/exporters/) for all available options.\n\n## Manual Instrumentation\n\nInject `TracingInterface` for one-liner span creation:\n\n```php\nuse Traceway\\OpenTelemetryBundle\\TracingInterface;\n\nclass OrderService\n{\n    public function __construct(private readonly TracingInterface $tracing) {}\n\n    public function process(int $orderId): void\n    {\n        $this-\u003etracing-\u003etrace('order.validate', function () use ($orderId) {\n            // validation logic...\n        });\n\n        $this-\u003etracing-\u003etrace('order.fulfill', function () {\n            $this-\u003etracing-\u003etrace('inventory.reserve', fn () =\u003e $this-\u003ereserve());\n            $this-\u003etracing-\u003etrace('payment.charge', fn () =\u003e $this-\u003echarge());\n        });\n    }\n}\n```\n\nMock in tests:\n\n```php\n$tracing = $this-\u003ecreateStub(TracingInterface::class);\n$tracing-\u003emethod('trace')-\u003ewillReturnCallback(fn ($name, $cb) =\u003e $cb());\n```\n\n## Performance\n\nThe bundle adds **near-zero overhead** when the SDK is not active — every component checks `isEnabled()` and short-circuits immediately.\n\nWhen tracing is active, most overhead comes from the SDK's span export, not instrumentation. PHP-FPM has no background thread, so `BatchSpanProcessor` flushes during request shutdown.\n\n### Export Protocol\n\n| Setup | Recommendation |\n|---|---|\n| `ext-protobuf` **installed** | Use `http/protobuf` — smallest payloads, fastest serialization |\n| `ext-protobuf` **not installed** | Use `http/json` — `json_encode()` is native C in PHP, much faster than pure-PHP protobuf |\n\n\u003e **Do not** use `http/protobuf` without `ext-protobuf`. The pure-PHP protobuf encoder adds significant CPU overhead under load.\n\n### Tips\n\n1. **Local OTel Collector** — export to `localhost:4318` (sub-ms latency), let the Collector forward asynchronously\n2. **Sampling** — `OTEL_TRACES_SAMPLER=parentbased_traceidratio` + `OTEL_TRACES_SAMPLER_ARG=0.1` traces 10% of requests\n3. **Install `ext-protobuf`** — if using `http/protobuf`, the C extension reduces serialization overhead dramatically ([pecl.php.net/protobuf](https://pecl.php.net/package/protobuf))\n4. **Exclude noisy paths** — use `excluded_paths` and `cache_excluded_pools` to reduce span volume\n\n## Contributing\n\n```bash\ngit clone https://github.com/tracewayapp/opentelemetry-symfony-bundle.git\ncd opentelemetry-symfony-bundle\ncomposer install\nvendor/bin/phpunit\nvendor/bin/phpstan analyse\n```\n\n## License\n\n[MIT](LICENSE)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ftracewayapp%2Fopentelemetry-symfony-bundle","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Ftracewayapp%2Fopentelemetry-symfony-bundle","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ftracewayapp%2Fopentelemetry-symfony-bundle/lists"}