3#include <xrpl/basics/chrono.h> 
    4#include <xrpl/ledger/Dir.h> 
    5#include <xrpl/protocol/Feature.h> 
    6#include <xrpl/protocol/Indexes.h> 
    7#include <xrpl/protocol/PayChan.h> 
    8#include <xrpl/protocol/TxFlags.h> 
    9#include <xrpl/protocol/jss.h> 
   13using namespace jtx::paychan;
 
   29        return {k.key, view.
read(k)};
 
 
   47        auto const slep = view.
read({ltPAYCHAN, chan});
 
   50        return (*slep)[sfAmount];
 
 
   56        auto const slep = view.
read({ltPAYCHAN, chan});
 
   59        if (
auto const r = (*slep)[~sfExpiration])
 
 
   70        Env env{*
this, features};
 
   71        auto const alice = 
Account(
"alice");
 
   72        auto const bob = 
Account(
"bob");
 
   73        auto USDA = alice[
"USD"];
 
   74        env.fund(
XRP(10000), alice, bob);
 
   75        auto const pk = alice.pk();
 
   76        auto const settleDelay = 100s;
 
   77        auto const chan = 
channel(alice, bob, env.seq(alice));
 
   78        env(
create(alice, bob, 
XRP(1000), settleDelay, pk));
 
   83            auto const preAlice = env.balance(alice);
 
   84            env(
fund(alice, chan, 
XRP(1000)));
 
   85            auto const feeDrops = env.current()->fees().base;
 
   86            BEAST_EXPECT(env.balance(alice) == preAlice - 
XRP(1000) - feeDrops);
 
   91        BEAST_EXPECT(chanBal == 
XRP(0));
 
   92        BEAST_EXPECT(chanAmt == 
XRP(2000));
 
   96            env(
create(alice, bob, USDA(1000), settleDelay, pk),
 
   99            env(
create(alice, bob, 
XRP(-1000), settleDelay, pk),
 
  105        env(
create(alice, 
"noAccount", 
XRP(1000), settleDelay, pk),
 
  108        env(
create(alice, alice, 
XRP(1000), settleDelay, pk),
 
  114                channel(alice, 
"noAccount", env.seq(alice) - 1),
 
  122            auto const iou = USDA(100).value();
 
  123            auto const negXRP = 
XRP(-100).value();
 
  124            auto const posXRP = 
XRP(100).value();
 
  134            auto const delta = 
XRP(500);
 
  135            auto const reqBal = chanBal + delta;
 
  136            auto const authAmt = reqBal + 
XRP(-100);
 
  137            assert(reqBal <= chanAmt);
 
  142            auto const preBob = env.balance(bob);
 
  143            auto const delta = 
XRP(500);
 
  144            auto const reqBal = chanBal + delta;
 
  145            auto const authAmt = reqBal + 
XRP(100);
 
  146            assert(reqBal <= chanAmt);
 
  147            env(
claim(alice, chan, reqBal, authAmt));
 
  149            BEAST_EXPECT(
channelAmount(*env.current(), chan) == chanAmt);
 
  150            BEAST_EXPECT(env.balance(bob) == preBob + delta);
 
  155            auto preBob = env.balance(bob);
 
  156            auto const delta = 
XRP(500);
 
  157            auto const reqBal = chanBal + delta;
 
  158            auto const authAmt = reqBal + 
XRP(100);
 
  159            assert(reqBal <= chanAmt);
 
  162            env(
claim(bob, chan, reqBal, authAmt, 
Slice(
sig), alice.pk()));
 
  164            BEAST_EXPECT(
channelAmount(*env.current(), chan) == chanAmt);
 
  165            auto const feeDrops = env.current()->fees().base;
 
  166            BEAST_EXPECT(env.balance(bob) == preBob + delta - feeDrops);
 
  170            preBob = env.balance(bob);
 
  171            env(
claim(bob, chan, reqBal, authAmt, 
Slice(
sig), alice.pk()),
 
  174            BEAST_EXPECT(
channelAmount(*env.current(), chan) == chanAmt);
 
  175            BEAST_EXPECT(env.balance(bob) == preBob - feeDrops);
 
  179            auto const preBob = env.balance(bob);
 
  182            assert(reqAmt <= chanAmt);
 
  185            env(
claim(bob, chan, reqAmt, authAmt, 
Slice(
sig), alice.pk()),
 
  188            BEAST_EXPECT(
channelAmount(*env.current(), chan) == chanAmt);
 
  189            BEAST_EXPECT(env.balance(bob) == preBob);
 
  195        BEAST_EXPECT(
channelAmount(*env.current(), chan) == chanAmt);
 
  209            BEAST_EXPECT(
channelAmount(*env.current(), chan) == chanAmt);
 
  223            BEAST_EXPECT(
channelAmount(*env.current(), chan) == chanAmt);
 
  227            auto const preAlice = env.balance(alice);
 
  228            auto const preBob = env.balance(bob);
 
  231            auto const feeDrops = env.current()->fees().base;
 
  232            auto const delta = chanAmt - chanBal;
 
  233            assert(delta > beast::zero);
 
  234            BEAST_EXPECT(env.balance(alice) == preAlice + delta);
 
  235            BEAST_EXPECT(env.balance(bob) == preBob - feeDrops);
 
 
  249            env.fund(
XRP(10000), alice);
 
  252            auto const sle = env.le(alice);
 
  259        auto const alice = 
Account(
"alice");
 
  260        auto const bob = 
Account(
"bob");
 
  261        auto const cho = 
Account(
"cho");
 
  262        env.fund(
XRP(10000), alice, bob, cho);
 
  263        auto const pk = alice.pk();
 
  264        auto const settleDelay = 100s;
 
  272            auto const chan = 
channel(alice, bob, env.seq(alice));
 
  273            env(
create(alice, bob, 
XRP(1000), settleDelay, pk),
 
  284            auto const chan = 
channel(bob, alice, env.seq(bob));
 
  285            env(
create(bob, alice, 
XRP(1000), settleDelay, pk),
 
  296            auto const chan = 
channel(alice, bob, env.seq(alice));
 
  297            env(
create(alice, bob, 
XRP(1000), settleDelay, pk),
 
  304            auto const chan = 
channel(cho, alice, env.seq(cho));
 
  305            env(
create(cho, alice, 
XRP(1000), settleDelay, pk),
 
  316            auto const chan = 
channel(cho, alice, env.seq(cho));
 
  317            env(
create(cho, alice, 
XRP(1000), settleDelay, pk),
 
 
  329        auto const alice = 
Account(
"alice");
 
  330        auto const bob = 
Account(
"bob");
 
  331        auto const carol = 
Account(
"carol");
 
  334            Env env{*
this, features};
 
  335            env.fund(
XRP(10000), alice, bob);
 
  336            auto const pk = alice.pk();
 
  337            auto const settleDelay = 100s;
 
  339                env.current()->info().parentCloseTime + 3600s;
 
  340            auto const channelFunds = 
XRP(1000);
 
  341            auto const chan = 
channel(alice, bob, env.seq(alice));
 
  342            env(
create(alice, bob, channelFunds, settleDelay, pk, cancelAfter));
 
  344            env.close(cancelAfter);
 
  349                auto preAlice = env.balance(alice);
 
  350                auto preBob = env.balance(bob);
 
  351                auto const delta = 
XRP(500);
 
  352                auto const reqBal = chanBal + delta;
 
  353                auto const authAmt = reqBal + 
XRP(100);
 
  354                assert(reqBal <= chanAmt);
 
  357                env(
claim(bob, chan, reqBal, authAmt, 
Slice(
sig), alice.pk()));
 
  358                auto const feeDrops = env.current()->fees().base;
 
  360                BEAST_EXPECT(env.balance(bob) == preBob - feeDrops);
 
  361                BEAST_EXPECT(env.balance(alice) == preAlice + channelFunds);
 
  366            Env env{*
this, features};
 
  367            env.fund(
XRP(10000), alice, bob, carol);
 
  368            auto const pk = alice.pk();
 
  369            auto const settleDelay = 100s;
 
  371                env.current()->info().parentCloseTime + 3600s;
 
  372            auto const channelFunds = 
XRP(1000);
 
  373            auto const chan = 
channel(alice, bob, env.seq(alice));
 
  374            env(
create(alice, bob, channelFunds, settleDelay, pk, cancelAfter));
 
  379            env.close(cancelAfter);
 
  381            auto const preAlice = env.balance(alice);
 
  384            BEAST_EXPECT(env.balance(alice) == preAlice + channelFunds);
 
  389            for (
bool const withFixPayChan : {
true, 
false})
 
  391                auto const amend = withFixPayChan
 
  393                    : features - fixPayChanCancelAfter;
 
  394                Env env{*
this, amend};
 
  395                env.
fund(
XRP(10000), alice, bob);
 
  398                auto const pk = alice.pk();
 
  399                auto const settleDelay = 100s;
 
  400                auto const channelFunds = 
XRP(1000);
 
  402                    env.current()->info().parentCloseTime - 1s;
 
  403                auto const txResult =
 
  406                        alice, bob, channelFunds, settleDelay, pk, cancelAfter),
 
  413            for (
bool const withFixPayChan : {
true, 
false})
 
  415                auto const amend = withFixPayChan
 
  417                    : features - fixPayChanCancelAfter;
 
  418                Env env{*
this, amend};
 
  419                env.
fund(
XRP(10000), alice, bob);
 
  422                auto const pk = alice.pk();
 
  423                auto const settleDelay = 100s;
 
  424                auto const channelFunds = 
XRP(1000);
 
  426                    env.current()->info().parentCloseTime;
 
  428                        alice, bob, channelFunds, settleDelay, pk, cancelAfter),
 
 
  440        Env env{*
this, features};
 
  441        auto const alice = 
Account(
"alice");
 
  442        auto const bob = 
Account(
"bob");
 
  443        auto const carol = 
Account(
"carol");
 
  444        env.fund(
XRP(10000), alice, bob, carol);
 
  445        auto const pk = alice.pk();
 
  446        auto const settleDelay = 3600s;
 
  447        auto const closeTime = env.current()->info().parentCloseTime;
 
  448        auto const minExpiration = closeTime + settleDelay;
 
  450        auto const channelFunds = 
XRP(1000);
 
  451        auto const chan = 
channel(alice, bob, env.seq(alice));
 
  452        env(
create(alice, bob, channelFunds, settleDelay, pk, cancelAfter));
 
  457        auto counts = [](
auto const& t) {
 
  458            return t.time_since_epoch().count();
 
  467            counts(minExpiration) + 100);
 
  473            counts(minExpiration) + 50);
 
  480            counts(minExpiration) + 50);
 
  484            counts(minExpiration) + 50);
 
  493        env.close(minExpiration);
 
 
  506        Env env{*
this, features};
 
  507        auto const alice = 
Account(
"alice");
 
  508        auto const bob = 
Account(
"bob");
 
  509        env.fund(
XRP(10000), alice, bob);
 
  510        auto const pk = alice.pk();
 
  511        auto const settleDelay = 3600s;
 
  513            env.current()->info().parentCloseTime + settleDelay;
 
  514        auto const channelFunds = 
XRP(1000);
 
  515        auto const chan = 
channel(alice, bob, env.seq(alice));
 
  516        env(
create(alice, bob, channelFunds, settleDelay, pk));
 
  521        env.close(settleTimepoint - settleDelay / 2);
 
  526            auto preBob = env.balance(bob);
 
  527            auto const delta = 
XRP(500);
 
  528            auto const reqBal = chanBal + delta;
 
  529            auto const authAmt = reqBal + 
XRP(100);
 
  530            assert(reqBal <= chanAmt);
 
  533            env(
claim(bob, chan, reqBal, authAmt, 
Slice(
sig), alice.pk()));
 
  535            BEAST_EXPECT(
channelAmount(*env.current(), chan) == chanAmt);
 
  536            auto const feeDrops = env.current()->fees().base;
 
  537            BEAST_EXPECT(env.balance(bob) == preBob + delta - feeDrops);
 
  539        env.close(settleTimepoint);
 
  544            auto const preAlice = env.balance(alice);
 
  545            auto preBob = env.balance(bob);
 
  546            auto const delta = 
XRP(500);
 
  547            auto const reqBal = chanBal + delta;
 
  548            auto const authAmt = reqBal + 
XRP(100);
 
  549            assert(reqBal <= chanAmt);
 
  552            env(
claim(bob, chan, reqBal, authAmt, 
Slice(
sig), alice.pk()));
 
  554            auto const feeDrops = env.current()->fees().base;
 
  555            BEAST_EXPECT(env.balance(alice) == preAlice + chanAmt - chanBal);
 
  556            BEAST_EXPECT(env.balance(bob) == preBob - feeDrops);
 
 
  566        Env env{*
this, features};
 
  567        auto const alice = 
Account(
"alice");
 
  568        auto const bob = 
Account(
"bob");
 
  569        env.fund(
XRP(10000), alice, bob);
 
  570        auto const pk = alice.pk();
 
  571        auto const settleDelay = 3600s;
 
  572        auto const channelFunds = 
XRP(1000);
 
  573        auto const chan = 
channel(alice, bob, env.seq(alice));
 
  574        env(
create(alice, bob, channelFunds, settleDelay, pk));
 
  581            auto const preBob = env.balance(bob);
 
  582            env(
claim(alice, chan, channelFunds.value(), channelFunds.value()));
 
  583            BEAST_EXPECT(
channelBalance(*env.current(), chan) == channelFunds);
 
  584            BEAST_EXPECT(env.balance(bob) == preBob + channelFunds);
 
  586        auto const preAlice = env.balance(alice);
 
  590        auto const feeDrops = env.current()->fees().base;
 
  591        BEAST_EXPECT(env.balance(alice) == preAlice - feeDrops);
 
 
  601        Env env{*
this, features};
 
  602        auto const alice = 
Account(
"alice");
 
  603        auto const bob = 
Account(
"bob");
 
  604        env.fund(
XRP(10000), alice, bob);
 
  605        auto const pk = alice.pk();
 
  606        auto const settleDelay = 3600s;
 
  607        auto const channelFunds = 
XRP(1000);
 
  608        auto const chan = 
channel(alice, bob, env.seq(alice));
 
  609        env(
create(alice, bob, channelFunds, settleDelay, pk));
 
  617            auto const preBob = env.balance(bob);
 
  619            auto const delta = 
XRP(500);
 
  620            auto const reqBal = chanBal + delta;
 
  621            assert(reqBal <= chanAmt);
 
  626            auto const feeDrops = env.current()->fees().base;
 
  627            BEAST_EXPECT(env.balance(bob) == preBob + delta - feeDrops);
 
  634            auto const preBob = env.balance(bob);
 
  636            auto const delta = 
XRP(500);
 
  637            auto const reqBal = chanBal + delta;
 
  638            assert(reqBal <= chanAmt);
 
  643            auto const feeDrops = env.current()->fees().base;
 
  644            BEAST_EXPECT(env.balance(bob) == preBob + delta - feeDrops);
 
 
  657        auto const alice = 
Account(
"alice");
 
  658        auto const bob = 
Account(
"bob");
 
  661            Env env(*
this, features - featureDepositAuth);
 
  662            env.
fund(
XRP(10000), alice, bob);
 
  664            auto const chan = 
channel(alice, bob, env.
seq(alice));
 
  665            env(
create(alice, bob, 
XRP(1000), 3600s, alice.pk()),
 
  672            Env env{*
this, features};
 
  673            env.fund(
XRP(10000), alice, bob);
 
  675            auto const chan = 
channel(alice, bob, env.seq(alice));
 
  676            env(
create(alice, bob, 
XRP(1000), 3600s, alice.pk()));
 
  683            Env env(*
this, features - featureDepositAuth);
 
  684            env.
fund(
XRP(10000), alice, bob);
 
  685            auto const chan = 
channel(alice, bob, env.
seq(alice));
 
  686            env(
create(alice, bob, 
XRP(1000), 3600s, alice.pk()));
 
  690            auto const reqBal = 
XRP(500).value();
 
  697            Env env{*
this, features};
 
  698            env.fund(
XRP(10000), alice, bob);
 
  699            auto const chan = 
channel(alice, bob, env.seq(alice));
 
  700            env(
create(alice, bob, 
XRP(1000), 3600s, alice.pk()));
 
  704            auto const reqBal = 
XRP(500).value();
 
  705            env(
claim(alice, chan, reqBal, reqBal));
 
 
  717        Env env{*
this, features};
 
  718        auto const alice = 
Account(
"alice");
 
  719        auto const bob = 
Account(
"bob");
 
  720        env.fund(
XRP(10000), alice, bob);
 
  722        auto const pk = alice.pk();
 
  723        auto const settleDelay = 3600s;
 
  724        auto const channelFunds = 
XRP(1000);
 
  726            auto const chan = 
channel(alice, bob, env.seq(alice));
 
  727            env(
create(alice, bob, channelFunds, settleDelay, pk),
 
  732            auto const chan = 
channel(alice, bob, env.seq(alice));
 
  734                alice, bob, channelFunds, settleDelay, pk, 
std::nullopt, 1));
 
 
  746        auto const alice = 
Account(
"alice");
 
  747        auto const bob = 
Account(
"bob");
 
  748        auto const carol = 
Account(
"carol");
 
  749        auto USDA = alice[
"USD"];
 
  751            Env env{*
this, features};
 
  752            env.fund(
XRP(10000), alice, bob, carol);
 
  757            auto const pk = alice.pk();
 
  758            auto const settleDelay = 100s;
 
  759            auto const chan = 
channel(alice, bob, env.seq(alice));
 
  760            env(
create(alice, bob, 
XRP(1000), settleDelay, pk));
 
  768            env(
fund(alice, chan, 
XRP(1000)));
 
  772            env(
claim(alice, chan, 
XRP(500).value(), 
XRP(500).value()),
 
  777            auto const baseFee = env.current()->fees().base;
 
  778            auto const preBob = env.balance(bob);
 
  780                auto const delta = 
XRP(500).value();
 
  788                BEAST_EXPECT(env.balance(bob) == preBob);
 
  800                BEAST_EXPECT(env.balance(bob) == preBob + delta - baseFee);
 
  804                auto const delta = 
XRP(600).value();
 
  836                    env.balance(bob) == preBob + delta - (3 * baseFee));
 
  841                auto const delta = 
XRP(800).value();
 
  855                env(
claim(alice, chan, delta, delta));
 
  858                    env.balance(bob) == preBob + 
XRP(800) - (5 * baseFee));
 
 
  866        testcase(
"Deposit Authorization with Credentials");
 
  870        char const credType[] = 
"abcde";
 
  875        Account const dillon(
"dillon");
 
  880            env.
fund(
XRP(10000), alice, bob, carol, dillon, zelda);
 
  882            auto const pk = alice.
pk();
 
  883            auto const settleDelay = 100s;
 
  884            auto const chan = 
channel(alice, bob, env.seq(alice));
 
  885            env(
create(alice, bob, 
XRP(1000), settleDelay, pk));
 
  889            env(
fund(alice, chan, 
XRP(1000)));
 
  893                "D007AE4B6E1274B4AF872588267B810C2F82716726351D1C7D38D3E5499FC6" 
  896            auto const delta = 
XRP(500).value();
 
  902                                       .parentCloseTime.time_since_epoch()
 
  905                jv[sfExpiration.jsonName] = t;
 
  912            std::string const credIdx = jv[jss::result][jss::index].asString();
 
  919            env(
claim(alice, chan, delta, delta),
 
  928            env(
claim(alice, chan, delta, delta),
 
  938            env(
claim(dillon, chan, delta, delta),
 
  946            env(
claim(alice, chan, delta, delta),
 
  951            env(
claim(alice, chan, delta, delta),
 
  959                for (
int i = 0; i < 10; ++i)
 
  962                env(
claim(alice, chan, delta, delta),
 
  977                    jv[jss::result][jss::index].asString();
 
  980                env(
claim(alice, chan, delta, delta),
 
  987            env.
fund(
XRP(10000), alice, bob, carol, dillon, zelda);
 
  989            auto const pk = alice.
pk();
 
  990            auto const settleDelay = 100s;
 
  991            auto const chan = 
channel(alice, bob, env.seq(alice));
 
  992            env(
create(alice, bob, 
XRP(1000), settleDelay, pk));
 
  996            env(
fund(alice, chan, 
XRP(1000)));
 
  999            auto const delta = 
XRP(500).value();
 
 1010            std::string const credIdx = jv[jss::result][jss::index].asString();
 
 1020            env.
fund(
XRP(5000), 
"alice", 
"bob");
 
 1023            auto const pk = alice.
pk();
 
 1024            auto const settleDelay = 100s;
 
 1025            auto const chan = 
channel(alice, bob, env.
seq(alice));
 
 1026            env(
create(alice, bob, 
XRP(1000), settleDelay, pk));
 
 1029            env(
fund(alice, chan, 
XRP(1000)));
 
 1032                "48004829F915654A81B11C4AB8218D96FED67F209B58328A72314FB6EA288B" 
 1041            env(
claim(alice, chan, 
XRP(500).value(), 
XRP(500).value()),
 
 
 1051        testcase(
"Multiple channels to the same account");
 
 1052        using namespace jtx;
 
 1054        Env env{*
this, features};
 
 1055        auto const alice = 
Account(
"alice");
 
 1056        auto const bob = 
Account(
"bob");
 
 1057        env.fund(
XRP(10000), alice, bob);
 
 1058        auto const pk = alice.pk();
 
 1059        auto const settleDelay = 3600s;
 
 1060        auto const channelFunds = 
XRP(1000);
 
 1061        auto const chan1 = 
channel(alice, bob, env.seq(alice));
 
 1062        env(
create(alice, bob, channelFunds, settleDelay, pk));
 
 1064        auto const chan2 = 
channel(alice, bob, env.seq(alice));
 
 1065        env(
create(alice, bob, channelFunds, settleDelay, pk));
 
 1067        BEAST_EXPECT(chan1 != chan2);
 
 
 1075        using namespace jtx;
 
 1077        Env env{*
this, features};
 
 1078        auto const alice = 
Account(
"alice");
 
 1079        auto const bob = 
Account(
"bob");
 
 1081        env.fund(
XRP(10000), alice, bob, charlie);
 
 1082        auto const pk = alice.pk();
 
 1083        auto const settleDelay = 3600s;
 
 1084        auto const channelFunds = 
XRP(1000);
 
 1086        env(
create(alice, bob, channelFunds, settleDelay, pk));
 
 1090            auto testInvalidAccountParam = [&](
auto const& param) {
 
 1092                params[jss::account] = param;
 
 1094                    "json", 
"account_channels", 
to_string(params))[jss::result];
 
 1095                BEAST_EXPECT(jrr[jss::error] == 
"invalidParams");
 
 1097                    jrr[jss::error_message] == 
"Invalid field 'account'.");
 
 1100            testInvalidAccountParam(1);
 
 1101            testInvalidAccountParam(1.1);
 
 1102            testInvalidAccountParam(
true);
 
 1109                env.rpc(
"account_channels", alice.human(), bob.human());
 
 1110            BEAST_EXPECT(r[jss::result][jss::channels].size() == 1);
 
 1112                r[jss::result][jss::channels][0u][jss::channel_id] == chan1Str);
 
 1113            BEAST_EXPECT(r[jss::result][jss::validated]);
 
 1116            auto const r = env.rpc(
"account_channels", alice.human());
 
 1117            BEAST_EXPECT(r[jss::result][jss::channels].size() == 1);
 
 1119                r[jss::result][jss::channels][0u][jss::channel_id] == chan1Str);
 
 1120            BEAST_EXPECT(r[jss::result][jss::validated]);
 
 1124                env.rpc(
"account_channels", bob.human(), alice.human());
 
 1125            BEAST_EXPECT(r[jss::result][jss::channels].size() == 0);
 
 1126            BEAST_EXPECT(r[jss::result][jss::validated]);
 
 1129        env(
create(alice, bob, channelFunds, settleDelay, pk));
 
 1133                env.rpc(
"account_channels", alice.human(), bob.human());
 
 1134            BEAST_EXPECT(r[jss::result][jss::channels].size() == 2);
 
 1135            BEAST_EXPECT(r[jss::result][jss::validated]);
 
 1136            BEAST_EXPECT(chan1Str != chan2Str);
 
 1137            for (
auto const& c : {chan1Str, chan2Str})
 
 1139                    r[jss::result][jss::channels][0u][jss::channel_id] == c ||
 
 1140                    r[jss::result][jss::channels][1u][jss::channel_id] == c);
 
 
 1147        testcase(
"Account channels RPC markers");
 
 1149        using namespace test::jtx;
 
 1152        auto const alice = 
Account(
"alice");
 
 1157            for (
int i = 0; i < n; ++i)
 
 1164        Env env{*
this, features};
 
 1165        env.fund(
XRP(10000), alice);
 
 1166        for (
auto const& a : bobs)
 
 1168            env.fund(
XRP(10000), a);
 
 1174            auto const settleDelay = 3600s;
 
 1175            auto const channelFunds = 
XRP(1);
 
 1176            for (
auto const& b : bobs)
 
 1178                env(
create(alice, b, channelFunds, settleDelay, alice.pk()));
 
 1189            jvc[jss::account] = src.human();
 
 1191                jvc[jss::destination_account] = dst->human();
 
 1193                jvc[jss::limit] = *limit;
 
 1195                jvc[jss::marker] = marker;
 
 1198                "json", 
"account_channels", 
to_string(jvc))[jss::result];
 
 1203            auto const r = testLimit(env, alice);
 
 1204            BEAST_EXPECT(r.isMember(jss::channels));
 
 1205            BEAST_EXPECT(r[jss::channels].size() == bobs.size());
 
 1210            for (
auto const& a : bobs)
 
 1215        for (
int limit = 1; limit < bobs.size() + 1; ++limit)
 
 1217            auto leftToFind = bobsB58;
 
 1218            auto const numFull = bobs.
size() / limit;
 
 1219            auto const numNonFull = bobs.size() % limit ? 1 : 0;
 
 1223            auto const testIt = [&](
bool expectMarker, 
int expectedBatchSize) {
 
 1224                auto const r = testLimit(env, alice, limit, marker);
 
 1225                BEAST_EXPECT(!expectMarker || r.isMember(jss::marker));
 
 1226                if (r.isMember(jss::marker))
 
 1227                    marker = r[jss::marker];
 
 1228                BEAST_EXPECT(r[jss::channels].size() == expectedBatchSize);
 
 1229                auto const c = r[jss::channels];
 
 1230                auto const s = r[jss::channels].size();
 
 1231                for (
int j = 0; j < s; ++j)
 
 1234                        c[j][jss::destination_account].asString();
 
 1235                    BEAST_EXPECT(leftToFind.count(dstAcc));
 
 1236                    leftToFind.erase(dstAcc);
 
 1240            for (
int i = 0; i < numFull; ++i)
 
 1242                bool const expectMarker = (numNonFull != 0 || i < numFull - 1);
 
 1243                testIt(expectMarker, limit);
 
 1248                testIt(
false, bobs.size() % limit);
 
 1250            BEAST_EXPECT(leftToFind.empty());
 
 1255            auto const r = testLimit(env, alice, 0);
 
 1256            BEAST_EXPECT(r.isMember(jss::error_message));
 
 
 1265        testcase(
"Account channels RPC owner only");
 
 1267        using namespace test::jtx;
 
 1270        auto const alice = 
Account(
"alice");
 
 1271        auto const bob = 
Account(
"bob");
 
 1272        Env env{*
this, features};
 
 1273        env.fund(
XRP(10000), alice, bob);
 
 1278        auto const settleDelay = 3600s;
 
 1279        auto const channelFunds = 
XRP(1000);
 
 1280        env(
create(alice, bob, channelFunds, settleDelay, alice.pk()));
 
 1281        env(
create(bob, alice, channelFunds, settleDelay, bob.pk()));
 
 1283        auto const r = [&] {
 
 1285            jvc[jss::account] = alice.human();
 
 1288                "json", 
"account_channels", 
to_string(jvc))[jss::result];
 
 1290        BEAST_EXPECT(r.isMember(jss::channels));
 
 1291        BEAST_EXPECT(r[jss::channels].size() == 1);
 
 1293            r[jss::channels][0u][jss::destination_account].asString() ==
 
 
 1300        using namespace jtx;
 
 1303        Env env{*
this, features};
 
 1304        auto const alice = 
Account(
"alice");
 
 1305        auto const bob = 
Account(
"bob");
 
 1307        env.fund(
XRP(10000), alice, bob, charlie);
 
 1308        auto const pk = alice.pk();
 
 1309        auto const settleDelay = 3600s;
 
 1310        auto const channelFunds = 
XRP(1000);
 
 1312        env(
create(alice, bob, channelFunds, settleDelay, pk));
 
 1316        args[jss::channel_id] = chan1Str;
 
 1317        args[jss::key_type] = 
"ed255191";
 
 1318        args[jss::seed] = 
"snHq1rzQoN2qiUkC3XF5RyxBzUtN";
 
 1319        args[jss::amount] = 51110000;
 
 1325            args[jss::api_version] = apiVersion;
 
 1326            auto const rs = env.rpc(
 
 1328                "channel_authorize",
 
 1329                args.toStyledString())[jss::result];
 
 1330            auto const error = apiVersion < 2u ? 
"invalidParams" : 
"badKeyType";
 
 1331            BEAST_EXPECT(rs[jss::error] == error);
 
 
 1338        testcase(
"PayChan Auth/Verify RPC");
 
 1339        using namespace jtx;
 
 1341        Env env{*
this, features};
 
 1342        auto const alice = 
Account(
"alice");
 
 1343        auto const bob = 
Account(
"bob");
 
 1345        env.fund(
XRP(10000), alice, bob, charlie);
 
 1346        auto const pk = alice.pk();
 
 1347        auto const settleDelay = 3600s;
 
 1348        auto const channelFunds = 
XRP(1000);
 
 1350        env(
create(alice, bob, channelFunds, settleDelay, pk));
 
 1355                env.rpc(
"account_channels", alice.human(), bob.human());
 
 1356            BEAST_EXPECT(r[jss::result][jss::channels].size() == 1);
 
 1358                r[jss::result][jss::channels][0u][jss::channel_id] == chan1Str);
 
 1359            BEAST_EXPECT(r[jss::result][jss::validated]);
 
 1361                r[jss::result][jss::channels][0u][jss::public_key].asString();
 
 1364            auto const r = env.rpc(
"account_channels", alice.human());
 
 1365            BEAST_EXPECT(r[jss::result][jss::channels].size() == 1);
 
 1367                r[jss::result][jss::channels][0u][jss::channel_id] == chan1Str);
 
 1368            BEAST_EXPECT(r[jss::result][jss::validated]);
 
 1370                r[jss::result][jss::channels][0u][jss::public_key].asString();
 
 1374                env.rpc(
"account_channels", bob.human(), alice.human());
 
 1375            BEAST_EXPECT(r[jss::result][jss::channels].size() == 0);
 
 1376            BEAST_EXPECT(r[jss::result][jss::validated]);
 
 1379        env(
create(alice, bob, channelFunds, settleDelay, pk));
 
 1383                env.rpc(
"account_channels", alice.human(), bob.human());
 
 1384            BEAST_EXPECT(r[jss::result][jss::channels].size() == 2);
 
 1385            BEAST_EXPECT(r[jss::result][jss::validated]);
 
 1386            BEAST_EXPECT(chan1Str != chan2Str);
 
 1387            for (
auto const& c : {chan1Str, chan2Str})
 
 1389                    r[jss::result][jss::channels][0u][jss::channel_id] == c ||
 
 1390                    r[jss::result][jss::channels][1u][jss::channel_id] == c);
 
 1398                s += 
"0123456789ABCDEF"[((
slice[i] & 0xf0) >> 4)];
 
 1399                s += 
"0123456789ABCDEF"[((
slice[i] & 0x0f) >> 0)];
 
 1407                env.rpc(
"channel_authorize", 
"alice", chan1Str, 
"1000");
 
 1408            auto const sig = rs[jss::result][jss::signature].asString();
 
 1409            BEAST_EXPECT(!
sig.empty());
 
 1411                auto const rv = env.rpc(
 
 1412                    "channel_verify", chan1PkStr, chan1Str, 
"1000", 
sig);
 
 1413                BEAST_EXPECT(rv[jss::result][jss::signature_verified].asBool());
 
 1420                    env.rpc(
"channel_verify", pkAsHex, chan1Str, 
"1000", 
sig);
 
 1421                BEAST_EXPECT(rv[jss::result][jss::signature_verified].asBool());
 
 1427                    env.rpc(
"channel_verify", pkAsHex, chan1Str, 
"1000x", 
sig);
 
 1428                BEAST_EXPECT(rv[jss::error] == 
"channelAmtMalformed");
 
 1429                rv = env.rpc(
"channel_verify", pkAsHex, chan1Str, 
"1000 ", 
sig);
 
 1430                BEAST_EXPECT(rv[jss::error] == 
"channelAmtMalformed");
 
 1431                rv = env.rpc(
"channel_verify", pkAsHex, chan1Str, 
"x1000", 
sig);
 
 1432                BEAST_EXPECT(rv[jss::error] == 
"channelAmtMalformed");
 
 1433                rv = env.rpc(
"channel_verify", pkAsHex, chan1Str, 
"x", 
sig);
 
 1434                BEAST_EXPECT(rv[jss::error] == 
"channelAmtMalformed");
 
 1435                rv = env.rpc(
"channel_verify", pkAsHex, chan1Str, 
" ", 
sig);
 
 1436                BEAST_EXPECT(rv[jss::error] == 
"channelAmtMalformed");
 
 1438                    "channel_verify", pkAsHex, chan1Str, 
"1000 1000", 
sig);
 
 1439                BEAST_EXPECT(rv[jss::error] == 
"channelAmtMalformed");
 
 1440                rv = env.rpc(
"channel_verify", pkAsHex, chan1Str, 
"1,000", 
sig);
 
 1441                BEAST_EXPECT(rv[jss::error] == 
"channelAmtMalformed");
 
 1442                rv = env.rpc(
"channel_verify", pkAsHex, chan1Str, 
" 1000", 
sig);
 
 1443                BEAST_EXPECT(rv[jss::error] == 
"channelAmtMalformed");
 
 1444                rv = env.rpc(
"channel_verify", pkAsHex, chan1Str, 
"", 
sig);
 
 1445                BEAST_EXPECT(rv[jss::error] == 
"channelAmtMalformed");
 
 1450                auto chan1StrBad = chan1Str;
 
 1451                chan1StrBad.pop_back();
 
 1453                    "channel_verify", pkAsHex, chan1StrBad, 
"1000", 
sig);
 
 1454                BEAST_EXPECT(rv[jss::error] == 
"channelMalformed");
 
 1455                rv = env.rpc(
"channel_authorize", 
"alice", chan1StrBad, 
"1000");
 
 1456                BEAST_EXPECT(rv[jss::error] == 
"channelMalformed");
 
 1458                chan1StrBad = chan1Str;
 
 1459                chan1StrBad.push_back(
'0');
 
 1461                    "channel_verify", pkAsHex, chan1StrBad, 
"1000", 
sig);
 
 1462                BEAST_EXPECT(rv[jss::error] == 
"channelMalformed");
 
 1463                rv = env.rpc(
"channel_authorize", 
"alice", chan1StrBad, 
"1000");
 
 1464                BEAST_EXPECT(rv[jss::error] == 
"channelMalformed");
 
 1466                chan1StrBad = chan1Str;
 
 1467                chan1StrBad.back() = 
'x';
 
 1469                    "channel_verify", pkAsHex, chan1StrBad, 
"1000", 
sig);
 
 1470                BEAST_EXPECT(rv[jss::error] == 
"channelMalformed");
 
 1471                rv = env.rpc(
"channel_authorize", 
"alice", chan1StrBad, 
"1000");
 
 1472                BEAST_EXPECT(rv[jss::error] == 
"channelMalformed");
 
 1476                auto illFormedPk = chan1PkStr.
substr(0, chan1PkStr.
size() - 1);
 
 1477                auto const rv = env.rpc(
 
 1478                    "channel_verify", illFormedPk, chan1Str, 
"1000", 
sig);
 
 1480                    !rv[jss::result][jss::signature_verified].asBool());
 
 1485                auto illFormedPk = pkAsHex.substr(0, chan1PkStr.
size() - 1);
 
 1486                auto const rv = env.rpc(
 
 1487                    "channel_verify", illFormedPk, chan1Str, 
"1000", 
sig);
 
 1489                    !rv[jss::result][jss::signature_verified].asBool());
 
 1495                env.rpc(
"channel_authorize", 
"alice", chan2Str, 
"1000");
 
 1496            auto const sig = rs[jss::result][jss::signature].asString();
 
 1497            BEAST_EXPECT(!
sig.empty());
 
 1499                auto const rv = env.rpc(
 
 1500                    "channel_verify", chan1PkStr, chan1Str, 
"1000", 
sig);
 
 1502                    !rv[jss::result][jss::signature_verified].asBool());
 
 1508                    env.rpc(
"channel_verify", pkAsHex, chan1Str, 
"1000", 
sig);
 
 1510                    !rv[jss::result][jss::signature_verified].asBool());
 
 1518                charlie, alice, channelFunds, settleDelay, charlie.pk()));
 
 1524                    env.rpc(
"account_channels", charlie.human(), alice.human());
 
 1525                BEAST_EXPECT(r[jss::result][jss::channels].size() == 1);
 
 1527                    r[jss::result][jss::channels][0u][jss::channel_id] == chan);
 
 1528                BEAST_EXPECT(r[jss::result][jss::validated]);
 
 1529                cpk = r[jss::result][jss::channels][0u][jss::public_key]
 
 1535                env.rpc(
"channel_authorize", 
"charlie", chan, 
"1000");
 
 1536            auto const sig = rs[jss::result][jss::signature].asString();
 
 1537            BEAST_EXPECT(!
sig.empty());
 
 1540                    env.rpc(
"channel_verify", cpk, chan, 
"1000", 
sig);
 
 1542                    !rv[jss::result][jss::signature_verified].asBool());
 
 1547                env.rpc(
"channel_authorize", 
"charlie", 
"nyx", chan, 
"1000");
 
 1548            BEAST_EXPECT(rs1[jss::error] == 
"badKeyType");
 
 1552            auto const rs2 = env.rpc(
 
 1553                "channel_authorize", 
"charlie", 
"secp256k1", chan, 
"1000");
 
 1554            auto const sig2 = rs2[jss::result][jss::signature].asString();
 
 1555            BEAST_EXPECT(!sig2.empty());
 
 1558                    env.rpc(
"channel_verify", cpk, chan, 
"1000", sig2);
 
 1560                    !rv[jss::result][jss::signature_verified].asBool());
 
 1564            auto const rs3 = env.rpc(
 
 1565                "channel_authorize", 
"charlie", 
"ed25519", chan, 
"1000");
 
 1566            auto const sig3 = rs3[jss::result][jss::signature].asString();
 
 1567            BEAST_EXPECT(!sig3.empty());
 
 1570                    env.rpc(
"channel_verify", cpk, chan, 
"1000", sig3);
 
 1571                BEAST_EXPECT(rv[jss::result][jss::signature_verified].asBool());
 
 1577            auto rs = env.rpc(
"channel_authorize", 
"alice", chan1Str, 
"1000x");
 
 1578            BEAST_EXPECT(rs[jss::error] == 
"channelAmtMalformed");
 
 1579            rs = env.rpc(
"channel_authorize", 
"alice", chan1Str, 
"x1000");
 
 1580            BEAST_EXPECT(rs[jss::error] == 
"channelAmtMalformed");
 
 1581            rs = env.rpc(
"channel_authorize", 
"alice", chan1Str, 
"x");
 
 1582            BEAST_EXPECT(rs[jss::error] == 
"channelAmtMalformed");
 
 1586                args[jss::amount] = 
