blob: b560aaa6f5fdc61b3acf137be78dc08ccfa020ed [file] [log] [blame]
Austin Schuh1ef01ef2021-02-07 20:40:36 -08001#ifndef AOS_TESTING_FLATBUFFER_EQ_H_
2#define AOS_TESTING_FLATBUFFER_EQ_H_
3
Philipp Schrader790cb542023-07-05 21:06:52 -07004#include "gmock/gmock.h"
5
Austin Schuh1ef01ef2021-02-07 20:40:36 -08006#include "aos/flatbuffer_merge.h"
7#include "aos/flatbuffers.h"
8#include "aos/json_to_flatbuffer.h"
Austin Schuh1ef01ef2021-02-07 20:40:36 -08009
10namespace aos {
11namespace testing {
12
Brian Silverman497838d2021-02-17 21:39:50 -080013// Use FlatbufferUnwrapped to instantiate this.
Austin Schuh1ef01ef2021-02-07 20:40:36 -080014template <typename T>
Brian Silverman497838d2021-02-17 21:39:50 -080015class FlatbufferUnwrappedMatcher {
Austin Schuh1ef01ef2021-02-07 20:40:36 -080016 public:
Brian Silverman497838d2021-02-17 21:39:50 -080017 FlatbufferUnwrappedMatcher(::testing::Matcher<const T *> matcher)
18 : matcher_(std::move(matcher)) {}
Austin Schuh1ef01ef2021-02-07 20:40:36 -080019
20 bool MatchAndExplain(const T *t,
21 ::testing::MatchResultListener *listener) const {
Brian Silverman497838d2021-02-17 21:39:50 -080022 return matcher_.MatchAndExplain(t, listener);
Austin Schuh1ef01ef2021-02-07 20:40:36 -080023 }
24
25 bool MatchAndExplain(const aos::Flatbuffer<T> &t,
26 ::testing::MatchResultListener *listener) const {
27 return MatchAndExplain(&t.message(), listener);
28 }
29
Brian Silverman497838d2021-02-17 21:39:50 -080030 void DescribeTo(std::ostream *os) const { matcher_.DescribeTo(os); }
31
32 void DescribeNegationTo(std::ostream *os) const {
33 matcher_.DescribeNegationTo(os);
34 }
35
36 private:
37 const ::testing::Matcher<const T *> matcher_;
38};
39
40// Returns a googlemock matcher which will compare a `const T *` or a `const
41// aos::Flatbuffer<T> &` against another matcher which only handles `const T *`.
42// This will automatically propagate the nice error messages.
43//
44// T must be a flatbuffer table type.
45template <typename T>
46inline auto FlatbufferUnwrapped(::testing::Matcher<const T *> matcher) {
47 return ::testing::MakePolymorphicMatcher(
48 FlatbufferUnwrappedMatcher(std::move(matcher)));
49}
50
51// Use FlatbufferEq to instantiate this.
52template <typename T>
53class FlatbufferEqMatcher : public ::testing::MatcherInterface<const T *> {
54 public:
Austin Schuh2bc31622021-11-19 13:34:17 -080055 FlatbufferEqMatcher(aos::FlatbufferVector<T> expected)
Brian Silverman497838d2021-02-17 21:39:50 -080056 : expected_(std::move(expected)) {}
57 ~FlatbufferEqMatcher() override = default;
58
59 bool MatchAndExplain(
60 const T *t, ::testing::MatchResultListener *listener) const override {
61 *listener << "is " << aos::FlatbufferToJson(t);
62 return aos::CompareFlatBuffer(t, &expected_.message());
63 }
64
65 void DescribeTo(std::ostream *os) const override {
Austin Schuh1ef01ef2021-02-07 20:40:36 -080066 *os << "is equal to " << aos::FlatbufferToJson(&expected_.message());
67 }
68
Brian Silverman497838d2021-02-17 21:39:50 -080069 void DescribeNegationTo(std::ostream *os) const override {
Austin Schuh1ef01ef2021-02-07 20:40:36 -080070 *os << "is not equal to " << aos::FlatbufferToJson(&expected_.message());
71 }
72
73 private:
Austin Schuh2bc31622021-11-19 13:34:17 -080074 const aos::FlatbufferVector<T> expected_;
Austin Schuh1ef01ef2021-02-07 20:40:36 -080075};
76
77// Returns a googlemock matcher which will compare a `const T *` or a `const
78// aos::Flatbuffer<T> &` against expected. This will automatically give nice
79// error messages if they don't match.
80//
81// T must be a flatbuffer table type.
82template <typename T>
Brian Silverman497838d2021-02-17 21:39:50 -080083inline auto FlatbufferEq(const aos::NonSizePrefixedFlatbuffer<T> &expected) {
84 return FlatbufferUnwrapped(::testing::MakeMatcher(
Austin Schuh2bc31622021-11-19 13:34:17 -080085 new FlatbufferEqMatcher(aos::FlatbufferVector<T>(expected))));
Austin Schuh1ef01ef2021-02-07 20:40:36 -080086}
87
88} // namespace testing
89} // namespace aos
90
91#endif // AOS_TESTING_FLATBUFFER_EQ_H_