userver: /data/code/userver/libraries/protobuf/tests/json/utils.cpp Source File
Loading...
Searching...
No Matches
utils.cpp
1#include "utils.hpp"
2
3#include <algorithm>
4#include <cmath>
5#include <exception>
6#include <stdexcept>
7
8#include <fmt/format.h>
9#include <google/protobuf/util/json_util.h>
10
11#include <userver/formats/json/serialize.hpp>
12#include <userver/protobuf/string.hpp>
13
14USERVER_NAMESPACE_BEGIN
15
16namespace protobuf::json::tests {
17
18template <typename T>
19concept SupportsCheckMessageEqual = requires(const T& lhs, const T& rhs) { CheckMessageEqual(lhs, rhs); };
20
21template <typename T>
22void AreProtobufRepeatedEqual(const T& lhs, const T& rhs) {
23 ASSERT_EQ(lhs.size(), rhs.size());
24
25 for (int i = 0; i < lhs.size(); ++i) {
26 if constexpr (SupportsCheckMessageEqual<typename T::value_type>) {
27 CheckMessageEqual(lhs[i], rhs[i]);
28 } else {
29 EXPECT_EQ(lhs[i], rhs[i]);
30 }
31 }
32}
33
34template <typename T>
35void AreProtobufMapsEqual(const T& lhs, const T& rhs) {
36 EXPECT_EQ(lhs.size(), rhs.size());
37
38 for (const auto& [key, val] : lhs) {
39 ASSERT_TRUE(rhs.contains(key));
40
41 if constexpr (SupportsCheckMessageEqual<typename T::mapped_type>) {
42 CheckMessageEqual(val, rhs.at(key));
43 } else {
44 EXPECT_EQ(val, rhs.at(key));
45 }
46 }
47}
48
49formats::json::Value PrepareJsonTestData(const std::string& json_data) { return formats::json::FromString(json_data); }
50
51formats::json::Value CreateSampleJson(const ::google::protobuf::Message& message, const PrintOptions& options) {
52 using StringType = std::decay_t<decltype(message.DebugString())>;
53
54 StringType result;
55 ::google::protobuf::util::JsonPrintOptions native_options;
56#if GOOGLE_PROTOBUF_VERSION >= 5026000
57 native_options.always_print_fields_with_no_presence = options.always_print_fields_with_no_presence;
58#else
59 native_options.always_print_primitive_fields = options.always_print_fields_with_no_presence;
60#endif
61 native_options.always_print_enums_as_ints = options.always_print_enums_as_ints;
62 native_options.preserve_proto_field_names = options.preserve_proto_field_names;
63
64 auto status = ::google::protobuf::util::MessageToJsonString(message, &result, native_options);
65
66 if (status.ok()) {
67 return formats::json::FromString(result);
68 } else {
69 throw SampleError(fmt::format(
70 "Failed to create sample JSON from protobuf message: {}",
71 protobuf::impl::ToStringView(status.message())
72 ));
73 }
74}
75
76void InitSampleMessage(const std::string& json, ::google::protobuf::Message& message, const ParseOptions& options) {
77 ::google::protobuf::util::JsonParseOptions native_options;
78 native_options.ignore_unknown_fields = options.ignore_unknown_fields;
79
80 try {
81 auto status = ::google::protobuf::util::JsonStringToMessage(json, &message, native_options);
82
83 if (!status.ok()) {
84 throw SampleError(fmt::format(
85 "Failed to initialize sample message from JSON: {}",
86 protobuf::impl::ToStringView(status.message())
87 ));
88 }
89 } catch (const SampleError&) {
90 throw;
91 } catch (const std::exception& e) {
92 throw SampleError(fmt::format("Failed to initialize sample message from JSON: {}", e.what()));
93 }
94}
95
96::google::protobuf::Value ProtoValueToNative(const ProtoValue& data) {
97 struct Visitor {
98 ::google::protobuf::Value result;
99
100 ::google::protobuf::Value operator()(std::monostate) const { return result; }
101
102 ::google::protobuf::Value operator()(ProtoNullValue) {
103 result.set_null_value(::google::protobuf::NULL_VALUE);
104 return result;
105 }
106
107 ::google::protobuf::Value operator()(double val) {
108 result.set_number_value(val);
109 return result;
110 }
111
112 ::google::protobuf::Value operator()(const std::string& val) {
113 result.set_string_value(val);
114 return result;
115 }
116
117 ::google::protobuf::Value operator()(bool val) {
118 result.set_bool_value(val);
119 return result;
120 }
121
122 ::google::protobuf::Value operator()(const std::vector<double>& val) {
123 auto& arr = *result.mutable_list_value();
124
125 for (const auto& item : val) {
126 arr.add_values()->set_number_value(item);
127 }
128
129 return result;
130 }
131
132 ::google::protobuf::Value operator()(const std::map<std::string, std::string>& val) {
133 auto& fields = *result.mutable_struct_value()->mutable_fields();
134
135 for (const auto& [key, value] : val) {
136 fields[key].set_string_value(value);
137 }
138
139 return result;
140 }
141 };
142
143 return std::visit(Visitor{}, data);
144}
145
146proto_json::messages::Int32Message PrepareTestData(const Int32MessageData& message_data) {
147 proto_json::messages::Int32Message message;
148 message.set_field1(message_data.field1);
149 message.set_field2(message_data.field2);
150 message.set_field3(message_data.field3);
151 return message;
152}
153
154void CheckMessageEqual(const proto_json::messages::Int32Message& lhs, const proto_json::messages::Int32Message& rhs) {
155 EXPECT_EQ(lhs.field1(), rhs.field1());
156 EXPECT_EQ(lhs.field2(), rhs.field2());
157 EXPECT_EQ(lhs.field3(), rhs.field3());
158}
159
160proto_json::messages::UInt32Message PrepareTestData(const UInt32MessageData& message_data) {
161 proto_json::messages::UInt32Message message;
162 message.set_field1(message_data.field1);
163 message.set_field2(message_data.field2);
164 return message;
165}
166
167void CheckMessageEqual(const proto_json::messages::UInt32Message& lhs, const proto_json::messages::UInt32Message& rhs) {
168 EXPECT_EQ(lhs.field1(), rhs.field1());
169 EXPECT_EQ(lhs.field2(), rhs.field2());
170}
171
172proto_json::messages::Int64Message PrepareTestData(const Int64MessageData& message_data) {
173 proto_json::messages::Int64Message message;
174 message.set_field1(message_data.field1);
175 message.set_field2(message_data.field2);
176 message.set_field3(message_data.field3);
177 return message;
178}
179
180void CheckMessageEqual(const proto_json::messages::Int64Message& lhs, const proto_json::messages::Int64Message& rhs) {
181 EXPECT_EQ(lhs.field1(), rhs.field1());
182 EXPECT_EQ(lhs.field2(), rhs.field2());
183 EXPECT_EQ(lhs.field3(), rhs.field3());
184}
185
186proto_json::messages::UInt64Message PrepareTestData(const UInt64MessageData& message_data) {
187 proto_json::messages::UInt64Message message;
188 message.set_field1(message_data.field1);
189 message.set_field2(message_data.field2);
190 return message;
191}
192
193void CheckMessageEqual(const proto_json::messages::UInt64Message& lhs, const proto_json::messages::UInt64Message& rhs) {
194 EXPECT_EQ(lhs.field1(), rhs.field1());
195 EXPECT_EQ(lhs.field2(), rhs.field2());
196}
197
198proto_json::messages::FloatMessage PrepareTestData(const FloatMessageData& message_data) {
199 proto_json::messages::FloatMessage message;
200 message.set_field1(message_data.field1);
201 return message;
202}
203
204void CheckMessageEqual(const proto_json::messages::FloatMessage& lhs, const proto_json::messages::FloatMessage& rhs) {
205 if (!std::isnan(lhs.field1())) {
206 EXPECT_EQ(lhs.field1(), rhs.field1());
207 } else {
208 EXPECT_TRUE(std::isnan(rhs.field1()));
209 }
210}
211
212proto_json::messages::DoubleMessage PrepareTestData(const DoubleMessageData& message_data) {
213 proto_json::messages::DoubleMessage message;
214 message.set_field1(message_data.field1);
215 return message;
216}
217
218void CheckMessageEqual(const proto_json::messages::DoubleMessage& lhs, const proto_json::messages::DoubleMessage& rhs) {
219 if (!std::isnan(lhs.field1())) {
220 EXPECT_EQ(lhs.field1(), rhs.field1());
221 } else {
222 EXPECT_TRUE(std::isnan(rhs.field1()));
223 }
224}
225
226proto_json::messages::BoolMessage PrepareTestData(const BoolMessageData& message_data) {
227 proto_json::messages::BoolMessage message;
228 message.set_field1(message_data.field1);
229 return message;
230}
231
232void CheckMessageEqual(const proto_json::messages::BoolMessage& lhs, const proto_json::messages::BoolMessage& rhs) {
233 EXPECT_EQ(lhs.field1(), rhs.field1());
234}
235
236proto_json::messages::StringMessage PrepareTestData(const StringMessageData& message_data) {
237 proto_json::messages::StringMessage message;
238 message.set_field1(message_data.field1);
239 return message;
240}
241
242void CheckMessageEqual(const proto_json::messages::StringMessage& lhs, const proto_json::messages::StringMessage& rhs) {
243 EXPECT_EQ(lhs.field1(), rhs.field1());
244}
245
246proto_json::messages::BytesMessage PrepareTestData(const BytesMessageData& message_data) {
247 proto_json::messages::BytesMessage message;
248 message.set_field1(message_data.field1);
249 return message;
250}
251
252void CheckMessageEqual(const proto_json::messages::BytesMessage& lhs, const proto_json::messages::BytesMessage& rhs) {
253 EXPECT_EQ(lhs.field1(), rhs.field1());
254}
255
256proto_json::messages::EnumMessage PrepareTestData(const EnumMessageData& message_data) {
257 proto_json::messages::EnumMessage message;
258 message.set_field1(message_data.field1);
259
260 if (message_data.field2) {
261 message.set_field2(message_data.field2.value());
262 }
263
264 return message;
265}
266
267void CheckMessageEqual(const proto_json::messages::EnumMessage& lhs, const proto_json::messages::EnumMessage& rhs) {
268 EXPECT_EQ(lhs.field1(), rhs.field1());
269 EXPECT_EQ(lhs.has_field2(), rhs.has_field2());
270 EXPECT_EQ(lhs.field2(), rhs.field2());
271}
272
273proto_json::messages::NestedMessage PrepareTestData(const NestedMessageData& message_data) {
274 proto_json::messages::NestedMessage message;
275 if (message_data.field1) {
276 message.mutable_parent()->set_field1(message_data.field1.value());
277 }
278 return message;
279}
280
281void CheckMessageEqual(const proto_json::messages::NestedMessage& lhs, const proto_json::messages::NestedMessage& rhs) {
282 EXPECT_EQ(lhs.has_parent(), rhs.has_parent());
283 EXPECT_EQ(lhs.parent().field1(), rhs.parent().field1());
284}
285
286proto_json::messages::WrapperMessage PrepareTestData(const WrapperMessageData& message_data) {
287 proto_json::messages::WrapperMessage message;
288
289 if (message_data.field1) {
290 message.mutable_field1()->set_value(message_data.field1.value());
291 }
292
293 if (message_data.field2) {
294 message.mutable_field2()->set_value(message_data.field2.value());
295 }
296
297 if (message_data.field3) {
298 message.mutable_field3()->set_value(message_data.field3.value());
299 }
300
301 if (message_data.field4) {
302 message.mutable_field4()->set_value(message_data.field4.value());
303 }
304
305 if (message_data.field5) {
306 message.mutable_field5()->set_value(message_data.field5.value());
307 }
308
309 if (message_data.field6) {
310 message.mutable_field6()->set_value(message_data.field6.value());
311 }
312
313 if (message_data.field7) {
314 message.mutable_field7()->set_value(message_data.field7.value());
315 }
316
317 if (message_data.field8) {
318 message.mutable_field8()->set_value(message_data.field8.value());
319 }
320
321 if (message_data.field9) {
322 message.mutable_field9()->set_value(message_data.field9.value());
323 }
324 return message;
325}
326
327void CheckMessageEqual(
328 const proto_json::messages::WrapperMessage& lhs,
329 const proto_json::messages::WrapperMessage& rhs
330) {
331 EXPECT_EQ(lhs.has_field1(), rhs.has_field1());
332 EXPECT_EQ(lhs.has_field2(), rhs.has_field2());
333 EXPECT_EQ(lhs.has_field3(), rhs.has_field3());
334 EXPECT_EQ(lhs.has_field4(), rhs.has_field4());
335 EXPECT_EQ(lhs.has_field5(), rhs.has_field5());
336 EXPECT_EQ(lhs.has_field6(), rhs.has_field6());
337 EXPECT_EQ(lhs.has_field7(), rhs.has_field7());
338 EXPECT_EQ(lhs.has_field8(), rhs.has_field8());
339 EXPECT_EQ(lhs.has_field9(), rhs.has_field9());
340
341 EXPECT_EQ(lhs.field1().value(), rhs.field1().value());
342 EXPECT_EQ(lhs.field2().value(), rhs.field2().value());
343 EXPECT_EQ(lhs.field3().value(), rhs.field3().value());
344 EXPECT_EQ(lhs.field4().value(), rhs.field4().value());
345 EXPECT_EQ(lhs.field5().value(), rhs.field5().value());
346 EXPECT_EQ(lhs.field6().value(), rhs.field6().value());
347 EXPECT_EQ(lhs.field7().value(), rhs.field7().value());
348 EXPECT_EQ(lhs.field8().value(), rhs.field8().value());
349 EXPECT_EQ(lhs.field9().value(), rhs.field9().value());
350}
351
352proto_json::messages::FieldMaskMessage PrepareTestData(const FieldMaskMessageData& message_data) {
353 proto_json::messages::FieldMaskMessage message;
354
355 if (!message_data.field1) {
356 return message;
357 }
358
359 (void)message.mutable_field1();
360
361 for (const auto& path : message_data.field1.value()) {
362 message.mutable_field1()->add_paths(path);
363 }
364
365 return message;
366}
367
368void CheckMessageEqual(const ::google::protobuf::FieldMask& lhs, const ::google::protobuf::FieldMask& rhs) {
369 std::vector<std::string> mask_lhs;
370 std::vector<std::string> mask_rhs;
371
372 for (const auto& path : lhs.paths()) {
373 mask_lhs.push_back(path);
374 }
375
376 for (const auto& path : rhs.paths()) {
377 mask_rhs.push_back(path);
378 }
379
380 std::ranges::sort(mask_lhs);
381 std::ranges::sort(mask_rhs);
382
383 EXPECT_EQ(mask_lhs, mask_rhs);
384}
385
386void CheckMessageEqual(
387 const proto_json::messages::FieldMaskMessage& lhs,
388 const proto_json::messages::FieldMaskMessage& rhs
389) {
390 EXPECT_EQ(lhs.has_field1(), rhs.has_field1());
391 CheckMessageEqual(lhs.field1(), rhs.field1());
392}
393
394proto_json::messages::DurationMessage PrepareTestData(const DurationMessageData& message_data) {
395 proto_json::messages::DurationMessage message;
396
397 if (!message_data.do_not_set) {
398 message.mutable_field1()->set_seconds(message_data.seconds);
399 message.mutable_field1()->set_nanos(message_data.nanos);
400 }
401
402 return message;
403}
404
405void CheckMessageEqual(const ::google::protobuf::Duration& lhs, const ::google::protobuf::Duration& rhs) {
406 EXPECT_EQ(lhs.seconds(), rhs.seconds());
407 EXPECT_EQ(lhs.nanos(), rhs.nanos());
408}
409
410void CheckMessageEqual(
411 const proto_json::messages::DurationMessage& lhs,
412 const proto_json::messages::DurationMessage& rhs
413) {
414 EXPECT_EQ(lhs.has_field1(), rhs.has_field1());
415 CheckMessageEqual(lhs.field1(), rhs.field1());
416}
417
418proto_json::messages::TimestampMessage PrepareTestData(const TimestampMessageData& message_data) {
419 proto_json::messages::TimestampMessage message;
420
421 if (!message_data.do_not_set) {
422 message.mutable_field1()->set_seconds(message_data.seconds);
423 message.mutable_field1()->set_nanos(message_data.nanos);
424 }
425
426 return message;
427}
428
429void CheckMessageEqual(const ::google::protobuf::Timestamp& lhs, const ::google::protobuf::Timestamp& rhs) {
430 EXPECT_EQ(lhs.seconds(), rhs.seconds());
431 EXPECT_EQ(lhs.nanos(), rhs.nanos());
432}
433
434void CheckMessageEqual(
435 const proto_json::messages::TimestampMessage& lhs,
436 const proto_json::messages::TimestampMessage& rhs
437) {
438 EXPECT_EQ(lhs.has_field1(), rhs.has_field1());
439 CheckMessageEqual(lhs.field1(), rhs.field1());
440}
441
442proto_json::messages::ValueMessage PrepareTestData(const ValueMessageData& message_data) {
443 struct Visitor {
444 proto_json::messages::ValueMessage result;
445
446 proto_json::messages::ValueMessage operator()(const ProtoValue& val) {
447 *result.mutable_field1() = ProtoValueToNative(val);
448 return result;
449 }
450
451 proto_json::messages::ValueMessage operator()(const std::vector<ProtoValue>& val) {
452 auto& arr = *result.mutable_field1()->mutable_list_value();
453
454 for (const auto& item : val) {
455 *arr.add_values() = ProtoValueToNative(item);
456 }
457
458 return result;
459 }
460
461 proto_json::messages::ValueMessage operator()(const std::map<std::string, ProtoValue>& val) {
462 auto& fields = *result.mutable_field1()->mutable_struct_value()->mutable_fields();
463
464 for (const auto& [key, value] : val) {
465 fields[key] = ProtoValueToNative(value);
466 }
467
468 return result;
469 }
470 };
471
472 if (message_data.field1) {
473 return std::visit(Visitor{}, *message_data.field1);
474 } else {
475 return proto_json::messages::ValueMessage{};
476 }
477}
478
479void CheckMessageEqual(const ::google::protobuf::Value& lhs, const ::google::protobuf::Value& rhs) {
480 if (lhs.has_null_value()) {
481 ASSERT_TRUE(rhs.has_null_value());
482 EXPECT_EQ(lhs.null_value(), rhs.null_value());
483 } else if (lhs.has_number_value()) {
484 ASSERT_TRUE(rhs.has_number_value());
485 EXPECT_EQ(lhs.number_value(), rhs.number_value());
486 } else if (lhs.has_string_value()) {
487 ASSERT_TRUE(rhs.has_string_value());
488 EXPECT_EQ(lhs.string_value(), rhs.string_value());
489 } else if (lhs.has_bool_value()) {
490 ASSERT_TRUE(rhs.has_bool_value());
491 EXPECT_EQ(lhs.bool_value(), rhs.bool_value());
492 } else if (lhs.has_list_value()) {
493 ASSERT_TRUE(rhs.has_list_value());
494 CheckMessageEqual(lhs.list_value(), rhs.list_value());
495 } else if (lhs.has_struct_value()) {
496 ASSERT_TRUE(rhs.has_struct_value());
497 CheckMessageEqual(lhs.struct_value(), rhs.struct_value());
498 } else {
499 EXPECT_TRUE(
500 !rhs.has_null_value() && !rhs.has_number_value() && !rhs.has_string_value() && !rhs.has_bool_value() &&
501 !rhs.has_list_value() && !rhs.has_struct_value()
502 );
503 }
504}
505
506void CheckMessageEqual(const ::google::protobuf::ListValue& lhs, const ::google::protobuf::ListValue& rhs) {
507 AreProtobufRepeatedEqual(lhs.values(), rhs.values());
508}
509
510void CheckMessageEqual(const ::google::protobuf::Struct& lhs, const ::google::protobuf::Struct& rhs) {
511 AreProtobufMapsEqual(lhs.fields(), rhs.fields());
512}
513
514void CheckMessageEqual(const proto_json::messages::ValueMessage& lhs, const proto_json::messages::ValueMessage& rhs) {
515 EXPECT_EQ(lhs.has_field1(), rhs.has_field1());
516 CheckMessageEqual(lhs.field1(), rhs.field1());
517}
518
519template <typename T>
520void CheckAnyPayloadEqual(const ::google::protobuf::Any& lhs, const ::google::protobuf::Any& rhs) {
521 ASSERT_TRUE(lhs.Is<T>());
522 ASSERT_TRUE(rhs.Is<T>());
523
524 T lhs_payload;
525 T rhs_payload;
526
527 ASSERT_TRUE(lhs.UnpackTo(&lhs_payload));
528 ASSERT_TRUE(rhs.UnpackTo(&rhs_payload));
529
530 CheckMessageEqual(lhs_payload, rhs_payload);
531}
532
533proto_json::messages::AnyMessage PrepareTestData(const AnyMessageData& message_data) {
534 struct Visitor {
535 ::google::protobuf::Any result;
536
537 ::google::protobuf::Any operator()(const Int32MessageData& payload) {
538 auto msg = PrepareTestData(payload);
539
540 if (!result.PackFrom(msg)) {
541 throw std::runtime_error("Failed to create 'google.protobuf.Any'");
542 }
543
544 return result;
545 }
546
547 ::google::protobuf::Any operator()(const DurationMessageData& payload) {
548 const auto msg = PrepareTestData(payload);
549
550 if (!result.PackFrom(msg.field1())) {
551 throw std::runtime_error("Failed to create 'google.protobuf.Any'");
552 }
553
554 return result;
555 }
556
557 ::google::protobuf::Any operator()(const ValueMessageData& payload) {
558 const auto msg = PrepareTestData(payload);
559
560 if (!result.PackFrom(msg.field1())) {
561 throw std::runtime_error("Failed to create 'google.protobuf.Any'");
562 }
563
564 return result;
565 }
566
567 ::google::protobuf::Any operator()(const RawAnyData& payload) {
568 result.set_type_url(payload.type_url);
569 result.set_value(payload.value);
570 return result;
571 }
572 };
573
574 proto_json::messages::AnyMessage result;
575
576 if (!message_data.field1) {
577 return result;
578 }
579
580 auto any_message = std::visit(Visitor{}, message_data.field1.value());
581
582 if (!message_data.add_nesting) {
583 *result.mutable_field1() = std::move(any_message);
584 } else {
585 ::google::protobuf::Any top;
586
587 if (!top.PackFrom(any_message)) {
588 throw std::runtime_error("Failed to create top-level 'google.protobuf.Any'");
589 }
590
591 *result.mutable_field1() = std::move(top);
592 }
593
594 return result;
595}
596
597void CheckMessageEqual(const ::google::protobuf::Any& lhs, const ::google::protobuf::Any& rhs) {
598 if (lhs.Is<proto_json::messages::Int32Message>()) {
599 CheckAnyPayloadEqual<proto_json::messages::Int32Message>(lhs, rhs);
600 } else if (lhs.Is<::google::protobuf::Duration>()) {
601 CheckAnyPayloadEqual<::google::protobuf::Duration>(lhs, rhs);
602 } else if (lhs.Is<::google::protobuf::Value>()) {
603 CheckAnyPayloadEqual<::google::protobuf::Value>(lhs, rhs);
604 } else if (lhs.Is<::google::protobuf::Any>()) {
605 CheckAnyPayloadEqual<::google::protobuf::Any>(lhs, rhs);
606 } else {
607 EXPECT_EQ(lhs.type_url(), rhs.type_url());
608 EXPECT_EQ(lhs.value(), rhs.value());
609 }
610}
611
612void CheckMessageEqual(const proto_json::messages::AnyMessage& lhs, const proto_json::messages::AnyMessage& rhs) {
613 EXPECT_EQ(lhs.has_field1(), rhs.has_field1());
614
615 if (lhs.has_field1()) {
616 CheckMessageEqual(lhs.field1(), rhs.field1());
617 }
618}
619
620proto_json::messages::OneofMessage PrepareTestData(const OneofMessageData& message_data) {
621 proto_json::messages::OneofMessage result;
622
623 if (message_data.field1) {
624 result.set_field1(message_data.field1.value());
625 } else if (message_data.field2) {
626 result.set_field2(message_data.field2.value());
627 }
628
629 return result;
630}
631
632void CheckMessageEqual(const proto_json::messages::OneofMessage& lhs, const proto_json::messages::OneofMessage& rhs) {
633 if (lhs.has_field1()) {
634 EXPECT_TRUE(rhs.has_field1());
635 EXPECT_EQ(lhs.field1(), rhs.field1());
636 } else if (lhs.has_field2()) {
637 EXPECT_TRUE(rhs.has_field2());
638 EXPECT_EQ(lhs.field2(), rhs.field2());
639 } else {
640 EXPECT_FALSE(rhs.has_field1() || rhs.has_field2());
641 }
642}
643
644proto_json::messages::RepeatedMessage PrepareTestData(const RepeatedMessageData& message_data) {
645 proto_json::messages::RepeatedMessage result;
646
647 for (const auto& item : message_data.field1) {
648 result.add_field1(item);
649 }
650
651 for (const auto& item : message_data.field2) {
652 *result.add_field2() = PrepareTestData(item);
653 }
654
655 for (const auto& item : message_data.field3) {
656 *result.add_field3() = PrepareTestData(item).field1();
657 }
658
659 for (const auto& item : message_data.field4) {
660 *result.add_field4() = ProtoValueToNative(item);
661 }
662
663 for (const auto& item : message_data.field5) {
664 result.add_field5(item);
665 }
666
667 for (const auto& item : message_data.field6) {
668 result.add_field6(item);
669 }
670
671 for (const auto& item : message_data.field7) {
672 result.add_field7(item);
673 }
674
675 for (const auto& item : message_data.field8) {
676 result.add_field8(item);
677 }
678
679 for (const auto& item : message_data.field9) {
680 result.add_field9(item);
681 }
682
683 for (const auto& item : message_data.field10) {
684 result.add_field10(item);
685 }
686
687 for (const auto& item : message_data.field11) {
688 result.add_field11(item);
689 }
690
691 for (const auto& item : message_data.field12) {
692 result.add_field12(item);
693 }
694
695 return result;
696}
697
698void CheckMessageEqual(
699 const proto_json::messages::RepeatedMessage& lhs,
700 const proto_json::messages::RepeatedMessage& rhs
701) {
702 AreProtobufRepeatedEqual(lhs.field1(), rhs.field1());
703 AreProtobufRepeatedEqual(lhs.field2(), rhs.field2());
704 AreProtobufRepeatedEqual(lhs.field3(), rhs.field3());
705 AreProtobufRepeatedEqual(lhs.field4(), rhs.field4());
706 AreProtobufRepeatedEqual(lhs.field5(), rhs.field5());
707 AreProtobufRepeatedEqual(lhs.field6(), rhs.field6());
708 AreProtobufRepeatedEqual(lhs.field7(), rhs.field7());
709 AreProtobufRepeatedEqual(lhs.field8(), rhs.field8());
710 AreProtobufRepeatedEqual(lhs.field9(), rhs.field9());
711 AreProtobufRepeatedEqual(lhs.field10(), rhs.field10());
712 AreProtobufRepeatedEqual(lhs.field11(), rhs.field11());
713 AreProtobufRepeatedEqual(lhs.field12(), rhs.field12());
714}
715
716proto_json::messages::MapMessage PrepareTestData(const MapMessageData& message_data) {
717 proto_json::messages::MapMessage result;
718
719 for (const auto& [key, val] : message_data.field1) {
720 (*result.mutable_field1())[key] = val;
721 }
722
723 for (const auto& [key, val] : message_data.field2) {
724 (*result.mutable_field2())[key] = val;
725 }
726
727 for (const auto& [key, val] : message_data.field3) {
728 (*result.mutable_field3())[key] = val;
729 }
730
731 for (const auto& [key, val] : message_data.field4) {
732 (*result.mutable_field4())[key] = val;
733 }
734
735 for (const auto& [key, val] : message_data.field5) {
736 (*result.mutable_field5())[key] = val;
737 }
738
739 for (const auto& [key, val] : message_data.field6) {
740 (*result.mutable_field6())[key] = PrepareTestData(val);
741 }
742
743 for (const auto& [key, val] : message_data.field7) {
744 (*result.mutable_field7())[key] = PrepareTestData(val).field1();
745 }
746
747 for (const auto& [key, val] : message_data.field8) {
748 (*result.mutable_field8())[key] = ProtoValueToNative(val);
749 }
750
751 return result;
752}
753
754void CheckMessageEqual(const proto_json::messages::MapMessage& lhs, const proto_json::messages::MapMessage& rhs) {
755 AreProtobufMapsEqual(lhs.field1(), rhs.field1());
756 AreProtobufMapsEqual(lhs.field2(), rhs.field2());
757 AreProtobufMapsEqual(lhs.field3(), rhs.field3());
758 AreProtobufMapsEqual(lhs.field4(), rhs.field4());
759 AreProtobufMapsEqual(lhs.field5(), rhs.field5());
760 AreProtobufMapsEqual(lhs.field6(), rhs.field6());
761 AreProtobufMapsEqual(lhs.field7(), rhs.field7());
762 AreProtobufMapsEqual(lhs.field8(), rhs.field8());
763}
764
765proto_json::messages::NullValueMessage PrepareTestData(const NullValueMessageData& message_data) {
766 proto_json::messages::NullValueMessage result;
767 result.set_field1(message_data.field1);
768
769 if (message_data.field2) {
770 result.set_field2(message_data.field2.value());
771 }
772
773 for (const auto& item : message_data.field3) {
774 result.add_field3(item);
775 }
776
777 for (const auto& [key, val] : message_data.field4) {
778 (*result.mutable_field4())[key] = val;
779 }
780
781 return result;
782}
783
784void CheckMessageEqual(
785 const proto_json::messages::NullValueMessage& lhs,
786 const proto_json::messages::NullValueMessage& rhs
787) {
788 EXPECT_EQ(lhs.field1(), rhs.field1());
789
790 if (lhs.has_field2()) {
791 EXPECT_TRUE(rhs.has_field2());
792 EXPECT_EQ(lhs.field2(), rhs.field2());
793 } else {
794 EXPECT_FALSE(rhs.has_field2());
795 }
796
797 AreProtobufRepeatedEqual(lhs.field3(), rhs.field3());
798 AreProtobufMapsEqual(lhs.field4(), rhs.field4());
799}
800
801proto_json::messages::PresenceMessage PrepareTestData(const PresenceMessageData& message_data) {
802 proto_json::messages::PresenceMessage result;
803
804 result.set_field1(message_data.field1);
805
806 if (message_data.field2) {
807 result.set_field2(message_data.field2.value());
808 }
809
810 if (message_data.field3) {
811 result.mutable_field3()->set_field1(message_data.field3->field1);
812 result.mutable_field3()->set_field2(message_data.field3->field2);
813 result.mutable_field3()->set_field3(message_data.field3->field3);
814 }
815
816 if (!message_data.field4.empty()) {
817 for (const auto& val : message_data.field4) {
818 result.add_field4(val);
819 }
820 }
821
822 if (!message_data.field5.empty()) {
823 for (const auto& [key, val] : message_data.field5) {
824 (*result.mutable_field5())[key] = val;
825 }
826 }
827
828 return result;
829}
830
831void CheckMessageEqual(
832 const proto_json::messages::PresenceMessage& lhs,
833 const proto_json::messages::PresenceMessage& rhs
834) {
835 EXPECT_EQ(lhs.field1(), rhs.field1());
836
837 if (lhs.has_field2()) {
838 EXPECT_TRUE(rhs.has_field2());
839 EXPECT_EQ(lhs.field2(), rhs.field2());
840 } else {
841 EXPECT_FALSE(rhs.has_field2());
842 }
843
844 if (lhs.has_field3()) {
845 EXPECT_TRUE(rhs.has_field3());
846 CheckMessageEqual(lhs.field3(), rhs.field3());
847 } else {
848 EXPECT_FALSE(rhs.has_field3());
849 }
850
851 AreProtobufRepeatedEqual(lhs.field4(), rhs.field4());
852 AreProtobufMapsEqual(lhs.field5(), rhs.field5());
853}
854
855proto_json::messages::UnknownFieldMessage PrepareTestData(const UnknownFieldMessageData& message_data) {
856 proto_json::messages::UnknownFieldMessage result;
857
858 *result.mutable_field1() = PrepareTestData(message_data.field1);
859
860 for (const auto& item : message_data.field2) {
861 *result.add_field2() = PrepareTestData(item);
862 }
863
864 for (const auto& [key, val] : message_data.field3) {
865 (*result.mutable_field3())[key] = PrepareTestData(val);
866 }
867
868 return result;
869}
870
871void CheckMessageEqual(
872 const proto_json::messages::UnknownFieldMessage& lhs,
873 const proto_json::messages::UnknownFieldMessage& rhs
874) {
875 EXPECT_EQ(lhs.has_field1(), rhs.has_field1());
876 CheckMessageEqual(lhs.field1(), rhs.field1());
877
878 AreProtobufRepeatedEqual(lhs.field2(), rhs.field2());
879 AreProtobufMapsEqual(lhs.field3(), rhs.field3());
880}
881
882} // namespace protobuf::json::tests
883
884USERVER_NAMESPACE_END