"2000";
 
 1587                args[jss::key_type] = 
"secp256k1";
 
 1588                args[jss::passphrase] = 
"passphrase_can_be_anything";
 
 1591                    "channel_authorize",
 
 1592                    args.toStyledString())[jss::result];
 
 1593                BEAST_EXPECT(rs[jss::error] == 
"invalidParams");
 
 1598                args[jss::channel_id] = chan1Str;
 
 1599                args[jss::key_type] = 
"secp256k1";
 
 1600                args[jss::passphrase] = 
"passphrase_can_be_anything";
 
 1603                    "channel_authorize",
 
 1604                    args.toStyledString())[jss::result];
 
 1605                BEAST_EXPECT(rs[jss::error] == 
"invalidParams");
 
 1610                args[jss::amount] = 
"2000";
 
 1611                args[jss::channel_id] = chan1Str;
 
 1612                args[jss::passphrase] = 
"passphrase_can_be_anything";
 
 1615                    "channel_authorize",
 
 1616                    args.toStyledString())[jss::result];
 
 1617                BEAST_EXPECT(rs[jss::error] == 
"invalidParams");
 
 1622                args[jss::amount] = 
"2000";
 
 1623                args[jss::channel_id] = chan1Str;
 
 1624                args[jss::key_type] = 
