3 releases

new 0.0.21 Apr 8, 2024
0.0.20 Apr 8, 2024
0.0.19 Apr 8, 2024

#5 in #better

Download history

68 downloads per month

MIT/Apache

185KB
2.5K SLoC

measured

A better metrics crate

docs

Benchmark results

Counters

Increment a counter. Keyed with 2 labels and 18 distinct label groupings (6 * 3). Runs concurrently among multiple threads. Medium contention.

Linux Ryzen 9 7950x (32 Threads)

Timer precision: 41 ns
counters              fastest       │ slowest       │ median        │ mean          │ samples │ iters
├─ measured           60.55 ns      │ 190.3 ns      │ 147.5 ns      │ 149.2 ns      │ 50450400000
├─ measured_sparse    380.4 ns      │ 538.5 ns      │ 497.9 ns      │ 495.6 ns      │ 50450400000
├─ metrics            1.06 µs       │ 1.327 µs      │ 1.233 µs      │ 1.228 µs      │ 50450400000
├─ prometheus         4.332 µs      │ 4.595 µs      │ 4.543 µs      │ 4.532 µs      │ 50450400000
╰─ prometheus_client  4.074 µs      │ 4.391 µs      │ 4.332 µs      │ 4.323 µs      │ 50450400000

Macbook Pro M2 Max (12 Threads)

Timer precision: 41 ns
counters              fastest       │ slowest       │ median        │ mean          │ samples │ iters
├─ measured           79.55 ns      │ 243.9 ns      │ 154.7 ns      │ 154.7 ns      │ 50450400000
├─ measured_sparse    396.3 ns      │ 551.6 ns      │ 488.4 ns      │ 486.6 ns      │ 50450400000
├─ metrics            873.9 ns      │ 1.411 µs      │ 1.121 µs      │ 1.126 µs      │ 50450400000
├─ prometheus         3.222 µs      │ 4.58 µs       │ 4.361 µs      │ 4.281 µs      │ 50450400000
╰─ prometheus_client  2.614 µs      │ 4.061 µs      │ 3.885 µs      │ 3.811 µs      │ 50450400000

Histograms

  • fixed_cardinality - Observe a value into a histogram. Keyed with 2 labels and 18 distinct label groupings (6 * 3). Runs concurrently among multiple threads. Medium contention.
  • no_cardinality - Start a timer and immediately stop it, record that time into a single histogram (no labels). Runs concurrently among multiple threads. Very high contention.

Linux Ryzen 9 7950x (32 Threads)

Timer precision: 2.36 µs
histograms               fastest       │ slowest       │ median        │ mean          │ samples │ iters
├─ fixed_cardinality                   │               │               │               │         │
│  ├─ measured           296 ns        │ 464.6 ns      │ 380.6 ns      │ 381.1 ns      │ 51251200000
│  ├─ measured_sparse    457.1 ns      │ 621.2 ns      │ 523.4 ns      │ 522 ns        │ 51251200000
│  ├─ metrics            4.146 µs      │ 4.867 µs      │ 4.314 µs      │ 4.346 µs      │ 51251200000
│  ├─ prometheus         1.43 µs       │ 1.872 µs      │ 1.525 µs      │ 1.546 µs      │ 51251200000
│  ╰─ prometheus_client  2.196 µs      │ 2.753 µs      │ 2.551 µs      │ 2.549 µs      │ 51251200000
╰─ no_cardinality                      │               │               │               │         │
   ├─ measured           7.211 µs      │ 12.88 µs      │ 7.283 µs      │ 7.685 µs      │ 51251200000
   ├─ metrics            11.68 µs      │ 12.67 µs      │ 11.81 µs      │ 11.89 µs      │ 51251200000
   ├─ prometheus         7.202 µs      │ 8.017 µs      │ 7.322 µs      │ 7.362 µs      │ 51251200000
   ╰─ prometheus_client  109.5 µs      │ 113.1 µs      │ 111.4 µs      │ 111.4 µs      │ 51251200000

Macbook Pro M2 Max (12 Threads)

