xrpld
Loading...
Searching...
No Matches
TER_test.cpp
1#include <xrpl/beast/unit_test/suite.h>
2#include <xrpl/protocol/TER.h>
3
4#include <cstddef>
5#include <string>
6#include <tuple>
7#include <type_traits>
8
9namespace xrpl {
10
12{
13 void
15 {
16 for (auto i = -400; i < 400; ++i)
17 {
18 TER const t = TER::fromInt(i);
19 auto inRange = isTelLocal(t) || isTemMalformed(t) || isTefFailure(t) || isTerRetry(t) ||
20 isTesSuccess(t) || isTecClaim(t);
21
22 std::string token, text;
23 auto good = transResultInfo(t, token, text);
24 BEAST_EXPECT(inRange || !good);
25 BEAST_EXPECT(transToken(t) == (good ? token : "-"));
26 BEAST_EXPECT(transHuman(t) == (good ? text : "-"));
27
28 auto code = transCode(token);
29 BEAST_EXPECT(good == !!code);
30 BEAST_EXPECT(!code || *code == t);
31 }
32 }
33
34 // Helper template that makes sure two types are not convertible or
35 // assignable if not the same.
36 // o I1 one tuple index.
37 // o I2 other tuple index.
38 // o Tup is expected to be a tuple.
39 // It's a functor, rather than a function template, since a class template
40 // can be a template argument without being full specified.
41 template <std::size_t I1, std::size_t I2>
43 {
44 public:
45 template <typename Tup>
46 void
47 operator()(Tup const& tup, beast::unit_test::Suite&) const
48 {
49 // Entries in the tuple should not be convertible or assignable
50 // unless they are the same types.
51 using To_t = std::decay_t<decltype(std::get<I1>(tup))>;
52 using From_t = std::decay_t<decltype(std::get<I2>(tup))>;
53 static_assert(
55 static_assert(
57 "Construct err");
58 static_assert(
60 "Assign err");
61
62 // Assignment or conversion from integer to type should never work.
63 static_assert(!std::is_convertible_v<int, To_t>, "Convert err");
64 static_assert(!std::is_constructible_v<To_t, int>, "Construct err");
65 static_assert(!std::is_assignable_v<To_t&, int const&>, "Assign err");
66 }
67 };
68
69 // Fast iteration over the tuple.
70 template <
71 std::size_t I1,
72 std::size_t I2,
73 template <std::size_t, std::size_t> class Func,
74 typename Tup>
75 void
77 requires(I1 != 0)
78 {
79 Func<I1, I2> const func;
80 func(tup, s);
81 testIterate<I1 - 1, I2, Func>(tup, s);
82 }
83
84 // Slow iteration over the tuple.
85 template <
86 std::size_t I1,
87 std::size_t I2,
88 template <std::size_t, std::size_t> class Func,
89 typename Tup>
90 void
92 requires(I1 == 0 && I2 != 0)
93 {
94 Func<I1, I2> const func;
95 func(tup, s);
96 testIterate<std::tuple_size_v<Tup> - 1, I2 - 1, Func>(tup, s);
97 }
98
99 // Finish iteration over the tuple.
100 template <
101 std::size_t I1,
102 std::size_t I2,
103 template <std::size_t, std::size_t> class Func,
104 typename Tup>
105 void
107 requires(I1 == 0 && I2 == 0)
108 {
109 Func<I1, I2> const func;
110 func(tup, s);
111 }
112
113 void
115 {
116 // Verify that valid conversions are valid and invalid conversions
117 // are not valid.
118
119 // Examples of each kind of enum.
120 static auto const kTerEnums = std::make_tuple(
122 static int const kHiIndex{std::tuple_size_v<decltype(kTerEnums)> - 1};
123
124 // Verify that enums cannot be converted to other enum types.
126
127 // Lambda that verifies assignability and convertibility.
128 auto isConvertible = [](auto from, auto to) {
129 using From_t = std::decay_t<decltype(from)>;
130 using To_t = std::decay_t<decltype(to)>;
131 static_assert(std::is_convertible_v<From_t, To_t>, "Convert err");
132 static_assert(std::is_constructible_v<To_t, From_t>, "Construct err");
133 static_assert(std::is_assignable_v<To_t&, From_t const&>, "Assign err");
134 };
135
136 // Verify the right types convert to NotTEC.
137 NotTEC const notTec;
138 isConvertible(telLOCAL_ERROR, notTec);
139 isConvertible(temMALFORMED, notTec);
140 isConvertible(tefFAILURE, notTec);
141 isConvertible(terRETRY, notTec);
142 isConvertible(tesSUCCESS, notTec);
143 isConvertible(notTec, notTec);
144
145 // Lambda that verifies types and not assignable or convertible.
146 auto notConvertible = [](auto from, auto to) {
147 using To_t = std::decay_t<decltype(to)>;
148 using From_t = std::decay_t<decltype(from)>;
149 static_assert(!std::is_convertible_v<From_t, To_t>, "Convert err");
150 static_assert(!std::is_constructible_v<To_t, From_t>, "Construct err");
151 static_assert(!std::is_assignable_v<To_t&, From_t const&>, "Assign err");
152 };
153
154 // Verify types that shouldn't convert to NotTEC.
155 TER const ter;
156 notConvertible(tecCLAIM, notTec);
157 notConvertible(ter, notTec);
158 notConvertible(4, notTec);
159
160 // Verify the right types convert to TER.
161 isConvertible(telLOCAL_ERROR, ter);
162 isConvertible(temMALFORMED, ter);
163 isConvertible(tefFAILURE, ter);
164 isConvertible(terRETRY, ter);
165 isConvertible(tesSUCCESS, ter);
166 isConvertible(tecCLAIM, ter);
167 isConvertible(notTec, ter);
168 isConvertible(ter, ter);
169
170 // Verify that you can't convert from int to ter.
171 notConvertible(4, ter);
172 }
173
174 // Helper template that makes sure two types are comparable. Also
175 // verifies that one of the types does not compare to int.
176 // o I1 one tuple index.
177 // o I2 other tuple index.
178 // o Tup is expected to be a tuple.
179 // It's a functor, rather than a function template, since a class template
180 // can be a template argument without being full specified.
181 template <std::size_t I1, std::size_t I2>
183 {
184 public:
185 template <typename Tup>
186 void
187 operator()(Tup const& tup, beast::unit_test::Suite& s) const
188 {
189 // All entries in the tuple should be comparable one to the other.
190 auto const lhs = std::get<I1>(tup);
191 auto const rhs = std::get<I2>(tup);
192
193 static_assert(std::is_same_v<decltype(operator==(lhs, rhs)), bool>, "== err");
194
195 static_assert(std::is_same_v<decltype(operator!=(lhs, rhs)), bool>, "!= err");
196
197 static_assert(std::is_same_v<decltype(operator<(lhs, rhs)), bool>, "< err");
198
199 static_assert(std::is_same_v<decltype(operator<=(lhs, rhs)), bool>, "<= err");
200
201 static_assert(std::is_same_v<decltype(operator>(lhs, rhs)), bool>, "> err");
202
203 static_assert(std::is_same_v<decltype(operator>=(lhs, rhs)), bool>, ">= err");
204
205 // Make sure a sampling of TER types exhibit the expected behavior
206 // for all comparison operators.
207 s.expect((lhs == rhs) == (TERtoInt(lhs) == TERtoInt(rhs)));
208 s.expect((lhs != rhs) == (TERtoInt(lhs) != TERtoInt(rhs)));
209 s.expect((lhs < rhs) == (TERtoInt(lhs) < TERtoInt(rhs)));
210 s.expect((lhs <= rhs) == (TERtoInt(lhs) <= TERtoInt(rhs)));
211 s.expect((lhs > rhs) == (TERtoInt(lhs) > TERtoInt(rhs)));
212 s.expect((lhs >= rhs) == (TERtoInt(lhs) >= TERtoInt(rhs)));
213 }
214 };
215
216 void
218 {
219 // All of the TER-related types should be comparable.
220
221 // Examples of all the types we expect to successfully compare.
222 static auto const kTers = std::make_tuple(
226 terRETRY,
228 tecCLAIM,
230 TER{tecCLAIM});
231 static int const kHiIndex{std::tuple_size_v<decltype(kTers)> - 1};
232
233 // Verify that all types in the ters tuple can be compared with all
234 // the other types in ters.
236 }
237
238 void
239 run() override
240 {
244 }
245};
246
248
249} // namespace xrpl
A testsuite class.
Definition suite.h:52
bool expect(Condition const &shouldBeTrue)
Evaluate a test condition.
Definition suite.h:235
static constexpr TERSubset fromInt(int from)
Definition TER.h:437
void operator()(Tup const &tup, beast::unit_test::Suite &s) const
Definition TER_test.cpp:187
void operator()(Tup const &tup, beast::unit_test::Suite &) const
Definition TER_test.cpp:47
T is_assignable_v
T is_constructible_v
T is_convertible_v
T is_same_v
T make_tuple(T... args)
Use hash_* containers for keys that do not need a cryptographically secure hashing algorithm.
Definition algorithm.h:5
@ telLOCAL_ERROR
Definition TER.h:38
bool operator<(Slice const &lhs, Slice const &rhs) noexcept
Definition Slice.h:212
@ terRETRY
Definition TER.h:210
bool isTerRetry(TER x) noexcept
Definition TER.h:670
constexpr bool operator==(BaseUInt< Bits, Tag > const &lhs, BaseUInt< Bits, Tag > const &rhs)
Definition base_uint.h:606
bool operator>=(STAmount const &lhs, STAmount const &rhs)
Definition STAmount.h:658
@ tefFAILURE
Definition TER.h:158
std::string transHuman(TER code)
Definition TER.cpp:260
bool transResultInfo(TER code, std::string &token, std::string &text)
Definition TER.cpp:236
std::string transToken(TER code)
Definition TER.cpp:251
bool operator!=(SecretKey const &lhs, SecretKey const &rhs)=delete
TERSubset< CanCvtToNotTEC > NotTEC
Definition TER.h:607
bool isTefFailure(TER x) noexcept
Definition TER.h:664
bool operator<=(STAmount const &lhs, STAmount const &rhs)
Definition STAmount.h:652
bool isTelLocal(TER x) noexcept
Definition TER.h:652
constexpr TERUnderlyingType TERtoInt(TELcodes v)
Definition TER.h:379
@ temMALFORMED
Definition TER.h:75
bool isTesSuccess(TER x) noexcept
Definition TER.h:676
TERSubset< CanCvtToTER > TER
Definition TER.h:647
std::optional< TER > transCode(std::string const &token)
Definition TER.cpp:269
@ tecCLAIM
Definition TER.h:284
bool isTecClaim(TER x) noexcept
Definition TER.h:683
BEAST_DEFINE_TESTSUITE(AccountTxPaging, app, xrpl)
bool isTemMalformed(TER x) noexcept
Definition TER.h:658
@ tesSUCCESS
Definition TER.h:245
void testIterate(Tup const &tup, beast::unit_test::Suite &s)
Definition TER_test.cpp:91
void testTransResultInfo()
Definition TER_test.cpp:14
void testComparison()
Definition TER_test.cpp:217
void testConversion()
Definition TER_test.cpp:114
void testIterate(Tup const &tup, beast::unit_test::Suite &s)
Definition TER_test.cpp:106
void testIterate(Tup const &tup, beast::unit_test::Suite &s)
Definition TER_test.cpp:76
void run() override
Runs the suite.
Definition TER_test.cpp:239
T tuple_size_v