1#include <gtest/gtest.h>
8#include <google/protobuf/dynamic_message.h>
10#include <userver/protobuf/datetime.hpp>
11#include <userver/protobuf/json/convert.hpp>
12#include <userver/utest/assert_macros.hpp>
16USERVER_NAMESPACE_BEGIN
20struct DurationToJsonSuccessTestParam {
22 std::string expected_json = {};
23 WriteOptions options = {};
26struct DurationToJsonFailureTestParam {
28 WriteErrorCode expected_errc = {};
29 std::string expected_path = {};
30 WriteOptions options = {};
33void PrintTo(
const DurationToJsonSuccessTestParam& param, std::ostream* os) {
34 *os << fmt::format(
"{{ input = {{.seconds={}, .nanos={}}} }}", param.input.seconds, param.input.nanos);
37void PrintTo(
const DurationToJsonFailureTestParam& param, std::ostream* os) {
38 *os << fmt::format(
"{{ input = {{.seconds={}, .nanos={}}} }}", param.input.seconds, param.input.nanos);
41class DurationToJsonSuccessTest :
public ::testing::TestWithParam<DurationToJsonSuccessTestParam> {};
42class DurationToJsonFailureTest :
public ::testing::TestWithParam<DurationToJsonFailureTestParam> {};
44INSTANTIATE_TEST_SUITE_P(
46 DurationToJsonSuccessTest,
48 DurationToJsonSuccessTestParam{DurationMessageData{0, 0,
true}, R"({})"},
49 DurationToJsonSuccessTestParam{DurationMessageData{0, 0}, R"({"field1": "0s"})"},
50 DurationToJsonSuccessTestParam{DurationMessageData{123, 0}, R"({"field1": "123s"})"},
51 DurationToJsonSuccessTestParam{DurationMessageData{-123, 0}, R"({"field1": "-123s"})"},
52 DurationToJsonSuccessTestParam{DurationMessageData{0, 567}, R"({"field1": "0.000000567s"})"},
53 DurationToJsonSuccessTestParam{DurationMessageData{0, -567}, R"({"field1": "-0.000000567s"})"},
54 DurationToJsonSuccessTestParam{DurationMessageData{123, 987654321}, R"({"field1": "123.987654321s"})"},
55 DurationToJsonSuccessTestParam{DurationMessageData{-123, -987654320}, R"({"field1": "-123.987654320s"})"},
56 DurationToJsonSuccessTestParam{DurationMessageData{123, 987654000}, R"({"field1": "123.987654s"})"},
57 DurationToJsonSuccessTestParam{DurationMessageData{-123, -987600000}, R"({"field1": "-123.987600s"})"},
58 DurationToJsonSuccessTestParam{DurationMessageData{123, 987000000}, R"({"field1": "123.987s"})"},
59 DurationToJsonSuccessTestParam{DurationMessageData{-123, -980000000}, R"({"field1": "-123.980s"})"},
60 DurationToJsonSuccessTestParam{
61 DurationMessageData{kMaxDurationSeconds, kMaxDurationNanos},
62 R"({"field1": "315576000000.999999999s"})"
64 DurationToJsonSuccessTestParam{
65 DurationMessageData{kMinDurationSeconds, kMinDurationNanos},
66 R"({"field1": "-315576000000.999999999s"})"
71INSTANTIATE_TEST_SUITE_P(
73 DurationToJsonFailureTest,
75 DurationToJsonFailureTestParam{
76 DurationMessageData{kMaxDurationSeconds + 1, 0},
77 WriteErrorCode::kInvalidValue,
80 DurationToJsonFailureTestParam{
81 DurationMessageData{kMinDurationSeconds - 1, 0},
82 WriteErrorCode::kInvalidValue,
85 DurationToJsonFailureTestParam{
86 DurationMessageData{0, kMaxDurationNanos + 1},
87 WriteErrorCode::kInvalidValue,
90 DurationToJsonFailureTestParam{
91 DurationMessageData{0, kMinDurationNanos - 1},
92 WriteErrorCode::kInvalidValue,
95 DurationToJsonFailureTestParam{DurationMessageData{1, -1}, WriteErrorCode::kInvalidValue,
"field1"}
99TEST_P(DurationToJsonSuccessTest, Test) {
100 const auto& param = GetParam();
102 auto input = PrepareTestData(param.input);
103 formats::json::Value json, expected_json, sample_json;
105 UASSERT_NO_THROW((json = MessageToJson(input, param.options)));
106 UASSERT_NO_THROW((expected_json = PrepareJsonTestData(param.expected_json)));
107 UASSERT_NO_THROW((sample_json = CreateSampleJson(input, param.options)));
109 EXPECT_EQ(json, expected_json);
110 EXPECT_EQ(expected_json, sample_json);
113TEST_P(DurationToJsonFailureTest, Test) {
114 const auto& param = GetParam();
115 auto input = PrepareTestData(param.input);
117 EXPECT_WRITE_ERROR((
void)MessageToJson(input, param.options), param.expected_errc, param.expected_path);
118 UEXPECT_THROW((
void)CreateSampleJson(input, param.options), SampleError);
121TEST(DurationToJsonAdditionalTest, InlinedNonNull) {
123 auto message = PrepareTestData(data);
124 formats::json::Value json, sample;
126 UASSERT_NO_THROW((json = MessageToJson(message.field1())));
127 UASSERT_NO_THROW((sample = CreateSampleJson(message.field1())));
128 ASSERT_TRUE(json.IsString());
129 EXPECT_EQ(json, sample);
130 EXPECT_EQ(json.As<std::string>(),
"123.000000321s");
133TEST(DurationToJsonAdditionalTest, InlinedNull) {
134 proto_json::messages::DurationMessage message;
135 formats::json::Value json, sample;
137 UASSERT_NO_THROW((json = MessageToJson(message.field1())));
138 UASSERT_NO_THROW((sample = CreateSampleJson(message.field1())));
139 ASSERT_TRUE(json.IsString());
140 EXPECT_EQ(json, sample);
141 EXPECT_EQ(json.As<std::string>(),
"0s");
144TEST(DurationToJsonAdditionalTest, DynamicMessage) {
145 using Message = ::google::protobuf::Duration;
146 ::google::protobuf::DynamicMessageFactory factory;
149 std::unique_ptr<::google::protobuf::Message> message(factory.GetPrototype(Message::descriptor())->New());
150 const auto reflection = message->GetReflection();
151 const auto seconds_desc = message->GetDescriptor()->FindFieldByName(
"seconds");
152 const auto nanos_desc = message->GetDescriptor()->FindFieldByName(
"nanos");
154 reflection->SetInt64(message.get(), seconds_desc, -123);
155 reflection->SetInt32(message.get(), nanos_desc, -987);
157 formats::json::Value json;
159 UASSERT_NO_THROW((json = MessageToJson(*message)));
160 ASSERT_TRUE(json.IsString());
161 EXPECT_EQ(json.As<std::string>(),
"-123.000000987s");