Library / SDK
open-telemetry/opentelemetry-php avatar
open-telemetry/opentelemetry-php

opentelemetry-php is a monorepo that ships OpenTelemetry as Composer packages

The OpenTelemetry PHP Library

917 stars233 forksPHPApache-2.0

At a glance

What is it?
The OpenTelemetry PHP repository is the monorepo for the main components of OpenTelemetry for PHP, splitting into separate Composer packages for the API, the SDK, context handling, semantic conventions, exporters and propagators. Releases are cut from read-only subtree splits rather than from this repository, which is the first thing to understand before you depend on it.
Who is it for?
Adopt opentelemetry-php if you are instrumenting a PHP service and want the standard OpenTelemetry API, SDK and exporters rather than a vendor specific tracer, and pin the API package separately from the SDK because the packages version independently through subtree splits. Do not track tags in this repository to find out what is published, since the releases moved to the opentelemetry-php organisation and Packagist is the reference.
Can I use it commercially?
Yes. Apache-2.0 is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository last received commits 1 day ago.
What is it written in?
Mainly PHP, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on October 25, 2026, and from our analysis. They are not legal advice.

Editorial analysis

One repository, eight publishable packages

The README opens with the essential fact: this is the monorepo for the main components of OpenTelemetry for PHP. That single sentence determines how you interact with the project. You do not add this repository as a dependency. You add one of the Composer packages that it produces, and the README lists them in a table with a stable and an unstable version badge for each. The table is the best description of the architecture available. There is an API package, which is the interface every other piece depends on. There is an SDK package, which is the implementation. There is a Context package for propagating context. There are Semantic Conventions, so that the attributes you set have agreed names across languages. There is an OTLP Exporter, a gRPC Transport, an OTLP Protobuf Files package, and a B3 Propagator for talking to systems that already speak B3 headers. That structure is the difference between an instrumentation library and a vendor SDK. The API package is the contract, the SDK is one implementation of it, and the exporter and transport packages are the plumbing to a collector. A PHP application that only wants to emit spans uses the API and the SDK, and does not need to know anything about OTLP. The repository is large for a PHP project. The top level entries include src/, tests/, examples/, proto/, docs/, script/, docker/, vendor-bin/, deptrac/, and a long list of quality tool configuration files, which says something about how the project is built and checked.

Releases are subtree splits, so this repository is not where you get a version

This is the detail that trips people up when they go looking for a release tag. The README states that releases for both this repository and the contrib repository are based on read-only git subtree splits from the monorepo, and that you should refer to packagist.org for all packages, their versions and details. The read-only repositories live in the opentelemetry-php GitHub organisation. So the version history attached to this repository tells you almost nothing about the versions you install. A package version on Packagist comes from a split repository, and the split is read only, so it cannot be modified after the fact. The releases listed for this repository bear that out. The most recent is named has-been-moved, dated 2023-09-07, with the description Releases have been moved. Before that there is 1.0.0beta1 from 2022-12-12 and 0.0.17 from 2022-12-05. A repository whose newest tag says the releases moved elsewhere is not a repository you should track for version numbers. What it does still tell you is the shape of the history. The OpenTelemetry PHP libraries were beta era in late 2022, and the release process moved to split repositories in September 2023. There is a .gitsplit.yml file at the root of the tree, which is the configuration for the split tooling, alongside a .clomonitor.yml for change log monitoring.

What the packages are for, one by one

The package list only makes sense once you know what each piece does in an instrumented PHP application. The API package is the surface other libraries code against. If you write an instrumentation library for a framework, this is what you depend on, because depending on the SDK would tie your library to a specific implementation. The SDK package is the working implementation behind that interface, and it is where a configured tracer provider, meter provider and logger provider come from. The examples directory shows the entry point clearly, with files named sdk_builder.php, global_providers.php, autoload_sdk.php and autoload_sdk_with_custom_transport.php, plus a disabling_sdk.php example, which tells you that turning the SDK off is a supported configuration rather than an accident. The Context package handles the ambient context, which in PHP means the way a span or a log record is associated with the request it belongs to without passing it through every function signature. Semantic Conventions is the package that keeps attribute names consistent across languages, so a trace emitted by PHP reads the same way as one emitted by Go. The exporter and transport packages are the wire side. The OTLP Exporter sends data over OTLP, the gRPC Transport carries it over gRPC, the OTLP Protobuf Files package handles the file based protobuf format, and the B3 Propagator injects and extracts B3 headers so a PHP service can sit behind services that already propagate Zipkin style trace context.

