fast-prometheus 0.3.0 → 0.3.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +27 -0
- data/README.md +1 -1
- data/lib/fast/prometheus/formats/protobuf.rb +20 -21
- data/lib/fast/prometheus/version.rb +1 -1
- metadata +3 -3
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 25cba069a74bd1f00499ff8d2c3a3feb84e9646b1447de704d2dff860dc5cea4
|
|
4
|
+
data.tar.gz: 533131b2461c719cb5525695a5abdc26b474bc6ce9fe35ba338855a698e887a3
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: c0a779b8563993d01400a7587852f2ec65c65621facd1bd3e9c44d39404e44eff0656a137a12f6a8da1b60b902d6bfe897b35ab82627064c8238f005171d0623
|
|
7
|
+
data.tar.gz: 8b9c2ce522dc9360c40f1779b7e4240370e5a7dbe4e6b333f9c39583bf2ba5a43805aa4b523763322ca62716b23c619047291beff28cb5b33abe88ad7874f96c
|
data/CHANGELOG.md
CHANGED
|
@@ -7,6 +7,33 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
7
7
|
|
|
8
8
|
## [Unreleased]
|
|
9
9
|
|
|
10
|
+
## [0.3.2] - 2026-09-19
|
|
11
|
+
|
|
12
|
+
### Changed
|
|
13
|
+
|
|
14
|
+
- `Formats::Protobuf.render` writes each family and each series straight
|
|
15
|
+
into the output behind a length prefix reserved first and filled in after
|
|
16
|
+
(`Fast::Protowire::Wire.reserve_length` / `close_length` /
|
|
17
|
+
`append_length_delimited_from`), instead of encoding the family header
|
|
18
|
+
to a String and copying every series out of a scratch buffer. Same
|
|
19
|
+
bytes; at 36,000 series x 12 labels a render went from 0.151 s and 29
|
|
20
|
+
objects to 0.144 s and 24, a protobuf scrape over HTTP from 0.162 s to
|
|
21
|
+
0.151 s (0.200 s to 0.192 s with gzip). Benchmarks page and README
|
|
22
|
+
updated.
|
|
23
|
+
|
|
24
|
+
## [0.3.1] - 2026-09-19
|
|
25
|
+
|
|
26
|
+
### Changed
|
|
27
|
+
|
|
28
|
+
- Requires [fast-protowire](https://github.com/jetpks/fast-protowire) `~> 0.2`,
|
|
29
|
+
whose encoder writes nested messages in place and allocates nothing per
|
|
30
|
+
message: the declared-message paths here (family headers, native
|
|
31
|
+
histograms, OTLP export) get that for free, and the `Wire` primitives the
|
|
32
|
+
per-series renderer uses append text as bytes with no binary copy on
|
|
33
|
+
Ruby 3.4+.
|
|
34
|
+
- Benchmarks re-taken on the new dependency and republished on the
|
|
35
|
+
benchmarks page and in the README.
|
|
36
|
+
|
|
10
37
|
## [0.3.0] - 2026-09-18
|
|
11
38
|
|
|
12
39
|
### Changed
|
data/README.md
CHANGED
|
@@ -94,7 +94,7 @@ Single process, locked, thread-safe by default (`benchmark-ips` and allocation
|
|
|
94
94
|
comparisons against `prometheus-client` and `google-protobuf`; see
|
|
95
95
|
[the benchmarks page](docs/explanation/benchmarks.md) for the full runs and conditions):
|
|
96
96
|
|
|
97
|
-
- A protobuf scrape of 36,000 series renders in **
|
|
97
|
+
- A protobuf scrape of 36,000 series renders in **24 objects**, where the
|
|
98
98
|
`google-protobuf` encoder needed 3.5 million Ruby objects and 504k native arenas, and
|
|
99
99
|
in a hundredth of the GC time; taking the snapshot it reads is 1 ms and one Hash per metric
|
|
100
100
|
- The text renderer allocates **66x fewer objects** than prometheus-client's formatter
|
|
@@ -12,10 +12,10 @@ module Fast
|
|
|
12
12
|
# Each family's header is a declared Proto::MetricFamily; the series
|
|
13
13
|
# under it are written straight to the wire with Fast::Protowire::Wire,
|
|
14
14
|
# no LabelPair/Metric/Counter objects, because a scrape's series count
|
|
15
|
-
# is the one thing here that is large.
|
|
16
|
-
#
|
|
17
|
-
#
|
|
18
|
-
#
|
|
15
|
+
# is the one thing here that is large. Each series' bytes are written
|
|
16
|
+
# straight into the output behind a length prefix filled in after them,
|
|
17
|
+
# so rendering allocates nothing per series and copies nothing. Native
|
|
18
|
+
# histograms, few and irregular,
|
|
19
19
|
# still go through Proto::Histogram. Bytes are identical to what the
|
|
20
20
|
# declared classes (and google-protobuf) produce; the tests check.
|
|
21
21
|
module Protobuf
|
|
@@ -64,32 +64,31 @@ module Fast
|
|
|
64
64
|
DOUBLE_SIZE = 9
|
|
65
65
|
private_constant :DOUBLE_SIZE
|
|
66
66
|
|
|
67
|
-
# One varint-length-prefixed MetricFamily frame per metric
|
|
67
|
+
# One varint-length-prefixed MetricFamily frame per metric, each
|
|
68
|
+
# written straight into the output behind a length prefix reserved
|
|
69
|
+
# first and filled in after (see Fast::Protowire::Wire).
|
|
68
70
|
def self.render(snapshot)
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
Fast::Protowire::Wire.
|
|
73
|
-
buffer << family
|
|
71
|
+
snapshot.metrics.each_with_object(String.new) do |ms, out|
|
|
72
|
+
start = Fast::Protowire::Wire.reserve_length(out)
|
|
73
|
+
append_metric_family(out, ms)
|
|
74
|
+
Fast::Protowire::Wire.close_length(out, start)
|
|
74
75
|
end
|
|
75
76
|
end
|
|
76
77
|
|
|
77
78
|
# A family's bytes are its header (name, help, type) followed by one
|
|
78
|
-
# metric entry per series,
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
79
|
+
# metric entry per series, in place. A family's series are alike, so
|
|
80
|
+
# the entry prefix width carries from one to the next.
|
|
81
|
+
private_class_method def self.append_metric_family(out, metric_snapshot)
|
|
82
|
+
Proto::MetricFamily.new(name: metric_snapshot.name.name, help: metric_snapshot.docstring,
|
|
83
|
+
type: TYPE_MAP.fetch(metric_snapshot.type)).encode(out)
|
|
82
84
|
type = metric_snapshot.type
|
|
83
85
|
names = metric_snapshot.label_names
|
|
84
|
-
|
|
86
|
+
width = 1
|
|
85
87
|
metric_snapshot.series.each_pair do |values, value|
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
Fast::Protowire::Wire.append_varint(buffer, scratch.bytesize)
|
|
90
|
-
buffer << scratch
|
|
88
|
+
width = Fast::Protowire::Wire.append_length_delimited_from(out, FAMILY_METRIC, width) do |buffer|
|
|
89
|
+
append_metric(buffer, names, values, value, type)
|
|
90
|
+
end
|
|
91
91
|
end
|
|
92
|
-
buffer
|
|
93
92
|
end
|
|
94
93
|
|
|
95
94
|
# Metric: labels (1) then the one value field for the type, in
|
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: fast-prometheus
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.3.
|
|
4
|
+
version: 0.3.2
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Eric Jacobs
|
|
@@ -71,14 +71,14 @@ dependencies:
|
|
|
71
71
|
requirements:
|
|
72
72
|
- - "~>"
|
|
73
73
|
- !ruby/object:Gem::Version
|
|
74
|
-
version: '0.
|
|
74
|
+
version: '0.2'
|
|
75
75
|
type: :runtime
|
|
76
76
|
prerelease: false
|
|
77
77
|
version_requirements: !ruby/object:Gem::Requirement
|
|
78
78
|
requirements:
|
|
79
79
|
- - "~>"
|
|
80
80
|
- !ruby/object:Gem::Version
|
|
81
|
-
version: '0.
|
|
81
|
+
version: '0.2'
|
|
82
82
|
- !ruby/object:Gem::Dependency
|
|
83
83
|
name: console
|
|
84
84
|
requirement: !ruby/object:Gem::Requirement
|