You are misunderstanding the purpose of sum. It is not performing a sum over time but over the dimensions of your metric.

In your example, assuming there are multiple requests metrics (with a dimension page by exemple), rate(requests[3 sec]) will give you (at some point in time):

{page="A"}  12.4
{page="B"}  1.5
{page="C"}  0 .... (and so on for each metrics requests with different label set)

The sum function will sum the values of the different rates; and sum(rate(requests[3 sec])) will give you only one value:

{}  42.13 <-- the sum of all rate(requests[3s]) values

BONUS: In the case you metric have multiple dimensions (represented by multiple labels in your metric) you can tell sum() to operate on a subset of them: sum(rate(requests[3 sec])) ON(foo)

Answer from Michael Doubez on Stack Overflow
🌐
Robust Perception
robustperception.io › rate-then-sum-never-sum-then-rate
Rate then sum, never sum then rate – Robust Perception | Prometheus Monitoring Experts
May 9, 2016 - Let's say you are aggregating up the rate of requests across all of your Node exporters. The individual rates would be: rate(http_requests_total{job="node"}[5m]) Now to aggregate those, you'd do: sum by (job)(rate(http_requests_total{job="node"}[5m])) # This is okay ·
Discussions

rate/sum confusion
What you're confusing is columns and rows. If you imagine each metric name like a column, and the label values as rows. If you want to add up a row, you use the + operator, if you want to add up a column, you use sum(). So if you want to sum up all the interfaces on a single instance, you do something like this: sum without (instance,name) ( rate(ifHCOutOctets{instance="10.1.2.3",job="Firewalls",name="Firewall-1"}[30s]) ) * 8 Note that I don't include the ifIndex label filter. This means all labels will match. If you want to match multiple labels at a time, you will need to use a regular expression match. Something like ifIndex=~"(500010723|500010724)". EDIT: An example of a valid use of the + operator would be something like this: sum by (name) (rate(ifHCOutOctets[1m])) + sum by (name) (rate(ifHCInOctets[1m])) Note that we're adding up two columns, in and out octets. More on reddit.com
🌐 r/PrometheusMonitoring
6
1
October 17, 2019
Prometheus: how to rate a sum of the same counter from different machines? - Stack Overflow
I have a Prometheus counter, for which I want to get its rate on a time range (the real target is to sum the rate, and sometimes use histogram_quantile on that for histogram metric). However, I've ... More on stackoverflow.com
🌐 stackoverflow.com
promql - Prometheus sum by rate give crazily high spike - Stack Overflow
Using PromQL, I can draw two charts, using different time interval. sum (rate (some_metrics[1s])) sum (rate (some_metrics[1h])) However, for the second chart: sum (rate (some_metrics[1h])) It somet... More on stackoverflow.com
🌐 stackoverflow.com
sum(rate(metricselector[rangevector])) over-represents short lived timeseries
Concretely, consider : given 15 ... of 1 minutes, generates 1000x the normal rate during that period. sum(rate(all16metrics[1m])) at the end of that bad pods lifetime will return 1015R in both the prometheus model and the VictoriaMetrics: the 15 pods that are stable and exist ... More on github.com
🌐 github.com
14
April 14, 2021
People also ask

Can rate() be used with all types of Prometheus metrics?
No, rate() should only be used with counter-metrics. It doesn't make sense to use rate() with gauge metrics, as they don't represent cumulative values.
🌐
last9.io
last9.io › blog › prometheus-rate-function
Prometheus Rate Function: A Practical Guide to Using It | Last9
How do you calculate request rates using the Prometheus rate function?
To calculate request rates, use a query like rate(http_requests_total[5m]). This will give the per-second rate of requests over the last 5 minutes. These rates can be summed or grouped as needed, e.g., sum(rate(http_requests_total[5m])) for the total request rate across all instances.
🌐
last9.io
last9.io › blog › prometheus-rate-function
Prometheus Rate Function: A Practical Guide to Using It | Last9
How does the Prometheus rate() function differ from increase()?
While rate() calculates the per-second average rate of increase, increase() calculates the total increase in the counter's value over the time range. rate() is generally more useful for ongoing monitoring, while increase() can help understand total change over a specific period.
🌐
last9.io
last9.io › blog › prometheus-rate-function
Prometheus Rate Function: A Practical Guide to Using It | Last9
🌐
Prometheus
prometheus.io › docs › prometheus › latest › querying › functions
Query functions | Prometheus
rate acts on native histograms by calculating a new histogram where each component (sum and count of observations, buckets) is the rate of increase between the respective component in the first and last native histogram in v.
🌐
Reddit
reddit.com › r/prometheusmonitoring › rate/sum confusion
r/PrometheusMonitoring on Reddit: rate/sum confusion
October 17, 2019 -