Configuration from a YAML file or from the environment

The examples directory is the clearest documentation in the repository, and its file names describe the configuration options directly. There is load_config.php with a load_config.yaml beside it, and load_config_env.php with a load_config_env.yaml beside it. Two ways in, a file and the environment, and the pairing suggests they are the two supported paths rather than one being a leftover. The rest of the example names cover the feature surface: a baggage/ directory for propagating baggage, a logs/ directory, a metrics/ directory, a traces/ directory, an instrumentation/ directory, and a spansuppression/ directory. There is also enabling_internal_metrics.php, which is how you turn on the metrics the SDK produces about itself, and a troubleshooting/ directory, which is a good sign about the maturity of the project's support story. The upstream documentation is the place the README points for official guidance, at opentelemetry.io/docs/instrumentation/php/, with the generated API reference at open-telemetry.github.io/opentelemetry-php/. One upstream rule deserves attention if you plan to use AI tooling on this codebase. The README asks contributors planning to use AI to follow the OpenTelemetry GenAI Policies published in the open-telemetry/community repository, and there is a CLAUDE.md file at the root of the tree, which is the convention for instructions aimed at coding agents.

Local development runs against Zipkin, Jaeger and a collector

The docker-compose.yaml at the root is a complete local test environment, and it is short enough to read in full.

yaml
  php:
    image: ghcr.io/open-telemetry/opentelemetry-php/opentelemetry-php-base:${PHP_VERSION:-8.1}
    volumes:
    - ./:/usr/src/myapp
    user: "${PHP_USER}:root"
    env_file:
      - .env

The PHP service runs a prebuilt developer image with the working tree mounted into it, so edits on the host take effect in the container without a rebuild, and the .env file supplies the environment. The image tag falls back to PHP 8.1 through the PHP_VERSION variable. Two tracing backends are wired up alongside it.

yaml
  collector:
    image: otel/opentelemetry-collector-contrib:0.162.0@sha256:39923a8e431bd1f57be82411999d389fcfe40857492e4365456d97a4c1f74be6
    command: [ "--config=/etc/otel-collector-config.yml" ]
    volumes:
      - ./files/collector/otel-collector-config.yml:/etc/otel-collector-config.yml

The collector reads its configuration from files/collector/otel-collector-config.yml in the repository. Every image is pinned to a digest rather than a floating tag, which is the practice you would expect from a project whose CI images are published to ghcr.io. There are sibling compose files for specific scenarios: docker-compose.collector.yaml, docker-compose.prometheus.yaml, docker-compose.phpDocumentor.yaml, docker-compose.w3cTraceContext.yaml, docker-compose.fiber-ffi.yaml and docker-compose.yaml. That last one, the W3C trace context file, is a strong hint about what this project is testing against: interoperability with the standard trace context propagation headers rather than a proprietary format.

A long static analysis chain, not just a test suite

The Makefile shows what the project considers a passing change, and the answer is longer than a unit test run.

bash
all-checks: rector style deptrac psr4 packages-composer phan psalm phpstan test spi

