3#include <xrpld/app/tx/applySteps.h>
5#include <xrpl/ledger/Dir.h>
6#include <xrpl/ledger/Sandbox.h>
7#include <xrpl/protocol/Feature.h>
8#include <xrpl/protocol/Indexes.h>
9#include <xrpl/protocol/STAmount.h>
10#include <xrpl/protocol/TxFlags.h>
11#include <xrpl/protocol/jss.h>
28 if (sle && sle->isFieldPresent(sfLockedAmount))
29 return (*sle)[sfLockedAmount];
37 if (sle && sle->isFieldPresent(sfLockedAmount))
38 return (*sle)[sfLockedAmount];
49 params[jss::account] = account.human();
50 auto jrr = env.
rpc(
"json",
"gateway_balances",
to_string(params));
51 auto const result = jrr[jss::result];
52 auto const obligations =
54 if (obligations.isNull())
55 return {
STAmount(issue, 0), account.name()};
57 return {
amount, account.name()};
67 params[jss::account] = account.human();
68 auto jrr = env.
rpc(
"json",
"gateway_balances",
to_string(params));
69 auto const result = jrr[jss::result];
72 return {
STAmount(issue, 0), account.name()};
74 return {
amount, account.name()};
85 for (
bool const withTokenEscrow : {
false,
true})
88 withTokenEscrow ? features : features - featureTokenEscrow;
89 Env env{*
this, amend};
90 auto const baseFee = env.
current()->fees().base;
91 auto const alice =
Account(
"alice");
92 auto const bob =
Account(
"bob");
93 auto const gw =
Account{
"gateway"};
94 auto const USD = gw[
"USD"];
95 env.fund(
XRP(5000), alice, bob, gw);
98 env.trust(USD(10'000), alice, bob);
100 env(
pay(gw, alice, USD(5000)));
101 env(
pay(gw, bob, USD(5000)));
104 auto const createResult =
106 auto const finishResult =
109 auto const seq1 = env.seq(alice);
123 auto const seq2 = env.seq(alice);
135 for (
bool const withTokenEscrow : {
false,
true})
138 withTokenEscrow ? features : features - featureTokenEscrow;
139 Env env{*
this, amend};
140 auto const baseFee = env.
current()->fees().base;
141 auto const alice =
Account(
"alice");
142 auto const bob =
Account(
"bob");
143 auto const gw =
Account{
"gateway"};
144 auto const USD = gw[
"USD"];
145 env.fund(
XRP(5000), alice, bob, gw);
148 env.trust(USD(10'000), alice, bob);
150 env(
pay(gw, alice, USD(5000)));
151 env(
pay(gw, bob, USD(5000)));
154 auto const seq1 = env.seq(alice);
175 Env env{*
this, features};
176 auto const baseFee = env.current()->fees().base;
177 auto const alice =
Account(
"alice");
178 auto const bob =
Account(
"bob");
179 auto const gw =
Account{
"gateway"};
180 auto const USD = gw[
"USD"];
181 env.fund(
XRP(5000), alice, bob, gw);
184 env.trust(USD(10'000), alice, bob);
186 env(
pay(gw, alice, USD(5000)));
187 env(
pay(gw, bob, USD(5000)));
191 auto const seq1 = env.seq(alice);
199 auto const seq2 = env.seq(alice);
237 using namespace test::jtx;
242 Env env{*
this, features};
243 auto const alice =
Account(
"alice");
244 auto const bob =
Account(
"bob");
245 auto const gw =
Account{
"gateway"};
246 auto const USD = gw[
"USD"];
247 env.fund(
XRP(5000), alice, bob, gw);
258 Env env{*
this, features};
259 auto const baseFee = env.current()->fees().base;
260 auto const alice =
Account(
"alice");
261 auto const bob =
Account(
"bob");
262 auto const gw =
Account{
"gateway"};
263 auto const USD = gw[
"USD"];
264 env.fund(
XRP(5000), alice, bob, gw);
276 Env env{*
this, features};
277 auto const baseFee = env.current()->fees().base;
278 auto const alice =
Account(
"alice");
279 auto const bob =
Account(
"bob");
280 auto const gw =
Account{
"gateway"};
282 env.fund(
XRP(5000), alice, bob, gw);
297 using namespace test::jtx;
302 Env env{*
this, features};
303 auto const baseFee = env.current()->fees().base;
304 auto const alice =
Account(
"alice");
305 auto const bob =
Account(
"bob");
306 auto const gw =
Account{
"gateway"};
307 auto const USD = gw[
"USD"];
308 env.fund(
XRP(5000), alice, bob, gw);
320 Env env{*
this, features};
321 auto const baseFee = env.current()->fees().base;
322 auto const alice =
Account(
"alice");
323 auto const bob =
Account(
"bob");
324 auto const gw =
Account{
"gateway"};
325 auto const USD = gw[
"USD"];
326 env.fund(
XRP(5000), alice, bob);
340 Env env{*
this, features};
341 auto const baseFee = env.current()->fees().base;
342 auto const alice =
Account(
"alice");
343 auto const bob =
Account(
"bob");
344 auto const gw =
Account{
"gateway"};
345 auto const USD = gw[
"USD"];
346 env.fund(
XRP(5000), alice, bob, gw);
348 env.trust(USD(10'000), alice, bob);
350 env(
pay(gw, alice, USD(5000)));
351 env(
pay(gw, bob, USD(5000)));
364 Env env{*
this, features};
365 auto const baseFee = env.current()->fees().base;
366 auto const alice =
Account(
"alice");
367 auto const bob =
Account(
"bob");
368 auto const gw =
Account{
"gateway"};
369 auto const USD = gw[
"USD"];
370 env.fund(
XRP(5000), alice, bob, gw);
385 Env env{*
this, features};
386 auto const baseFee = env.current()->fees().base;
387 auto const alice =
Account(
"alice");
388 auto const bob =
Account(
"bob");
389 auto const gw =
Account{
"gateway"};
390 auto const USD = gw[
"USD"];
391 env.fund(
XRP(5000), alice, bob, gw);
395 env.trust(USD(10'000), alice, bob);
408 Env env{*
this, features};
409 auto const baseFee = env.current()->fees().base;
410 auto const alice =
Account(
"alice");
411 auto const bob =
Account(
"bob");
412 auto const gw =
Account{
"gateway"};
413 auto const USD = gw[
"USD"];
414 auto const aliceUSD = alice[
"USD"];
415 env.fund(
XRP(5000), alice, bob, gw);
420 env.trust(USD(10'000), alice, bob);
434 Env env{*
this, features};
435 auto const alice =
Account(
"alice");
436 auto const bob =
Account(
"bob");
437 auto const gw =
Account{
"gateway"};
438 auto const USD = gw[
"USD"];
439 auto const baseFee = env.current()->fees().base;
440 env.fund(
XRP(10'000), alice, bob, gw);
443 env(
trust(alice, USD(100'000)));
444 env(
trust(bob, USD(100'000)));
446 env(
pay(gw, alice, USD(10'000)));
447 env(
pay(gw, bob, USD(10'000)));
465 Env env{*
this, features};
466 auto const alice =
Account(
"alice");
467 auto const bob =
Account(
"bob");
468 auto const gw =
Account{
"gateway"};
469 auto const USD = gw[
"USD"];
470 auto const baseFee = env.current()->fees().base;
471 env.fund(
XRP(10'000), alice, bob, gw);
474 env(
trust(alice, USD(100'000)));
475 env(
trust(bob, USD(100'000)));
477 env(
pay(gw, alice, USD(10'000)));
478 env(
pay(gw, bob, USD(10'000)));
496 Env env{*
this, features};
497 auto const alice =
Account(
"alice");
498 auto const bob =
Account(
"bob");
499 auto const gw =
Account{
"gateway"};
500 auto const USD = gw[
"USD"];
501 auto const baseFee = env.current()->fees().base;
502 env.fund(
XRP(10'000), alice, bob, gw);
505 env(
trust(alice, USD(100'000)));
506 env(
trust(bob, USD(100'000)));
520 Env env{*
this, features};
521 auto const alice =
Account(
"alice");
522 auto const bob =
Account(
"bob");
523 auto const gw =
Account{
"gateway"};
524 auto const USD = gw[
"USD"];
525 auto const baseFee = env.current()->fees().base;
526 env.fund(
XRP(10'000), alice, bob, gw);
529 env(
trust(alice, USD(100'000)));
530 env(
trust(bob, USD(100'000)));
532 env(
pay(gw, alice, USD(10'000)));
533 env(
pay(gw, bob, USD(10'000)));
546 Env env{*
this, features};
547 auto const alice =
Account(
"alice");
548 auto const bob =
Account(
"bob");
549 auto const gw =
Account{
"gateway"};
550 auto const USD = gw[
"USD"];
551 auto const baseFee = env.current()->fees().base;
552 env.fund(
XRP(10'000), alice, bob, gw);
555 env.trust(USD(100000000000000000), alice);
556 env.trust(USD(100000000000000000), bob);
558 env(
pay(gw, alice, USD(10000000000000000)));
559 env(
pay(gw, bob, USD(1)));
562 bool const largeMantissa = features[featureSingleAssetVault] ||
563 features[featureLendingProtocol];
579 using namespace test::jtx;
584 Env env{*
this, features};
585 auto const baseFee = env.current()->fees().base;
586 auto const alice =
Account(
"alice");
587 auto const bob =
Account(
"bob");
588 auto const gw =
Account{
"gateway"};
589 auto const USD = gw[
"USD"];
590 auto const aliceUSD = alice[
"USD"];
591 auto const bobUSD = bob[
"USD"];
592 env.fund(
XRP(5000), alice, bob, gw);
598 env.trust(USD(10'000), alice, bob);
600 env(
pay(gw, alice, USD(10'000)));
601 env(
pay(gw, bob, USD(10'000)));
604 auto const seq1 = env.seq(alice);
612 env(
pay(bob, gw, USD(10'000)));
614 env(
trust(bob, USD(0)));
617 env.trust(USD(10'000), bob);
631 Env env{*
this, features};
632 auto const baseFee = env.current()->fees().base;
633 auto const alice =
Account(
"alice");
634 auto const bob =
Account(
"bob");
635 auto const gw =
Account{
"gateway"};
636 auto const USD = gw[
"USD"];
637 env.fund(
XRP(5000), alice, bob, gw);
640 env.trust(USD(10'000), alice, bob);
642 env(
pay(gw, alice, USD(10'000)));
643 env(
pay(gw, bob, USD(10'000)));
646 auto const seq1 = env.seq(alice);
671 using namespace test::jtx;
676 Env env{*
this, features};
677 auto const baseFee = env.current()->fees().base;
678 auto const acctReserve = env.current()->fees().reserve;
679 auto const incReserve = env.current()->fees().increment;
680 auto const alice =
Account(
"alice");
681 auto const bob =
Account(
"bob");
682 auto const gw =
Account{
"gateway"};
683 auto const USD = gw[
"USD"];
684 env.fund(
XRP(5000), alice, gw);
685 env.fund(acctReserve + (incReserve - 1), bob);
689 env.trust(USD(10'000), alice);
691 env(
pay(gw, alice, USD(10'000)));
694 auto const seq1 = env.seq(alice);
713 Env env{*
this, features};
714 auto const baseFee = env.current()->fees().base;
715 auto const alice =
Account(
"alice");
716 auto const bob =
Account(
"bob");
717 auto const gw =
Account{
"gateway"};
718 auto const USD = gw[
"USD"];
719 env.fund(
XRP(5000), alice, bob, gw);
723 env.trust(USD(10'000), alice);
725 env(
pay(gw, alice, USD(10'000)));
728 auto const seq1 = env.seq(alice);
747 Env env{*
this, features};
748 auto const baseFee = env.current()->fees().base;
749 auto const alice =
Account(
"alice");
750 auto const bob =
Account(
"bob");
751 auto const gw =
Account{
"gateway"};
752 auto const USD = gw[
"USD"];
753 env.fund(
XRP(5000), alice, bob, gw);
757 env.trust(USD(1000), alice, bob);
759 env(
pay(gw, alice, USD(1000)));
762 auto const seq1 = env.seq(alice);
770 env.trust(USD(1), bob);
784 Env env{*
this, features};
785 auto const baseFee = env.current()->fees().base;
786 auto const alice =
Account(
"alice");
787 auto const bob =
Account(
"bob");
788 auto const gw =
Account{
"gateway"};
789 auto const USD = gw[
"USD"];
790 env.fund(
XRP(5000), alice, bob, gw);
794 env.trust(USD(1000), alice, bob);
796 env(
pay(gw, alice, USD(1000)));
799 auto const seq1 = env.seq(alice);
807 env.trust(USD(1), bob);
811 auto const bobPreLimit = env.limit(bob, USD);
821 BEAST_EXPECT(env.limit(bob, USD) == bobPreLimit);
829 using namespace test::jtx;
834 Env env{*
this, features};
835 auto const baseFee = env.current()->fees().base;
836 auto const alice =
Account(
"alice");
837 auto const bob =
Account(
"bob");
838 auto const gw =
Account{
"gateway"};
839 auto const USD = gw[
"USD"];
840 auto const aliceUSD = alice[
"USD"];
841 auto const bobUSD = bob[
"USD"];
842 env.fund(
XRP(5000), alice, bob, gw);
848 env.trust(USD(10'000), alice, bob);
850 env(
pay(gw, alice, USD(10'000)));
851 env(
pay(gw, bob, USD(10'000)));
854 auto const seq1 = env.seq(alice);
862 env(
pay(alice, gw, USD(9'999)));
864 env(
trust(alice, USD(0)));
867 env.trust(USD(10'000), alice);
886 Env env{*
this, features};
887 auto const baseFee = env.current()->fees().base;
888 auto const alice =
Account(
"alice");
889 auto const bob =
Account(
"bob");
890 auto const gw =
Account{
"gateway"};
891 auto const USD = gw[
"USD"];
892 env.fund(
XRP(5000), alice, bob, gw);
895 env.trust(USD(10'000), alice, bob);
897 env(
pay(gw, alice, USD(5'000)));
898 env(
pay(gw, bob, USD(5'000)));
901 auto const outstandingUSD = USD(10'000);
904 auto const seq1 = env.seq(alice);
906 auto const preAliceUSD = env.balance(alice, USD);
907 auto const preBobUSD = env.balance(bob, USD);
915 BEAST_EXPECT(env.balance(alice, USD) == preAliceUSD - USD(1'000));
916 BEAST_EXPECT(env.balance(bob, USD) == preBobUSD);
922 auto const preAliceUSD = env.balance(alice, USD);
923 auto const preBobUSD = env.balance(bob, USD);
931 BEAST_EXPECT(env.balance(alice, USD) == preAliceUSD);
932 BEAST_EXPECT(env.balance(bob, USD) == preBobUSD + USD(1'000));
938 auto const seq2 = env.seq(alice);
940 auto const preAliceUSD = env.balance(alice, USD);
941 auto const preBobUSD = env.balance(bob, USD);
950 BEAST_EXPECT(env.balance(alice, USD) == preAliceUSD - USD(1'000));
951 BEAST_EXPECT(env.balance(bob, USD) == preBobUSD);
957 auto const preAliceUSD = env.balance(alice, USD);
958 auto const preBobUSD = env.balance(bob, USD);
962 BEAST_EXPECT(env.balance(alice, USD) == preAliceUSD + USD(1'000));
963 BEAST_EXPECT(env.balance(bob, USD) == preBobUSD);
975 auto const alice =
Account(
"alice");
976 auto const bob =
Account(
"bob");
977 auto const carol =
Account(
"carol");
978 auto const gw =
Account{
"gateway"};
979 auto const USD = gw[
"USD"];
983 Env env{*
this, features};
984 env.fund(
XRP(5000), alice, bob, carol, gw);
987 env.trust(USD(10'000), alice, bob, carol);
989 env(
pay(gw, alice, USD(5000)));
990 env(
pay(gw, bob, USD(5000)));
991 env(
pay(gw, carol, USD(5000)));
993 auto const aseq = env.seq(alice);
994 auto const bseq = env.seq(bob);
1000 (*env.meta())[sfTransactionResult] ==
1023 (*env.meta())[sfTransactionResult] ==
1048 (*env.meta())[sfTransactionResult] ==
1072 (*env.meta())[sfTransactionResult] ==
1089 Env env{*
this, features};
1090 env.fund(
XRP(5000), alice, bob, carol, gw);
1093 env.trust(USD(10'000), alice, bob, carol);
1095 env(
pay(gw, alice, USD(5000)));
1096 env(
pay(gw, bob, USD(5000)));
1097 env(
pay(gw, carol, USD(5000)));
1099 auto const aseq = env.seq(alice);
1100 auto const bseq = env.seq(bob);
1105 (*env.meta())[sfTransactionResult] ==
1112 (*env.meta())[sfTransactionResult] ==
1208 testcase(
"IOU Metadata to issuer");
1210 Env env{*
this, features};
1211 env.fund(
XRP(5000), alice, carol, gw);
1214 env.trust(USD(10'000), alice, carol);
1216 env(
pay(gw, alice, USD(5000)));
1217 env(
pay(gw, carol, USD(5000)));
1219 auto const aseq = env.seq(alice);
1225 (*env.meta())[sfTransactionResult] ==
1277 using namespace test::jtx;
1280 struct TestAccountData
1308 for (
auto const& t : tests)
1310 Env env{*
this, features};
1311 auto const baseFee = env.current()->fees().base;
1312 auto const USD = t.gw[
"USD"];
1313 env.fund(
XRP(5000), t.src, t.dst, t.gw);
1318 env.trust(USD(100'000), t.src, t.dst);
1320 env.trust(USD(100'000), t.src);
1323 env(
pay(t.gw, t.src, USD(10'000)));
1325 env(
pay(t.gw, t.dst, USD(10'000)));
1329 auto const seq1 = env.seq(t.src);
1330 auto const delta = USD(1'000);
1334 fee(baseFee * 150));
1338 auto const preSrc = env.balance(t.src, USD);
1339 auto const preDst = env.balance(t.dst, USD);
1344 fee(baseFee * 150));
1347 BEAST_EXPECT(env.balance(t.src, USD) == preSrc);
1348 BEAST_EXPECT(env.balance(t.dst, USD) == preDst + delta);
1356 using namespace test::jtx;
1359 struct TestAccountData
1368 auto const gw =
Account{
"gateway"};
1369 auto const alice =
Account{
"alice"};
1370 Env env{*
this, features};
1371 auto const baseFee = env.current()->fees().base;
1372 auto const USD = gw[
"USD"];
1373 env.fund(
XRP(5000), alice, gw);
1376 env.trust(USD(100'000), alice);
1379 env(
pay(gw, alice, USD(10'000)));
1403 for (
auto const& t : gwDstTests)
1405 Env env{*
this, features};
1406 auto const baseFee = env.current()->fees().base;
1407 auto const USD = t.dst[
"USD"];
1408 env.fund(
XRP(5000), t.dst, t.src);
1412 env.trust(USD(100'000), t.src);
1415 env(
pay(t.dst, t.src, USD(10'000)));
1419 auto const seq1 = env.seq(t.src);
1420 auto const preSrc = env.balance(t.src, USD);
1424 fee(baseFee * 150));
1431 fee(baseFee * 150));
1433 auto const preAmount = 10'000;
1434 BEAST_EXPECT(preSrc == USD(preAmount));
1435 auto const postAmount = 9000;
1436 BEAST_EXPECT(env.balance(t.src, USD) == USD(postAmount));
1437 BEAST_EXPECT(env.balance(t.dst, USD) == USD(0));
1442 auto const gw =
Account{
"gateway"};
1443 auto const USD = gw[
"USD"];
1444 Env env{*
this, features};
1445 auto const baseFee = env.current()->fees().base;
1446 env.fund(
XRP(5000), gw);
1464 using namespace test::jtx;
1467 auto const alice =
Account(
"alice");
1468 auto const bob =
Account(
"bob");
1469 auto const carol =
Account(
"carol");
1470 auto const gw =
Account{
"gateway"};
1471 auto const USD = gw[
"USD"];
1475 Env env{*
this, features};
1476 auto const baseFee = env.current()->fees().base;
1477 env.fund(
XRP(10'000), alice, bob, gw);
1479 env(
rate(gw, 1.25));
1481 env.trust(USD(100'000), alice);
1482 env.trust(USD(100'000), bob);
1484 env(
pay(gw, alice, USD(10'000)));
1485 env(
pay(gw, bob, USD(10'000)));
1489 auto const preAlice = env.balance(alice, USD);
1490 auto const seq1 = env.seq(alice);
1491 auto const delta = USD(125);
1495 fee(baseFee * 150));
1505 fee(baseFee * 150));
1508 BEAST_EXPECT(env.balance(alice, USD) == preAlice - delta);
1509 BEAST_EXPECT(env.balance(bob, USD) == USD(10'100));
1513 Env env{*
this, features};
1514 auto const baseFee = env.current()->fees().base;
1515 env.fund(
XRP(10'000), alice, bob, gw);
1517 env(
rate(gw, 1.25));
1519 env.trust(USD(100'000), alice);
1520 env.trust(USD(100'000), bob);
1522 env(
pay(gw, alice, USD(10'000)));
1523 env(
pay(gw, bob, USD(10'000)));
1527 auto const preAlice = env.balance(alice, USD);
1528 auto const seq1 = env.seq(alice);
1529 auto const delta = USD(125);
1533 fee(baseFee * 150));
1540 env(
rate(gw, 1.26));
1547 fee(baseFee * 150));
1550 BEAST_EXPECT(env.balance(alice, USD) == preAlice - delta);
1551 BEAST_EXPECT(env.balance(bob, USD) == USD(10'100));
1556 Env env{*
this, features};
1557 auto const baseFee = env.current()->fees().base;
1558 env.fund(
XRP(10'000), alice, bob, gw);
1560 env(
rate(gw, 1.25));
1562 env.trust(USD(100'000), alice);
1563 env.trust(USD(100'000), bob);
1565 env(
pay(gw, alice, USD(10'000)));
1566 env(
pay(gw, bob, USD(10'000)));
1570 auto const preAlice = env.balance(alice, USD);
1571 auto const seq1 = env.seq(alice);
1572 auto const delta = USD(125);
1576 fee(baseFee * 150));
1583 env(
rate(gw, 1.00));
1590 fee(baseFee * 150));
1593 BEAST_EXPECT(env.balance(alice, USD) == preAlice - delta);
1594 BEAST_EXPECT(env.balance(bob, USD) == USD(10125));
1599 Env env{*
this, features};
1600 auto const baseFee = env.current()->fees().base;
1601 env.fund(
XRP(10'000), alice, bob, gw);
1603 env(
rate(gw, 1.25));
1605 env.trust(USD(100'000), alice);
1606 env.trust(USD(100'000), bob);
1608 env(
pay(gw, alice, USD(10'000)));
1609 env(
pay(gw, bob, USD(10'000)));
1613 auto const preAlice = env.balance(alice, USD);
1614 auto const seq1 = env.seq(alice);
1615 auto const delta = USD(125);
1626 env(
rate(gw, 1.00));
1633 BEAST_EXPECT(env.balance(alice, USD) == preAlice);
1634 BEAST_EXPECT(env.balance(bob, USD) == USD(10000));
1642 using namespace test::jtx;
1645 auto const alice =
Account(
"alice");
1646 auto const bob =
Account(
"bob");
1647 auto const gw =
Account{
"gateway"};
1648 auto const USD = gw[
"USD"];
1652 Env env{*
this, features};
1653 auto const baseFee = env.current()->fees().base;
1654 env.fund(
XRP(1'000), alice, bob, gw);
1657 env.trust(USD(10'000), alice, bob);
1659 env(
pay(gw, alice, USD(1'000)));
1660 env(
pay(gw, bob, USD(1'000)));
1664 auto seq1 = env.seq(alice);
1665 auto const delta = USD(125);
1669 fee(baseFee * 150));
1673 auto const preBobLimit = env.limit(bob, USD);
1677 fee(baseFee * 150));
1679 auto const postBobLimit = env.limit(bob, USD);
1681 BEAST_EXPECT(postBobLimit == preBobLimit);
1689 using namespace test::jtx;
1692 auto const alice =
Account(
"alice");
1693 auto const bob =
Account(
"bob");
1694 auto const carol =
Account(
"carol");
1695 auto const gw =
Account{
"gateway"};
1696 auto const USD = gw[
"USD"];
1698 auto const aliceUSD = alice[
"USD"];
1699 auto const bobUSD = bob[
"USD"];
1701 Env env{*
this, features};
1702 auto const baseFee = env.current()->fees().base;
1703 env.fund(
XRP(1'000), alice, bob, gw);
1708 env(
trust(alice, USD(10'000)));
1709 env(
trust(bob, USD(10'000)));
1711 env(
pay(gw, alice, USD(1'000)));
1715 auto seq1 = env.seq(alice);
1716 auto const delta = USD(125);
1726 env(
trust(bob, USD(10'000)));
1728 env(
pay(gw, bob, USD(1'000)));
1732 seq1 = env.seq(alice);
1736 fee(baseFee * 150));
1743 fee(baseFee * 150));
1751 using namespace test::jtx;
1754 auto const alice =
Account(
"alice");
1755 auto const bob =
Account(
"bob");
1756 auto const carol =
Account(
"carol");
1757 auto const gw =
Account{
"gateway"};
1758 auto const USD = gw[
"USD"];
1762 Env env{*
this, features};
1763 auto const baseFee = env.current()->fees().base;
1764 env.fund(
XRP(10'000), alice, bob, gw);
1767 env.trust(USD(100'000), alice);
1768 env.trust(USD(100'000), bob);
1770 env(
pay(gw, alice, USD(10'000)));
1771 env(
pay(gw, bob, USD(10'000)));
1777 auto seq1 = env.seq(alice);
1778 auto const delta = USD(125);
1793 seq1 = env.seq(alice);
1797 fee(baseFee * 150));
1808 fee(baseFee * 150));
1816 seq1 = env.seq(alice);
1820 fee(baseFee * 150));
1835 Env env{*
this, features};
1836 auto const baseFee = env.current()->fees().base;
1837 env.fund(
XRP(10'000), alice, bob, gw);
1840 env(
trust(alice, USD(100'000)));
1841 env(
trust(bob, USD(100'000)));
1843 env(
pay(gw, alice, USD(10'000)));
1844 env(
pay(gw, bob, USD(10'000)));
1852 auto seq1 = env.seq(alice);
1853 auto const delta = USD(125);
1868 seq1 = env.seq(alice);
1872 fee(baseFee * 150));
1883 fee(baseFee * 150));
1892 seq1 = env.seq(alice);
1896 fee(baseFee * 150));
1911 Env env{*
this, features};
1912 auto const baseFee = env.current()->fees().base;
1913 env.fund(
XRP(10'000), alice, bob, gw);
1916 env(
trust(alice, USD(100'000)));
1917 env(
trust(bob, USD(100'000)));
1919 env(
pay(gw, alice, USD(10'000)));
1920 env(
pay(gw, bob, USD(10'000)));
1928 auto seq1 = env.seq(alice);
1929 auto const delta = USD(125);
1945 seq1 = env.seq(alice);
1949 fee(baseFee * 150));
1971 seq1 = env.seq(alice);
1975 fee(baseFee * 150));
1992 testcase(
"IOU Insufficient Funds");
1993 using namespace test::jtx;
1996 auto const alice =
Account(
"alice");
1997 auto const bob =
Account(
"bob");
1998 auto const carol =
Account(
"carol");
1999 auto const gw =
Account{
"gateway"};
2000 auto const USD = gw[
"USD"];
2004 Env env{*
this, features};
2005 auto const baseFee = env.current()->fees().base;
2006 env.fund(
XRP(10'000), alice, bob, gw);
2009 env.trust(USD(100'000), alice);
2010 env.trust(USD(100'000), bob);
2012 env(
pay(gw, alice, USD(10'000)));
2013 env(
pay(gw, bob, USD(10'000)));
2017 auto const delta = USD(1'000);
2021 fee(baseFee * 150));
2028 Env env{*
this, features};
2029 auto const baseFee = env.current()->fees().base;
2030 env.fund(
XRP(10'000), alice, bob, gw);
2033 env.trust(USD(100'000), alice);
2034 env.trust(USD(100'000), bob);
2036 env(
pay(gw, alice, USD(10'000)));
2037 env(
pay(gw, bob, USD(10'000)));
2040 auto const delta = USD(1'000);
2044 fee(baseFee * 150));
2060 using namespace test::jtx;
2063 auto const alice =
Account(
"alice");
2064 auto const bob =
Account(
"bob");
2065 auto const gw =
Account{
"gateway"};
2066 auto const USD = gw[
"USD"];
2070 Env env(*
this, features);
2071 auto const baseFee = env.
current()->fees().base;
2072 env.
fund(
XRP(10'000), alice, bob, gw);
2075 env.
trust(USD(100000000000000000), alice);
2076 env.
trust(USD(100000000000000000), bob);
2078 env(
pay(gw, alice, USD(10000000000000000)));
2079 env(
pay(gw, bob, USD(1)));
2082 bool const largeMantissa = features[featureSingleAssetVault] ||
2083 features[featureLendingProtocol];
2093 auto const seq1 = env.
seq(alice);
2098 fee(baseFee * 150));
2105 fee(baseFee * 150));
2115 using namespace jtx;
2118 for (
bool const withTokenEscrow : {
false,
true})
2121 withTokenEscrow ? features : features - featureTokenEscrow;
2122 Env env{*
this, amend};
2123 auto const baseFee = env.
current()->fees().base;
2124 auto const alice =
Account(
"alice");
2125 auto const bob =
Account(
"bob");
2126 auto const gw =
Account(
"gw");
2127 env.fund(
XRP(5000), bob);
2129 MPTTester mptGw(env, gw, {.holders = {alice}});
2134 mptGw.authorize({.account = alice});
2135 auto const MPT = mptGw[
"MPT"];
2136 env(
pay(gw, alice,
MPT(10'000)));
2139 auto const createResult =
2141 auto const finishResult =
2144 auto const seq1 = env.seq(alice);
2157 auto const seq2 = env.seq(alice);
2174 using namespace test::jtx;
2177 for (
bool const withMPT : {
true,
false})
2180 withMPT ? features : features - featureMPTokensV1;
2181 Env env{*
this, amend};
2182 auto const baseFee = env.
current()->fees().base;
2183 auto const alice =
Account(
"alice");
2184 auto const bob =
Account(
"bob");
2185 auto const gw =
Account(
"gw");
2186 env.fund(
XRP(1'000), alice, bob, gw);
2190 jv[jss::Amount][jss::mpt_issuance_id] =
2191 "00000004A407AF5856CCF3C42619DAA925813FC955C72983";
2192 jv[jss::Amount][jss::value] =
"-1";
2205 Env env{*
this, features};
2206 auto const baseFee = env.current()->fees().base;
2207 auto const alice =
Account(
"alice");
2208 auto const bob =
Account(
"bob");
2209 auto const gw =
Account(
"gw");
2211 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
2216 mptGw.authorize({.account = alice});
2217 mptGw.authorize({.account = bob});
2218 auto const MPT = mptGw[
"MPT"];
2219 env(
pay(gw, alice,
MPT(10'000)));
2220 env(
pay(gw, bob,
MPT(10'000)));
2236 using namespace test::jtx;
2241 Env env{*
this, features};
2242 auto const baseFee = env.current()->fees().base;
2243 auto const alice =
Account(
"alice");
2244 auto const gw =
Account(
"gw");
2246 MPTTester mptGw(env, gw, {.holders = {alice}});
2251 mptGw.authorize({.account = alice});
2252 auto const MPT = mptGw[
"MPT"];
2253 env(
pay(gw, alice,
MPT(10'000)));
2266 Env env{*
this, features};
2267 auto const baseFee = env.current()->fees().base;
2268 auto const alice =
Account(
"alice");
2269 auto const bob =
Account(
"bob");
2270 auto const gw =
Account(
"gw");
2271 env.fund(
XRP(10'000), alice, bob, gw);
2275 alice.name(),
makeMptID(env.seq(alice), alice));
2277 jv[jss::Amount][jss::mpt_issuance_id] =
2278 "00000004A407AF5856CCF3C42619DAA925813FC955C72983";
2289 Env env{*
this, features};
2290 auto const baseFee = env.current()->fees().base;
2291 auto const alice =
Account(
"alice");
2292 auto const bob =
Account(
"bob");
2293 auto const gw =
Account(
"gw");
2295 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
2298 mptGw.authorize({.account = alice});
2299 mptGw.authorize({.account = bob});
2300 auto const MPT = mptGw[
"MPT"];
2301 env(
pay(gw, alice,
MPT(10'000)));
2302 env(
pay(gw, bob,
MPT(10'000)));
2315 Env env{*
this, features};
2316 auto const baseFee = env.current()->fees().base;
2317 auto const alice =
Account(
"alice");
2318 auto const bob =
Account(
"bob");
2319 auto const gw =
Account(
"gw");
2321 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
2326 auto const MPT = mptGw[
"MPT"];
2338 Env env{*
this, features};
2339 auto const baseFee = env.current()->fees().base;
2340 auto const alice =
Account(
"alice");
2341 auto const bob =
Account(
"bob");
2342 auto const gw =
Account(
"gw");
2344 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
2350 mptGw.authorize({.account = alice});
2351 mptGw.authorize({.account = gw, .holder = alice});
2352 auto const MPT = mptGw[
"MPT"];
2353 env(
pay(gw, alice,
MPT(10'000)));
2370 Env env{*
this, features};
2371 auto const baseFee = env.current()->fees().base;
2372 auto const alice =
Account(
"alice");
2373 auto const bob =
Account(
"bob");
2374 auto const gw =
Account(
"gw");
2376 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
2382 mptGw.authorize({.account = alice});
2383 mptGw.authorize({.account = gw, .holder = alice});
2384 mptGw.authorize({.account = bob});
2385 mptGw.authorize({.account = gw, .holder = bob});
2386 auto const MPT = mptGw[
"MPT"];
2387 env(
pay(gw, alice,
MPT(10'000)));
2388 env(
pay(gw, bob,
MPT(10'000)));
2405 Env env{*
this, features};
2406 auto const baseFee = env.current()->fees().base;
2407 auto const alice =
Account(
"alice");
2408 auto const bob =
Account(
"bob");
2409 auto const gw =
Account(
"gw");
2411 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
2416 mptGw.authorize({.account = alice});
2417 mptGw.authorize({.account = bob});
2418 auto const MPT = mptGw[
"MPT"];
2419 env(
pay(gw, alice,
MPT(10'000)));
2420 env(
pay(gw, bob,
MPT(10'000)));
2424 mptGw.set({.account = gw, .holder = alice, .flags =
tfMPTLock});
2436 Env env{*
this, features};
2437 auto const baseFee = env.current()->fees().base;
2438 auto const alice =
Account(
"alice");
2439 auto const bob =
Account(
"bob");
2440 auto const gw =
Account(
"gw");
2442 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
2447 mptGw.authorize({.account = alice});
2448 mptGw.authorize({.account = bob});
2449 auto const MPT = mptGw[
"MPT"];
2450 env(
pay(gw, alice,
MPT(10'000)));
2451 env(
pay(gw, bob,
MPT(10'000)));
2455 mptGw.set({.account = gw, .holder = bob, .flags =
tfMPTLock});
2467 Env env{*
this, features};
2468 auto const baseFee = env.current()->fees().base;
2469 auto const alice =
Account(
"alice");
2470 auto const bob =
Account(
"bob");
2471 auto const gw =
Account(
"gw");
2473 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
2476 mptGw.authorize({.account = alice});
2477 mptGw.authorize({.account = bob});
2478 auto const MPT = mptGw[
"MPT"];
2479 env(
pay(gw, alice,
MPT(10'000)));
2480 env(
pay(gw, bob,
MPT(10'000)));
2493 Env env{*
this, features};
2494 auto const baseFee = env.current()->fees().base;
2495 auto const alice =
Account(
"alice");
2496 auto const bob =
Account(
"bob");
2497 auto const gw =
Account(
"gw");
2499 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
2504 mptGw.authorize({.account = alice});
2505 mptGw.authorize({.account = bob});
2506 auto const MPT = mptGw[
"MPT"];
2507 env(
pay(gw, bob,
MPT(10)));
2520 Env env{*
this, features};
2521 auto const baseFee = env.current()->fees().base;
2522 auto const alice =
Account(
"alice");
2523 auto const bob =
Account(
"bob");
2524 auto const gw =
Account(
"gw");
2526 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
2531 mptGw.authorize({.account = alice});
2532 mptGw.authorize({.account = bob});
2533 auto const MPT = mptGw[
"MPT"];
2534 env(
pay(gw, alice,
MPT(10)));
2535 env(
pay(gw, bob,
MPT(10)));
2551 using namespace test::jtx;
2556 Env env{*
this, features};
2557 auto const baseFee = env.current()->fees().base;
2558 auto const alice =
Account(
"alice");
2559 auto const bob =
Account(
"bob");
2560 auto const gw =
Account(
"gw");
2562 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
2568 mptGw.authorize({.account = alice});
2569 mptGw.authorize({.account = gw, .holder = alice});
2570 mptGw.authorize({.account = bob});
2571 mptGw.authorize({.account = gw, .holder = bob});
2572 auto const MPT = mptGw[
"MPT"];
2573 env(
pay(gw, alice,
MPT(10'000)));
2574 env(
pay(gw, bob,
MPT(10'000)));
2577 auto const seq1 = env.seq(alice);
2599 Env env{*
this, features};
2600 auto const baseFee = env.current()->fees().base;
2601 auto const alice =
Account(
"alice");
2602 auto const bob =
Account(
"bob");
2603 env.fund(
XRP(10'000), alice, bob);
2606 auto const seq1 = env.seq(alice);
2607 env.app().openLedger().modify(
2615 sleNew->setAccountID(sfDestination, bob);
2616 sleNew->setFieldAmount(sfAmount, amt);
2632 Env env{*
this, features};
2633 auto const baseFee = env.current()->fees().base;
2634 auto const alice =
Account(
"alice");
2635 auto const bob =
Account(
"bob");
2636 auto const gw =
Account(
"gw");
2638 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
2643 mptGw.authorize({.account = alice});
2644 mptGw.authorize({.account = bob});
2645 auto const MPT = mptGw[
"MPT"];
2646 env(
pay(gw, alice,
MPT(10'000)));
2647 env(
pay(gw, bob,
MPT(10'000)));
2650 auto const seq1 = env.seq(alice);
2659 mptGw.set({.account = gw, .holder = bob, .flags =
tfMPTLock});
2674 using namespace test::jtx;
2679 Env env{*
this, features};
2680 auto const baseFee = env.current()->fees().base;
2681 auto const acctReserve = env.current()->fees().reserve;
2682 auto const incReserve = env.current()->fees().increment;
2684 auto const alice =
Account(
"alice");
2685 auto const bob =
Account(
"bob");
2686 auto const gw =
Account(
"gw");
2687 env.fund(acctReserve + (incReserve - 1), bob);
2690 MPTTester mptGw(env, gw, {.holders = {alice}});
2695 mptGw.authorize({.account = alice});
2696 auto const MPT = mptGw[
"MPT"];
2697 env(
pay(gw, alice,
MPT(10'000)));
2700 auto const seq1 = env.seq(alice);
2718 Env env{*
this, features};
2719 auto const baseFee = env.current()->fees().base;
2720 auto const alice =
Account(
"alice");
2721 auto const bob =
Account(
"bob");
2722 auto const gw =
Account(
"gw");
2723 env.fund(
XRP(10'000), bob);
2726 MPTTester mptGw(env, gw, {.holders = {alice}});
2731 mptGw.authorize({.account = alice});
2732 auto const MPT = mptGw[
"MPT"];
2733 env(
pay(gw, alice,
MPT(10'000)));
2736 auto const seq1 = env.seq(alice);
2754 Env env{*
this, features};
2755 auto const baseFee = env.current()->fees().base;
2756 auto const alice =
Account(
"alice");
2757 auto const bob =
Account(
"bob");
2758 auto const carol =
Account(
"carol");
2759 auto const gw =
Account(
"gw");
2760 env.fund(
XRP(10'000), bob, carol);
2763 MPTTester mptGw(env, gw, {.holders = {alice}});
2768 mptGw.authorize({.account = alice});
2769 auto const MPT = mptGw[
"MPT"];
2770 env(
pay(gw, alice,
MPT(10'000)));
2773 auto const seq1 = env.seq(alice);
2794 using namespace test::jtx;
2799 Env env{*
this, features};
2800 auto const baseFee = env.current()->fees().base;
2801 auto const alice =
Account(
"alice");
2802 auto const bob =
Account(
"bob");
2803 auto const gw =
Account(
"gw");
2805 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
2811 mptGw.authorize({.account = alice});
2812 mptGw.authorize({.account = gw, .holder = alice});
2813 mptGw.authorize({.account = bob});
2814 mptGw.authorize({.account = gw, .holder = bob});
2815 auto const MPT = mptGw[
"MPT"];
2816 env(
pay(gw, alice,
MPT(10'000)));
2817 env(
pay(gw, bob,
MPT(10'000)));
2820 auto const seq1 = env.seq(alice);
2838 Env env{*
this, features};
2839 auto const baseFee = env.current()->fees().base;
2840 auto const alice =
Account(
"alice");
2841 auto const bob =
Account(
"bob");
2842 env.fund(
XRP(10'000), alice, bob);
2844 auto const seq1 = env.seq(alice);
2845 env.app().openLedger().modify(
2853 sleNew->setAccountID(sfDestination, bob);
2854 sleNew->setFieldAmount(sfAmount, amt);
2872 using namespace jtx;
2875 Env env{*
this, features};
2876 auto const baseFee = env.current()->fees().base;
2877 auto const alice =
Account(
"alice");
2878 auto const bob =
Account(
"bob");
2879 auto const carol =
Account(
"carol");
2880 auto const gw =
Account(
"gw");
2881 env.fund(
XRP(5000), bob);
2883 MPTTester mptGw(env, gw, {.holders = {alice, carol}});
2888 mptGw.authorize({.account = alice});
2889 mptGw.authorize({.account = carol});
2890 auto const MPT = mptGw[
"MPT"];
2891 env(
pay(gw, alice,
MPT(10'000)));
2892 env(
pay(gw, carol,
MPT(10'000)));
2895 auto outstandingMPT = env.balance(gw,
MPT);
2898 auto const seq1 = env.seq(alice);
2900 auto const preAliceMPT = env.balance(alice,
MPT);
2901 auto const preBobMPT = env.balance(bob,
MPT);
2909 BEAST_EXPECT(env.balance(alice,
MPT) == preAliceMPT -
MPT(1'000));
2911 BEAST_EXPECT(env.balance(bob,
MPT) == preBobMPT);
2913 BEAST_EXPECT(env.balance(gw,
MPT) == outstandingMPT);
2917 auto const preAliceMPT = env.balance(alice,
MPT);
2918 auto const preBobMPT = env.balance(bob,
MPT);
2926 BEAST_EXPECT(env.balance(alice,
MPT) == preAliceMPT);
2928 BEAST_EXPECT(env.balance(bob,
MPT) == preBobMPT +
MPT(1'000));
2930 BEAST_EXPECT(env.balance(gw,
MPT) == outstandingMPT);
2935 auto const seq2 = env.seq(alice);
2937 auto const preAliceMPT = env.balance(alice,
MPT);
2938 auto const preBobMPT = env.balance(bob,
MPT);
2947 BEAST_EXPECT(env.balance(alice,
MPT) == preAliceMPT -
MPT(1'000));
2949 BEAST_EXPECT(env.balance(bob,
MPT) == preBobMPT);
2951 BEAST_EXPECT(env.balance(gw,
MPT) == outstandingMPT);
2955 auto const preAliceMPT = env.balance(alice,
MPT);
2956 auto const preBobMPT = env.balance(bob,
MPT);
2960 BEAST_EXPECT(env.balance(alice,
MPT) == preAliceMPT +
MPT(1'000));
2962 BEAST_EXPECT(env.balance(bob,
MPT) == preBobMPT);
2964 BEAST_EXPECT(env.balance(gw,
MPT) == outstandingMPT);
2970 auto const seq = env.
seq(alice);
2971 auto const preAliceMPT = env.balance(alice,
MPT);
2979 BEAST_EXPECT(env.balance(alice,
MPT) == preAliceMPT -
MPT(1'000));
2981 BEAST_EXPECT(env.balance(gw,
MPT) == outstandingMPT);
2991 BEAST_EXPECT(env.balance(alice,
MPT) == preAliceMPT);
2993 BEAST_EXPECT(env.balance(gw,
MPT) == outstandingMPT);
2999 auto const seq = env.
seq(alice);
3000 auto const preAliceMPT = env.balance(alice,
MPT);
3009 BEAST_EXPECT(env.balance(alice,
MPT) == preAliceMPT -
MPT(1'000));
3011 BEAST_EXPECT(env.balance(gw,
MPT) == outstandingMPT);
3017 BEAST_EXPECT(env.balance(alice,
MPT) == preAliceMPT);
3019 BEAST_EXPECT(env.balance(gw,
MPT) == outstandingMPT);
3025 auto const preAliceMPT = env.balance(alice,
MPT);
3026 auto const preBobMPT = env.balance(bob,
MPT);
3027 auto const preCarolMPT = env.balance(carol,
MPT);
3042 BEAST_EXPECT(env.balance(alice,
MPT) == preAliceMPT -
MPT(1'000));
3044 BEAST_EXPECT(env.balance(bob,
MPT) == preBobMPT);
3046 BEAST_EXPECT(env.balance(carol,
MPT) == preCarolMPT -
MPT(1'000));
3048 BEAST_EXPECT(env.balance(gw,
MPT) == outstandingMPT);
3054 Env env{*
this, features};
3055 auto const baseFee = env.current()->fees().base;
3056 auto const alice =
Account(
"alice");
3057 auto const bob =
Account(
"bob");
3058 auto const gw =
Account(
"gw");
3060 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
3065 mptGw.authorize({.account = alice});
3066 mptGw.authorize({.account = bob});
3067 auto const MPT = mptGw[
"MPT"];
3071 auto const preAliceMPT = env.balance(alice,
MPT);
3072 auto const preBobMPT = env.balance(bob,
MPT);
3073 auto const outstandingMPT = env.balance(gw,
MPT);
3075 auto const seq1 = env.seq(alice);
3079 fee(baseFee * 150));
3082 BEAST_EXPECT(env.balance(alice,
MPT) == preAliceMPT -
MPT(1));
3084 BEAST_EXPECT(env.balance(bob,
MPT) == preBobMPT);
3086 BEAST_EXPECT(env.balance(gw,
MPT) == outstandingMPT);
3096 BEAST_EXPECT(env.balance(alice,
MPT) == preAliceMPT -
MPT(1));
3099 ->isFieldPresent(sfLockedAmount));
3100 BEAST_EXPECT(env.balance(bob,
MPT) == preBobMPT +
MPT(1));
3102 BEAST_EXPECT(env.balance(gw,
MPT) == outstandingMPT);
3105 ->isFieldPresent(sfLockedAmount));
3110 Env env{*
this, features};
3111 auto const baseFee = env.current()->fees().base;
3112 auto const alice =
Account(
"alice");
3113 auto const bob =
Account(
"bob");
3114 auto const gw =
Account(
"gw");
3116 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
3121 mptGw.authorize({.account = alice});
3122 mptGw.authorize({.account = bob});
3123 auto const MPT = mptGw[
"MPT"];
3127 auto const preAliceMPT = env.balance(alice,
MPT);
3128 auto const preBobMPT = env.balance(bob,
MPT);
3129 auto const outstandingMPT = env.balance(gw,
MPT);
3132 auto const seq1 = env.seq(alice);
3136 fee(baseFee * 150));
3140 auto const seq2 = env.seq(alice);
3144 fee(baseFee * 150));
3150 BEAST_EXPECT(env.balance(bob,
MPT) == preBobMPT);
3152 BEAST_EXPECT(env.balance(gw,
MPT) == outstandingMPT);
3175 BEAST_EXPECT(env.balance(gw,
MPT) == outstandingMPT);
3183 using namespace jtx;
3186 auto const alice =
Account(
"alice");
3187 auto const bob =
Account(
"bob");
3188 auto const carol =
Account(
"carol");
3189 auto const gw =
Account{
"gateway"};
3193 Env env{*
this, features};
3194 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
3199 mptGw.authorize({.account = alice});
3200 mptGw.authorize({.account = bob});
3201 auto const MPT = mptGw[
"MPT"];
3202 env(
pay(gw, alice,
MPT(10'000)));
3203 env(
pay(gw, bob,
MPT(10'000)));
3205 auto const aseq = env.seq(alice);
3206 auto const bseq = env.seq(bob);
3212 (*env.meta())[sfTransactionResult] ==
3235 (*env.meta())[sfTransactionResult] ==
3253 (*env.meta())[sfTransactionResult] ==
3272 (*env.meta())[sfTransactionResult] ==
3285 Env env{*
this, features};
3286 MPTTester mptGw(env, gw, {.holders = {alice, bob, carol}});
3291 mptGw.authorize({.account = alice});
3292 mptGw.authorize({.account = bob});
3293 mptGw.authorize({.account = carol});
3294 auto const MPT = mptGw[
"MPT"];
3295 env(
pay(gw, alice,
MPT(10'000)));
3296 env(
pay(gw, bob,
MPT(10'000)));
3297 env(
pay(gw, carol,
MPT(10'000)));
3299 auto const aseq = env.seq(alice);
3300 auto const bseq = env.seq(bob);
3305 (*env.meta())[sfTransactionResult] ==
3312 (*env.meta())[sfTransactionResult] ==
3391 using namespace test::jtx;
3396 Env env{*
this, features};
3397 auto const baseFee = env.current()->fees().base;
3398 auto const alice =
Account(
"alice");
3399 auto const gw =
Account(
"gw");
3401 MPTTester mptGw(env, gw, {.holders = {alice}});
3406 mptGw.authorize({.account = alice});
3407 auto const MPT = mptGw[
"MPT"];
3408 env(
pay(gw, alice,
MPT(10'000)));
3412 auto const seq1 = env.seq(alice);
3413 auto const preAliceMPT = env.balance(alice,
MPT);
3414 auto const preOutstanding = env.balance(gw,
MPT);
3416 BEAST_EXPECT(preOutstanding ==
MPT(-10'000));
3417 BEAST_EXPECT(preEscrowed == 0);
3422 fee(baseFee * 150));
3425 BEAST_EXPECT(env.balance(alice,
MPT) == preAliceMPT -
MPT(1'000));
3427 BEAST_EXPECT(env.balance(gw,
MPT) == preOutstanding);
3434 fee(baseFee * 150));
3437 BEAST_EXPECT(env.balance(alice,
MPT) == preAliceMPT -
MPT(1'000));
3439 BEAST_EXPECT(env.balance(gw,
MPT) == preOutstanding +
MPT(1'000));
3448 using namespace test::jtx;
3451 auto const alice =
Account(
"alice");
3452 auto const bob =
Account(
"bob");
3453 auto const carol =
Account(
"carol");
3454 auto const gw =
Account{
"gateway"};
3455 auto const USD = gw[
"USD"];
3459 Env env{*
this, features};
3460 auto const baseFee = env.current()->fees().base;
3461 auto const alice =
Account(
"alice");
3462 auto const bob =
Account(
"bob");
3463 auto const gw =
Account(
"gw");
3465 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
3467 {.transferFee = 25000,
3471 mptGw.authorize({.account = alice});
3472 mptGw.authorize({.account = bob});
3473 auto const MPT = mptGw[
"MPT"];
3474 env(
pay(gw, alice,
MPT(10'000)));
3475 env(
pay(gw, bob,
MPT(10'000)));
3479 auto const preAlice = env.balance(alice,
MPT);
3480 auto const seq1 = env.seq(alice);
3481 auto const delta =
MPT(125);
3485 fee(baseFee * 150));
3493 BEAST_EXPECT(env.balance(gw,
MPT) ==
MPT(-20'000));
3499 fee(baseFee * 150));
3502 BEAST_EXPECT(env.balance(alice,
MPT) == preAlice - delta);
3503 BEAST_EXPECT(env.balance(bob,
MPT) ==
MPT(10'100));
3505 auto const escrowedWithFix =
3506 env.current()->rules().enabled(fixTokenEscrowV1) ? 0 : 25;
3507 auto const outstandingWithFix =
3508 env.current()->rules().enabled(fixTokenEscrowV1) ?
MPT(19'975)
3512 BEAST_EXPECT(env.balance(gw,
MPT) == -outstandingWithFix);
3517 Env env{*
this, features};
3518 auto const baseFee = env.current()->fees().base;
3519 auto const alice =
Account(
"alice");
3520 auto const bob =
Account(
"bob");
3521 auto const gw =
Account(
"gw");
3523 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
3525 {.transferFee = 25000,
3529 mptGw.authorize({.account = alice});
3530 mptGw.authorize({.account = bob});
3531 auto const MPT = mptGw[
"MPT"];
3532 env(
pay(gw, alice,
MPT(10'000)));
3533 env(
pay(gw, bob,
MPT(10'000)));
3537 auto const preAlice = env.balance(alice,
MPT);
3538 auto const preBob = env.balance(bob,
MPT);
3539 auto const seq1 = env.seq(alice);
3540 auto const delta =
MPT(125);
3545 fee(baseFee * 150));
3555 BEAST_EXPECT(env.balance(alice,
MPT) == preAlice);
3556 BEAST_EXPECT(env.balance(bob,
MPT) == preBob);
3557 BEAST_EXPECT(env.balance(gw,
MPT) ==
MPT(-20'000));
3564 Env env{*
this, features};
3565 auto const baseFee = env.current()->fees().base;
3566 auto const alice =
Account(
"alice");
3567 auto const bob =
Account(
"bob");
3568 auto const gw =
Account(
"gw");
3570 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
3572 {.transferFee = 25000,
3576 mptGw.authorize({.account = alice});
3577 mptGw.authorize({.account = bob});
3578 auto const MPT = mptGw[
"MPT"];
3579 env(
pay(gw, alice,
MPT(10'000)));
3580 env(
pay(gw, bob,
MPT(10'000)));
3584 auto const preAlice = env.balance(alice,
MPT);
3585 auto const seq1 = env.seq(alice);
3586 auto const delta =
MPT(125);
3590 fee(baseFee * 150));
3598 BEAST_EXPECT(env.balance(gw,
MPT) ==
MPT(-20'000));
3604 fee(baseFee * 150));
3607 BEAST_EXPECT(env.balance(alice,
MPT) == preAlice - delta);
3610 BEAST_EXPECT(env.balance(gw,
MPT) ==
MPT(-19'875));
3618 using namespace test::jtx;
3621 Env env{*
this, features};
3622 auto const baseFee = env.current()->fees().base;
3623 auto const alice =
Account(
"alice");
3624 auto const bob =
Account(
"bob");
3625 auto const gw =
Account(
"gw");
3627 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
3632 mptGw.authorize({.account = alice});
3633 mptGw.authorize({.account = gw, .holder = alice});
3634 mptGw.authorize({.account = bob});
3635 mptGw.authorize({.account = gw, .holder = bob});
3636 auto const MPT = mptGw[
"MPT"];
3637 env(
pay(gw, alice,
MPT(10'000)));
3640 auto seq = env.
seq(alice);
3641 auto const delta =
MPT(125);
3646 fee(baseFee * 150));
3653 fee(baseFee * 150));
3661 using namespace test::jtx;
3664 Env env{*
this, features};
3665 auto const baseFee = env.current()->fees().base;
3666 auto const alice =
Account(
"alice");
3667 auto const bob =
Account(
"bob");
3668 auto const gw =
Account(
"gw");
3670 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
3675 mptGw.authorize({.account = alice});
3676 mptGw.authorize({.account = bob});
3677 auto const MPT = mptGw[
"MPT"];
3678 env(
pay(gw, alice,
MPT(10'000)));
3679 env(
pay(gw, bob,
MPT(10'000)));
3683 auto seq1 = env.seq(alice);
3688 fee(baseFee * 150));
3692 mptGw.set({.account = gw, .holder = alice, .flags =
tfMPTLock});
3693 mptGw.set({.account = gw, .holder = bob, .flags =
tfMPTLock});
3712 using namespace test::jtx;
3715 Env env{*
this, features};
3716 auto const baseFee = env.current()->fees().base;
3717 auto const alice =
Account(
"alice");
3718 auto const bob =
Account(
"bob");
3719 auto const gw =
Account(
"gw");
3721 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
3724 mptGw.authorize({.account = alice});
3725 mptGw.authorize({.account = bob});
3726 auto const MPT = mptGw[
"MPT"];
3727 env(
pay(gw, alice,
MPT(10'000)));
3728 env(
pay(gw, bob,
MPT(10'000)));
3743 auto seq = env.
seq(alice);
3747 fee(baseFee * 150));
3754 fee(baseFee * 150));
3761 auto seq = env.
seq(alice);
3766 fee(baseFee * 150));
3779 using namespace test::jtx;
3784 Env env{*
this, features};
3785 auto const baseFee = env.current()->fees().base;
3786 auto const alice =
Account(
"alice");
3787 auto const bob =
Account(
"bob");
3788 auto const gw =
Account(
"gw");
3790 MPTTester mptGw(env, gw, {.holders = {alice, bob}});
3795 mptGw.authorize({.account = alice});
3796 mptGw.authorize({.account = bob});
3797 auto const MPT = mptGw[
"MPT"];
3798 env(
pay(gw, alice,
MPT(10'000)));
3799 env(
pay(gw, bob,
MPT(10'000)));
3802 auto const seq1 = env.seq(alice);
3806 fee(baseFee * 150));
3810 env(
pay(alice, gw,
MPT(9'990)));
3811 env(
pay(bob, gw,
MPT(10'000)));
3812 BEAST_EXPECT(env.balance(alice,
MPT) ==
MPT(0));
3814 BEAST_EXPECT(env.balance(bob,
MPT) ==
MPT(0));
3816 BEAST_EXPECT(env.balance(gw,
MPT) ==
MPT(-10));
3819 {.id = mptGw.issuanceID(),
3830 env(
pay(bob, gw,
MPT(10)));
3831 mptGw.destroy({.id = mptGw.issuanceID(), .
ownerCount = 0});
3836 Env env{*
this, features};
3837 auto const baseFee = env.current()->fees().base;
3838 auto const alice =
Account(
"alice");
3839 auto const bob =
Account(
"bob");
3840 auto const gw =
Account(
"gw");
3841 env.fund(
XRP(10'000), bob);
3844 MPTTester mptGw(env, gw, {.holders = {alice}});
3849 mptGw.authorize({.account = alice});
3850 auto const MPT = mptGw[
"MPT"];
3851 env(
pay(gw, alice,
MPT(10'000)));
3854 auto const seq1 = env.seq(alice);
3862 env(
pay(alice, gw,
MPT(9'990)));
3865 BEAST_EXPECT(env.balance(alice,
MPT) ==
MPT(0));
3879 BEAST_EXPECT(env.balance(alice,
MPT) ==
MPT(0));
3931 using namespace test::jtx;
3934 {
all - featureSingleAssetVault - featureLendingProtocol,
all})
3943BEAST_DEFINE_TESTSUITE(EscrowToken, app,
xrpl);
Value removeMember(char const *key)
Remove and return the named member.
A generic endpoint for log messages.
testcase_t testcase
Memberspace for declaring test cases.
A class that simplifies iterating ledger directory pages.
const_iterator begin() const
const_iterator end() const
A currency issued by an account.
Writable ledger view that accumulates state and tx changes.
Discardable, editable view to a ledger.
void insert(std::shared_ptr< SLE > const &sle) override
Insert a new state SLE.
Immutable cryptographic account descriptor.
A transaction testing environment.
bool close(NetClock::time_point closeTime, std::optional< std::chrono::milliseconds > consensusDelay=std::nullopt)
Close and advance the ledger.
std::shared_ptr< SLE const > le(Account const &account) const
Return an account root.
void fund(bool setDefaultRipple, STAmount const &amount, Account const &account)
std::uint32_t seq(Account const &account) const
Returns the next sequence number on account.
void trust(STAmount const &amount, Account const &account)
Establish trust lines.
Json::Value rpc(unsigned apiVersion, std::unordered_map< std::string, std::string > const &headers, std::string const &cmd, Args &&... args)
Execute an RPC command.
std::shared_ptr< OpenView const > current() const
Returns the current ledger.
NetClock::time_point now()
Returns the current network time.
Converts to IOU Issue or STAmount.
void create(MPTCreate const &arg=MPTCreate{})
Converts to MPT Issue or STAmount.
xrpl::MPTID const & mpt() const
Match clear account flags.
Set the expected result code for a JTx The test will fail if the code doesn't match.
Keylet escrow(AccountID const &src, std::uint32_t seq) noexcept
An escrow entry.
Keylet ownerDir(AccountID const &id) noexcept
The root page of an account's directory.
Keylet mptIssuance(std::uint32_t seq, AccountID const &issuer) noexcept
Keylet mptoken(MPTID const &issuanceID, AccountID const &holder) noexcept
auto const finish_time
Set the "FinishAfter" time tag on a JTx.
Json::Value create(AccountID const &account, AccountID const &to, STAmount const &amount)
Rate rate(Env &env, Account const &account, std::uint32_t const &seq)
Json::Value cancel(AccountID const &account, Account const &from, std::uint32_t seq)
std::array< std::uint8_t, 39 > const cb2
std::array< std::uint8_t, 39 > const cb1
auto const cancel_time
Set the "CancelAfter" time tag on a JTx.
Json::Value finish(AccountID const &account, AccountID const &from, std::uint32_t seq)
std::array< std::uint8_t, 4 > const fb1
Json::Value trust(Account const &account, STAmount const &amount, std::uint32_t flags)
Modify a trust line.
std::uint32_t ownerCount(Env const &env, Account const &account)
Json::Value rate(Account const &account, double multiplier)
Set a transfer rate.
XRP_t const XRP
Converts to XRP Issue or STAmount.
Json::Value pay(AccountID const &account, AccountID const &to, AnyAmount amount)
Create a payment.
Json::Value fclear(Account const &account, std::uint32_t off)
Remove account flag.
FeatureBitset testable_amendments()
Json::Value fset(Account const &account, std::uint32_t on, std::uint32_t off=0)
Add and/or remove flag.
Use hash_* containers for keys that do not need a cryptographically secure hashing algorithm.
constexpr std::uint32_t asfGlobalFreeze
constexpr std::uint32_t const tfMPTCanTransfer
std::string to_string(base_uint< Bits, Tag > const &a)
constexpr std::uint32_t const tfMPTRequireAuth
std::uint64_t constexpr maxMPTokenAmount
The maximum amount of MPTokenIssuance.
STAmount amountFromString(Asset const &asset, std::string const &amount)
base_uint< 160, detail::AccountIDTag > AccountID
A 160-bit unsigned that uniquely identifies an account.
constexpr std::uint32_t const tfMPTCanLock
constexpr std::uint32_t tfClearFreeze
TERSubset< CanCvtToTER > TER
constexpr std::uint32_t const tfMPTLock
constexpr std::uint32_t tfClearDeepFreeze
Rate transferRate(ReadView const &view, AccountID const &issuer)
Returns IOU issuer transfer fee as Rate.
constexpr std::uint32_t tfSetDeepFreeze
constexpr std::uint32_t const tfMPTUnauthorize
constexpr std::uint32_t tfSetfAuth
constexpr std::uint32_t asfRequireAuth
@ tecNO_LINE_INSUF_RESERVE
@ tecINSUFFICIENT_RESERVE
Currency const & badCurrency()
We deliberately disallow the currency that looks like "XRP" because too many people were using it ins...
constexpr std::uint32_t tfSetFreeze
constexpr std::uint32_t const tfMPTCanEscrow
constexpr std::uint32_t asfAllowTrustLineLocking
MPTID makeMptID(std::uint32_t sequence, AccountID const &account)
void testMPTCreatePreclaim(FeatureBitset features)
void testMPTFinishDoApply(FeatureBitset features)
void testMPTMetaAndOwnership(FeatureBitset features)
void testIOUBalances(FeatureBitset features)
void testIOUCreatePreclaim(FeatureBitset features)
void testMPTGateway(FeatureBitset features)
void testMPTCanTransfer(FeatureBitset features)
void testIOUFinishPreclaim(FeatureBitset features)
void run() override
Runs the suite.
void testIOUMetaAndOwnership(FeatureBitset features)
void testIOUPrecisionLoss(FeatureBitset features)
void testMPTLock(FeatureBitset features)
void testMPTCancelPreclaim(FeatureBitset features)
void testIOUEnablement(FeatureBitset features)
void testMPTBalances(FeatureBitset features)
void testMPTRequireAuth(FeatureBitset features)
void testIOUFinishDoApply(FeatureBitset features)
jtx::PrettyAmount issuerEscrowed(jtx::Env &env, jtx::Account const &account, Issue const &issue)
void testIOUFreeze(FeatureBitset features)
void testMPTEnablement(FeatureBitset features)
static uint64_t mptEscrowed(jtx::Env const &env, jtx::Account const &account, jtx::MPT const &mpt)
void testIOUCancelPreclaim(FeatureBitset features)
void testIOUGateway(FeatureBitset features)
static uint64_t issuerMPTEscrowed(jtx::Env const &env, jtx::MPT const &mpt)
void testIOULimitAmount(FeatureBitset features)
void testIOUAllowLockingFlag(FeatureBitset features)
void testMPTCreatePreflight(FeatureBitset features)
void testIOULockedRate(FeatureBitset features)
void testMPTFinishPreclaim(FeatureBitset features)
void testIOUINSF(FeatureBitset features)
jtx::PrettyAmount issuerBalance(jtx::Env &env, jtx::Account const &account, Issue const &issue)
void testIOUWithFeats(FeatureBitset features)
void testMPTLockedRate(FeatureBitset features)
void testMPTWithFeats(FeatureBitset features)
void testIOUCreatePreflight(FeatureBitset features)
void testIOURequireAuth(FeatureBitset features)
void testMPTDestroy(FeatureBitset features)
void testIOURippleState(FeatureBitset features)
Represents an XRP or IOU quantity This customizes the string conversion and supports XRP conversions ...
Set the sequence number on a JTx.