json_decoder_ut.cpp 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179
  1. #include "json_decoder.cpp"
  2. #include <library/cpp/monlib/consumers/collecting_consumer.h>
  3. #include <library/cpp/testing/unittest/registar.h>
  4. #include <array>
  5. using namespace NMonitoring;
  6. enum EJsonPart : ui8 {
  7. METRICS = 0,
  8. COMMON_TS = 1,
  9. COMMON_LABELS = 2,
  10. };
  11. constexpr std::array<TStringBuf, 3> JSON_PARTS = {
  12. TStringBuf(R"("metrics": [{
  13. "labels": { "key": "value" },
  14. "type": "GAUGE",
  15. "value": 123
  16. }])"),
  17. TStringBuf(R"("ts": 1)"),
  18. TStringBuf(R"("commonLabels": {
  19. "key1": "value1",
  20. "key2": "value2"
  21. })"),
  22. };
  23. TString BuildJson(std::initializer_list<EJsonPart> parts) {
  24. TString data = "{";
  25. for (auto it = parts.begin(); it != parts.end(); ++it) {
  26. data += JSON_PARTS[*it];
  27. if (it + 1 != parts.end()) {
  28. data += ",";
  29. }
  30. }
  31. data += "}";
  32. return data;
  33. }
  34. void ValidateCommonParts(TCommonParts&& commonParts, bool checkLabels, bool checkTs) {
  35. if (checkTs) {
  36. UNIT_ASSERT_VALUES_EQUAL(commonParts.CommonTime.MilliSeconds(), 1000);
  37. }
  38. if (checkLabels) {
  39. auto& labels = commonParts.CommonLabels;
  40. UNIT_ASSERT_VALUES_EQUAL(labels.Size(), 2);
  41. UNIT_ASSERT(labels.Has(TStringBuf("key1")));
  42. UNIT_ASSERT(labels.Has(TStringBuf("key2")));
  43. UNIT_ASSERT_VALUES_EQUAL(labels.Get(TStringBuf("key1")).value()->Value(), "value1");
  44. UNIT_ASSERT_VALUES_EQUAL(labels.Get(TStringBuf("key2")).value()->Value(), "value2");
  45. }
  46. }
  47. void ValidateMetrics(const TVector<TMetricData>& metrics) {
  48. UNIT_ASSERT_VALUES_EQUAL(metrics.size(), 1);
  49. auto& m = metrics[0];
  50. UNIT_ASSERT_VALUES_EQUAL(m.Kind, EMetricType::GAUGE);
  51. auto& l = m.Labels;
  52. UNIT_ASSERT_VALUES_EQUAL(l.Size(), 1);
  53. UNIT_ASSERT_VALUES_EQUAL(l.Get(0)->Name(), "key");
  54. UNIT_ASSERT_VALUES_EQUAL(l.Get(0)->Value(), "value");
  55. UNIT_ASSERT_VALUES_EQUAL(m.Values->Size(), 1);
  56. UNIT_ASSERT_VALUES_EQUAL((*m.Values)[0].GetValue().AsDouble(), 123);
  57. }
  58. void CheckCommonPartsCollector(TString data, bool shouldBeStopped, bool checkLabels = true, bool checkTs = true, TStringBuf metricNameLabel = "name") {
  59. TCommonPartsCollector commonPartsCollector;
  60. TMemoryInput memIn(data);
  61. TDecoderJson decoder(data, &commonPartsCollector, metricNameLabel);
  62. bool isOk{false};
  63. UNIT_ASSERT_NO_EXCEPTION(isOk = NJson::ReadJson(&memIn, &decoder));
  64. UNIT_ASSERT_VALUES_EQUAL(isOk, !shouldBeStopped);
  65. ValidateCommonParts(commonPartsCollector.CommonParts(), checkLabels, checkTs);
  66. }
  67. Y_UNIT_TEST_SUITE(TJsonDecoderTest) {
  68. Y_UNIT_TEST(FullCommonParts) {
  69. CheckCommonPartsCollector(BuildJson({COMMON_LABELS, COMMON_TS, METRICS}), true);
  70. CheckCommonPartsCollector(BuildJson({COMMON_TS, COMMON_LABELS, METRICS}), true);
  71. CheckCommonPartsCollector(BuildJson({METRICS, COMMON_TS, COMMON_LABELS}), true);
  72. CheckCommonPartsCollector(BuildJson({METRICS, COMMON_LABELS, COMMON_TS}), true);
  73. CheckCommonPartsCollector(BuildJson({COMMON_LABELS, METRICS, COMMON_TS}), true);
  74. CheckCommonPartsCollector(BuildJson({COMMON_TS, METRICS, COMMON_LABELS}), true);
  75. }
  76. Y_UNIT_TEST(PartialCommonParts) {
  77. CheckCommonPartsCollector(BuildJson({COMMON_TS, METRICS}), false, false, true);
  78. CheckCommonPartsCollector(BuildJson({COMMON_LABELS, METRICS}), false, true, false);
  79. CheckCommonPartsCollector(BuildJson({METRICS, COMMON_LABELS}), false, true, false);
  80. CheckCommonPartsCollector(BuildJson({METRICS, COMMON_TS}), false, false, true);
  81. CheckCommonPartsCollector(BuildJson({METRICS}), false, false, false);
  82. }
  83. Y_UNIT_TEST(CheckCommonPartsAndMetrics) {
  84. auto data = BuildJson({COMMON_LABELS, COMMON_TS, METRICS});
  85. TCollectingConsumer collector;
  86. DecodeJson(data, &collector);
  87. TCommonParts commonParts;
  88. commonParts.CommonTime = collector.CommonTime;
  89. commonParts.CommonLabels = collector.CommonLabels;
  90. ValidateCommonParts(std::move(commonParts), true, true);
  91. ValidateMetrics(collector.Metrics);
  92. }
  93. Y_UNIT_TEST(CanParseHistogramsWithInf) {
  94. const char* metricsData = R"({
  95. "metrics":
  96. [
  97. {
  98. "hist": {
  99. "bounds": [
  100. 10
  101. ],
  102. "buckets": [
  103. 11
  104. ],
  105. "inf": 12
  106. },
  107. "name":"s1",
  108. "type": "HIST_RATE"
  109. },
  110. {
  111. "hist": {
  112. "bounds": [
  113. 20
  114. ],
  115. "buckets": [
  116. 21
  117. ]
  118. },
  119. "name":"s2",
  120. "type":"HIST_RATE"
  121. }
  122. ]
  123. })";
  124. TCollectingConsumer consumer(false);
  125. DecodeJson(metricsData, &consumer);
  126. UNIT_ASSERT_VALUES_EQUAL(consumer.Metrics.size(), 2);
  127. {
  128. const auto& m = consumer.Metrics[0];
  129. UNIT_ASSERT_VALUES_EQUAL(m.Kind, EMetricType::HIST_RATE);
  130. UNIT_ASSERT_VALUES_EQUAL(m.Values->Size(), 1);
  131. const auto* histogram = (*m.Values)[0].GetValue().AsHistogram();
  132. UNIT_ASSERT_VALUES_EQUAL(histogram->Count(), 2);
  133. UNIT_ASSERT_VALUES_EQUAL(histogram->UpperBound(1), Max<TBucketBound>());
  134. UNIT_ASSERT_VALUES_EQUAL(histogram->Value(0), 11);
  135. UNIT_ASSERT_VALUES_EQUAL(histogram->Value(1), 12);
  136. }
  137. {
  138. const auto& m = consumer.Metrics[1];
  139. UNIT_ASSERT_VALUES_EQUAL(m.Kind, EMetricType::HIST_RATE);
  140. UNIT_ASSERT_VALUES_EQUAL(m.Values->Size(), 1);
  141. const auto* histogram = (*m.Values)[0].GetValue().AsHistogram();
  142. UNIT_ASSERT_VALUES_EQUAL(histogram->Count(), 1);
  143. UNIT_ASSERT_VALUES_EQUAL(histogram->UpperBound(0), 20);
  144. UNIT_ASSERT_VALUES_EQUAL(histogram->Value(0), 21);
  145. }
  146. }
  147. }