"secp256k1";
 
 1625                args[jss::passphrase] = 
"passphrase_can_be_anything";
 
 1626                args[jss::seed] = 
"seed can be anything";
 
 1629                    "channel_authorize",
 
 1630                    args.toStyledString())[jss::result];
 
 1631                BEAST_EXPECT(rs[jss::error] == 
"invalidParams");
 
 1636                args[jss::amount] = 
"2000";
 
 1637                args[jss::channel_id] = chan1Str + 
"1";
 
 1638                args[jss::key_type] = 
"secp256k1";
 
 1639                args[jss::passphrase] = 
"passphrase_can_be_anything";
 
 1642                    "channel_authorize",
 
 1643                    args.toStyledString())[jss::result];
 
 1644                BEAST_EXPECT(rs[jss::error] == 
"channelMalformed");
 
 1649                args[jss::amount] = 2000;
 
 1650                args[jss::channel_id] = chan1Str;
 
 1651                args[jss::key_type] = 
"secp256k1";
 
 1652                args[jss::passphrase] = 
"passphrase_can_be_anything";
 
 1655                    "channel_authorize",
 
 1656                    args.toStyledString())[jss::result];
 
 1657                BEAST_EXPECT(rs[jss::error] == 
"channelAmtMalformed");
 
 1662                args[jss::amount] = 