Timer precision: 41 ns
histograms               fastest       │ slowest       │ median        │ mean          │ samples │ iters
├─ fixed_cardinality                   │               │               │               │         │
│  ├─ measured           325.1 ns      │ 433.4 ns      │ 417.7 ns      │ 414.4 ns      │ 50450400000
│  ├─ measured_sparse    503.3 ns      │ 690 ns        │ 580.1 ns      │ 579.6 ns      │ 50450400000
│  ├─ metrics            1.147 µs      │ 1.462 µs      │ 1.275 µs      │ 1.275 µs      │ 50450400000
│  ├─ prometheus         4.055 µs      │ 4.297 µs      │ 4.247 µs      │ 4.235 µs      │ 50450400000
│  ╰─ prometheus_client  3.913 µs      │ 4.186 µs      │ 4.14 µs       │ 4.129 µs      │ 50450400000
╰─ no_cardinality                      │               │               │               │         │
   ├─ measured           4.829 µs      │ 5.187 µs      │ 5.133 µs      │ 5.122 µs      │ 50450400000
   ├─ metrics            5.753 µs      │ 7.257 µs      │ 6.971 µs      │ 6.937 µs      │ 50450400000
   ├─ prometheus         4.639 µs      │ 5.309 µs      │ 5.125 µs      │ 5.108 µs      │ 50450400000
   ╰─ prometheus_client  2.092 µs      │ 2.471 µs      │ 2.352 µs      │ 2.344 µs      │ 50450400000

Memory

This benchmark tests a high-cardinality scenario. Each iteration inserts a unique label group into a Counter. Each benchmark uses the same deterministic random set of labels. This test runs single-threaded.

The first block of benchmark outputs runs a single iteration per sample, so the timer imprecision becomes a limitation. The second block removes the memory tracking and runs 100 iterators per sample. This makes the fast/mean times more accurate but makes latency spikes less accurate as they end up diluted.

  • measured sweeps the floor in this benchmark.
  • prometheus_client is fast and uses quite little memory, but reallocs are extremely expensive and will introduce latency spikes.
  • metrics/prometheus both use lots of memory, with the majority of inserts needing several allocations.

Linux Ryzen 9 7950x (32 Threads)

Timer precision: 2.39 µs
memory                fastest       │ slowest       │ median        │ mean          │ samples │ iters
├─ measured           2.089 µs      │ 777.3 µs      │ 2.709 µs      │ 2.811 µs      │ 50000005000000
│                     alloc:        │               │               │               │         │
│                       0100.001         │         │
│                       0 B         │ 1.638 MB0 B           │ 132.5 B       │         │
│                     dealloc:      │               │               │               │         │
│                       0100             │         │
│                       0 B         │ 819.2 KB0 B           │ 62.92 B       │         │
├─ metrics            2.129 µs      │ 18.05 ms      │ 2.889 µs      │ 3.228 µs      │ 50000005000000
│                     alloc:        │               │               │               │         │
│                       7856.635         │         │
│                       394 B       │ 21.23 MB289 B         │ 648.1 B       │         │
│                     dealloc:      │               │               │               │         │
│                       4544             │         │
│                       205 B       │ 10.61 MB203 B         │ 341.8 B       │         │
├─ prometheus         2.119 µs      │ 41.79 ms      │ 3.229 µs      │ 3.357 µs      │ 50000005000000
│                     alloc:        │               │               │               │         │
│                       20212018.17         │         │
│                       821 B       │ 142.6 MB832 B         │ 810.5 B       │         │
│                     dealloc:      │               │               │               │         │
│                       6765.453         │         │
│                       355 B       │ 71.3 MB355 B         │ 351.1 B       │         │
│                     grow:         │               │               │               │         │
│                       3332.726         │         │
│                       20 B        │ 20 B          │ 20 B          │ 18.17 B       │         │
╰─ prometheus_client  2.109 µs      │ 452.1 ms      │ 2.759 µs      │ 2.979 µs      │ 50000005000000
                      alloc:        │               │               │               │         │
                        2321.817         │         │
                        41 B        │ 478.1 MB41 B          │ 225.3 B       │         │
                      dealloc:      │               │               │               │         │
                        1211             │         │
                        17 B        │ 239 MB19 B          │ 112 B         │         │
