prometheus-client: a native Rust client for the OpenMetrics spec
Prometheus / OpenMetrics client library in Rust
At a glance
- What is it?
- prometheus-client is a Rust implementation of the OpenMetrics specification that aims at no unsafe code, compile-time type safety for instrumentation and low overhead so teams can instrument freely. It is published under Apache-2.0 or MIT, and its README carries an explicit list of the spec requirements it does not yet enforce.
- Who is it for?
- Adopt prometheus-client if you want to instrument a Rust service in a type safe way with no unsafe code inside the library, and you are willing to read the specification compliance list before relying on it for strict conformance. Skip it if you need the summary metric type, a state set metric, gauge histograms or protobuf exposition today, since each is listed as a gap.
- 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 4 days ago.
- What is it written in?
- Mainly Rust, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on October 22, 2026, and from our analysis. They are not legal advice.
Editorial analysis
Three goals that rule out most of the usual designs
The README states three goals, and each one excludes a common approach. The first is no unsafe, with the instruction not to use unsafe Rust within the library itself, which means every metric implementation is safe Rust and the usual escape hatches for a hot path are not available to the library authors. The second is type safe, leveraging Rust's type system to catch common instrumentation mistakes at compile time, so a counter cannot be used where a gauge is expected and a label set with the wrong shape does not compile. The third is fast, with the requirement not to force users to worry about the performance impact of instrumentation, and the stated encouragement to instrument often and extensively. The framing of that third goal is what makes the library interesting. A metrics library that is cheap enough to call on every request changes what people do, because the cost of a counter increment stops being a design discussion. The library is the crate prometheus-client, and its Cargo metadata describes it as an Open Metrics client library allowing users to natively instrument applications.
The compliance list is the most useful paragraph in the README
The specification compliance section is unusual, because it publishes the gaps rather than implying full conformance. The README lists the properties where this client library implementation lags behind the Open Metrics specification, and states that not being compliant with all requirements, the MUST and MUST NOT items, is considered a bug and likely to be fixed in the future, with contributions welcome. The list is specific. State set metric is not implemented. The library does not enforce that a histogram metric point must contain at least one bucket, that a metric family must have UNIT metadata, that metric family names must be unique within a metric set, that names should be in snake_case, that metric family names beginning with underscores are reserved and must not be used unless specified by the standard, or that exposers should avoid names that could be confused with the suffixes that text format sample metric names use. Gauge histogram metric is missing. It also does not allow the created timestamp value that a metric point in a counter or histogram should have. Summary metric is not implemented. For a team whose monitoring stack validates exposition strictly, that list is the adoption checklist, and for a team that scrapes permissive text output, most of it does not matter.
Protobuf exposition is behind feature flags
The Cargo features are where the exposition formats live. The default feature set is empty, so a plain dependency gives you the core behaviour and nothing else. There is a prometheus_protobuf feature that pulls in prost, prost-types and prost-build, an openmetrics_protobuf feature that pulls in the same three, and a protobuf feature that is simply an alias for openmetrics_protobuf. A separate protobuf-protox feature adds protox as a dependency, and the build dependencies list includes prost-build and protox. So the design is that the classic Prometheus text format is what you get by default, and the protobuf encodings are opt-in with the code generation machinery brought in only when you ask for them. The separate workspace member derive-encode/ suggests the code generation lives in its own crate with its own published version, and it is pulled in as a path dependency with a matching version number. There is also a test-util feature, and the comment attached to it is a good example of a responsible feature flag. It provides additional APIs for testing downstream code using prometheus-client, and the note says that interfaces gated by it are not subject to stability guarantees and may be changed or removed in patch releases. That is the kind of note that saves a downstream user from depending on something that was never promised.
The examples tell you which web frameworks it has been fitted to
The examples directory is the fastest way to see how the library is used in practice, and the file names are informative. There is actix-web.rs, axum.rs, hyper.rs and tide.rs, which covers the common Rust web stacks between them, so you can find the integration closest to the one you already run rather than assembling an exporter from scratch. There is custom-metric.rs, which is the one to read if you need a metric type the default set does not cover. And there is io_write.rs, which is about writing the exposition output rather than about a specific framework. The dev dependencies confirm the coverage, with axum 0.8, actix-web 4, hyper 1.3.1 with server and http1 features, hyper-util, http-body-util, http-types 2 and tide 0.16, plus tokio with the multi-threaded runtime, net, macros and signal features, and futures. The presence of http-body-util and http-types alongside two different server frameworks suggests the output is written as a body rather than as a raw socket, which is the shape a modern framework wants. The runtime dependencies are small and deliberate, with dtoa and itoa for number formatting, parking_lot for locking, and prost for the optional protobuf path.
Testing, benchmarking and the Python bridge
The dev dependency list is longer than the runtime one, which is what a library with correctness requirements looks like. criterion 0.8 is there for benchmarks, and the repository has a benches/ directory, so the fast goal is measured rather than asserted. quickcheck and rand 0.10.1 are there for property based testing, which suits a metrics library because the interesting failures are in edge cases like label combinations and empty buckets rather than in the happy path. async-std with the attributes feature is there for async tests, and pyo3 0.29 is present, which points to a binding or test harness that reaches the library from Python, useful for cross-checking exposition output against a reference implementation. The Cargo manifest also sets the edition to 2021, and the version is 0.25.1, with the release list showing v0.25.1 on 2026-09-01, v0.25.0 on 2026-06-15 and v0.24.1 on 2026-03-31. The pre-1.0 version number is the honest signal that the public API may still move, and the last push to the repository was on 2026-10-19 with the repository not archived, so the work continues between releases.
How it compares with rust-prometheus, and what the choice costs
The README points at a related library rather than pretending there is no alternative. rust-prometheus is the other Rust client in common use, and the README links to a specific issue in that project for a high-level comparison, so the comparison exists and is written by people who know both. The differences the goals imply are real. A library that forbids unsafe code internally and leans on the type system will have a different ergonomics profile from one that optimises aggressively, and the no-unsafe goal is a real constraint on how a counter can be stored and updated. There is also a scope difference. This library targets the OpenMetrics specification with a published compliance list, while the more widely used client in the ecosystem has a longer history and a larger user base, which usually means more third party integrations and more Stack Overflow answers. The cost of choosing this one is the smaller ecosystem and the pre-1.0 API surface. The benefit is that the compliance list tells you exactly where you stand with respect to the specification, which is something a mature library with historical behaviour cannot always promise.
Licensing, contribution terms and where the tool is wrong
The licence is the standard Rust dual option, licensed under either the Apache License 2.0 or the MIT license at your option, and the Cargo manifest agrees with the identifier Apache-2.0 OR MIT. The contribution terms are spelled out with a small twist worth reading. Unless you explicitly state otherwise, any contribution intentionally submitted for inclusion in the work by you, as defined in the Apache-2.0 licence, shall be dual licensed as above, without any additional terms or conditions. In other words, contributions are accepted under the same dual option and cannot be imposed on a different licence, and a contributor who wants other terms has to say so explicitly. The repository also carries a MAINTAINERS.md file, a CHANGELOG.md, a SECURITY.md, a CODE_OF_CONDUCT.md and a CONTRIBUTING.md, which is the expected set for a library that takes outside patches. As for when this is the wrong tool, the compliance list answers most of it. If your pipeline requires summary metrics, you need them. If a state set metric is required by your monitoring stack, it does not exist here. If you want the Prometheus protobuf exposition today, it is behind a feature flag with a build-time code generation dependency. And if your requirement is a stable 1.0 API for a long-lived service, the version number says that is not what this is yet.
Editorial conclusion
Adopt prometheus-client if you want to instrument a Rust service in a type safe way with no unsafe code inside the library, and you are willing to read the specification compliance list before relying on it for strict conformance. Skip it if you need the summary metric type, a state set metric, gauge histograms or protobuf exposition today, since each is listed as a gap. Verify first which OpenMetrics requirements your monitoring stack actually enforces, that your exporter matches the metric families the stack expects, and that the version you pin matches the specification level your scraper expects.
Frequently asked questions
What does the prometheus-client crate do and what are its goals?
It is a Rust client library implementation of the OpenMetrics specification, letting developers instrument applications so operators can monitor them with systems like Prometheus. Its three stated goals are no unsafe code inside the library, type safety that catches instrumentation mistakes at compile time, and low overhead so instrumentation can be used often and extensively.
Is prometheus-client fully OpenMetrics compliant?
No, and the README publishes the gaps. Missing or unenforced items include the state set metric, gauge histogram metric, summary metric, enforcement of histogram bucket presence, UNIT metadata, unique metric family names, snake_case naming, reserved names that begin with an underscore, and the created timestamp value for counters and histograms.
How do I enable protobuf exposition in prometheus-client?
Through Cargo features. The prometheus_protobuf feature pulls in prost, prost-types and prost-build, openmetrics_protobuf does the same for OpenMetrics, and protobuf is an alias for openmetrics_protobuf. There is also a protobuf-protox feature adding protox, and the default feature set is empty.
Official sources
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.
[](https://hysenlabs.com/projects/prometheus-client-rust)Was this useful?