"TwoThousand";
 
 1663                args[jss::channel_id] = chan1Str;
 
 1664                args[jss::key_type] = 
"secp256k1";
 
 1665                args[jss::passphrase] = 
"passphrase_can_be_anything";
 
 1668                    "channel_authorize",
 
 1669                    args.toStyledString())[jss::result];
 
 1670                BEAST_EXPECT(rs[jss::error] == 
"channelAmtMalformed");
 
 
 1679        using namespace jtx;
 
 1681        Env env{*
this, features};
 
 1682        auto const alice = 
Account(
"alice");
 
 1683        auto const bob = 
Account(
"bob");
 
 1684        auto const carol = 
Account(
"carol");
 
 1685        auto const dan = 
Account(
"dan");
 
 1686        env.fund(
XRP(10000), alice, bob, carol, dan);
 
 1687        auto const pk = alice.pk();
 
 1688        auto const settleDelay = 3600s;
 
 1689        auto const channelFunds = 
XRP(1000);
 
 1695            env(
create(alice, bob, channelFunds, settleDelay, pk));
 
 1697                env.rpc(
"account_channels", alice.human(), bob.human());
 
 1698            BEAST_EXPECT(r[jss::result][jss::channels].size() == 1);
 
 1700                r[jss::result][jss::channels][0u][jss::channel_id] == chan);
 
 1701            BEAST_EXPECT(!r[jss::result][jss::channels][0u].isMember(
 
 1702                jss::destination_tag));
 
 1716                env.rpc(
"account_channels", alice.human(), carol.human());
 
 1717            BEAST_EXPECT(r[jss::result][jss::channels].size() == 1);
 
 1719                r[jss::result][jss::channels][0u][jss::channel_id] == chan);
 
 1721                r[jss::result][jss::channels][0u][jss::destination_tag] ==
 
 
 1730        using namespace jtx;
 
 1732        Env env{*
this, features};
 
 1733        auto const alice = 
