38 using namespace test::jtx;
39 Env env(*
this, features);
42 Account alice{
"alice"};
45 env.fund(XRP(1000), G1, alice, bob);
48 env.trust(G1[
"USD"](100), bob);
49 env.trust(G1[
"USD"](100), alice);
52 env(pay(G1, bob, G1[
"USD"](10)));
53 env(pay(G1, alice, G1[
"USD"](100)));
56 env(offer(alice, XRP(500), G1[
"USD"](100)));
60 auto lines = getAccountLines(env, bob);
61 if (!BEAST_EXPECT(checkArraySize(lines[jss::lines], 1u)))
63 BEAST_EXPECT(lines[jss::lines][0u][jss::account] == G1.human());
64 BEAST_EXPECT(lines[jss::lines][0u][jss::limit] ==
"100");
65 BEAST_EXPECT(lines[jss::lines][0u][jss::balance] ==
"10");
69 auto lines = getAccountLines(env, alice);
70 if (!BEAST_EXPECT(checkArraySize(lines[jss::lines], 1u)))
72 BEAST_EXPECT(lines[jss::lines][0u][jss::account] == G1.human());
73 BEAST_EXPECT(lines[jss::lines][0u][jss::limit] ==
"100");
74 BEAST_EXPECT(lines[jss::lines][0u][jss::balance] ==
"100");
80 env(pay(alice, bob, G1[
"USD"](1)));
83 env(pay(bob, alice, G1[
"USD"](1)));
91 auto affected = env.meta()->getJson(
93 if (!BEAST_EXPECT(checkArraySize(affected, 2u)))
96 affected[1u][sfModifiedNode.fieldName][sfFinalFields.fieldName];
98 ff[sfLowLimit.fieldName] ==
108 env(offer(bob, G1[
"USD"](5), XRP(25)));
109 auto affected = env.meta()->getJson(
111 if (!BEAST_EXPECT(checkArraySize(affected, 5u)))
114 affected[3u][sfModifiedNode.fieldName][sfFinalFields.fieldName];
116 ff[sfHighLimit.fieldName] ==
121 BEAST_EXPECT(ff[sfBalance.fieldName] == amt);
130 env(pay(alice, bob, G1[
"USD"](1)));
133 env(pay(bob, alice, G1[
"USD"](1)), ter(
tecPATH_DRY));
139 auto lines = getAccountLines(env, G1);
141 for (
auto const& it : lines[jss::lines])
143 if (it[jss::account] == bob.human())
149 if (!BEAST_EXPECT(bobLine))
151 BEAST_EXPECT(bobLine[jss::freeze] ==
true);
152 BEAST_EXPECT(bobLine[jss::balance] ==
"-16");
157 auto lines = getAccountLines(env, bob);
159 for (
auto const& it : lines[jss::lines])
161 if (it[jss::account] == G1.human())
167 if (!BEAST_EXPECT(g1Line))
169 BEAST_EXPECT(g1Line[jss::freeze_peer] ==
true);
170 BEAST_EXPECT(g1Line[jss::balance] ==
"16");
177 auto affected = env.meta()->getJson(
179 if (!BEAST_EXPECT(checkArraySize(affected, 2u)))
182 affected[1u][sfModifiedNode.fieldName][sfFinalFields.fieldName];
184 ff[sfLowLimit.fieldName] ==
186 BEAST_EXPECT(!(ff[jss::Flags].asUInt() &
lsfLowFreeze));
384 using namespace test::jtx;
385 Env env(*
this, features);
393 env.fund(XRP(12000), G1);
394 env.fund(XRP(1000), A1);
395 env.fund(XRP(20000), A2, A3, A4);
398 env.trust(G1[
"USD"](1200), A1);
399 env.trust(G1[
"USD"](200), A2);
400 env.trust(G1[
"BTC"](100), A3);
401 env.trust(G1[
"BTC"](100), A4);
404 env(pay(G1, A1, G1[
"USD"](1000)));
405 env(pay(G1, A2, G1[
"USD"](100)));
406 env(pay(G1, A3, G1[
"BTC"](100)));
407 env(pay(G1, A4, G1[
"BTC"](100)));
410 env(offer(G1, XRP(10000), G1[
"USD"](100)), txflags(
tfPassive));
411 env(offer(G1, G1[
"USD"](100), XRP(10000)), txflags(
tfPassive));
412 env(offer(A1, XRP(10000), G1[
"USD"](100)), txflags(
tfPassive));
413 env(offer(A2, G1[
"USD"](100), XRP(10000)), txflags(
tfPassive));
433 auto offers = env.rpc(
436 "XRP")[jss::result][jss::offers];
437 if (!BEAST_EXPECT(checkArraySize(offers, 2u)))
440 for (
auto const& offer : offers)
442 accounts.
insert(offer[jss::Account].asString());
444 BEAST_EXPECT(accounts.
find(A2.human()) !=
std::end(accounts));
445 BEAST_EXPECT(accounts.
find(G1.human()) !=
std::end(accounts));
451 std::string(
"USD/") + G1.human())[jss::result][jss::offers];
452 if (!BEAST_EXPECT(checkArraySize(offers, 2u)))
455 for (
auto const& offer : offers)
457 accounts.
insert(offer[jss::Account].asString());
459 BEAST_EXPECT(accounts.
find(A1.human()) !=
std::end(accounts));
460 BEAST_EXPECT(accounts.
find(G1.human()) !=
std::end(accounts));
466 env(offer(A3, G1[
"BTC"](1), XRP(1)));
469 env(offer(A4, XRP(1), G1[
"BTC"](1)));
472 env(pay(G1, A2, G1[
"USD"](1)));
475 env(pay(A2, G1, G1[
"USD"](1)));
478 env(pay(A2, A1, G1[
"USD"](1)));
481 env(pay(A1, A2, G1[
"USD"](1)));
494 env(offer(A3, G1[
"BTC"](1), XRP(1)), ter(
tecFROZEN));
497 env(offer(A4, XRP(1), G1[
"BTC"](1)), ter(
tecFROZEN));
503 auto offers = getAccountOffers(env, G1)[jss::offers];
504 if (!BEAST_EXPECT(checkArraySize(offers, 2u)))
512 std::string(
"USD/") + G1.human())[jss::result][jss::offers];
513 if (!BEAST_EXPECT(checkArraySize(offers, 2u)))
519 "XRP")[jss::result][jss::offers];
520 if (!BEAST_EXPECT(checkArraySize(offers, 2u)))
527 env(pay(G1, A2, G1[
"USD"](1)));
530 env(pay(A2, G1, G1[
"USD"](1)));
655 testcase(
"Offers for Frozen Trust Lines");
657 using namespace test::jtx;
658 Env env(*
this, features);
665 env.fund(XRP(1000), G1, A3, A4);
666 env.fund(XRP(2000), A2);
669 env.trust(G1[
"USD"](1000), A2);
670 env.trust(G1[
"USD"](2000), A3);
671 env.trust(G1[
"USD"](2000), A4);
674 env(pay(G1, A3, G1[
"USD"](2000)));
675 env(pay(G1, A4, G1[
"USD"](2000)));
678 env(offer(A3, XRP(1000), G1[
"USD"](1000)), txflags(
tfPassive));
683 env(pay(A2, G1, G1[
"USD"](1)), paths(G1[
"USD"]), sendmax(XRP(1)));
687 auto offers = getAccountOffers(env, A3)[jss::offers];
688 if (!BEAST_EXPECT(checkArraySize(offers, 1u)))
691 offers[0u][jss::taker_gets] ==
695 env(offer(A4, XRP(999), G1[
"USD"](999)));
702 if (!BEAST_EXPECT(checkArraySize(affected, 2u)))
705 affected[1u][sfModifiedNode.fieldName][sfFinalFields.fieldName];
707 ff[sfHighLimit.fieldName] ==
709 BEAST_EXPECT(!(ff[jss::Flags].asUInt() &
lsfLowFreeze));
714 offers = getAccountOffers(env, A3)[jss::offers];
715 if (!BEAST_EXPECT(checkArraySize(offers, 1u)))
719 env(pay(A2, G1, G1[
"USD"](1)), paths(G1[
"USD"]), sendmax(XRP(1)));
723 offers = getAccountOffers(env, A3)[jss::offers];
724 if (!BEAST_EXPECT(checkArraySize(offers, 0u)))
732 if (!BEAST_EXPECT(checkArraySize(affected, 2u)))
734 ff = affected[0u][sfModifiedNode.fieldName][sfFinalFields.fieldName];
736 ff[sfLowLimit.fieldName] ==
743 env(offer(A2, G1[
"USD"](999), XRP(999)));
746 if (!BEAST_EXPECT(checkArraySize(affected, 8u)))
748 auto created = affected[0u][sfCreatedNode.fieldName];
750 created[sfNewFields.fieldName][jss::Account] == A2.human());
754 offers = getAccountOffers(env, A4)[jss::offers];
755 if (!BEAST_EXPECT(checkArraySize(offers, 0u)))
762 testcase(
"Offers on frozen trust lines");
764 using namespace test::jtx;
765 Env env(*
this, features);
771 auto const USD{G1[
"USD"]};
773 env.fund(XRP(10000), G1, A1, A2, A3);
776 auto const limit = USD(10000);
777 env.trust(limit, A1, A2, A3);
780 env(pay(G1, A1, USD(1000)));
781 env(pay(G1, A2, USD(1000)));
786 env(offer(A2, XRP(100), USD(50)), txflags(
tfPassive));
790 env(offer(A3, USD(100), XRP(100)), txflags(
tfPassive));
792 env.require(offers(A2, 1), offers(A3, 1));
797 env.require(balance(A1, USD(1001)), balance(A2, USD(999)));
802 env.require(balance(A1, USD(1000)), balance(A3, USD(1)));
811 env(offer(A1, USD(1), XRP(0.5)), txflags(
tfPassive));
813 env.require(balance(A1, USD(1000)), offers(A1, 1));
815 env(offer_cancel(A1, env.seq(A1) - 1));
816 env.require(offers(A1, 0));
823 balance(A1, USD(1001)), balance(A2, USD(998)), offers(A1, 0));
826 env(offer(A1, XRP(2), USD(1)),
830 env.require(balance(A1, USD(1001)), offers(A1, 0));
833 env(offer(A1, XRP(1), USD(1)),
837 env.require(balance(A1, USD(1001)), offers(A1, 0));
845 if (features[featureDeepFreeze])
851 env(offer(A1, USD(1), XRP(0.5)),
857 env(offer(A1, USD(1), XRP(2)),
863 env(offer(A1, XRP(2), USD(1)),
869 env(offer(A1, XRP(1), USD(1)),
876 env.require(balance(A1, USD(1001)), offers(A1, 0));
882 env.require(balance(A1, USD(1001)));
883 env(offer(A1, XRP(1.9), USD(1)));
884 env(offer(A1, USD(1), XRP(1.1)));
886 env.require(balance(A1, USD(1001)), offers(A1, 2));
892 env.require(balance(A1, USD(1001)), balance(A2, USD(998)));
893 env(offer(A2, XRP(1.1), USD(1)), txflags(
tfFillOrKill));
896 balance(A1, USD(1002)), balance(A2, USD(997)), offers(A1, 1));
900 balance(A1, USD(1002)), balance(A3, USD(1)), offers(A1, 1));
901 env(offer(A3, USD(1), XRP(1.9)),
906 balance(A1, USD(1002)), balance(A3, USD(1)), offers(A1, 0));
914 if (features[featureDeepFreeze])
916 env.require(balance(A1, USD(1002)));
917 env(offer(A1, XRP(1.9), USD(1)));
918 env(offer(A1, USD(1), XRP(1.1)));
920 env.require(balance(A1, USD(1002)), offers(A1, 2));
926 env.require(balance(A1, USD(1002)), balance(A2, USD(997)));
927 env(offer(A2, XRP(1.1), USD(1)),
932 balance(A1, USD(1002)), balance(A2, USD(997)), offers(A1, 1));
936 balance(A1, USD(1002)), balance(A3, USD(1)), offers(A1, 1));
937 env(offer(A3, USD(1), XRP(1.9)),
942 balance(A1, USD(1002)), balance(A3, USD(1)), offers(A1, 0));
955 env(offer(A1, USD(1), XRP(0.5)), txflags(
tfPassive));
957 env.require(balance(A1, USD(1002)), offers(A1, 1));
959 env(offer_cancel(A1, env.seq(A1) - 1));
960 env.require(offers(A1, 0));
964 env(offer(A1, USD(1), XRP(2)),
969 balance(A1, USD(1002)), balance(A2, USD(997)), offers(A1, 0));
972 env(offer(A1, XRP(2), USD(1)), txflags(
tfPassive));
974 env.require(balance(A1, USD(1002)), offers(A1, 1));
976 env(offer_cancel(A1, env.seq(A1) - 1));
977 env.require(offers(A1, 0));
983 env.require(balance(A1, USD(1001)), offers(A1, 0));
991 if (features[featureDeepFreeze])
997 env(offer(A1, USD(1), XRP(0.5)),
1003 env(offer(A1, USD(1), XRP(2)),
1009 env(offer(A1, XRP(2), USD(1)),
1015 env(offer(A1, XRP(1), USD(1)),
1028 testcase(
"Longer paths payment on frozen trust lines");
1029 using namespace test::jtx;
1032 Env env(*
this, features);
1036 auto const USD{G1[
"USD"]};
1038 env.fund(XRP(10000), G1, A1, A2);
1041 auto const limit = USD(10000);
1042 env.trust(limit, A1, A2);
1045 env(pay(G1, A1, USD(1000)));
1046 env(pay(G1, A2, USD(1000)));
1049 env(offer(A2, XRP(100), USD(100)), txflags(
tfPassive));
1058 env(pay(A1, G1, USD(10)),
1066 env(pay(G1, A1, USD(10)),
1078 if (features[featureDeepFreeze])
1084 env(pay(A1, G1, USD(10)),
1092 env(pay(G1, A1, USD(10)),
1110 env(pay(A1, G1, USD(10)),
1117 env(pay(G1, A1, USD(10)),
1129 if (features[featureDeepFreeze])
1135 env(pay(A1, G1, USD(10)),
1143 env(pay(G1, A1, USD(10)),
1155 env(offer_cancel(A1, env.seq(A1) - 1));
1156 env.require(offers(A1, 0));
1159 env(offer(A2, USD(100), XRP(100)), txflags(
tfPassive));
1168 env(pay(A1, G1, XRP(10)),
1175 env(pay(G1, A1, XRP(10)),
1187 if (features[featureDeepFreeze])
1193 env(pay(A1, G1, XRP(10)),
1201 env(pay(G1, A1, XRP(10)),
1219 env(pay(A1, G1, XRP(10)),
1226 env(pay(G1, A1, XRP(10)),
1238 if (features[featureDeepFreeze])
1244 env(pay(A1, G1, XRP(10)),
1252 env(pay(G1, A1, XRP(10)),
1264 env(offer_cancel(A1, env.seq(A1) - 1));
1265 env.require(offers(A1, 0));
1272 testcase(
"Direct payments on frozen trust lines");
1274 using namespace test::jtx;
1275 Env env(*
this, features);
1280 auto const USD{G1[
"USD"]};
1282 env.fund(XRP(10000), G1, A1, A2);
1285 auto const limit = USD(10000);
1286 env.trust(limit, A1, A2);
1289 env(pay(G1, A1, USD(1000)));
1290 env(pay(G1, A2, USD(1000)));
1295 env(pay(A1, G1, USD(1)));
1296 env(pay(A2, G1, USD(1)));
1300 env(pay(A1, A2, USD(1)));
1301 env(pay(A2, A1, USD(1)));
1309 env(pay(A1, G1, USD(1)));
1310 env(pay(G1, A1, USD(1)));
1317 env(pay(A2, A1, USD(1)));
1320 if (features[featureDeepFreeze])
1327 env(pay(A1, G1, USD(1)));
1328 env(pay(G1, A1, USD(1)));
1351 env(pay(A2, G1, USD(1)));
1352 env(pay(G1, A2, USD(1)));
1356 env(pay(A1, G1, USD(1)));
1359 env(pay(A1, A2, USD(1)));
1363 env(pay(G1, A1, USD(1)));
1367 if (features[featureDeepFreeze])
1374 env(pay(A2, G1, USD(1)));
1375 env(pay(G1, A2, USD(1)));
1379 env(pay(A1, G1, USD(1)));
1383 env(pay(G1, A1, USD(1)));
1394 testcase(
"Checks on frozen trust lines");
1396 using namespace test::jtx;
1397 Env env(*
this, features);
1402 auto const USD{G1[
"USD"]};
1404 env.fund(XRP(10000), G1, A1, A2);
1407 auto const limit = USD(10000);
1408 env.trust(limit, A1, A2);
1411 env(pay(G1, A1, USD(1000)));
1412 env(pay(G1, A2, USD(1000)));
1418 env(check::create(G1, A1, USD(10)));
1420 env(check::cash(A1, checkId, USD(10)));
1426 env(check::create(G1, A2, USD(10)));
1428 env(check::cash(A2, checkId, USD(10)));
1434 env(check::create(A1, G1, USD(10)));
1436 env(check::cash(G1, checkId, USD(10)));
1442 env(check::create(A1, A2, USD(10)));
1444 env(check::cash(A2, checkId, USD(10)));
1450 env(check::create(A2, G1, USD(10)));
1452 env(check::cash(G1, checkId, USD(10)));
1458 env(check::create(A2, A1, USD(10)));
1460 env(check::cash(A1, checkId, USD(10)));
1473 env(check::create(G1, A1, USD(10)));
1475 env(check::cash(A1, checkId, USD(10)), ter(
tecFROZEN));
1482 env(check::create(A2, A1, USD(10)));
1485 env(check::cash(A1, checkId, USD(10)), ter(
tecFROZEN));
1491 env(check::create(A1, G1, USD(10)), ter(
tecFROZEN));
1498 env(check::create(A1, A2, USD(10)), ter(
tecFROZEN));
1508 env(check::create(A1, G1, USD(10)));
1511 env(check::create(A1, A2, USD(10)));
1535 if (features[featureDeepFreeze])
1543 env(check::create(G1, A1, USD(10)));
1546 env(check::cash(A1, checkId, USD(10)), ter(
tecFROZEN));
1553 env(check::create(A2, A1, USD(10)));
1556 env(check::cash(A1, checkId, USD(10)), ter(
tecFROZEN));
1562 env(check::create(A1, G1, USD(10)), ter(
tecFROZEN));
1569 env(check::create(A1, A2, USD(10)), ter(
tecFROZEN));
1579 env(check::create(A1, G1, USD(10)));
1582 env(check::create(A1, A2, USD(10)));
1612 env(check::create(G1, A1, USD(10)), ter(
tecFROZEN));
1618 env(check::create(A2, A1, USD(10)), ter(
tecFROZEN));
1625 env(check::create(A1, G1, USD(10)));
1627 env(check::cash(G1, checkId, USD(10)));
1634 env(check::create(A1, A2, USD(10)));
1636 env(check::cash(A2, checkId, USD(10)));
1646 if (features[featureDeepFreeze])
1653 env(check::create(G1, A1, USD(10)), ter(
tecFROZEN));
1659 env(check::create(A2, A1, USD(10)), ter(
tecFROZEN));
1666 env(check::create(A1, G1, USD(10)));
1675 env(check::create(A1, A2, USD(10)));
1689 testcase(
"AMM payments on frozen trust lines");
1690 using namespace test::jtx;
1693 Env env(*
this, features);
1697 auto const USD{G1[
"USD"]};
1699 env.fund(XRP(10000), G1, A1, A2);
1702 env.trust(G1[
"USD"](10000), A1, A2);
1705 env(pay(G1, A1, USD(1000)));
1706 env(pay(G1, A2, USD(1000)));
1709 AMM ammG1(env, G1, XRP(1'000), USD(1'000));
1718 env(pay(A1, A2, USD(10)),
1725 env(pay(A1, A2, XRP(10)),
1733 env(pay(A2, A1, USD(10)),
1740 env(pay(A2, A1, XRP(10)),
1752 if (features[featureDeepFreeze])
1758 env(pay(A1, A2, USD(10)),
1765 env(pay(A1, A2, XRP(10)),
1773 env(pay(A2, A1, USD(10)),
1781 env(pay(A2, A1, XRP(10)),
1795 testcase(
"NFT offers on frozen trust lines");
1796 using namespace test::jtx;
1798 Env env(*
this, features);
1802 auto const USD{G1[
"USD"]};
1804 env.fund(XRP(10000), G1, A1, A2);
1807 auto const limit = USD(10000);
1808 env.trust(limit, A1, A2);
1811 env(pay(G1, A1, USD(1000)));
1812 env(pay(G1, A2, USD(1000)));
1822 env(token::acceptSellOffer(A1, sellOfferIndex));
1830 if (features[featureDeepFreeze])
1838 env(token::acceptSellOffer(A1, sellOfferIndex), ter(
tecFROZEN));
1852 env(token::acceptSellOffer(A2, sellOfferIndex),
1861 if (features[featureDeepFreeze])
1868 env(token::acceptSellOffer(A2, sellOfferIndex),
1877 if (features[featureDeepFreeze] &&
1878 features[fixEnforceNFTokenTrustlineV2])
1888 env(token::createOffer(A1, nftID, USD(10)), token::owner(A2));
1891 env(token::acceptBuyOffer(A2, buyIdx), ter(
tecFROZEN));
1897 env(token::acceptBuyOffer(A2, buyIdx));
1908 env(token::acceptSellOffer(A1, sellOfferIndex));
1916 if (features[featureDeepFreeze])
1924 env(token::acceptSellOffer(A1, sellOfferIndex), ter(
tecFROZEN));
1938 env(token::acceptSellOffer(A2, sellOfferIndex));
1946 if (features[featureDeepFreeze])
1953 env(token::acceptSellOffer(A2, sellOfferIndex),
1962 if (features[featureDeepFreeze] &&
1963 features[fixEnforceNFTokenTrustlineV2])
1965 Account broker{
"broker"};
1966 env.fund(XRP(10000), broker);
1976 env(token::createOffer(A2, nftID, USD(10)), txflags(
tfSellNFToken));
1979 env(token::createOffer(A1, nftID, USD(11)), token::owner(A2));
1982 env(token::brokerOffers(broker, buyIdx, sellIdx),
1983 token::brokerFee(USD(1)),
1989 if (features[featureDeepFreeze] &&
1990 features[fixEnforceNFTokenTrustlineV2])
1992 Account minter{
"minter"};
1993 env.fund(XRP(10000), minter);
1995 env(trust(G1, minter[
"USD"](1000)));
2000 env(token::mint(minter, 0),
2007 env(token::createOffer(minter, nftID, drops(1)),
2010 env(token::acceptSellOffer(A2, minterSellIdx));
2014 env(token::createOffer(A2, nftID, USD(100)),
2019 env(token::acceptSellOffer(A1, sellIdx), ter(
tecFROZEN));