Hi,

So I'm struggling with summing up bandwidth usage on my firewalls. Without going into too much detail, I'm using Prom to receive the snmp stats for bandwidth use on multiple interfaces of my FW (over 15 at last count). This works fine when graphing in Grafana.

rate(ifHCOutOctets{ifIndex="500010723",instance="10.1.2.3",job="Firewalls",name="Firewall-1"}[30s]) * 8

rate(ifHCOutOctets{ifIndex="500010724",instance="10.1.2.3",job="Firewalls",name="Firewall-1"}[30s]) * 8

rate(ifHCOutOctets{ifIndex="500010725",instance="10.1.2.3",job="Firewalls",name="Firewall-1"}[30s]) * 8

This works great and when using a graph configured for bits per second, gives me a nice overlaid graph of every interface's bandwidth use over the day, identifying which interface (and connected agency) is rinsing the bandwidth.

What I'm looking for now is a concatination of the day's bandwidth use. I know I'm going to be needing a sum and from reading this: https://www.robustperception.io/rate-then-sum-never-sum-then-rate, it seems that rate should not come first. However, this: https://prometheus.io/docs/prometheus/latest/querying/functions/#rate says exactly the opposite (as far as I'm understanding it - "Note that when combining rate() with an aggregation operator (e.g. sum()) or a function aggregating over time (any function ending in _over_time), always take a rate() first, then aggregate. Otherwise rate() cannot detect counter resets when your target restarts."

So, I was struggling initially but now I'm even more confused. In my mind, I want this:

sum(rate(ifHCOutOctets{ifIndex="500010723",instance="10.1.2.3",job="Firewalls",name="Firewall-1"}[30s]) * 8 + rate(ifHCOutOctets{ifIndex="500010724",instance="10.1.2.3",job="Firewalls",name="Firewall-1"}[30s]) * 8)

and so on so that I can see the total bandwidth in use at the time on all interfaces. I can then use that to graph a 24 hour period and see if all interfaces combined are topping out our bandwidth allowance.

Thanks for any pointers you can offer.

🌐
Medium
giuscri.medium.com › about-sum-rate-in-prometheus-883e492ba542
About sum(rate…) in Prometheus - Giuseppe Crinò - Medium
January 17, 2023 - About sum(rate…) in Prometheus You can’t do the rate of a sum because you can’t use range selectors (i.e. [5m]) on the output of a function; as rate takes a range vector and one would write …
🌐
Last9
last9.io › blog › prometheus-rate-function
Prometheus Rate Function: A Practical Guide to Using It | Last9
June 15, 2026 - This query calculates the request rate for each endpoint over the last 5 minutes and sums up the rates for all methods.
Find elsewhere
🌐
MetricFire
metricfire.com › blog › understanding-the-prometheus-rate-function
How the Prometheus rate() function works | MetricFire
March 12, 2026 - Summary: Similar to a histogram, this metric type records a total count of observations and a sum of observed values. It processes the information while computing configurable quantities for a sliding time window.
🌐
Google Groups
groups.google.com › g › prometheus-users › c › ewWNOK10vWY
Rate of Sums vs Sum of Rates
sum by(foo) (irate(my_federated_counter_total[1m])) 2) A and B already compute rates via recording rules and C then federates over those rates.
Top answer
1 of 2
5

You'd better expose your counters at 0 on application start, if the other labels (aaa, etc) have a limited set of possible combinations. This way rate() function works correctly at the bottom level and sum() will give you correct results.

If you have to do a rate() of the sum(), read this first:

Note that when combining rate() with an aggregation operator (e.g. sum()) or a function aggregating over time (any function ending in _over_time), always take a rate() first, then aggregate. Otherwise rate() cannot detect counter resets when your target restarts.

If you can tolerate this (or the instances reset counters at the same time), there's a way to work around. Define a recording rule as

record: job:mycounter:sum
expr: sum without(instance) (mycounter)

and then this expression works:

sum(rate(job:mycounter:sum[5m]))
2 of 2
0

The obvious query rate(sum(...)) won't work in most cases, since the resulting sum(...) may hide possible resets to zero for individual time series, which are passed to sum. So usually the correct answer is to use sum(rate(...)) instead. See this article for details.