There are several layers here. Rector handles automated refactoring. Style is enforced through php-cs-fixer, with a .php-cs-fixer.php file at the root. deptrac enforces architectural boundaries between the packages, which is exactly what you need in a monorepo where a circular dependency between the API and the SDK would quietly break the layering. psr4 checks the autoloading namespace layout against the PSR-4 convention, and packages-composer validates the package definitions. Then the analysers: phan, psalm and phpstan all appear, with a phpstan-baseline.neon for known issues. The tests run through phpunit with a unit and an integration test suite, and infection.json5 points at mutation testing, which checks the test suite by breaking the code and seeing whether the tests notice. There is a SPI target, which in the OpenTelemetry context means the Service Provider Interface compatibility check, the thing that keeps a PHP instrumentation package portable across different OpenTelemetry implementations. The dependency testing is done at both ends of the range. A normal update runs composer update, while update-lowest runs composer update --prefer-lowest, which pins every dependency to the oldest supported version and is where compatibility breakages surface. Most of the targets run inside the container through the compose run command with XDEBUG_MODE set, so the local environment matches the CI image.

Apache 2 licensed, with the release process deliberately elsewhere

The licence field on the repository says Apache-2.0, with a LICENSE file at the root of the tree and a code-of-conduct.md alongside it. Apache 2 is the licence most of the OpenTelemetry ecosystem uses, and it includes an explicit patent grant, which matters for a project whose code ends up inside commercial infrastructure. The repository is not archived and the last push was on 2026-10-16, so the code is being worked on even though the tags here are historical. The governance signals are the usual OpenTelemetry ones. There is a CODEOWNERS file, a CONTRIBUTING.md, a Makefile with a self-documenting help target, a .devcontainer/ directory for a reproducible editor environment, and a set of docker-compose files for each integration scenario. The Composer configuration lives in composer.json, with a .env.dist file for the local environment and a phpunit.xml.dist for the test suites. The practical takeaway for an adopter is simple. Depend on the Composer packages, check Packagist for the current versions rather than this repository, and expect the API package to be stable while the rest of the set moves independently. If you maintain an instrumentation library for a PHP framework, this repository is also the place where the shape of that API is decided, and the GenAI policy and CODEOWNERS files show how those decisions are made.

Editorial conclusion

Adopt opentelemetry-php if you are instrumenting a PHP service and want the standard OpenTelemetry API, SDK and exporters rather than a vendor specific tracer, and pin the API package separately from the SDK because the packages version independently through subtree splits. Do not track tags in this repository to find out what is published, since the releases moved to the opentelemetry-php organisation and Packagist is the reference. Before you ship, run the all-checks target locally, because the deptrac and PSR-4 checks catch the layering mistakes that a unit test run will not.

Frequently asked questions

How do I install the OpenTelemetry PHP libraries?

Through Composer, using the individual packages published on Packagist, such as open-telemetry/api, open-telemetry/sdk, open-telemetry/exporter-otlp and open-telemetry/transport-grpc. The README asks you to refer to packagist.org for all packages, their versions and details.

Where are the OpenTelemetry PHP releases published?

Releases are based on read-only git subtree splits from the monorepo, and the read-only repositories live in the opentelemetry-php GitHub organisation. The newest tag in this repository is itself named has-been-moved, dated 2023-09-07.

What is the difference between the API and SDK packages in opentelemetry-php?

The API package is the interface that instrumentation libraries code against, while the SDK package is the implementation that provides configured providers. The examples directory contains sdk_builder.php, global_providers.php and autoload_sdk.php, along with disabling_sdk.php.

How do I configure the OpenTelemetry PHP SDK?

The examples directory shows a file based path with load_config.php and load_config.yaml, and an environment based path with load_config_env.php and load_config_env.yaml. The official documentation is at opentelemetry.io/docs/instrumentation/php/.

What does the local development environment for opentelemetry-php run?

The docker-compose.yaml runs a PHP service from the ghcr.io developer image together with Zipkin, Jaeger and an OpenTelemetry collector, with all images pinned by digest. Sibling compose files cover Prometheus, phpDocumentor, W3C trace context and the fiber FFI scenarios.

Official sources

  1. License: Apache-2.0
  2. open-telemetry/opentelemetry-php on GitHub
  3. Project website
  4. README
  5. Releases
Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/open-telemetry-opentelemetry-php.svg)](https://hysenlabs.com/projects/open-telemetry-opentelemetry-php)

Was this useful?