aboutsummaryrefslogtreecommitdiffstats
path: root/library/cpp/monlib/metrics/metric_registry_ut.cpp
diff options
context:
space:
mode:
authorDevtools Arcadia <arcadia-devtools@yandex-team.ru>2022-02-07 18:08:42 +0300
committerDevtools Arcadia <arcadia-devtools@mous.vla.yp-c.yandex.net>2022-02-07 18:08:42 +0300
commit1110808a9d39d4b808aef724c861a2e1a38d2a69 (patch)
treee26c9fed0de5d9873cce7e00bc214573dc2195b7 /library/cpp/monlib/metrics/metric_registry_ut.cpp
downloadydb-1110808a9d39d4b808aef724c861a2e1a38d2a69.tar.gz
intermediate changes
ref:cde9a383711a11544ce7e107a78147fb96cc4029
Diffstat (limited to 'library/cpp/monlib/metrics/metric_registry_ut.cpp')
-rw-r--r--library/cpp/monlib/metrics/metric_registry_ut.cpp302
1 files changed, 302 insertions, 0 deletions
diff --git a/library/cpp/monlib/metrics/metric_registry_ut.cpp b/library/cpp/monlib/metrics/metric_registry_ut.cpp
new file mode 100644
index 0000000000..afcbcd6801
--- /dev/null
+++ b/library/cpp/monlib/metrics/metric_registry_ut.cpp
@@ -0,0 +1,302 @@
+#include "metric_registry.h"
+
+#include <library/cpp/monlib/encode/protobuf/protobuf.h>
+#include <library/cpp/monlib/encode/json/json.h>
+#include <library/cpp/resource/resource.h>
+
+#include <library/cpp/testing/unittest/registar.h>
+
+#include <util/stream/str.h>
+
+using namespace NMonitoring;
+
+template<>
+void Out<NMonitoring::NProto::TSingleSample::ValueCase>(IOutputStream& os, NMonitoring::NProto::TSingleSample::ValueCase val) {
+ switch (val) {
+ case NMonitoring::NProto::TSingleSample::ValueCase::kInt64:
+ os << "Int64";
+ break;
+ case NMonitoring::NProto::TSingleSample::ValueCase::kUint64:
+ os << "Uint64";
+ break;
+ case NMonitoring::NProto::TSingleSample::ValueCase::kHistogram:
+ os << "Histogram";
+ break;
+ case NMonitoring::NProto::TSingleSample::ValueCase::kFloat64:
+ os << "Float64";
+ break;
+ case NMonitoring::NProto::TSingleSample::ValueCase::kSummaryDouble:
+ os << "DSummary";
+ break;
+ case NMonitoring::NProto::TSingleSample::ValueCase::kLogHistogram:
+ os << "LogHistogram";
+ break;
+ case NMonitoring::NProto::TSingleSample::ValueCase::VALUE_NOT_SET:
+ os << "NOT SET";
+ break;
+ }
+}
+
+Y_UNIT_TEST_SUITE(TMetricRegistryTest) {
+ Y_UNIT_TEST(Gauge) {
+ TMetricRegistry registry(TLabels{{"common", "label"}});
+ TGauge* g = registry.Gauge({{"my", "gauge"}});
+
+ UNIT_ASSERT_DOUBLES_EQUAL(g->Get(), 0.0, 1E-6);
+ g->Set(12.34);
+ UNIT_ASSERT_DOUBLES_EQUAL(g->Get(), 12.34, 1E-6);
+
+ double val;
+
+ val = g->Add(1.2);
+ UNIT_ASSERT_DOUBLES_EQUAL(g->Get(), 13.54, 1E-6);
+ UNIT_ASSERT_DOUBLES_EQUAL(g->Get(), val, 1E-6);
+
+ val = g->Add(-3.47);
+ UNIT_ASSERT_DOUBLES_EQUAL(g->Get(), 10.07, 1E-6);
+ UNIT_ASSERT_DOUBLES_EQUAL(g->Get(), val, 1E-6);
+ }
+
+ Y_UNIT_TEST(LazyGauge) {
+ TMetricRegistry registry(TLabels{{"common", "label"}});
+ double val = 0.0;
+ TLazyGauge* g = registry.LazyGauge({{"my", "lazyGauge"}}, [&val](){return val;});
+
+ UNIT_ASSERT_DOUBLES_EQUAL(g->Get(), 0.0, 1E-6);
+ val = 12.34;
+ UNIT_ASSERT_DOUBLES_EQUAL(g->Get(), 12.34, 1E-6);
+
+ val += 1.2;
+ UNIT_ASSERT_DOUBLES_EQUAL(g->Get(), 13.54, 1E-6);
+ UNIT_ASSERT_DOUBLES_EQUAL(g->Get(), val, 1E-6);
+
+ val += -3.47;
+ UNIT_ASSERT_DOUBLES_EQUAL(g->Get(), 10.07, 1E-6);
+ UNIT_ASSERT_DOUBLES_EQUAL(g->Get(), val, 1E-6);
+ }
+
+ Y_UNIT_TEST(IntGauge) {
+ TMetricRegistry registry(TLabels{{"common", "label"}});
+ TIntGauge* g = registry.IntGauge({{"my", "gauge"}});
+
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), 0);
+
+ i64 val;
+
+ val = g->Inc();
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), 1);
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), val);
+
+ val = g->Dec();
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), 0);
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), val);
+
+ val = g->Add(1);
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), 1);
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), val);
+
+ val = g->Add(2);
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), 3);
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), val);
+
+ val = g->Add(-5);
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), -2);
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), val);
+ }
+
+ Y_UNIT_TEST(LazyIntGauge) {
+ TMetricRegistry registry(TLabels{{"common", "label"}});
+ i64 val = 0;
+ TLazyIntGauge* g = registry.LazyIntGauge({{"my", "gauge"}}, [&val](){return val;});
+
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), 0);
+ val += 1;
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), 1);
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), val);
+
+ val -= 1;
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), 0);
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), val);
+
+ val = 42;
+ UNIT_ASSERT_VALUES_EQUAL(g->Get(), val);
+ }
+
+ Y_UNIT_TEST(Counter) {
+ TMetricRegistry registry(TLabels{{"common", "label"}});
+ TCounter* c = registry.Counter({{"my", "counter"}});
+
+ UNIT_ASSERT_VALUES_EQUAL(c->Get(), 0);
+ UNIT_ASSERT_VALUES_EQUAL(c->Inc(), 1);
+ UNIT_ASSERT_VALUES_EQUAL(c->Get(), 1);
+ UNIT_ASSERT_VALUES_EQUAL(c->Add(10), 11);
+ UNIT_ASSERT_VALUES_EQUAL(c->Get(), 11);
+ }
+
+ Y_UNIT_TEST(LazyCounter) {
+ TMetricRegistry registry(TLabels{{"common", "label"}});
+ ui64 val = 0;
+
+ TLazyCounter* c = registry.LazyCounter({{"my", "counter"}}, [&val](){return val;});
+
+ UNIT_ASSERT_VALUES_EQUAL(c->Get(), 0);
+ val = 42;
+ UNIT_ASSERT_VALUES_EQUAL(c->Get(), 42);
+ }
+
+ Y_UNIT_TEST(LazyRate) {
+ TMetricRegistry registry(TLabels{{"common", "label"}});
+ ui64 val = 0;
+
+ TLazyRate* r = registry.LazyRate({{"my", "rate"}}, [&val](){return val;});
+
+ UNIT_ASSERT_VALUES_EQUAL(r->Get(), 0);
+ val = 42;
+ UNIT_ASSERT_VALUES_EQUAL(r->Get(), 42);
+ }
+
+ Y_UNIT_TEST(DoubleCounter) {
+ TMetricRegistry registry(TLabels{{"common", "label"}});
+
+ TCounter* c = registry.Counter({{"my", "counter"}});
+ UNIT_ASSERT_VALUES_EQUAL(c->Get(), 0);
+ c->Add(10);
+
+ c = registry.Counter({{"my", "counter"}});
+ UNIT_ASSERT_VALUES_EQUAL(c->Get(), 10);
+ }
+
+ Y_UNIT_TEST(Sample) {
+ TMetricRegistry registry(TLabels{{"common", "label"}});
+
+ TGauge* g = registry.Gauge({{"my", "gauge"}});
+ g->Set(12.34);
+
+ TCounter* c = registry.Counter({{"my", "counter"}});
+ c->Add(10);
+
+ NProto::TSingleSamplesList samples;
+ auto encoder = EncoderProtobuf(&samples);
+ auto now = TInstant::Now();
+ registry.Accept(now, encoder.Get());
+
+ UNIT_ASSERT_VALUES_EQUAL(samples.SamplesSize(), 2);
+ UNIT_ASSERT_VALUES_EQUAL(samples.CommonLabelsSize(), 1);
+ {
+ const NProto::TLabel& label = samples.GetCommonLabels(0);
+ UNIT_ASSERT_STRINGS_EQUAL(label.GetName(), "common");
+ UNIT_ASSERT_STRINGS_EQUAL(label.GetValue(), "label");
+ }
+
+
+ for (const NProto::TSingleSample& sample : samples.GetSamples()) {
+ UNIT_ASSERT_VALUES_EQUAL(sample.LabelsSize(), 1);
+ UNIT_ASSERT_VALUES_EQUAL(sample.GetTime(), now.MilliSeconds());
+
+ if (sample.GetMetricType() == NProto::GAUGE) {
+ UNIT_ASSERT_VALUES_EQUAL(sample.GetValueCase(), NProto::TSingleSample::kFloat64);
+ UNIT_ASSERT_DOUBLES_EQUAL(sample.GetFloat64(), 12.34, 1E-6);
+
+ const NProto::TLabel& label = sample.GetLabels(0);
+ UNIT_ASSERT_STRINGS_EQUAL(label.GetName(), "my");
+ UNIT_ASSERT_STRINGS_EQUAL(label.GetValue(), "gauge");
+ } else if (sample.GetMetricType() == NProto::COUNTER) {
+ UNIT_ASSERT_VALUES_EQUAL(sample.GetValueCase(), NProto::TSingleSample::kUint64);
+ UNIT_ASSERT_VALUES_EQUAL(sample.GetUint64(), 10);
+
+ const NProto::TLabel& label = sample.GetLabels(0);
+ UNIT_ASSERT_STRINGS_EQUAL(label.GetName(), "my");
+ UNIT_ASSERT_STRINGS_EQUAL(label.GetValue(), "counter");
+ } else {
+ UNIT_FAIL("unexpected sample type");
+ }
+ }
+ }
+
+ Y_UNIT_TEST(Histograms) {
+ TMetricRegistry registry(TLabels{{"common", "label"}});
+
+ THistogram* h1 = registry.HistogramCounter(
+ {{"sensor", "readTimeMillis"}},
+ ExponentialHistogram(5, 2));
+
+ THistogram* h2 = registry.HistogramRate(
+ {{"sensor", "writeTimeMillis"}},
+ ExplicitHistogram({1, 5, 15, 20, 25}));
+
+ for (i64 i = 0; i < 100; i++) {
+ h1->Record(i);
+ h2->Record(i);
+ }
+
+ TStringStream ss;
+ {
+ auto encoder = EncoderJson(&ss, 2);
+ registry.Accept(TInstant::Zero(), encoder.Get());
+ }
+ ss << '\n';
+
+ UNIT_ASSERT_NO_DIFF(ss.Str(), NResource::Find("/histograms.json"));
+ }
+
+ Y_UNIT_TEST(StreamingEncoderTest) {
+ const TString expected {
+ "{\"commonLabels\":{\"common\":\"label\"},"
+ "\"sensors\":[{\"kind\":\"GAUGE\",\"labels\":{\"my\":\"gauge\"},\"value\":12.34}]}"
+ };
+
+ TMetricRegistry registry(TLabels{{"common", "label"}});
+
+ TGauge* g = registry.Gauge({{"my", "gauge"}});
+ g->Set(12.34);
+
+ TStringStream os;
+ auto encoder = EncoderJson(&os);
+ registry.Accept(TInstant::Zero(), encoder.Get());
+
+ UNIT_ASSERT_STRINGS_EQUAL(os.Str(), expected);
+ }
+
+ Y_UNIT_TEST(CreatingSameMetricWithDifferentTypesShouldThrow) {
+ TMetricRegistry registry;
+
+ registry.Gauge({{"foo", "bar"}});
+ UNIT_ASSERT_EXCEPTION(registry.Counter({{"foo", "bar"}}), yexception);
+
+ registry.HistogramCounter({{"bar", "baz"}}, nullptr);
+ UNIT_ASSERT_EXCEPTION(registry.HistogramRate({{"bar", "baz"}}, nullptr), yexception);
+ }
+
+ Y_UNIT_TEST(EncodeRegistryWithCommonLabels) {
+ TMetricRegistry registry(TLabels{{"common", "label"}});
+
+ TGauge* g = registry.Gauge({{"my", "gauge"}});
+ g->Set(12.34);
+
+ // Append() adds common labels to each metric, allowing to combine
+ // several metric registries in one resulting blob
+ {
+ TStringStream os;
+ auto encoder = EncoderJson(&os);
+ encoder->OnStreamBegin();
+ registry.Append(TInstant::Zero(), encoder.Get());
+ encoder->OnStreamEnd();
+
+ UNIT_ASSERT_STRINGS_EQUAL(
+ os.Str(),
+ "{\"sensors\":[{\"kind\":\"GAUGE\",\"labels\":{\"common\":\"label\",\"my\":\"gauge\"},\"value\":12.34}]}");
+ }
+
+ // Accept() adds common labels to the beginning of the blob
+ {
+ TStringStream os;
+ auto encoder = EncoderJson(&os);
+ registry.Accept(TInstant::Zero(), encoder.Get());
+
+ UNIT_ASSERT_STRINGS_EQUAL(
+ os.Str(),
+ "{\"commonLabels\":{\"common\":\"label\"},"
+ "\"sensors\":[{\"kind\":\"GAUGE\",\"labels\":{\"my\":\"gauge\"},\"value\":12.34}]}");
+ }
+ }
+}