Unfortunately, Prometheus may miss some increases for slow-changing counter when calculating rate() as shown in the original question above. The same applies to increase() calculations. See this issue, this comment and this article for details. Prometheus developers are going to fix these issues - see this design doc.

In the mean time try to use VictoriaMetrics when you need exact values for rate() and increase() functions over slow-changing counter (and distributed counter).

🌐
Prometheus
prometheus.io › docs › practices › histograms
Histograms and summaries | Prometheus
In all variants (even quantile-less ... the average of the observed values. To do so, you generally first take a rate over the desired duration and then divide the “rate of the sum” by the “rate of the count”....
🌐
Chronosphere
chronosphere.io › home › top 3 queries to add to your promql cheat sheet
Top 3 queries to add to your PromQL cheat sheet
April 2, 2025 - This level of dimensional insight ... sum() aggregator comes in: It sums the values of many time series into fewer series, but still preserves the dimensions that you want to see in the result....
🌐
Google Groups
groups.google.com › g › prometheus-users › c › 07PARWIGc30
How to rate a sum of the same counter from different machines?
October 21, 2018 - Rate may be emulated with offset. Try something like the following in Prometheus: sum(counter - counter offset 60s) without (instance) / 60
🌐
SigNoz
signoz.io › guides › how to measure total requests with prometheus - a time-based guide
How to Measure Total Requests with Prometheus - A Time-Based Guide | SigNoz
July 25, 2024 - To get the total requests across all instances, use the sum() function: ... This query aggregates the request counts across all monitored instances, giving you a comprehensive view of your system's traffic.
🌐
GitHub
github.com › VictoriaMetrics › VictoriaMetrics › issues › 1215
sum(rate(metricselector[rangevector])) over-represents short lived timeseries · Issue #1215 · VictoriaMetrics/VictoriaMetrics
April 14, 2021 - Concretely, consider : given 15 long lived healthy pods for a service with constant rates R, and a single new pod that is unhealthy which lives for a total of 1 minutes, generates 1000x the normal rate during that period. sum(rate(all16metrics[1m])) at the end of that bad pods lifetime will return 1015R in both the prometheus model and the VictoriaMetrics: the 15 pods that are stable and exist beyond the range vector contribute 15R ; the bad pod contributes an increase of 1000R * 60 seconds / 60.
Author: VictoriaMetrics
🌐
Last9
last9.io › blog › how-sum_over_time-works-in-prometheus
sum_over_time in Prometheus: Syntax and Pitfalls | Last9
July 25, 2025 - The sum_over_time() function in Prometheus gives you a way to aggregate counter resets, gauge fluctuations, and histogram samples across specific time windows. Instead of seeing point-in-time values, you get the cumulative total of all data ...
🌐
Google Groups
groups.google.com › g › prometheus-users › c › V7IbFb-w4ag
Simple increase - sum of the metrics in time range with dynamic metric count
September 22, 2023 - Speaking generally though, given ... the whole window period. This may give a non-integer result). You should then be able to sum() over that: sum(increase(foo[time]))....
🌐
Reddit
reddit.com › r/prometheusmonitoring › help with promql query (sum over time)
r/PrometheusMonitoring on Reddit: Help with PromQL query (sum over time)
July 17, 2024 -

Hello,

I have this graph monitoring the bandwidth of a VLAN on a switch every 1m using SNMP Exporter, but I also what to get the total/sum data over time, so if I select the last hour it will show x amount inbound and x amount outbound.

sum by(ifName) (irate(ifHCInOctets{instance=~"192.168.200.10", job="snmp_exporter", ifName=~".*(1001).*"}[1m])) * 8

My current graph:

I'd like to duplicate and create a stat panel show how much data in total has passed over what period I choose that's all.

For the metric I'm not sure whether to use bytes(SI) or bytes(IEC), but are similar if I change to either.

Not sure how to calculate this, but I have this created for the past 1 hour.

by copying the PromQL in Grafana and changing to a stat panel and then editing to use this:

Not sure if this is ok as I'm not sure how to calculate it all, maths was never my best subject.

Any help would be great.

I think something like is close: with sum_over_time

sum by(ifName) (sum_over_time(ifHCInOctets{instance=~"192.168.200.10", job="snmp_exporter", ifName=~".*(1001).*"}[1m])) * 8

but it comes back as 85.8 Pib when it should be 85.8 TB with my calculations.

EDIT

Observium:

What Grafana shows