> For the complete documentation index, see [llms.txt](https://docs.lenses.io/latest/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.lenses.io/latest/devx/6.3/deployment/configuration/hq/kafka-metrics.md).

# Consumer Group Metrics Endpoint

This page describes the Lenses-compatible consumer group metrics endpoint exposed by HQ.

HQ exposes consumer group lag and state as Prometheus gauges in the same shape the Lenses Agent served them, so dashboards and alerts written against it keep working when the data behind them comes from HQ. The one addition is an `environment` label on every series, since a single HQ covers many Kafka environments.

## Endpoint

```
GET  /kafka-metrics
HEAD /kafka-metrics
```

The endpoint is served on HQ's **Prometheus listener**, not the HTTP API listener. The address is set by the `metrics.prometheusAddress` [configuration setting](/latest/devx/6.3/deployment/configuration/hq/configuration-reference.md) (default `:9090`), alongside `GET /metrics`.

| Status | When                                                                           |
| ------ | ------------------------------------------------------------------------------ |
| `200`  | Prometheus text exposition of the selected series.                             |
| `400`  | `metrics=` names a metric that does not exist; the body lists the valid names. |
| `405`  | Any method other than `GET` or `HEAD` (`Allow: GET, HEAD`).                    |
| `500`  | Fetching the data failed.                                                      |

## Parameters

Both parameters are optional, comma-separated and repeatable, so `?environment=a,b` and `?environment=a&environment=b` are equivalent. Values are trimmed and deduplicated, and omitting a parameter means no filter on that dimension.

| Parameter      | Values                   | Effect                            |
| -------------- | ------------------------ | --------------------------------- |
| `environment=` | Environment names        | Serve only these environments.    |
| `metrics=`     | One or more metric names | Serve only these metric families. |

{% hint style="info" %}
Both parameters narrow the work HQ does, not just the response it returns, which makes them the controls for scrape cost.
{% endhint %}

## Exposed metrics

The endpoint exposes six gauge families:

| Metric                                  | Labels                                               | Scope            | Meaning                                                               |
| --------------------------------------- | ---------------------------------------------------- | ---------------- | --------------------------------------------------------------------- |
| `lenses_consumer_group_state`           | `environment`, `consumerGroup`, `state`              | Group-scoped     | The group's state, carried in the `state` label.                      |
| `lenses_consumer_group_max_lag`         | `environment`, `consumerGroup`                       | Group-scoped     | Highest lag in records across the partitions the group consumes.      |
| `lenses_consumer_group_max_lag_seconds` | `environment`, `consumerGroup`                       | Group-scoped     | That same maximum as an estimated time behind, in seconds.            |
| `lenses_topic_consumer_lag`             | `environment`, `topic`, `consumerGroup`              | Partition-scoped | The group's lag in records for one topic, summed over its partitions. |
| `lenses_partition_consumer_lag`         | `environment`, `topic`, `partition`, `consumerGroup` | Partition-scoped | Lag in records for one group, topic and partition.                    |
| `lenses_partition_consumer_lag_seconds` | `environment`, `topic`, `partition`, `consumerGroup` | Partition-scoped | That same lag as an estimated time behind, in seconds.                |

The `state` label is one of `Stable`, `Rebalancing`, `NoActiveMembers`, `ExistsNot` or `Unknown`.

## Scrape cost

A scrape returns every series the filters allow, and its cost is set by **how many topic partitions HQ holds in total, across all environments**. Response size, memory and scrape time all scale with that total partition count.

Up to a couple of hundred thousand total topic partitions, an unfiltered scrape should be comfortable. Past that, measure it against your own hardware and setup to confirm the scrape completes within the time Prometheus allows it, and reach for the filters below if it does not.

## Choosing a scrape strategy

### No filters

```
GET /kafka-metrics
```

Everything in one scrape. Use this while the total topic partition count across all environments stays within a couple of hundred thousand.

{% hint style="warning" %}
Beyond that, an unfiltered scrape can grow long enough to outrun Prometheus' default 10 s `scrape_timeout`. Measure a scrape on your own setup before relying on it.
{% endhint %}

### One scrape per environment

```
GET /kafka-metrics?environment=prod-eu
```

For a large total partition count, configure one Prometheus target per environment and scrape each individually. Each target then costs one environment's worth of work, and all six metric families are still served.

### Group-scoped families only, all environments

```
GET /kafka-metrics?metrics=lenses_consumer_group_state,lenses_consumer_group_max_lag,lenses_consumer_group_max_lag_seconds
```

For when a single environment is already too large to scrape. These three families never touch per-partition data, so their cost tracks consumer group count rather than partition count.

### Both filters together

```
GET /kafka-metrics?environment=prod-eu&metrics=lenses_consumer_group_state,lenses_consumer_group_max_lag
```

The filters compose, so a single target can narrow on both dimensions at once. This suits a setup where one environment is large enough that only group-level alerting is wanted from it, while the smaller environments are still scraped in full from their own targets.


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation by asking a question.

Perform an HTTP GET request on the following URL with the `ask` and `goal` query parameters:

```
GET https://docs.lenses.io/latest/devx/6.3/deployment/configuration/hq/kafka-metrics.md?ask=<question>&goal=<user_goal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is what the user is ultimately trying to achieve, the reason they need the answer. Sharing it helps GitBook give you a better, more relevant answer. A goal is most helpful when it describes the outcome the user wants rather than restating the question. For example, with `ask=how do I create an API token`, a goal like `automate deployments from our CI pipeline` lets GitBook tailor the answer to that use case.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
