rippled
Loading...
Searching...
No Matches
AMMTests.cpp
1// Auto-generated unit tests for ledger entry AMM
2
3
4#include <gtest/gtest.h>
5
6#include <protocol_autogen/TestHelpers.h>
7
8#include <xrpl/protocol/STLedgerEntry.h>
9#include <xrpl/protocol_autogen/ledger_entries/AMM.h>
10#include <xrpl/protocol_autogen/ledger_entries/Ticket.h>
11
12#include <string>
13
14namespace xrpl::ledger_entries {
15
16// 1 & 4) Set fields via builder setters, build, then read them back via
17// wrapper getters. After build(), validate() should succeed for both the
18// builder's STObject and the wrapper's SLE.
19TEST(AMMTests, BuilderSettersRoundTrip)
20{
21 uint256 const index{1u};
22
23 auto const accountValue = canonical_ACCOUNT();
24 auto const tradingFeeValue = canonical_UINT16();
25 auto const voteSlotsValue = canonical_ARRAY();
26 auto const auctionSlotValue = canonical_OBJECT();
27 auto const lPTokenBalanceValue = canonical_AMOUNT();
28 auto const assetValue = canonical_ISSUE();
29 auto const asset2Value = canonical_ISSUE();
30 auto const ownerNodeValue = canonical_UINT64();
31 auto const previousTxnIDValue = canonical_UINT256();
32 auto const previousTxnLgrSeqValue = canonical_UINT32();
33
34 AMMBuilder builder{
35 accountValue,
36 lPTokenBalanceValue,
37 assetValue,
38 asset2Value,
39 ownerNodeValue
40 };
41
42 builder.setTradingFee(tradingFeeValue);
43 builder.setVoteSlots(voteSlotsValue);
44 builder.setAuctionSlot(auctionSlotValue);
45 builder.setPreviousTxnID(previousTxnIDValue);
46 builder.setPreviousTxnLgrSeq(previousTxnLgrSeqValue);
47
48 builder.setLedgerIndex(index);
49 builder.setFlags(0x1u);
50
51 EXPECT_TRUE(builder.validate());
52
53 auto const entry = builder.build(index);
54
55 EXPECT_TRUE(entry.validate());
56
57 {
58 auto const& expected = accountValue;
59 auto const actual = entry.getAccount();
60 expectEqualField(expected, actual, "sfAccount");
61 }
62
63 {
64 auto const& expected = lPTokenBalanceValue;
65 auto const actual = entry.getLPTokenBalance();
66 expectEqualField(expected, actual, "sfLPTokenBalance");
67 }
68
69 {
70 auto const& expected = assetValue;
71 auto const actual = entry.getAsset();
72 expectEqualField(expected, actual, "sfAsset");
73 }
74
75 {
76 auto const& expected = asset2Value;
77 auto const actual = entry.getAsset2();
78 expectEqualField(expected, actual, "sfAsset2");
79 }
80
81 {
82 auto const& expected = ownerNodeValue;
83 auto const actual = entry.getOwnerNode();
84 expectEqualField(expected, actual, "sfOwnerNode");
85 }
86
87 {
88 auto const& expected = tradingFeeValue;
89 auto const actualOpt = entry.getTradingFee();
90 ASSERT_TRUE(actualOpt.has_value());
91 expectEqualField(expected, *actualOpt, "sfTradingFee");
92 EXPECT_TRUE(entry.hasTradingFee());
93 }
94
95 {
96 auto const& expected = voteSlotsValue;
97 auto const actualOpt = entry.getVoteSlots();
98 ASSERT_TRUE(actualOpt.has_value());
99 expectEqualField(expected, *actualOpt, "sfVoteSlots");
100 EXPECT_TRUE(entry.hasVoteSlots());
101 }
102
103 {
104 auto const& expected = auctionSlotValue;
105 auto const actualOpt = entry.getAuctionSlot();
106 ASSERT_TRUE(actualOpt.has_value());
107 expectEqualField(expected, *actualOpt, "sfAuctionSlot");
108 EXPECT_TRUE(entry.hasAuctionSlot());
109 }
110
111 {
112 auto const& expected = previousTxnIDValue;
113 auto const actualOpt = entry.getPreviousTxnID();
114 ASSERT_TRUE(actualOpt.has_value());
115 expectEqualField(expected, *actualOpt, "sfPreviousTxnID");
116 EXPECT_TRUE(entry.hasPreviousTxnID());
117 }
118
119 {
120 auto const& expected = previousTxnLgrSeqValue;
121 auto const actualOpt = entry.getPreviousTxnLgrSeq();
122 ASSERT_TRUE(actualOpt.has_value());
123 expectEqualField(expected, *actualOpt, "sfPreviousTxnLgrSeq");
124 EXPECT_TRUE(entry.hasPreviousTxnLgrSeq());
125 }
126
127 EXPECT_TRUE(entry.hasLedgerIndex());
128 auto const ledgerIndex = entry.getLedgerIndex();
129 ASSERT_TRUE(ledgerIndex.has_value());
130 EXPECT_EQ(*ledgerIndex, index);
131 EXPECT_EQ(entry.getKey(), index);
132}
133
134// 2 & 4) Start from an SLE, set fields directly on it, construct a builder
135// from that SLE, build a new wrapper, and verify all fields (and validate()).
136TEST(AMMTests, BuilderFromSleRoundTrip)
137{
138 uint256 const index{2u};
139
140 auto const accountValue = canonical_ACCOUNT();
141 auto const tradingFeeValue = canonical_UINT16();
142 auto const voteSlotsValue = canonical_ARRAY();
143 auto const auctionSlotValue = canonical_OBJECT();
144 auto const lPTokenBalanceValue = canonical_AMOUNT();
145 auto const assetValue = canonical_ISSUE();
146 auto const asset2Value = canonical_ISSUE();
147 auto const ownerNodeValue = canonical_UINT64();
148 auto const previousTxnIDValue = canonical_UINT256();
149 auto const previousTxnLgrSeqValue = canonical_UINT32();
150
151 auto sle = std::make_shared<SLE>(AMM::entryType, index);
152
153 sle->at(sfAccount) = accountValue;
154 sle->at(sfTradingFee) = tradingFeeValue;
155 sle->setFieldArray(sfVoteSlots, voteSlotsValue);
156 sle->setFieldObject(sfAuctionSlot, auctionSlotValue);
157 sle->at(sfLPTokenBalance) = lPTokenBalanceValue;
158 sle->at(sfAsset) = STIssue(sfAsset, assetValue);
159 sle->at(sfAsset2) = STIssue(sfAsset2, asset2Value);
160 sle->at(sfOwnerNode) = ownerNodeValue;
161 sle->at(sfPreviousTxnID) = previousTxnIDValue;
162 sle->at(sfPreviousTxnLgrSeq) = previousTxnLgrSeqValue;
163
164 AMMBuilder builderFromSle{sle};
165 EXPECT_TRUE(builderFromSle.validate());
166
167 auto const entryFromBuilder = builderFromSle.build(index);
168
169 AMM entryFromSle{sle};
170 EXPECT_TRUE(entryFromBuilder.validate());
171 EXPECT_TRUE(entryFromSle.validate());
172
173 {
174 auto const& expected = accountValue;
175
176 auto const fromSle = entryFromSle.getAccount();
177 auto const fromBuilder = entryFromBuilder.getAccount();
178
179 expectEqualField(expected, fromSle, "sfAccount");
180 expectEqualField(expected, fromBuilder, "sfAccount");
181 }
182
183 {
184 auto const& expected = lPTokenBalanceValue;
185
186 auto const fromSle = entryFromSle.getLPTokenBalance();
187 auto const fromBuilder = entryFromBuilder.getLPTokenBalance();
188
189 expectEqualField(expected, fromSle, "sfLPTokenBalance");
190 expectEqualField(expected, fromBuilder, "sfLPTokenBalance");
191 }
192
193 {
194 auto const& expected = assetValue;
195
196 auto const fromSle = entryFromSle.getAsset();
197 auto const fromBuilder = entryFromBuilder.getAsset();
198
199 expectEqualField(expected, fromSle, "sfAsset");
200 expectEqualField(expected, fromBuilder, "sfAsset");
201 }
202
203 {
204 auto const& expected = asset2Value;
205
206 auto const fromSle = entryFromSle.getAsset2();
207 auto const fromBuilder = entryFromBuilder.getAsset2();
208
209 expectEqualField(expected, fromSle, "sfAsset2");
210 expectEqualField(expected, fromBuilder, "sfAsset2");
211 }
212
213 {
214 auto const& expected = ownerNodeValue;
215
216 auto const fromSle = entryFromSle.getOwnerNode();
217 auto const fromBuilder = entryFromBuilder.getOwnerNode();
218
219 expectEqualField(expected, fromSle, "sfOwnerNode");
220 expectEqualField(expected, fromBuilder, "sfOwnerNode");
221 }
222
223 {
224 auto const& expected = tradingFeeValue;
225
226 auto const fromSleOpt = entryFromSle.getTradingFee();
227 auto const fromBuilderOpt = entryFromBuilder.getTradingFee();
228
229 ASSERT_TRUE(fromSleOpt.has_value());
230 ASSERT_TRUE(fromBuilderOpt.has_value());
231
232 expectEqualField(expected, *fromSleOpt, "sfTradingFee");
233 expectEqualField(expected, *fromBuilderOpt, "sfTradingFee");
234 }
235
236 {
237 auto const& expected = voteSlotsValue;
238
239 auto const fromSleOpt = entryFromSle.getVoteSlots();
240 auto const fromBuilderOpt = entryFromBuilder.getVoteSlots();
241
242 ASSERT_TRUE(fromSleOpt.has_value());
243 ASSERT_TRUE(fromBuilderOpt.has_value());
244
245 expectEqualField(expected, *fromSleOpt, "sfVoteSlots");
246 expectEqualField(expected, *fromBuilderOpt, "sfVoteSlots");
247 }
248
249 {
250 auto const& expected = auctionSlotValue;
251
252 auto const fromSleOpt = entryFromSle.getAuctionSlot();
253 auto const fromBuilderOpt = entryFromBuilder.getAuctionSlot();
254
255 ASSERT_TRUE(fromSleOpt.has_value());
256 ASSERT_TRUE(fromBuilderOpt.has_value());
257
258 expectEqualField(expected, *fromSleOpt, "sfAuctionSlot");
259 expectEqualField(expected, *fromBuilderOpt, "sfAuctionSlot");
260 }
261
262 {
263 auto const& expected = previousTxnIDValue;
264
265 auto const fromSleOpt = entryFromSle.getPreviousTxnID();
266 auto const fromBuilderOpt = entryFromBuilder.getPreviousTxnID();
267
268 ASSERT_TRUE(fromSleOpt.has_value());
269 ASSERT_TRUE(fromBuilderOpt.has_value());
270
271 expectEqualField(expected, *fromSleOpt, "sfPreviousTxnID");
272 expectEqualField(expected, *fromBuilderOpt, "sfPreviousTxnID");
273 }
274
275 {
276 auto const& expected = previousTxnLgrSeqValue;
277
278 auto const fromSleOpt = entryFromSle.getPreviousTxnLgrSeq();
279 auto const fromBuilderOpt = entryFromBuilder.getPreviousTxnLgrSeq();
280
281 ASSERT_TRUE(fromSleOpt.has_value());
282 ASSERT_TRUE(fromBuilderOpt.has_value());
283
284 expectEqualField(expected, *fromSleOpt, "sfPreviousTxnLgrSeq");
285 expectEqualField(expected, *fromBuilderOpt, "sfPreviousTxnLgrSeq");
286 }
287
288 EXPECT_EQ(entryFromSle.getKey(), index);
289 EXPECT_EQ(entryFromBuilder.getKey(), index);
290}
291
292// 3) Verify wrapper throws when constructed from wrong ledger entry type.
293TEST(AMMTests, WrapperThrowsOnWrongEntryType)
294{
295 uint256 const index{3u};
296
297 // Build a valid ledger entry of a different type
298 // Ticket requires: Account, OwnerNode, TicketSequence, PreviousTxnID, PreviousTxnLgrSeq
299 // Check requires: Account, Destination, SendMax, Sequence, OwnerNode, DestinationNode, PreviousTxnID, PreviousTxnLgrSeq
300 TicketBuilder wrongBuilder{
306 auto wrongEntry = wrongBuilder.build(index);
307
308 EXPECT_THROW(AMM{wrongEntry.getSle()}, std::runtime_error);
309}
310
311// 4) Verify builder throws when constructed from wrong ledger entry type.
312TEST(AMMTests, BuilderThrowsOnWrongEntryType)
313{
314 uint256 const index{4u};
315
316 // Build a valid ledger entry of a different type
317 TicketBuilder wrongBuilder{
323 auto wrongEntry = wrongBuilder.build(index);
324
325 EXPECT_THROW(AMMBuilder{wrongEntry.getSle()}, std::runtime_error);
326}
327
328// 5) Build with only required fields and verify optional fields return nullopt.
329TEST(AMMTests, OptionalFieldsReturnNullopt)
330{
331 uint256 const index{3u};
332
333 auto const accountValue = canonical_ACCOUNT();
334 auto const lPTokenBalanceValue = canonical_AMOUNT();
335 auto const assetValue = canonical_ISSUE();
336 auto const asset2Value = canonical_ISSUE();
337 auto const ownerNodeValue = canonical_UINT64();
338
339 AMMBuilder builder{
340 accountValue,
341 lPTokenBalanceValue,
342 assetValue,
343 asset2Value,
344 ownerNodeValue
345 };
346
347 auto const entry = builder.build(index);
348
349 // Verify optional fields are not present
350 EXPECT_FALSE(entry.hasTradingFee());
351 EXPECT_FALSE(entry.getTradingFee().has_value());
352 EXPECT_FALSE(entry.hasVoteSlots());
353 EXPECT_FALSE(entry.getVoteSlots().has_value());
354 EXPECT_FALSE(entry.hasAuctionSlot());
355 EXPECT_FALSE(entry.getAuctionSlot().has_value());
356 EXPECT_FALSE(entry.hasPreviousTxnID());
357 EXPECT_FALSE(entry.getPreviousTxnID().has_value());
358 EXPECT_FALSE(entry.hasPreviousTxnLgrSeq());
359 EXPECT_FALSE(entry.getPreviousTxnLgrSeq().has_value());
360}
361}
AMMBuilder & setTradingFee(std::decay_t< typename SF_UINT16::type::value_type > const &value)
Set sfTradingFee (soeDEFAULT)
AMMBuilder & setPreviousTxnLgrSeq(std::decay_t< typename SF_UINT32::type::value_type > const &value)
Set sfPreviousTxnLgrSeq (soeOPTIONAL)
AMMBuilder & setAuctionSlot(STObject const &value)
Set sfAuctionSlot (soeOPTIONAL)
AMMBuilder & setPreviousTxnID(std::decay_t< typename SF_UINT256::type::value_type > const &value)
Set sfPreviousTxnID (soeOPTIONAL)
AMMBuilder & setVoteSlots(STArray const &value)
Set sfVoteSlots (soeOPTIONAL)
std::shared_ptr< SLE const > getSle() const
Get the underlying SLE object.
Derived & setLedgerIndex(uint256 const &value)
Set the ledger index.
Derived & setFlags(uint32_t value)
Set the flags.
Builder for Ticket ledger entries.
Definition Ticket.h:112
T is_same_v
TEST(AccountRootTests, BuilderSettersRoundTrip)
void expectEqualField(T const &expected, T const &actual, char const *fieldName)