Timer precision: 2.26 µs
memory                fastest       │ slowest       │ median        │ mean          │ samples │ iters
├─ measured           81.44 ns      │ 20.1 µs       │ 271.6 ns      │ 305.1 ns      │ 500005000000
├─ metrics            226.2 ns      │ 177 µs        │ 416.4 ns      │ 635.6 ns      │ 500005000000
├─ prometheus         445.8 ns      │ 427.5 µs      │ 724.5 ns      │ 688.4 ns      │ 500005000000
╰─ prometheus_client  113.1 ns      │ 4.231 ms      │ 260.4 ns      │ 416.8 ns      │ 500005000000

Macbook Pro M2 Max (12 Threads)

Timer precision: 41 ns
memory                fastest       │ slowest       │ median        │ mean          │ samples │ iters
├─ measured           41.58 ns      │ 1.521 ms      │ 457.5 ns      │ 578.2 ns      │ 50000005000000
│                     alloc:        │               │               │               │         │
│                       0100             │         │
│                       0 B         │ 3.276 MB0 B           │ 132.5 B       │         │
│                     dealloc:      │               │               │               │         │
│                       0100             │         │
│                       0 B         │ 1.638 MB0 B           │ 62.91 B       │         │
├─ metrics            249.5 ns      │ 100.6 ms      │ 624.5 ns      │ 1.148 µs      │ 50000005000000
│                     alloc:        │               │               │               │         │
│                       3876.635         │         │
│                       183 B       │ 42.46 MB388 B         │ 648.1 B       │         │
│                     dealloc:      │               │               │               │         │
│                       4544             │         │
│                       191 B       │ 21.23 MB202 B         │ 341.8 B       │         │
├─ prometheus         124.5 ns      │ 86.45 ms      │ 1.04 µs       │ 1.228 µs      │ 50000005000000
│                     alloc:        │               │               │               │         │
│                       0212018.17         │         │
│                       0 B         │ 142.6 MB823 B         │ 810.5 B       │         │
│                     dealloc:      │               │               │               │         │
│                       0765.453         │         │
│                       0 B         │ 71.3 MB355 B         │ 351.1 B       │         │
│                     grow:         │               │               │               │         │
│                       0332.726         │         │
│                       0 B         │ 20 B          │ 20 B          │ 18.17 B       │         │
╰─ prometheus_client  40.58 ns      │ 437.2 ms      │ 374.5 ns      │ 587.3 ns      │ 50000005000000
                      alloc:        │               │               │               │         │
                        0321.817         │         │
                        0 B         │ 478.1 MB37 B          │ 225.3 B       │         │
                      dealloc:      │               │               │               │         │
                        1211             │         │
                        16 B        │ 239 MB16 B          │ 112 B         │         │
Timer precision: 41 ns
memory                fastest       │ slowest       │ median        │ mean          │ samples │ iters
├─ measured           97.5 ns       │ 26.6 µs       │ 327.9 ns      │ 370.8 ns      │ 500005000000
├─ metrics            427.5 ns      │ 928.9 µs      │ 726.2 ns      │ 1.095 µs      │ 500005000000
├─ prometheus         752.9 ns      │ 768.3 µs      │ 979.5 ns      │ 1.06 µs       │ 500005000000
╰─ prometheus_client  186.2 ns      │ 3.909 ms      │ 387 ns        │ 552 ns        │ 500005000000

Encoding

Encode a counter family into a prometheus text format. With the extra dimension of number of counters in the counter family.

Linux Ryzen 9 7950x (32 Threads)