Account(
"alice");
 
 1734        auto const bob = 
Account(
"bob");
 
 1735        auto USDA = alice[
"USD"];
 
 1736        env.fund(
XRP(10000), alice, bob);
 
 1737        auto const pk = alice.pk();
 
 1738        auto const settleDelay = 100s;
 
 1740        auto const chan = 
channel(alice, bob, env.seq(alice));
 
 1741        auto jv = 
create(alice, bob, 
XRP(1000), settleDelay, pk);
 
 1742        auto const pkHex = 
strHex(pk.slice());
 
 1743        jv[
"PublicKey"] = pkHex.substr(2, pkHex.size() - 2);
 
 1745        jv[
"PublicKey"] = pkHex.substr(0, pkHex.size() - 2);
 
 1747        auto badPrefix = pkHex;
 
 1750        jv[
"PublicKey"] = badPrefix;
 
 1753        jv[
"PublicKey"] = pkHex;
 
 1756        auto const authAmt = 
XRP(100);
 
 1765        jv[
"PublicKey"] = pkHex.substr(2, pkHex.size() - 2);
 
 1767        jv[
"PublicKey"] = pkHex.substr(0, pkHex.size() - 2);
 
 1772        jv[
"PublicKey"] = badPrefix;
 
 1776        jv.removeMember(
"PublicKey");
 
 1780            auto const txn = R
