Skip to content

Commit

Permalink
Change timestamp data type to unixnano in Metrics Protobuf definitions
Browse files Browse the repository at this point in the history
This change applies the refinement approach that is already performed on Traces
Protobuf definitions as part of open-telemetry/oteps#59 and
which proved to yield significant performance improvements.

I replaced google.protobuf.Timestamp by int64 time in unix epoch nanoseconds.

Simple benchmark in Go demonstrates the following improvement of encoding and decoding
compared to the current state:

```
===== Encoded sizes
Encoding                       Uncompressed  Improved        Compressed  Improved
Baseline/MetricOne              20000 bytes  [1.000], gziped 1506 bytes  [1.000]
Proposed/MetricOne              18250 bytes  [1.096], gziped 1433 bytes  [1.051]

Encoding                       Uncompressed  Improved        Compressed  Improved
Baseline/MetricSeries           51797 bytes  [1.000], gziped 6455 bytes  [1.000]
Proposed/MetricSeries           43047 bytes  [1.203], gziped 6093 bytes  [1.059]

goos: darwin
goarch: amd64
pkg: github.com/tigrannajaryan/exp-otelproto/encodings
BenchmarkEncode/Baseline/MetricOne-8         	      30	 186998840 ns/op
BenchmarkEncode/Proposed/MetricOne-8         	      36	 166668705 ns/op

BenchmarkEncode/Baseline/MetricSeries-8      	       8	 632391842 ns/op
BenchmarkEncode/Proposed/MetricSeries-8      	      10	 537384515 ns/op

BenchmarkDecode/Baseline/MetricOne-8         	      16	 348156010 ns/op	171896049 B/op	 4974000 allocs/op
BenchmarkDecode/Proposed/MetricOne-8         	      19	 314727259 ns/op	155096036 B/op	 4624000 allocs/op

BenchmarkDecode/Baseline/MetricSeries-8      	       5	1013035422 ns/op	440696048 B/op	11874000 allocs/op
BenchmarkDecode/Proposed/MetricSeries-8      	       6	 846887981 ns/op	356696040 B/op	10124000 allocs/op
```

It is 10-15% faster and is 10-20% smaller on the wire and in memory.

Benchmarks encode and decode 500 batches of 2 metrics: one int64 Gauge with 5 time series
and one Histogram of doubles with 1 time series and single bucket. Each time series for
both metrics contains either 1 data point (MetricOne) or 5 data points (MetricSeries).
Both metrics have 2 labels.

Benchmark source code is available at:
https://github.com/tigrannajaryan/exp-otelproto/blob/master/encodings/encoding_test.go
  • Loading branch information
Tigran Najaryan committed Oct 30, 2019
1 parent 7b88843 commit 704ee70
Showing 1 changed file with 21 additions and 11 deletions.
32 changes: 21 additions & 11 deletions opentelemetry/proto/metrics/v1/metrics.proto
Original file line number Diff line number Diff line change
Expand Up @@ -124,15 +124,24 @@ message LabelValue {

// A timestamped measurement.
message Point {
// Must be present for counter/cumulative metrics. The time when the
// cumulative value was reset to zero. The cumulative value is over the time
// interval (start_timestamp, timestamp]. If not specified, the backend can
// use the previous recorded value.
google.protobuf.Timestamp start_timestamp = 1;

// The moment when this point was recorded.
// If not specified, the timestamp will be decided by the backend.
google.protobuf.Timestamp timestamp = 2;
// start_time_unixnano is the time when the cumulative value was reset to zero.
// This is used for Counter type only. For Gauge the value is not specified and
// defaults to 0.
//
// The cumulative value is over the time interval [start_time_unixnano, timestamp_unixnano].
// Value is UNIX Epoch time in nanoseconds since 00:00:00 UTC on 1 January 1970.
//
// Value of 0 indicates that the start_time is the same as that of the previous
// data point in this timeseries. When creating timeseries of this type it is recommended
// to omit this value if the start_time does not change, since it results in more
// compact encoding on the wire.
// If the value of 0 occurs for the first data point in the timeseries it means that
// the timestamp is unspecified. In that case the timestamp may be decided by the backend.
int64 start_time_unixnano = 1;

// timestamp_unixnano is the moment when this value was recorded.
// Value is UNIX Epoch time in nanoseconds since 00:00:00 UTC on 1 January 1970.
sfixed64 timestamp_unixnano = 2;

// The actual point value.
oneof value {
Expand Down Expand Up @@ -204,8 +213,9 @@ message HistogramValue {
// belongs to.
double value = 1;

// The observation (sampling) time of the above value.
google.protobuf.Timestamp timestamp = 2;
// timestamp_unixnano is the moment when this exemplar was recorded.
// Value is UNIX Epoch time in nanoseconds since 00:00:00 UTC on 1 January 1970.
sfixed64 timestamp_unixnano = 2;

// Contextual information about the example value.
map<string, string> attachments = 3;
Expand Down

0 comments on commit 704ee70

Please sign in to comment.