Timer precision: 2.24 µs
encoding              fastest       │ slowest       │ median        │ mean          │ samples │ iters
├─ measured                         │               │               │               │         │
│  ├─ 100             2.945 µs      │ 5.269 µs      │ 3.119 µs      │ 3.195 µs      │ 1001000
│  ├─ 1000            24.12 µs      │ 39.75 µs      │ 25.02 µs      │ 25.43 µs      │ 1001000
│  ├─ 10000           247.8 µs      │ 411.6 µs      │ 257.3 µs      │ 263.4 µs      │ 1001000
│  ╰─ 100000          2.486 ms      │ 3.594 ms      │ 2.566 ms      │ 2.604 ms      │ 1001000
├─ metrics                          │               │               │               │         │
│  ├─ 100             40.14 µs      │ 44.47 µs      │ 40.64 µs      │ 40.91 µs      │ 1001000
│  ├─ 1000            395.4 µs      │ 404.2 µs      │ 397.7 µs      │ 398 µs        │ 1001000
│  ├─ 10000           4.084 ms      │ 4.741 ms      │ 4.298 ms      │ 4.281 ms      │ 1001000
│  ╰─ 100000          63.26 ms      │ 77.02 ms      │ 65.06 ms      │ 65.96 ms      │ 1001000
├─ prometheus                       │               │               │               │         │
│  ├─ 100             22.17 µs      │ 24.76 µs      │ 22.5 µs       │ 22.65 µs      │ 1001000
│  ├─ 1000            259.1 µs      │ 270 µs        │ 262.4 µs      │ 262.5 µs      │ 1001000
│  ├─ 10000           3.542 ms      │ 3.664 ms      │ 3.556 ms      │ 3.558 ms      │ 1001000
│  ╰─ 100000          62.62 ms      │ 67.59 ms      │ 65.59 ms      │ 65.49 ms      │ 1001000
╰─ prometheus_client                │               │               │               │         │
   ├─ 100             4.992 µs      │ 7.61 µs       │ 5.508 µs      │ 5.515 µs      │ 1001000
   ├─ 1000            50.56 µs      │ 57.72 µs      │ 53.1 µs       │ 53.11 µs      │ 1001000
   ├─ 10000           515.1 µs      │ 532.2 µs      │ 522.3 µs      │ 522.7 µs      │ 1001000
   ╰─ 100000          5.184 ms      │ 5.347 ms      │ 5.265 ms      │ 5.261 ms      │ 1001000

Macbook Pro M2 Max (12 Threads)

Timer precision: 41 ns
encoding              fastest       │ slowest       │ median        │ mean          │ samples │ iters
├─ measured                         │               │               │               │         │
│  ├─ 100             4.066 µs      │ 5.062 µs      │ 4.132 µs      │ 4.172 µs      │ 1001000
│  ├─ 1000            41.52 µs      │ 51.17 µs      │ 42.57 µs      │ 43 µs         │ 1001000
│  ├─ 10000           403.8 µs      │ 542.9 µs      │ 423.6 µs      │ 424.2 µs      │ 1001000
│  ╰─ 100000          4.221 ms      │ 4.76 ms       │ 4.393 ms      │ 4.399 ms      │ 1001000
├─ metrics                          │               │               │               │         │
│  ├─ 100             61.47 µs      │ 66.87 µs      │ 61.98 µs      │ 62.13 µs      │ 1001000
│  ├─ 1000            698.2 µs      │ 917.1 µs      │ 772.3 µs      │ 779.3 µs      │ 1001000
│  ├─ 10000           7.47 ms       │ 8.927 ms      │ 8.132 ms      │ 8.176 ms      │ 1001000
│  ╰─ 100000          161.5 ms      │ 214.8 ms      │ 197 ms        │ 196.8 ms      │ 1001000
├─ prometheus                       │               │               │               │         │
│  ├─ 100             27.76 µs      │ 33.16 µs      │ 28.62 µs      │ 28.84 µs      │ 1001000
│  ├─ 1000            460.8 µs      │ 828.3 µs      │ 469.2 µs      │ 480.3 µs      │ 1001000
│  ├─ 10000           4.802 ms      │ 6.212 ms      │ 5.112 ms      │ 5.159 ms      │ 1001000
│  ╰─ 100000          72.99 ms      │ 91.93 ms      │ 78.84 ms      │ 79.97 ms      │ 1001000
╰─ prometheus_client                │               │               │               │         │
   ├─ 100             7.145 µs      │ 9.07 µs       │ 7.191 µs      │ 7.381 µs      │ 1001000
   ├─ 1000            73.57 µs      │ 80.57 µs      │ 75.45 µs      │ 75.64 µs      │ 1001000
   ├─ 10000           732.4 µs      │ 771 µs        │ 740 µs        │ 742.7 µs      │ 1001000
   ╰─ 100000          7.441 ms      │ 8.54 ms       │ 7.613 ms      │ 7.683 ms      │ 1001000

Dependencies

~5–16MB
~186K SLoC