"*( 
 1783        "channel_id":"5DB01B7FFED6B67E6B0414DED11E051D2EE2B7619CE0EAA6286D67A3A4D5BDB3", 
 1785        "304402204EF0AFB78AC23ED1C472E74F4299C0C21F1B21D07EFC0A3838A420F76D783A400220154FB11B6F54320666E4C36CA7F686C16A3A0456800BBC43746F34AF50290064", 
 1787        "aKijDDiC2q2gXjMpM7i4BUS6cmixgsEe18e7CjsUxwihKfuoFgS5", 
 1791            auto const r = env.rpc(
"json", 
"channel_verify", txn);
 
 1792            BEAST_EXPECT(r[
"result"][
"error"] == 
"publicMalformed");
 
 
 1801        using namespace jtx;
 
 1804        auto const alice = 
Account(
"alice");
 
 1805        auto const bob = 
Account(
"bob");
 
 1806        auto const settleDelay = 100s;
 
 1807        auto const pk = alice.pk();
 
 1809        auto inOwnerDir = [](
ReadView const& view,
 
 1813            return std::find(ownerDir.begin(), ownerDir.end(), chan) !=
 
 1817        auto ownerDirCount = [](
ReadView const& view,
 
 1826            Env env(*
this, features - fixPayChanRecipientOwnerDir);
 
 1827            env.
fund(
XRP(10000), alice, bob);
 
 1828            env(
create(alice, bob, 
XRP(1000), settleDelay, pk));
 
 1830            auto const [chan, chanSle] =
 
 1832            BEAST_EXPECT(inOwnerDir(*env.
current(), alice, chanSle));
 
 1833            BEAST_EXPECT(ownerDirCount(*env.
current(), alice) == 1);
 
 1834            BEAST_EXPECT(!inOwnerDir(*env.
current(), bob, chanSle));
 
 1835            BEAST_EXPECT(ownerDirCount(*env.
current(), bob) == 0);
 
 1836            if (features[fixIncludeKeyletFields])
 
 1838                BEAST_EXPECT((*chanSle)[sfSequence] == env.
seq(alice) - 1);
 
 1842                BEAST_EXPECT(!chanSle->isFieldPresent(sfSequence));
 
 1847            BEAST_EXPECT(!inOwnerDir(*env.
current(), alice, chanSle));
 
 1848            BEAST_EXPECT(ownerDirCount(*env.
current(), alice) == 0);
 
 1849            BEAST_EXPECT(!inOwnerDir(*env.
current(), bob, chanSle));
 
 1850            BEAST_EXPECT(ownerDirCount(*env.
current(), bob) == 0);
 
 1855            Env env{*
this, features};
 
 1856            env.fund(
XRP(10000), alice, bob);
 
 1857            env(
create(alice, bob, 
XRP(1000), settleDelay, pk));
 
 1859            auto const [chan, chanSle] =
 
 1861            BEAST_EXPECT(inOwnerDir(*env.current(), alice, chanSle));
 
 1862            BEAST_EXPECT(ownerDirCount(*env.current(), alice) == 1);
 
 1863            BEAST_EXPECT(inOwnerDir(*env.current(), bob, chanSle));
 
 1864            BEAST_EXPECT(ownerDirCount(*env.current(), bob) == 1);
 
 1868            BEAST_EXPECT(!inOwnerDir(*env.current(), alice, chanSle));
 
 1869            BEAST_EXPECT(ownerDirCount(*env.current(), alice) == 0);
 
 1870            BEAST_EXPECT(!inOwnerDir(*env.current(), bob, chanSle));
 
 1871            BEAST_EXPECT(ownerDirCount(*env.current(), bob) == 0);
 
 1877            Env env(*
this, features - fixPayChanRecipientOwnerDir);
 
 1878            env.
fund(
XRP(10000), alice, bob);
 
 1880            env(
create(alice, bob, 
XRP(1000), settleDelay, pk));
 
 1882            auto const [chan, chanSle] =
 
 1884            BEAST_EXPECT(inOwnerDir(*env.
current(), alice, chanSle));
 
 1885            BEAST_EXPECT(ownerDirCount(*env.
current(), alice) == 1);
 
 1886            BEAST_EXPECT(!inOwnerDir(*env.
current(), bob, chanSle));
 
 1887            BEAST_EXPECT(ownerDirCount(*env.
current(), bob) == 0);
 
 1891                env.
current()->rules().enabled(fixPayChanRecipientOwnerDir));
 
 1896            BEAST_EXPECT(inOwnerDir(*env.
current(), alice, chanSle));
 
 1897            BEAST_EXPECT(!inOwnerDir(*env.
current(), bob, chanSle));
 
 1898            BEAST_EXPECT(ownerDirCount(*env.
current(), bob) == 0);
 
 1903            BEAST_EXPECT(!inOwnerDir(*env.
current(), alice, chanSle));
 
 1904            BEAST_EXPECT(ownerDirCount(*env.
current(), alice) == 0);
 
 1905            BEAST_EXPECT(!inOwnerDir(*env.
current(), bob, chanSle));
 
 1906            BEAST_EXPECT(ownerDirCount(*env.
current(), bob) == 0);
 
 
 1914        using namespace test::jtx;
 
 1916        auto rmAccount = [
this](
 
 1923            for (
auto minRmSeq = env.
seq(toRm) + 257;
 
 1924                 env.
current()->seq() < minRmSeq;
 
 1938        auto const alice = 
Account(
"alice");
 
 1939        auto const bob = 
Account(
"bob");
 
 1940        auto const carol = 
Account(
"carol");
 
 1942        for (
bool const withOwnerDirFix : {
false, 
true})
 
 1944            auto const amd = withOwnerDirFix
 
 1946                : features - fixPayChanRecipientOwnerDir;
 
 1947            Env env{*
this, amd};
 
 1948            env.
fund(
XRP(10000), alice, bob, carol);
 
 1952            auto const pk = alice.pk();
 
 1953            auto const settleDelay = 100s;
 
 1954            auto const chan = 
channel(alice, bob, env.
seq(alice));
 
 1955            env(
create(alice, bob, 
XRP(1000), settleDelay, pk));
 
 1968            auto const feeDrops = env.
current()->fees().base;
 
 1971            BEAST_EXPECT(chanBal == 
XRP(0));
 
 1972            BEAST_EXPECT(chanAmt == 
XRP(1000));
 
 1974            auto preBob = env.
balance(bob);
 
 1975            auto const delta = 
XRP(50);
 
 1976            auto reqBal = chanBal + delta;
 
 1977            auto authAmt = reqBal + 
XRP(100);
 
 1978            assert(reqBal <= chanAmt);
 
 1981            if (withOwnerDirFix)
 
 1983                env(
claim(alice, chan, reqBal, authAmt));
 
 1987                BEAST_EXPECT(env.
balance(bob) == preBob + delta);
 
 1992                auto const preAlice = env.
balance(alice);
 
 1997                BEAST_EXPECT(env.
balance(bob) == preBob);
 
 1998                BEAST_EXPECT(env.
balance(alice) == preAlice - feeDrops);
 
 2002            if (withOwnerDirFix)
 
 2004                auto const preAlice = env.
balance(alice);
 
 2005                env(
fund(alice, chan, 
XRP(1000)));
 
 2008                    env.
balance(alice) == preAlice - 
XRP(1000) - feeDrops);
 
 2011                chanAmt = chanAmt + 
XRP(1000);
 
 2015                auto const preAlice = env.
balance(alice);
 
 2018                BEAST_EXPECT(env.
balance(alice) == preAlice - feeDrops);
 
 2028                auto const closeTime = env.
current()->info().parentCloseTime;
 
 2029                auto const minExpiration = closeTime + settleDelay;
 
 2030                env.
close(minExpiration);
 
 2038            Env env{*
this, features - fixPayChanRecipientOwnerDir};
 
 2039            env.
fund(
XRP(10000), alice, bob, carol);
 
 2043            auto const pk = alice.pk();
 
 2044            auto const settleDelay = 100s;
 
 2045            auto const chan = 
channel(alice, bob, env.
seq(alice));
 
 2046            env(
create(alice, bob, 
XRP(1000), settleDelay, pk));
 
 2052            rmAccount(env, bob, carol);
 
 2055            auto const feeDrops = env.
current()->fees().base;
 
 2058            BEAST_EXPECT(chanBal == 
XRP(0));
 
 2059            BEAST_EXPECT(chanAmt == 
XRP(1000));
 
 2060            auto preBob = env.
balance(bob);
 
 2061            auto const delta = 
XRP(50);
 
 2062            auto reqBal = chanBal + delta;
 
 2063            auto authAmt = reqBal + 
XRP(100);
 
 2064            assert(reqBal <= chanAmt);
 
 2068                auto const preAlice = env.
balance(alice);
 
 2073                BEAST_EXPECT(env.
balance(bob) == preBob);
 
 2074                BEAST_EXPECT(env.
balance(alice) == preAlice - feeDrops);
 
 2079                auto const preAlice = env.
balance(alice);
 
 2082                BEAST_EXPECT(env.
balance(alice) == preAlice - feeDrops);
 
 2087            env(
pay(alice, bob, 
XRP(20)));
 
 2094                reqBal = chanBal + delta;
 
 2095                authAmt = reqBal + 
XRP(100);
 
 2096                env(
claim(alice, chan, reqBal, authAmt));
 
 2099                BEAST_EXPECT(env.
balance(bob) == preBob + delta);
 
 2106                reqBal = chanBal + delta;
 
 2107                authAmt = reqBal + 
XRP(100);
 
 2110                env(
claim(bob, chan, reqBal, authAmt, 
Slice(
sig), alice.pk()));
 
 2113                BEAST_EXPECT(env.
balance(bob) == preBob + delta - feeDrops);
 
 2119                auto const preAlice = env.
balance(alice);
 
 2120                env(
fund(alice, chan, 
XRP(1000)));
 
 2122                    env.
balance(alice) == preAlice - 
XRP(1000) - feeDrops);
 
 2125                chanAmt = chanAmt + 
XRP(1000);
 
 2134                auto const closeTime = env.
current()->info().parentCloseTime;
 
 2135                auto const minExpiration = closeTime + settleDelay;
 
 2136                env.
close(minExpiration);
 
 
 2147        using namespace jtx;
 
 2149        Env env{*
this, features};
 
 2150        auto const alice = 
Account(
"alice");
 
 2151        auto const bob = 
Account(
"bob");
 
 2152        auto USDA = alice[
"USD"];
 
 2153        env.fund(
XRP(10000), alice, bob);
 
 2166        auto const pk = alice.pk();
 
 2167        auto const settleDelay = 100s;
 
 2168        auto const chan = 
channel(alice, bob, aliceTicketSeq);
 
 2170        env(
create(alice, bob, 
XRP(1000), settleDelay, pk),
 
 2173        env.require(
tickets(alice, env.seq(alice) - aliceTicketSeq));
 
 2174        BEAST_EXPECT(env.seq(alice) == aliceSeq);
 
 2180            auto const preAlice = env.balance(alice);
 
 2183            env.require(
tickets(alice, env.seq(alice) - aliceTicketSeq));
 
 2184            BEAST_EXPECT(env.seq(alice) == aliceSeq);
 
 2186            auto const feeDrops = env.current()->fees().base;
 
 2187            BEAST_EXPECT(env.balance(alice) == preAlice - 
XRP(1000) - feeDrops);
 
 2192        BEAST_EXPECT(chanBal == 
XRP(0));
 
 2193        BEAST_EXPECT(chanAmt == 
XRP(2000));
 
 2197            auto const preBob = env.balance(bob);
 
 2198            auto const delta = 
XRP(500);
 
 2199            auto const reqBal = chanBal + delta;
 
 2200            auto const authAmt = reqBal + 
XRP(100);
 
 2201            assert(reqBal <= chanAmt);
 
 2202            env(
claim(alice, chan, reqBal, authAmt),
 
 2205            env.require(
tickets(alice, env.seq(alice) - aliceTicketSeq));
 
 2206            BEAST_EXPECT(env.seq(alice) == aliceSeq);
 
 2209            BEAST_EXPECT(
channelAmount(*env.current(), chan) == chanAmt);
 
 2210            BEAST_EXPECT(env.balance(bob) == preBob + delta);
 
 2215            auto preBob = env.balance(bob);
 
 2216            auto const delta = 
XRP(500);
 
 2217            auto const reqBal = chanBal + delta;
 
 2218            auto const authAmt = reqBal + 
XRP(100);
 
 2219            assert(reqBal <= chanAmt);
 
 2222            env(
claim(bob, chan, reqBal, authAmt, 
Slice(
sig), alice.pk()),
 
 2225            env.require(
tickets(bob, env.seq(bob) - bobTicketSeq));
 
 2226            BEAST_EXPECT(env.seq(bob) == bobSeq);
 
 2229            BEAST_EXPECT(
channelAmount(*env.current(), chan) == chanAmt);
 
 2230            auto const feeDrops = env.current()->fees().base;
 
 2231            BEAST_EXPECT(env.balance(bob) == preBob + delta - feeDrops);
 
 2235            preBob = env.balance(bob);
 
 2237            env(
claim(bob, chan, reqBal, authAmt, 
Slice(
sig), alice.pk()),
 
 2241            env.require(
tickets(bob, env.seq(bob) - bobTicketSeq));
 
 2242            BEAST_EXPECT(env.seq(bob) == bobSeq);
 
 2245            BEAST_EXPECT(
channelAmount(*env.current(), chan) == chanAmt);
 
 2246            BEAST_EXPECT(env.balance(bob) == preBob - feeDrops);
 
 2250            auto const preBob = env.balance(bob);
 
 2253            assert(reqAmt <= chanAmt);
 
 2258            env(
claim(bob, chan, reqAmt, authAmt, 
Slice(
sig), alice.pk()),
 
 2262            env.require(
tickets(bob, env.seq(bob) - bobTicketSeq));
 
 2263            BEAST_EXPECT(env.seq(bob) == bobSeq);
 
 2266            BEAST_EXPECT(
channelAmount(*env.current(), chan) == chanAmt);
 
 2267            BEAST_EXPECT(env.balance(bob) == preBob);
 
 2271        env(
fund(bob, chan, 
XRP(1000)),
 
 2275        env.require(
tickets(bob, env.seq(bob) - bobTicketSeq));
 
 2276        BEAST_EXPECT(env.seq(bob) == bobSeq);
 
 2279        BEAST_EXPECT(
channelAmount(*env.current(), chan) == chanAmt);
 
 2283            auto const preAlice = env.balance(alice);
 
 2284            auto const preBob = env.balance(bob);
 
 2285            env(
claim(bob, chan),
 
 2289            env.require(
tickets(bob, env.seq(bob) - bobTicketSeq));
 
 2290            BEAST_EXPECT(env.seq(bob) == bobSeq);
 
 2293            auto const feeDrops = env.current()->fees().base;
 
 2294            auto const delta = chanAmt - chanBal;
 
 2295            assert(delta > beast::zero);
 
 2296            BEAST_EXPECT(env.balance(alice) == preAlice + delta);
 
 2297            BEAST_EXPECT(env.balance(bob) == preBob - feeDrops);
 
 2299        env.require(
tickets(alice, env.seq(alice) - aliceTicketSeq));
 
 2300        BEAST_EXPECT(env.seq(alice) == aliceSeq);
 
 2301        env.require(
tickets(bob, env.seq(bob) - bobTicketSeq));
 
 2302        BEAST_EXPECT(env.seq(bob) == bobSeq);
 
 
 2335        using namespace test::jtx;
 
 
 
testcase_t testcase
Memberspace for declaring test cases.
 
Like std::vector<char> but better.
 
A class that simplifies iterating ledger directory pages.
 
virtual std::shared_ptr< SLE const > read(Keylet const &k) const =0
Return the state item associated with a key.
 
Slice slice() const noexcept
 
An immutable linear range of bytes.
 
Immutable cryptographic account descriptor.
 
PublicKey const & pk() const
Return the public key.
 
A transaction testing environment.
 
std::shared_ptr< ReadView const > closed()
Returns the last closed ledger.
 
std::uint32_t seq(Account const &account) const
Returns the next sequence number on account.
 
std::shared_ptr< OpenView const > current() const
Returns the current ledger.
 
bool close(NetClock::time_point closeTime, std::optional< std::chrono::milliseconds > consensusDelay=std::nullopt)
Close and advance the ledger.
 
void enableFeature(uint256 const feature)
 
Json::Value rpc(unsigned apiVersion, std::unordered_map< std::string, std::string > const &headers, std::string const &cmd, Args &&... args)
Execute an RPC command.
 
void fund(bool setDefaultRipple, STAmount const &amount, Account const &account)
 
PrettyAmount balance(Account const &account) const
Returns the XRP balance on an account.
 
Set the regular signature on a JTx.
 
Set the expected result code for a JTx The test will fail if the code doesn't match.
 
Set a ticket sequence on a JTx.
 
T emplace_back(T... args)
 
@ arrayValue
array value (ordered list)
 
@ objectValue
object value (collection of name/value pairs).
 
Keylet account(AccountID const &id) noexcept
AccountID root.
 
Keylet ownerDir(AccountID const &id) noexcept
The root page of an account's directory.
 
Keylet payChan(AccountID const &src, AccountID const &dst, std::uint32_t seq) noexcept
A PaymentChannel.
 
Json::Value create(jtx::Account const &subject, jtx::Account const &issuer, std::string_view credType)
 
Json::Value accept(jtx::Account const &subject, jtx::Account const &issuer, std::string_view credType)
 
Json::Value ledgerEntry(jtx::Env &env, jtx::Account const &subject, jtx::Account const &issuer, std::string_view credType)
 
Json::Value unauth(Account const &account, Account const &unauth)
Remove preauthorization for deposit.
 
Json::Value auth(Account const &account, Account const &auth)
Preauthorize for deposit.
 
Json::Value authCredentials(jtx::Account const &account, std::vector< AuthorizeCredentials > const &auth)
 
bool channelExists(ReadView const &view, uint256 const &chan)
 
Json::Value create(AccountID const &account, AccountID const &to, STAmount const &amount, NetClock::duration const &settleDelay, PublicKey const &pk, std::optional< NetClock::time_point > const &cancelAfter, std::optional< std::uint32_t > const &dstTag)
 
uint256 channel(AccountID const &account, AccountID const &dst, std::uint32_t seqProxyValue)
 
Json::Value claim(AccountID const &account, uint256 const &channel, std::optional< STAmount > const &balance, std::optional< STAmount > const &amount, std::optional< Slice > const &signature, std::optional< PublicKey > const &pk)
 
STAmount channelBalance(ReadView const &view, uint256 const &chan)
 
Json::Value create(Account const &account, std::uint32_t count)
Create one of more tickets.
 
Json::Value fclear(Account const &account, std::uint32_t off)
Remove account flag.
 
PrettyAmount drops(Integer i)
Returns an XRP PrettyAmount, which is trivially convertible to STAmount.
 
Json::Value fset(Account const &account, std::uint32_t on, std::uint32_t off=0)
Add and/or remove flag.
 
Json::Value pay(AccountID const &account, AccountID const &to, AnyAmount amount)
Create a payment.
 
void fund(jtx::Env &env, jtx::Account const &gw, std::vector< jtx::Account > const &accounts, std::vector< STAmount > const &amts, Fund how)
 
FeatureBitset testable_amendments()
 
void sign(Json::Value &jv, Account const &account, Json::Value &sigObject)
Sign automatically into a specific Json field of the jv object.
 
Json::Value acctdelete(Account const &account, Account const &dest)
Delete account.
 
owner_count< ltTICKET > tickets
Match the number of tickets on the account.
 
XRP_t const XRP
Converts to XRP Issue or STAmount.
 
Use hash_* containers for keys that do not need a cryptographically secure hashing algorithm.
 
constexpr std::uint32_t asfDepositAuth
 
constexpr std::uint32_t asfRequireDest
 
constexpr std::uint32_t tfRenew
 
static std::string sliceToHex(Slice const &slice)
 
@ lsfDisallowIncomingPayChan
 
void serializePayChanAuthorization(Serializer &msg, uint256 const &key, XRPAmount const &amt)
 
std::string strHex(FwdIt begin, FwdIt end)
 
void forAllApiVersions(Fn const &fn, Args &&... args)
 
bool isTesSuccess(TER x) noexcept
 
std::string to_string(base_uint< Bits, Tag > const &a)
 
constexpr std::uint32_t asfDisallowIncomingPayChan
 
constexpr std::uint32_t tfClose
 
TERSubset< CanCvtToTER > TER
 
constexpr std::uint32_t asfDisallowXRP
 
static std::pair< uint256, std::shared_ptr< SLE const > > channelKeyAndSle(ReadView const &view, jtx::Account const &account, jtx::Account const &dst)
 
void testSimple(FeatureBitset features)
 
FeatureBitset const disallowIncoming
 
void testMultiple(FeatureBitset features)
 
void testAccountChannelsRPC(FeatureBitset features)
 
void testUsingTickets(FeatureBitset features)
 
void run() override
Runs the suite.
 
void testSettleDelay(FeatureBitset features)
 
void testDisallowXRP(FeatureBitset features)
 
void testDepositAuth(FeatureBitset features)
 
static std::optional< std::int64_t > channelExpiration(ReadView const &view, uint256 const &chan)
 
void testAccountDelete(FeatureBitset features)
 
void testCloseDry(FeatureBitset features)
 
void testExpiration(FeatureBitset features)
 
void testMetaAndOwnership(FeatureBitset features)
 
void testDefaultAmount(FeatureBitset features)
 
void testAuthVerifyRPC(FeatureBitset features)
 
void testMalformedPK(FeatureBitset features)
 
void testCancelAfter(FeatureBitset features)
 
void testWithFeats(FeatureBitset features)
 
void testDisallowIncoming(FeatureBitset features)
 
void testAccountChannelsRPCMarkers(FeatureBitset features)
 
void testAccountChannelAuthorize(FeatureBitset features)
 
void testAccountChannelsRPCSenderOnly(FeatureBitset features)
 
void testDstTag(FeatureBitset features)
 
static STAmount channelAmount(ReadView const &view, uint256 const &chan)
 
void testDepositAuthCreds()
 
static Buffer signClaimAuth(PublicKey const &pk, SecretKey const &sk, uint256 const &channel, STAmount const &authAmt)
 
void testOptionalFields(FeatureBitset features)