mirror of
https://github.com/Xahau/xahaud.git
synced 2025-12-05 16:57:53 +00:00
add transfer rate
This commit is contained in:
@@ -295,11 +295,13 @@ EscrowCreate::doApply()
|
|||||||
|
|
||||||
// Create escrow in ledger. Note that we we use the value from the
|
// Create escrow in ledger. Note that we we use the value from the
|
||||||
// sequence or ticket. For more explanation see comments in SeqProxy.h.
|
// sequence or ticket. For more explanation see comments in SeqProxy.h.
|
||||||
|
auto xferRate = transferRate(view(), amount.getIssuer());
|
||||||
Keylet const escrowKeylet =
|
Keylet const escrowKeylet =
|
||||||
keylet::escrow(account, ctx_.tx.getSeqProxy().value());
|
keylet::escrow(account, ctx_.tx.getSeqProxy().value());
|
||||||
auto const slep = std::make_shared<SLE>(escrowKeylet);
|
auto const slep = std::make_shared<SLE>(escrowKeylet);
|
||||||
(*slep)[sfAmount] = ctx_.tx[sfAmount];
|
(*slep)[sfAmount] = ctx_.tx[sfAmount];
|
||||||
(*slep)[sfAccount] = account;
|
(*slep)[sfAccount] = account;
|
||||||
|
(*slep)[sfTransferRate] = xferRate.value;
|
||||||
(*slep)[~sfCondition] = ctx_.tx[~sfCondition];
|
(*slep)[~sfCondition] = ctx_.tx[~sfCondition];
|
||||||
(*slep)[~sfSourceTag] = ctx_.tx[~sfSourceTag];
|
(*slep)[~sfSourceTag] = ctx_.tx[~sfSourceTag];
|
||||||
(*slep)[sfDestination] = ctx_.tx[sfDestination];
|
(*slep)[sfDestination] = ctx_.tx[sfDestination];
|
||||||
@@ -560,6 +562,13 @@ EscrowFinish::doApply()
|
|||||||
if (!ctx_.view().rules().enabled(featurePaychanAndEscrowForTokens))
|
if (!ctx_.view().rules().enabled(featurePaychanAndEscrowForTokens))
|
||||||
return temDISABLED;
|
return temDISABLED;
|
||||||
|
|
||||||
|
Rate lockedRate = ripple::Rate(slep->getFieldU32(sfTransferRate));
|
||||||
|
auto issuerAccID = amount.getIssuer();
|
||||||
|
auto const xferRate = transferRate(view(), issuerAccID);
|
||||||
|
// update if issuer rate is less than locked rate
|
||||||
|
if (xferRate < lockedRate)
|
||||||
|
lockedRate = xferRate;
|
||||||
|
|
||||||
// perform a dry run of the transfer before we
|
// perform a dry run of the transfer before we
|
||||||
// change anything on-ledger
|
// change anything on-ledger
|
||||||
TER result = trustTransferLockedBalance(
|
TER result = trustTransferLockedBalance(
|
||||||
@@ -569,6 +578,7 @@ EscrowFinish::doApply()
|
|||||||
sled, // dst account
|
sled, // dst account
|
||||||
amount, // xfer amount
|
amount, // xfer amount
|
||||||
-1,
|
-1,
|
||||||
|
lockedRate,
|
||||||
j_,
|
j_,
|
||||||
DryRun // dry run
|
DryRun // dry run
|
||||||
);
|
);
|
||||||
@@ -607,6 +617,14 @@ EscrowFinish::doApply()
|
|||||||
(*sled)[sfBalance] = (*sled)[sfBalance] + (*slep)[sfAmount];
|
(*sled)[sfBalance] = (*sled)[sfBalance] + (*slep)[sfAmount];
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
// compute transfer fee, if any
|
||||||
|
Rate lockedRate = ripple::Rate(slep->getFieldU32(sfTransferRate));
|
||||||
|
auto issuerAccID = amount.getIssuer();
|
||||||
|
auto const xferRate = transferRate(view(), issuerAccID);
|
||||||
|
// update if issuer rate is less than locked rate
|
||||||
|
if (xferRate < lockedRate)
|
||||||
|
lockedRate = xferRate;
|
||||||
|
|
||||||
// all the significant complexity of checking the validity of this
|
// all the significant complexity of checking the validity of this
|
||||||
// transfer and ensuring the lines exist etc is hidden away in this
|
// transfer and ensuring the lines exist etc is hidden away in this
|
||||||
// function, all we need to do is call it and return if unsuccessful.
|
// function, all we need to do is call it and return if unsuccessful.
|
||||||
@@ -617,6 +635,7 @@ EscrowFinish::doApply()
|
|||||||
sled, // dst account
|
sled, // dst account
|
||||||
amount, // xfer amount
|
amount, // xfer amount
|
||||||
-1,
|
-1,
|
||||||
|
lockedRate,
|
||||||
j_,
|
j_,
|
||||||
WetRun // wet run;
|
WetRun // wet run;
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -335,6 +335,7 @@ PayChanCreate::doApply()
|
|||||||
|
|
||||||
STAmount const amount{ctx_.tx[sfAmount]};
|
STAmount const amount{ctx_.tx[sfAmount]};
|
||||||
bool isIssuer = amount.getIssuer() == account;
|
bool isIssuer = amount.getIssuer() == account;
|
||||||
|
auto xferRate = transferRate(view(), amount.getIssuer());
|
||||||
|
|
||||||
// Create PayChan in ledger.
|
// Create PayChan in ledger.
|
||||||
//
|
//
|
||||||
@@ -351,6 +352,7 @@ PayChanCreate::doApply()
|
|||||||
(*slep)[sfAccount] = account;
|
(*slep)[sfAccount] = account;
|
||||||
(*slep)[sfDestination] = dst;
|
(*slep)[sfDestination] = dst;
|
||||||
(*slep)[sfSettleDelay] = ctx_.tx[sfSettleDelay];
|
(*slep)[sfSettleDelay] = ctx_.tx[sfSettleDelay];
|
||||||
|
(*slep)[sfTransferRate] = xferRate.value;
|
||||||
(*slep)[sfPublicKey] = ctx_.tx[sfPublicKey];
|
(*slep)[sfPublicKey] = ctx_.tx[sfPublicKey];
|
||||||
(*slep)[~sfCancelAfter] = ctx_.tx[~sfCancelAfter];
|
(*slep)[~sfCancelAfter] = ctx_.tx[~sfCancelAfter];
|
||||||
(*slep)[~sfSourceTag] = ctx_.tx[~sfSourceTag];
|
(*slep)[~sfSourceTag] = ctx_.tx[~sfSourceTag];
|
||||||
@@ -468,6 +470,19 @@ PayChanFund::doApply()
|
|||||||
auto const txAccount = ctx_.tx[sfAccount];
|
auto const txAccount = ctx_.tx[sfAccount];
|
||||||
auto const expiration = (*slep)[~sfExpiration];
|
auto const expiration = (*slep)[~sfExpiration];
|
||||||
bool isIssuer = amount.getIssuer() == txAccount;
|
bool isIssuer = amount.getIssuer() == txAccount;
|
||||||
|
// auto const chanFunds = (*slep)[sfAmount];
|
||||||
|
|
||||||
|
// adjust transfer rate
|
||||||
|
Rate lockedRate = ripple::Rate(slep->getFieldU32(sfTransferRate));
|
||||||
|
auto issuerAccID = amount.getIssuer();
|
||||||
|
auto const xferRate = transferRate(view(), issuerAccID);
|
||||||
|
// update if issuer rate less than locked rate
|
||||||
|
if (xferRate < lockedRate)
|
||||||
|
(*slep)[sfTransferRate] = xferRate.value;
|
||||||
|
// throw if issuer rate greater than locked rate
|
||||||
|
if (xferRate > lockedRate)
|
||||||
|
return temBAD_TRANSFER_RATE;
|
||||||
|
|
||||||
// if this is a Fund operation on an IOU then perform a dry run here
|
// if this is a Fund operation on an IOU then perform a dry run here
|
||||||
if (!isXRP(amount) &&
|
if (!isXRP(amount) &&
|
||||||
ctx_.view().rules().enabled(featurePaychanAndEscrowForTokens))
|
ctx_.view().rules().enabled(featurePaychanAndEscrowForTokens))
|
||||||
@@ -727,6 +742,17 @@ PayChanClaim::doApply()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// compute transfer fee, if any
|
||||||
|
Rate lockedRate = ripple::Rate(slep->getFieldU32(sfTransferRate));
|
||||||
|
auto issuerAccID = chanFunds.getIssuer();
|
||||||
|
auto const xferRate = transferRate(view(), issuerAccID);
|
||||||
|
// update if issuer rate is less than locked rate
|
||||||
|
if (xferRate < lockedRate)
|
||||||
|
{
|
||||||
|
(*slep)[sfTransferRate] = xferRate.value;
|
||||||
|
lockedRate = xferRate;
|
||||||
|
}
|
||||||
|
|
||||||
(*slep)[sfBalance] = ctx_.tx[sfBalance];
|
(*slep)[sfBalance] = ctx_.tx[sfBalance];
|
||||||
STAmount const reqDelta = reqBalance - chanBalance;
|
STAmount const reqDelta = reqBalance - chanBalance;
|
||||||
assert(reqDelta >= beast::zero);
|
assert(reqDelta >= beast::zero);
|
||||||
@@ -748,6 +774,7 @@ PayChanClaim::doApply()
|
|||||||
sled,
|
sled,
|
||||||
reqDelta,
|
reqDelta,
|
||||||
0,
|
0,
|
||||||
|
lockedRate,
|
||||||
ctx_.journal,
|
ctx_.journal,
|
||||||
WetRun);
|
WetRun);
|
||||||
|
|
||||||
|
|||||||
@@ -490,7 +490,6 @@ trustAdjustLockedBalance(
|
|||||||
|
|
||||||
// dry runs are explicit in code, but really the view type determines
|
// dry runs are explicit in code, but really the view type determines
|
||||||
// what occurs here, so this combination is invalid.
|
// what occurs here, so this combination is invalid.
|
||||||
|
|
||||||
static_assert(!(std::is_same<V, ReadView const>::value && !dryRun));
|
static_assert(!(std::is_same<V, ReadView const>::value && !dryRun));
|
||||||
|
|
||||||
if (!view.rules().enabled(featurePaychanAndEscrowForTokens))
|
if (!view.rules().enabled(featurePaychanAndEscrowForTokens))
|
||||||
@@ -772,6 +771,7 @@ trustTransferLockedBalance(
|
|||||||
S& sleDstAcc,
|
S& sleDstAcc,
|
||||||
STAmount const& amount, // issuer, currency are in this field
|
STAmount const& amount, // issuer, currency are in this field
|
||||||
int deltaLockCount, // -1 decrement, +1 increment, 0 unchanged
|
int deltaLockCount, // -1 decrement, +1 increment, 0 unchanged
|
||||||
|
Rate const& xferRate, // TransferRate
|
||||||
beast::Journal const& j,
|
beast::Journal const& j,
|
||||||
R dryRun)
|
R dryRun)
|
||||||
{
|
{
|
||||||
@@ -829,7 +829,7 @@ trustTransferLockedBalance(
|
|||||||
Keylet klSrcLine{keylet::line(srcAccID, issuerAccID, currency)};
|
Keylet klSrcLine{keylet::line(srcAccID, issuerAccID, currency)};
|
||||||
SLEPtr sleSrcLine = peek(klSrcLine);
|
SLEPtr sleSrcLine = peek(klSrcLine);
|
||||||
|
|
||||||
// source account IS issuer
|
// source account is not issuer use locked balance
|
||||||
if (!isIssuer)
|
if (!isIssuer)
|
||||||
{
|
{
|
||||||
if (!sleSrcLine)
|
if (!sleSrcLine)
|
||||||
@@ -920,15 +920,17 @@ trustTransferLockedBalance(
|
|||||||
// on the destination line
|
// on the destination line
|
||||||
bool flipDstAmt = !((dstHigh && srcHigh) || (!dstHigh && !srcHigh));
|
bool flipDstAmt = !((dstHigh && srcHigh) || (!dstHigh && !srcHigh));
|
||||||
|
|
||||||
// compute transfer fee, if any
|
// default to amount
|
||||||
auto xferRate = transferRate(view, issuerAccID);
|
auto dstAmt = amount;
|
||||||
|
// if transfer rate
|
||||||
// the destination will sometimes get less depending on xfer rate
|
if (xferRate != parityRate)
|
||||||
// with any difference in tokens burned
|
{
|
||||||
auto dstAmt = xferRate == parityRate
|
// compute transfer fee, if any
|
||||||
? amount
|
auto const xferFee =
|
||||||
: multiplyRound(amount, xferRate, amount.issue(), true);
|
amount.value() - divideRound(amount, xferRate, amount.issue(), true);
|
||||||
|
// compute balance to transfer
|
||||||
|
dstAmt = amount.value() - xferFee;
|
||||||
|
}
|
||||||
// check for a destination line
|
// check for a destination line
|
||||||
Keylet klDstLine = keylet::line(dstAccID, issuerAccID, currency);
|
Keylet klDstLine = keylet::line(dstAccID, issuerAccID, currency);
|
||||||
SLEPtr sleDstLine = peek(klDstLine);
|
SLEPtr sleDstLine = peek(klDstLine);
|
||||||
@@ -945,7 +947,6 @@ trustTransferLockedBalance(
|
|||||||
if (std::uint32_t const ownerCount = {sleDstAcc->at(sfOwnerCount)};
|
if (std::uint32_t const ownerCount = {sleDstAcc->at(sfOwnerCount)};
|
||||||
dstBalanceDrops < view.fees().accountReserve(ownerCount + 1))
|
dstBalanceDrops < view.fees().accountReserve(ownerCount + 1))
|
||||||
return tecNO_LINE_INSUF_RESERVE;
|
return tecNO_LINE_INSUF_RESERVE;
|
||||||
|
|
||||||
// yes we can... we will
|
// yes we can... we will
|
||||||
|
|
||||||
auto const finalDstAmt =
|
auto const finalDstAmt =
|
||||||
|
|||||||
@@ -116,15 +116,16 @@ LedgerFormats::LedgerFormats()
|
|||||||
{sfAccount, soeREQUIRED},
|
{sfAccount, soeREQUIRED},
|
||||||
{sfDestination, soeREQUIRED},
|
{sfDestination, soeREQUIRED},
|
||||||
{sfAmount, soeREQUIRED},
|
{sfAmount, soeREQUIRED},
|
||||||
|
{sfTransferRate, soeREQUIRED},
|
||||||
{sfCondition, soeOPTIONAL},
|
{sfCondition, soeOPTIONAL},
|
||||||
{sfCancelAfter, soeOPTIONAL},
|
{sfCancelAfter, soeOPTIONAL},
|
||||||
{sfFinishAfter, soeOPTIONAL},
|
{sfFinishAfter, soeOPTIONAL},
|
||||||
{sfSourceTag, soeOPTIONAL},
|
{sfSourceTag, soeOPTIONAL},
|
||||||
{sfDestinationTag, soeOPTIONAL},
|
{sfDestinationTag, soeOPTIONAL},
|
||||||
|
{sfDestinationNode, soeOPTIONAL},
|
||||||
{sfOwnerNode, soeREQUIRED},
|
{sfOwnerNode, soeREQUIRED},
|
||||||
{sfPreviousTxnID, soeREQUIRED},
|
{sfPreviousTxnID, soeREQUIRED},
|
||||||
{sfPreviousTxnLgrSeq, soeREQUIRED},
|
{sfPreviousTxnLgrSeq, soeREQUIRED},
|
||||||
{sfDestinationNode, soeOPTIONAL},
|
|
||||||
},
|
},
|
||||||
commonFields);
|
commonFields);
|
||||||
|
|
||||||
@@ -189,14 +190,15 @@ LedgerFormats::LedgerFormats()
|
|||||||
{sfBalance, soeREQUIRED},
|
{sfBalance, soeREQUIRED},
|
||||||
{sfPublicKey, soeREQUIRED},
|
{sfPublicKey, soeREQUIRED},
|
||||||
{sfSettleDelay, soeREQUIRED},
|
{sfSettleDelay, soeREQUIRED},
|
||||||
|
{sfTransferRate, soeREQUIRED},
|
||||||
{sfExpiration, soeOPTIONAL},
|
{sfExpiration, soeOPTIONAL},
|
||||||
{sfCancelAfter, soeOPTIONAL},
|
{sfCancelAfter, soeOPTIONAL},
|
||||||
{sfSourceTag, soeOPTIONAL},
|
{sfSourceTag, soeOPTIONAL},
|
||||||
{sfDestinationTag, soeOPTIONAL},
|
{sfDestinationTag, soeOPTIONAL},
|
||||||
|
{sfDestinationNode, soeOPTIONAL},
|
||||||
{sfOwnerNode, soeREQUIRED},
|
{sfOwnerNode, soeREQUIRED},
|
||||||
{sfPreviousTxnID, soeREQUIRED},
|
{sfPreviousTxnID, soeREQUIRED},
|
||||||
{sfPreviousTxnLgrSeq, soeREQUIRED},
|
{sfPreviousTxnLgrSeq, soeREQUIRED},
|
||||||
{sfDestinationNode, soeOPTIONAL},
|
|
||||||
},
|
},
|
||||||
commonFields);
|
commonFields);
|
||||||
|
|
||||||
|
|||||||
@@ -202,6 +202,15 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
return STAmount(iou, 0);
|
return STAmount(iou, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static Rate
|
||||||
|
escrowRate(jtx::Env const& env, jtx::Account const& account, uint32_t const& seq)
|
||||||
|
{
|
||||||
|
auto const sle = env.le(keylet::escrow(account.id(), seq));
|
||||||
|
if (sle->isFieldPresent(sfTransferRate))
|
||||||
|
return ripple::Rate((*sle)[sfTransferRate]);
|
||||||
|
return Rate{0};
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
testEnablement(FeatureBitset features)
|
testEnablement(FeatureBitset features)
|
||||||
{
|
{
|
||||||
@@ -210,7 +219,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
using namespace jtx;
|
using namespace jtx;
|
||||||
using namespace std::chrono;
|
using namespace std::chrono;
|
||||||
|
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob");
|
env.fund(XRP(5000), "alice", "bob");
|
||||||
env(escrow("alice", "bob", XRP(1000)), finish_time(env.now() + 1s));
|
env(escrow("alice", "bob", XRP(1000)), finish_time(env.now() + 1s));
|
||||||
env.close();
|
env.close();
|
||||||
@@ -246,7 +255,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
testcase("Timing: Finish Only");
|
testcase("Timing: Finish Only");
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob");
|
env.fund(XRP(5000), "alice", "bob");
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
@@ -268,7 +277,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
testcase("Timing: Cancel Only");
|
testcase("Timing: Cancel Only");
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob");
|
env.fund(XRP(5000), "alice", "bob");
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
@@ -300,7 +309,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
testcase("Timing: Finish and Cancel -> Finish");
|
testcase("Timing: Finish and Cancel -> Finish");
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob");
|
env.fund(XRP(5000), "alice", "bob");
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
@@ -334,7 +343,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
testcase("Timing: Finish and Cancel -> Cancel");
|
testcase("Timing: Finish and Cancel -> Cancel");
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob");
|
env.fund(XRP(5000), "alice", "bob");
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
@@ -383,7 +392,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
using namespace jtx;
|
using namespace jtx;
|
||||||
using namespace std::chrono;
|
using namespace std::chrono;
|
||||||
|
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
|
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
@@ -432,7 +441,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
{
|
{
|
||||||
// Ignore the "asfDisallowXRP" account flag, which we should
|
// Ignore the "asfDisallowXRP" account flag, which we should
|
||||||
// have been doing before.
|
// have been doing before.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
|
|
||||||
env.fund(XRP(5000), "bob", "george");
|
env.fund(XRP(5000), "bob", "george");
|
||||||
env(fset("george", asfDisallowXRP));
|
env(fset("george", asfDisallowXRP));
|
||||||
@@ -483,7 +492,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
{
|
{
|
||||||
testcase("Implied Finish Time (with fix1571)");
|
testcase("Implied Finish Time (with fix1571)");
|
||||||
|
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob", "carol");
|
env.fund(XRP(5000), "alice", "bob", "carol");
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
@@ -517,7 +526,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
using namespace jtx;
|
using namespace jtx;
|
||||||
using namespace std::chrono;
|
using namespace std::chrono;
|
||||||
|
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob");
|
env.fund(XRP(5000), "alice", "bob");
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
@@ -651,7 +660,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
// Unconditional
|
// Unconditional
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob");
|
env.fund(XRP(5000), "alice", "bob");
|
||||||
auto const seq = env.seq("alice");
|
auto const seq = env.seq("alice");
|
||||||
env(escrow("alice", "alice", XRP(1000)),
|
env(escrow("alice", "alice", XRP(1000)),
|
||||||
@@ -675,7 +684,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
// Unconditionally pay from Alice to Bob. Zelda (neither source nor
|
// Unconditionally pay from Alice to Bob. Zelda (neither source nor
|
||||||
// destination) signs all cancels and finishes. This shows that
|
// destination) signs all cancels and finishes. This shows that
|
||||||
// Escrow will make a payment to Bob with no intervention from Bob.
|
// Escrow will make a payment to Bob with no intervention from Bob.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob", "zelda");
|
env.fund(XRP(5000), "alice", "bob", "zelda");
|
||||||
auto const seq = env.seq("alice");
|
auto const seq = env.seq("alice");
|
||||||
env(escrow("alice", "bob", XRP(1000)), finish_time(env.now() + 5s));
|
env(escrow("alice", "bob", XRP(1000)), finish_time(env.now() + 5s));
|
||||||
@@ -700,7 +709,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
{
|
{
|
||||||
// Bob sets DepositAuth so only Bob can finish the escrow.
|
// Bob sets DepositAuth so only Bob can finish the escrow.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
|
|
||||||
env.fund(XRP(5000), "alice", "bob", "zelda");
|
env.fund(XRP(5000), "alice", "bob", "zelda");
|
||||||
env(fset("bob", asfDepositAuth));
|
env(fset("bob", asfDepositAuth));
|
||||||
@@ -738,7 +747,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
{
|
{
|
||||||
// Bob sets DepositAuth but preauthorizes Zelda, so Zelda can
|
// Bob sets DepositAuth but preauthorizes Zelda, so Zelda can
|
||||||
// finish the escrow.
|
// finish the escrow.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
|
|
||||||
env.fund(XRP(5000), "alice", "bob", "zelda");
|
env.fund(XRP(5000), "alice", "bob", "zelda");
|
||||||
env(fset("bob", asfDepositAuth));
|
env(fset("bob", asfDepositAuth));
|
||||||
@@ -765,7 +774,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
{
|
{
|
||||||
// Conditional
|
// Conditional
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob");
|
env.fund(XRP(5000), "alice", "bob");
|
||||||
auto const seq = env.seq("alice");
|
auto const seq = env.seq("alice");
|
||||||
env(escrow("alice", "alice", XRP(1000)),
|
env(escrow("alice", "alice", XRP(1000)),
|
||||||
@@ -806,7 +815,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
{
|
{
|
||||||
// Self-escrowed conditional with DepositAuth.
|
// Self-escrowed conditional with DepositAuth.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
|
|
||||||
env.fund(XRP(5000), "alice", "bob");
|
env.fund(XRP(5000), "alice", "bob");
|
||||||
auto const seq = env.seq("alice");
|
auto const seq = env.seq("alice");
|
||||||
@@ -842,7 +851,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
{
|
{
|
||||||
// Self-escrowed conditional with DepositAuth and DepositPreauth.
|
// Self-escrowed conditional with DepositAuth and DepositPreauth.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
|
|
||||||
env.fund(XRP(5000), "alice", "bob", "zelda");
|
env.fund(XRP(5000), "alice", "bob", "zelda");
|
||||||
auto const seq = env.seq("alice");
|
auto const seq = env.seq("alice");
|
||||||
@@ -893,7 +902,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
using namespace std::chrono;
|
using namespace std::chrono;
|
||||||
|
|
||||||
{ // Test cryptoconditions
|
{ // Test cryptoconditions
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob", "carol");
|
env.fund(XRP(5000), "alice", "bob", "carol");
|
||||||
auto const seq = env.seq("alice");
|
auto const seq = env.seq("alice");
|
||||||
BEAST_EXPECT((*env.le("alice"))[sfOwnerCount] == 0);
|
BEAST_EXPECT((*env.le("alice"))[sfOwnerCount] == 0);
|
||||||
@@ -966,7 +975,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
env(cancel("bob", "carol", 1), ter(tecNO_TARGET));
|
env(cancel("bob", "carol", 1), ter(tecNO_TARGET));
|
||||||
}
|
}
|
||||||
{ // Test cancel when condition is present
|
{ // Test cancel when condition is present
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob", "carol");
|
env.fund(XRP(5000), "alice", "bob", "carol");
|
||||||
auto const seq = env.seq("alice");
|
auto const seq = env.seq("alice");
|
||||||
BEAST_EXPECT((*env.le("alice"))[sfOwnerCount] == 0);
|
BEAST_EXPECT((*env.le("alice"))[sfOwnerCount] == 0);
|
||||||
@@ -982,7 +991,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
BEAST_EXPECT(!env.le(keylet::escrow(Account("alice").id(), seq)));
|
BEAST_EXPECT(!env.le(keylet::escrow(Account("alice").id(), seq)));
|
||||||
}
|
}
|
||||||
{
|
{
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob", "carol");
|
env.fund(XRP(5000), "alice", "bob", "carol");
|
||||||
env.close();
|
env.close();
|
||||||
auto const seq = env.seq("alice");
|
auto const seq = env.seq("alice");
|
||||||
@@ -1004,7 +1013,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
env.require(balance("carol", XRP(5000)));
|
env.require(balance("carol", XRP(5000)));
|
||||||
}
|
}
|
||||||
{ // Test long & short conditions during creation
|
{ // Test long & short conditions during creation
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob", "carol");
|
env.fund(XRP(5000), "alice", "bob", "carol");
|
||||||
|
|
||||||
std::vector<std::uint8_t> v;
|
std::vector<std::uint8_t> v;
|
||||||
@@ -1061,7 +1070,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
env.require(balance("carol", XRP(6000)));
|
env.require(balance("carol", XRP(6000)));
|
||||||
}
|
}
|
||||||
{ // Test long and short conditions & fulfillments during finish
|
{ // Test long and short conditions & fulfillments during finish
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob", "carol");
|
env.fund(XRP(5000), "alice", "bob", "carol");
|
||||||
|
|
||||||
std::vector<std::uint8_t> cv;
|
std::vector<std::uint8_t> cv;
|
||||||
@@ -1207,7 +1216,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
{ // Test empty condition during creation and
|
{ // Test empty condition during creation and
|
||||||
// empty condition & fulfillment during finish
|
// empty condition & fulfillment during finish
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob", "carol");
|
env.fund(XRP(5000), "alice", "bob", "carol");
|
||||||
|
|
||||||
env(escrow("alice", "carol", XRP(1000)),
|
env(escrow("alice", "carol", XRP(1000)),
|
||||||
@@ -1253,7 +1262,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
{ // Test a condition other than PreimageSha256, which
|
{ // Test a condition other than PreimageSha256, which
|
||||||
// would require a separate amendment
|
// would require a separate amendment
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), "alice", "bob");
|
env.fund(XRP(5000), "alice", "bob");
|
||||||
|
|
||||||
std::array<std::uint8_t, 45> cb = {
|
std::array<std::uint8_t, 45> cb = {
|
||||||
@@ -1285,7 +1294,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
{
|
{
|
||||||
testcase("Metadata to self");
|
testcase("Metadata to self");
|
||||||
|
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), alice, bruce, carol);
|
env.fund(XRP(5000), alice, bruce, carol);
|
||||||
auto const aseq = env.seq(alice);
|
auto const aseq = env.seq(alice);
|
||||||
auto const bseq = env.seq(bruce);
|
auto const bseq = env.seq(bruce);
|
||||||
@@ -1360,7 +1369,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
{
|
{
|
||||||
testcase("Metadata to other");
|
testcase("Metadata to other");
|
||||||
|
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), alice, bruce, carol);
|
env.fund(XRP(5000), alice, bruce, carol);
|
||||||
auto const aseq = env.seq(alice);
|
auto const aseq = env.seq(alice);
|
||||||
auto const bseq = env.seq(bruce);
|
auto const bseq = env.seq(bruce);
|
||||||
@@ -1456,7 +1465,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
using namespace jtx;
|
using namespace jtx;
|
||||||
using namespace std::chrono;
|
using namespace std::chrono;
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
|
|
||||||
env.memoize("alice");
|
env.memoize("alice");
|
||||||
env.memoize("bob");
|
env.memoize("bob");
|
||||||
@@ -1521,7 +1530,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
// Create escrow and finish using tickets.
|
// Create escrow and finish using tickets.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), alice, bob);
|
env.fund(XRP(5000), alice, bob);
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
@@ -1582,7 +1591,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
// Create escrow and cancel using tickets.
|
// Create escrow and cancel using tickets.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), alice, bob);
|
env.fund(XRP(5000), alice, bob);
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
@@ -1656,7 +1665,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
using namespace jtx;
|
using namespace jtx;
|
||||||
using namespace std::chrono;
|
using namespace std::chrono;
|
||||||
|
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const gw = Account{"gateway"};
|
auto const gw = Account{"gateway"};
|
||||||
@@ -1703,7 +1712,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
testcase("Timing: IC Finish Only");
|
testcase("Timing: IC Finish Only");
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const gw = Account{"gateway"};
|
auto const gw = Account{"gateway"};
|
||||||
@@ -1732,7 +1741,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
testcase("Timing: IC Cancel Only");
|
testcase("Timing: IC Cancel Only");
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const gw = Account{"gateway"};
|
auto const gw = Account{"gateway"};
|
||||||
@@ -1773,7 +1782,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
testcase("Timing: IC Finish and Cancel -> Finish");
|
testcase("Timing: IC Finish and Cancel -> Finish");
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const gw = Account{"gateway"};
|
auto const gw = Account{"gateway"};
|
||||||
@@ -1816,7 +1825,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
testcase("Timing: IC Finish and Cancel -> Cancel");
|
testcase("Timing: IC Finish and Cancel -> Cancel");
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const gw = Account{"gateway"};
|
auto const gw = Account{"gateway"};
|
||||||
@@ -1874,7 +1883,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
using namespace jtx;
|
using namespace jtx;
|
||||||
using namespace std::chrono;
|
using namespace std::chrono;
|
||||||
|
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const gw = Account{"gateway"};
|
auto const gw = Account{"gateway"};
|
||||||
@@ -1937,7 +1946,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
{
|
{
|
||||||
// Ignore the "asfDisallowXRP" account flag, which we should
|
// Ignore the "asfDisallowXRP" account flag, which we should
|
||||||
// have been doing before.
|
// have been doing before.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), bob, george, gw);
|
env.fund(XRP(5000), bob, george, gw);
|
||||||
env.close();
|
env.close();
|
||||||
env.trust(USD(10000), bob, george);
|
env.trust(USD(10000), bob, george);
|
||||||
@@ -2003,7 +2012,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
{
|
{
|
||||||
testcase("IC Implied Finish Time (with fix1571)");
|
testcase("IC Implied Finish Time (with fix1571)");
|
||||||
|
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const carol = Account("carol");
|
auto const carol = Account("carol");
|
||||||
@@ -2048,7 +2057,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
using namespace jtx;
|
using namespace jtx;
|
||||||
using namespace std::chrono;
|
using namespace std::chrono;
|
||||||
|
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const gw = Account{"gateway"};
|
auto const gw = Account{"gateway"};
|
||||||
@@ -2206,7 +2215,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
// Unconditional
|
// Unconditional
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const gw = Account{"gateway"};
|
auto const gw = Account{"gateway"};
|
||||||
@@ -2245,7 +2254,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
// Unconditionally pay from Alice to Bob. Zelda (neither source nor
|
// Unconditionally pay from Alice to Bob. Zelda (neither source nor
|
||||||
// destination) signs all cancels and finishes. This shows that
|
// destination) signs all cancels and finishes. This shows that
|
||||||
// Escrow will make a payment to Bob with no intervention from Bob.
|
// Escrow will make a payment to Bob with no intervention from Bob.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const carol = Account("carol");
|
auto const carol = Account("carol");
|
||||||
@@ -2291,7 +2300,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
{
|
{
|
||||||
// Bob sets DepositAuth so only Bob can finish the escrow.
|
// Bob sets DepositAuth so only Bob can finish the escrow.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const carol = Account("carol");
|
auto const carol = Account("carol");
|
||||||
@@ -2352,7 +2361,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
{
|
{
|
||||||
// Bob sets DepositAuth but preauthorizes Zelda, so Zelda can
|
// Bob sets DepositAuth but preauthorizes Zelda, so Zelda can
|
||||||
// finish the escrow.
|
// finish the escrow.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const carol = Account("carol");
|
auto const carol = Account("carol");
|
||||||
@@ -2400,7 +2409,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
{
|
{
|
||||||
// Conditional
|
// Conditional
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const gw = Account{"gateway"};
|
auto const gw = Account{"gateway"};
|
||||||
@@ -2456,7 +2465,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
{
|
{
|
||||||
// Self-escrowed conditional with DepositAuth.
|
// Self-escrowed conditional with DepositAuth.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const gw = Account{"gateway"};
|
auto const gw = Account{"gateway"};
|
||||||
@@ -2507,7 +2516,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
{
|
{
|
||||||
// Self-escrowed conditional with DepositAuth and DepositPreauth.
|
// Self-escrowed conditional with DepositAuth and DepositPreauth.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const carol = Account("carol");
|
auto const carol = Account("carol");
|
||||||
@@ -2576,7 +2585,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
using namespace std::chrono;
|
using namespace std::chrono;
|
||||||
|
|
||||||
{ // Test cryptoconditions
|
{ // Test cryptoconditions
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const carol = Account("carol");
|
auto const carol = Account("carol");
|
||||||
@@ -2666,7 +2675,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
env(cancel(bob, carol, 1), ter(tecNO_TARGET));
|
env(cancel(bob, carol, 1), ter(tecNO_TARGET));
|
||||||
}
|
}
|
||||||
{ // Test cancel when condition is present
|
{ // Test cancel when condition is present
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const carol = Account("carol");
|
auto const carol = Account("carol");
|
||||||
@@ -2702,7 +2711,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
BEAST_EXPECT(!env.le(keylet::escrow(Account(alice).id(), seq)));
|
BEAST_EXPECT(!env.le(keylet::escrow(Account(alice).id(), seq)));
|
||||||
}
|
}
|
||||||
{
|
{
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const carol = Account("carol");
|
auto const carol = Account("carol");
|
||||||
@@ -2735,7 +2744,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
env.require(balance(carol, USD(5000)));
|
env.require(balance(carol, USD(5000)));
|
||||||
}
|
}
|
||||||
{ // Test long & short conditions during creation
|
{ // Test long & short conditions during creation
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const carol = Account("carol");
|
auto const carol = Account("carol");
|
||||||
@@ -2810,7 +2819,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
env.require(balance(carol, USD(6000)));
|
env.require(balance(carol, USD(6000)));
|
||||||
}
|
}
|
||||||
{ // Test long and short conditions & fulfillments during finish
|
{ // Test long and short conditions & fulfillments during finish
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const carol = Account("carol");
|
auto const carol = Account("carol");
|
||||||
@@ -2973,7 +2982,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
{ // Test empty condition during creation and
|
{ // Test empty condition during creation and
|
||||||
// empty condition & fulfillment during finish
|
// empty condition & fulfillment during finish
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const carol = Account("carol");
|
auto const carol = Account("carol");
|
||||||
@@ -3034,7 +3043,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
{ // Test a condition other than PreimageSha256, which
|
{ // Test a condition other than PreimageSha256, which
|
||||||
// would require a separate amendment
|
// would require a separate amendment
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
auto const gw = Account{"gateway"};
|
auto const gw = Account{"gateway"};
|
||||||
@@ -3077,7 +3086,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
{
|
{
|
||||||
testcase("IC Metadata to self");
|
testcase("IC Metadata to self");
|
||||||
|
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), alice, bob, carol, gw);
|
env.fund(XRP(5000), alice, bob, carol, gw);
|
||||||
env.close();
|
env.close();
|
||||||
env.trust(USD(10000), alice, bob, carol);
|
env.trust(USD(10000), alice, bob, carol);
|
||||||
@@ -3158,7 +3167,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
{
|
{
|
||||||
testcase("IC Metadata to other");
|
testcase("IC Metadata to other");
|
||||||
|
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), alice, bob, carol, gw);
|
env.fund(XRP(5000), alice, bob, carol, gw);
|
||||||
env.close();
|
env.close();
|
||||||
env.trust(USD(10000), alice, bob, carol);
|
env.trust(USD(10000), alice, bob, carol);
|
||||||
@@ -3261,7 +3270,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
using namespace jtx;
|
using namespace jtx;
|
||||||
using namespace std::chrono;
|
using namespace std::chrono;
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
|
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
auto const bob = Account("bob");
|
auto const bob = Account("bob");
|
||||||
@@ -3342,7 +3351,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
// Create escrow and finish using tickets.
|
// Create escrow and finish using tickets.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), alice, bob, gw);
|
env.fund(XRP(5000), alice, bob, gw);
|
||||||
env.close();
|
env.close();
|
||||||
env.trust(USD(10000), alice, bob);
|
env.trust(USD(10000), alice, bob);
|
||||||
@@ -3407,7 +3416,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
|
|
||||||
{
|
{
|
||||||
// Create escrow and cancel using tickets.
|
// Create escrow and cancel using tickets.
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), alice, bob, gw);
|
env.fund(XRP(5000), alice, bob, gw);
|
||||||
env.close();
|
env.close();
|
||||||
env.trust(USD(10000), alice, bob);
|
env.trust(USD(10000), alice, bob);
|
||||||
@@ -3492,7 +3501,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
// test create escrow from issuer with ic
|
// test create escrow from issuer with ic
|
||||||
// test with dest tl
|
// test with dest tl
|
||||||
// test finish from destination account
|
// test finish from destination account
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), alice, gw);
|
env.fund(XRP(5000), alice, gw);
|
||||||
env.close();
|
env.close();
|
||||||
env.trust(USD(10000), alice);
|
env.trust(USD(10000), alice);
|
||||||
@@ -3517,7 +3526,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
{
|
{
|
||||||
// setup env
|
// setup env
|
||||||
Env env(*this, features);
|
Env env{*this, features};
|
||||||
env.fund(XRP(5000), alice, gw);
|
env.fund(XRP(5000), alice, gw);
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
@@ -3541,6 +3550,126 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
testICLockedRate(FeatureBitset features)
|
||||||
|
{
|
||||||
|
testcase("IC Locked Rate");
|
||||||
|
using namespace test::jtx;
|
||||||
|
using namespace std::literals;
|
||||||
|
|
||||||
|
auto const alice = Account("alice");
|
||||||
|
auto const bob = Account("bob");
|
||||||
|
auto const carol = Account("carol");
|
||||||
|
auto const gw = Account{"gateway"};
|
||||||
|
auto const USD = gw["USD"];
|
||||||
|
|
||||||
|
auto const aliceUSD = alice["USD"];
|
||||||
|
auto const bobUSD = bob["USD"];
|
||||||
|
|
||||||
|
// test TransferRate
|
||||||
|
{
|
||||||
|
Env env{*this, features};
|
||||||
|
env.fund(XRP(10000), alice, bob, gw);
|
||||||
|
env(rate(gw, 1.25));
|
||||||
|
env.close();
|
||||||
|
env.trust(USD(100000), alice);
|
||||||
|
env.trust(USD(100000), bob);
|
||||||
|
env.close();
|
||||||
|
env(pay(gw, alice, USD(10000)));
|
||||||
|
env(pay(gw, bob, USD(10000)));
|
||||||
|
env.close();
|
||||||
|
auto const preAlice = env.balance(alice, USD.issue());
|
||||||
|
auto const seq1 = env.seq(alice);
|
||||||
|
auto const delta = USD(125);
|
||||||
|
env(escrow(alice, bob, delta),
|
||||||
|
condition(cb1),
|
||||||
|
finish_time(env.now() + 1s),
|
||||||
|
fee(1500));
|
||||||
|
env.close();
|
||||||
|
auto const transferRate = escrowRate(env, alice, seq1);
|
||||||
|
BEAST_EXPECT(transferRate.value == std::uint32_t(1000000000 * 1.25));
|
||||||
|
env(finish(bob, alice, seq1),
|
||||||
|
condition(cb1),
|
||||||
|
fulfillment(fb1),
|
||||||
|
fee(1500));
|
||||||
|
env.close();
|
||||||
|
auto const postLocked = lockedAmount(env, alice, gw, USD);
|
||||||
|
BEAST_EXPECT(postLocked == USD(0));
|
||||||
|
BEAST_EXPECT(env.balance(alice, USD.issue()) == preAlice - delta);
|
||||||
|
BEAST_EXPECT(env.balance(bob, USD.issue()) == USD(10100));
|
||||||
|
}
|
||||||
|
// issuer changes to higher rate
|
||||||
|
{
|
||||||
|
Env env{*this, features};
|
||||||
|
env.fund(XRP(10000), alice, bob, gw);
|
||||||
|
env(rate(gw, 1.25));
|
||||||
|
env.close();
|
||||||
|
env.trust(USD(100000), alice);
|
||||||
|
env.trust(USD(100000), bob);
|
||||||
|
env.close();
|
||||||
|
env(pay(gw, alice, USD(10000)));
|
||||||
|
env(pay(gw, bob, USD(10000)));
|
||||||
|
env.close();
|
||||||
|
auto const preAlice = env.balance(alice, USD.issue());
|
||||||
|
auto const seq1 = env.seq(alice);
|
||||||
|
auto const delta = USD(125);
|
||||||
|
env(escrow(alice, bob, delta),
|
||||||
|
condition(cb1),
|
||||||
|
finish_time(env.now() + 1s),
|
||||||
|
fee(1500));
|
||||||
|
env.close();
|
||||||
|
auto transferRate = escrowRate(env, alice, seq1);
|
||||||
|
BEAST_EXPECT(transferRate.value == std::uint32_t(1000000000 * 1.25));
|
||||||
|
env(rate(gw, 1.26));
|
||||||
|
env.close();
|
||||||
|
|
||||||
|
env(finish(bob, alice, seq1),
|
||||||
|
condition(cb1),
|
||||||
|
fulfillment(fb1),
|
||||||
|
fee(1500));
|
||||||
|
env.close();
|
||||||
|
auto const postLocked = lockedAmount(env, alice, gw, USD);
|
||||||
|
BEAST_EXPECT(postLocked == USD(0));
|
||||||
|
BEAST_EXPECT(env.balance(alice, USD.issue()) == preAlice - delta);
|
||||||
|
BEAST_EXPECT(env.balance(bob, USD.issue()) == USD(10100));
|
||||||
|
}
|
||||||
|
// issuer changes to lower rate
|
||||||
|
{
|
||||||
|
Env env{*this, features};
|
||||||
|
env.fund(XRP(10000), alice, bob, gw);
|
||||||
|
env(rate(gw, 1.25));
|
||||||
|
env.close();
|
||||||
|
env.trust(USD(100000), alice);
|
||||||
|
env.trust(USD(100000), bob);
|
||||||
|
env.close();
|
||||||
|
env(pay(gw, alice, USD(10000)));
|
||||||
|
env(pay(gw, bob, USD(10000)));
|
||||||
|
env.close();
|
||||||
|
auto const preAlice = env.balance(alice, USD.issue());
|
||||||
|
auto const seq1 = env.seq(alice);
|
||||||
|
auto const delta = USD(125);
|
||||||
|
env(escrow(alice, bob, delta),
|
||||||
|
condition(cb1),
|
||||||
|
finish_time(env.now() + 1s),
|
||||||
|
fee(1500));
|
||||||
|
env.close();
|
||||||
|
auto transferRate = escrowRate(env, alice, seq1);
|
||||||
|
BEAST_EXPECT(transferRate.value == std::uint32_t(1000000000 * 1.25));
|
||||||
|
env(rate(gw, 1.00));
|
||||||
|
env.close();
|
||||||
|
env(finish(bob, alice, seq1),
|
||||||
|
condition(cb1),
|
||||||
|
fulfillment(fb1),
|
||||||
|
fee(1500));
|
||||||
|
env.close();
|
||||||
|
auto const postLocked = lockedAmount(env, alice, gw, USD);
|
||||||
|
BEAST_EXPECT(postLocked == USD(0));
|
||||||
|
BEAST_EXPECT(env.balance(alice, USD.issue()) == preAlice - delta);
|
||||||
|
std::cout << "BOB BAL: " << env.balance(bob, USD.issue()) << "\n";
|
||||||
|
BEAST_EXPECT(env.balance(bob, USD.issue()) == USD(10125));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
testWithFeats(FeatureBitset features)
|
testWithFeats(FeatureBitset features)
|
||||||
{
|
{
|
||||||
@@ -3567,6 +3696,7 @@ struct Escrow_test : public beast::unit_test::suite
|
|||||||
testICConsequences(features);
|
testICConsequences(features);
|
||||||
testICEscrowWithTickets(features);
|
testICEscrowWithTickets(features);
|
||||||
testICGateway(features);
|
testICGateway(features);
|
||||||
|
testICLockedRate(features);
|
||||||
}
|
}
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
|||||||
@@ -111,6 +111,15 @@ struct PayChan_test : public beast::unit_test::suite
|
|||||||
return (*slep)[sfAmount];
|
return (*slep)[sfAmount];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static Rate
|
||||||
|
channelRate(ReadView const& view, uint256 const& chan)
|
||||||
|
{
|
||||||
|
auto const slep = view.read({ltPAYCHAN, chan});
|
||||||
|
if (!slep)
|
||||||
|
return Rate{0};
|
||||||
|
return ripple::Rate((*slep)[sfTransferRate]);
|
||||||
|
}
|
||||||
|
|
||||||
static STAmount
|
static STAmount
|
||||||
lockedAmount(
|
lockedAmount(
|
||||||
jtx::Env const& env,
|
jtx::Env const& env,
|
||||||
@@ -4641,6 +4650,7 @@ struct PayChan_test : public beast::unit_test::suite
|
|||||||
using namespace std::literals;
|
using namespace std::literals;
|
||||||
|
|
||||||
auto const alice = Account("alice");
|
auto const alice = Account("alice");
|
||||||
|
auto const bob = Account("bob");
|
||||||
auto const gw = Account{"gateway"};
|
auto const gw = Account{"gateway"};
|
||||||
auto const USD = gw["USD"];
|
auto const USD = gw["USD"];
|
||||||
{
|
{
|
||||||
@@ -4656,6 +4666,63 @@ struct PayChan_test : public beast::unit_test::suite
|
|||||||
env(create(gw, alice, USD(1000), settleDelay, pk));
|
env(create(gw, alice, USD(1000), settleDelay, pk));
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
|
// gw can not claim
|
||||||
|
auto const preAlice = env.balance(alice, USD.issue());
|
||||||
|
auto chanBal = channelBalance(*env.current(), chan);
|
||||||
|
auto chanAmt = channelAmount(*env.current(), chan);
|
||||||
|
auto const delta = USD(500);
|
||||||
|
auto const reqBal = chanBal + delta;
|
||||||
|
auto const authAmt = reqBal + USD(100);
|
||||||
|
// env(claim(gw, chan, reqBal, authAmt), ter(tecNO_LINE));
|
||||||
|
|
||||||
|
auto const sig = signClaimICAuth(gw.pk(), gw.sk(), chan, authAmt);
|
||||||
|
env(claim(bob, chan, reqBal, authAmt, Slice(sig), gw.pk()));
|
||||||
|
env.close();
|
||||||
|
}
|
||||||
|
{
|
||||||
|
Env env(*this, features);
|
||||||
|
env.fund(XRP(10000), alice, bob, gw);
|
||||||
|
env.close();
|
||||||
|
env.trust(USD(1000), alice);
|
||||||
|
env.trust(USD(1000), bob);
|
||||||
|
env.close();
|
||||||
|
env(pay(gw, alice, USD(1000)));
|
||||||
|
env(pay(gw, bob, USD(1000)));
|
||||||
|
env.close();
|
||||||
|
|
||||||
|
auto const pk = alice.pk();
|
||||||
|
auto const settleDelay = 100s;
|
||||||
|
auto const chan = channel(alice, bob, env.seq(alice));
|
||||||
|
env(create(alice, bob, USD(1000), settleDelay, pk));
|
||||||
|
env.close();
|
||||||
|
BEAST_EXPECT(channelBalance(*env.current(), chan) == USD(0));
|
||||||
|
BEAST_EXPECT(channelAmount(*env.current(), chan) == USD(1000));
|
||||||
|
auto chanBal = channelBalance(*env.current(), chan);
|
||||||
|
auto chanAmt = channelAmount(*env.current(), chan);
|
||||||
|
BEAST_EXPECT(chanBal == USD(0));
|
||||||
|
BEAST_EXPECT(chanAmt == USD(1000));
|
||||||
|
auto preBob = env.balance(bob);
|
||||||
|
auto const delta = USD(50);
|
||||||
|
auto reqBal = chanBal + delta;
|
||||||
|
auto authAmt = reqBal + USD(100);
|
||||||
|
assert(reqBal <= chanAmt);
|
||||||
|
auto const preLocked = lockedAmount(env, alice, gw, USD);
|
||||||
|
BEAST_EXPECT(preLocked == USD(1000));
|
||||||
|
env(claim(alice, chan, reqBal, authAmt));
|
||||||
|
}
|
||||||
|
{
|
||||||
|
// test create paychan from issuer with ic
|
||||||
|
// test where dest has no tl
|
||||||
|
// test claim from issuer account
|
||||||
|
Env env(*this, features);
|
||||||
|
env.fund(XRP(10000), alice, gw);
|
||||||
|
env.close();
|
||||||
|
auto const pk = gw.pk();
|
||||||
|
auto const settleDelay = 100s;
|
||||||
|
auto const chan = channel(gw, alice, env.seq(gw));
|
||||||
|
env(create(gw, alice, USD(1000), settleDelay, pk));
|
||||||
|
env.close();
|
||||||
|
|
||||||
// gw can not claim
|
// gw can not claim
|
||||||
auto const preAlice = env.balance(alice, USD.issue());
|
auto const preAlice = env.balance(alice, USD.issue());
|
||||||
auto chanBal = channelBalance(*env.current(), chan);
|
auto chanBal = channelBalance(*env.current(), chan);
|
||||||
@@ -4754,6 +4821,114 @@ struct PayChan_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
testICLockedRate(FeatureBitset features)
|
||||||
|
{
|
||||||
|
testcase("IC Locked Rate");
|
||||||
|
using namespace test::jtx;
|
||||||
|
using namespace std::literals;
|
||||||
|
|
||||||
|
auto const alice = Account("alice");
|
||||||
|
auto const bob = Account("bob");
|
||||||
|
auto const carol = Account("carol");
|
||||||
|
auto const gw = Account{"gateway"};
|
||||||
|
auto const USD = gw["USD"];
|
||||||
|
|
||||||
|
auto const aliceUSD = alice["USD"];
|
||||||
|
auto const bobUSD = bob["USD"];
|
||||||
|
|
||||||
|
// test TransferRate
|
||||||
|
{
|
||||||
|
Env env(*this, features);
|
||||||
|
env.fund(XRP(10000), alice, bob, gw);
|
||||||
|
env(rate(gw, 1.25));
|
||||||
|
env.close();
|
||||||
|
env.trust(USD(100000), alice);
|
||||||
|
env.trust(USD(100000), bob);
|
||||||
|
env.close();
|
||||||
|
env(pay(gw, alice, USD(10000)));
|
||||||
|
env(pay(gw, bob, USD(10000)));
|
||||||
|
env.close();
|
||||||
|
auto const preAlice = env.balance(alice, USD.issue());
|
||||||
|
auto const pk = alice.pk();
|
||||||
|
auto const settleDelay = 100s;
|
||||||
|
auto const chan = channel(alice, bob, env.seq(alice));
|
||||||
|
env(create(alice, bob, USD(1000), settleDelay, pk));
|
||||||
|
env.close();
|
||||||
|
auto const transferRate = channelRate(*env.current(), chan);
|
||||||
|
BEAST_EXPECT(transferRate.value == std::uint32_t(1000000000 * 1.25));
|
||||||
|
auto chanBal = channelBalance(*env.current(), chan);
|
||||||
|
auto chanAmt = channelAmount(*env.current(), chan);
|
||||||
|
auto const delta = USD(125);
|
||||||
|
auto reqBal = chanBal + delta;
|
||||||
|
auto authAmt = reqBal + USD(500);
|
||||||
|
// alice can claim
|
||||||
|
env(claim(alice, chan, reqBal, authAmt));
|
||||||
|
env.close();
|
||||||
|
auto const postLocked = lockedAmount(env, alice, gw, USD);
|
||||||
|
BEAST_EXPECT(postLocked == USD(875));
|
||||||
|
BEAST_EXPECT(env.balance(alice, USD.issue()) == preAlice - delta);
|
||||||
|
BEAST_EXPECT(env.balance(bob, USD.issue()) == USD(10100));
|
||||||
|
}
|
||||||
|
// test rate locked in
|
||||||
|
// test fund fail
|
||||||
|
{
|
||||||
|
Env env(*this, features);
|
||||||
|
env.fund(XRP(10000), alice, bob, gw);
|
||||||
|
env(rate(gw, 1.25));
|
||||||
|
env.close();
|
||||||
|
env.trust(USD(100000), alice);
|
||||||
|
env.trust(USD(100000), bob);
|
||||||
|
env.close();
|
||||||
|
env(pay(gw, alice, USD(10000)));
|
||||||
|
env(pay(gw, bob, USD(10000)));
|
||||||
|
env.close();
|
||||||
|
|
||||||
|
auto const pk = alice.pk();
|
||||||
|
auto const settleDelay = 100s;
|
||||||
|
auto const chan = channel(alice, bob, env.seq(alice));
|
||||||
|
env(create(alice, bob, USD(1000), settleDelay, pk));
|
||||||
|
env.close();
|
||||||
|
auto transferRate = channelRate(*env.current(), chan);
|
||||||
|
BEAST_EXPECT(transferRate.value == std::uint32_t(1000000000 * 1.25));
|
||||||
|
|
||||||
|
auto const preAlice = env.balance(alice, USD.issue());
|
||||||
|
auto chanBal = channelBalance(*env.current(), chan);
|
||||||
|
auto chanAmt = channelAmount(*env.current(), chan);
|
||||||
|
auto const delta = USD(100);
|
||||||
|
auto reqBal = chanBal + delta;
|
||||||
|
auto authAmt = reqBal + USD(500);
|
||||||
|
|
||||||
|
// alice can fund paychan at rate
|
||||||
|
// no change in rate
|
||||||
|
env(fund(alice, chan, USD(1000)));
|
||||||
|
env.close();
|
||||||
|
transferRate = channelRate(*env.current(), chan);
|
||||||
|
BEAST_EXPECT(transferRate.value == std::uint32_t(1000000000 * 1.25));
|
||||||
|
|
||||||
|
// issuer changes rate lower
|
||||||
|
env(rate(gw, 1.00));
|
||||||
|
env.close();
|
||||||
|
|
||||||
|
// alice can fund after issuer rate change
|
||||||
|
env(fund(alice, chan, USD(1000)));
|
||||||
|
env.close();
|
||||||
|
transferRate = channelRate(*env.current(), chan);
|
||||||
|
BEAST_EXPECT(transferRate.value == std::uint32_t(1000000000 * 1.00));
|
||||||
|
|
||||||
|
// issuer changes rate higher
|
||||||
|
env(rate(gw, 1.01));
|
||||||
|
env.close();
|
||||||
|
|
||||||
|
// alice cant fund after issuer rate change
|
||||||
|
// issuer rate stays the same
|
||||||
|
env(fund(alice, chan, USD(1000)), ter(temBAD_TRANSFER_RATE));
|
||||||
|
env.close();
|
||||||
|
transferRate = channelRate(*env.current(), chan);
|
||||||
|
BEAST_EXPECT(transferRate.value == std::uint32_t(1000000000 * 1.00));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
testICTLFeatures(FeatureBitset features)
|
testICTLFeatures(FeatureBitset features)
|
||||||
{
|
{
|
||||||
@@ -4854,64 +5029,11 @@ struct PayChan_test : public beast::unit_test::suite
|
|||||||
// alice can claim
|
// alice can claim
|
||||||
env(claim(alice, chan, reqBal, authAmt));
|
env(claim(alice, chan, reqBal, authAmt));
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
// bob can claim
|
// bob can claim
|
||||||
// auto const sig = signClaimICAuth(alice.pk(), alice.sk(), chan,
|
auto const sig = signClaimICAuth(alice.pk(), alice.sk(), chan, authAmt);
|
||||||
// authAmt); env(claim(bob, chan, reqBal, authAmt, Slice(sig),
|
env(claim(bob, chan, reqBal, authAmt, Slice(sig), alice.pk()));
|
||||||
// alice.pk())); env.close();
|
|
||||||
}
|
|
||||||
// test TransferRate
|
|
||||||
{
|
|
||||||
Env env(*this, features);
|
|
||||||
env.fund(XRP(10000), alice, bob, gw);
|
|
||||||
env(rate(gw, 1.25));
|
|
||||||
env.close();
|
env.close();
|
||||||
env.trust(USD(100000), alice);
|
|
||||||
env.trust(USD(100000), bob);
|
|
||||||
env.close();
|
|
||||||
env(pay(gw, alice, USD(10000)));
|
|
||||||
env(pay(gw, bob, USD(10000)));
|
|
||||||
env.close();
|
|
||||||
|
|
||||||
// env(pay(alice, bob, USD(100)), sendmax(USD(125)));
|
|
||||||
// env(pay(alice, bob, USD(100)), txflags(tfPartialPayment));
|
|
||||||
// env.close();
|
|
||||||
// env.require(
|
|
||||||
// balance(alice, xrpMinusFee(env, 10000 - 50)),
|
|
||||||
// balance(bob, USD(2.5)), // owner pays transfer fee
|
|
||||||
// balance(carol, USD(50)));
|
|
||||||
|
|
||||||
auto const pk = alice.pk();
|
|
||||||
auto const settleDelay = 100s;
|
|
||||||
auto const chan = channel(alice, bob, env.seq(alice));
|
|
||||||
env(create(alice, bob, USD(1000), settleDelay, pk));
|
|
||||||
env.close();
|
|
||||||
|
|
||||||
auto chanBal = channelBalance(*env.current(), chan);
|
|
||||||
auto chanAmt = channelAmount(*env.current(), chan);
|
|
||||||
auto const delta = USD(100);
|
|
||||||
auto reqBal = chanBal + delta;
|
|
||||||
auto authAmt = reqBal + USD(200);
|
|
||||||
// alice can claim
|
|
||||||
env(claim(alice, chan, reqBal, authAmt));
|
|
||||||
env.close();
|
|
||||||
|
|
||||||
// bob can claim, increasing the limit amount
|
|
||||||
// auto const preBobLimit = limitAmount(env, bob, gw, USD);
|
|
||||||
// auto const sig = signClaimICAuth(alice.pk(), alice.sk(), chan,
|
|
||||||
// authAmt); env(claim(bob, chan, reqBal, authAmt, Slice(sig),
|
|
||||||
// alice.pk())); env.close();
|
|
||||||
|
|
||||||
auto const postLocked = lockedAmount(env, alice, gw, USD);
|
|
||||||
auto const aliceLimit = limitAmount(env, alice, gw, USD);
|
|
||||||
auto const bobLimit = limitAmount(env, bob, gw, USD);
|
|
||||||
// std::cout << "ALICE AMOUNT: " << env.balance(alice, USD.issue())
|
|
||||||
// << "\n"; std::cout << "BOB AMOUNT: " << env.balance(bob,
|
|
||||||
// USD.issue()) << "\n"; std::cout << "ALICE LIMIT: " << aliceLimit
|
|
||||||
// << "\n"; std::cout << "BOB LIMIT: " << bobLimit << "\n";
|
|
||||||
// std::cout << "POST LOCKED: " << postLocked << "\n";
|
|
||||||
// std::cout << "CHAN BAL: " << channelBalance(*env.current(), chan)
|
|
||||||
// << "\n"; std::cout << "CHAN AUTH: " <<
|
|
||||||
// channelAmount(*env.current(), chan) << "\n";
|
|
||||||
}
|
}
|
||||||
// test Global Freeze
|
// test Global Freeze
|
||||||
{
|
{
|
||||||
@@ -4924,53 +5046,38 @@ struct PayChan_test : public beast::unit_test::suite
|
|||||||
env(pay(gw, alice, USD(10000)));
|
env(pay(gw, alice, USD(10000)));
|
||||||
env(pay(gw, bob, USD(10000)));
|
env(pay(gw, bob, USD(10000)));
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
env(fset(gw, asfGlobalFreeze));
|
env(fset(gw, asfGlobalFreeze));
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
auto const pk = alice.pk();
|
auto const pk = alice.pk();
|
||||||
auto const settleDelay = 100s;
|
auto const settleDelay = 100s;
|
||||||
auto chan = channel(alice, bob, env.seq(alice));
|
auto chan = channel(alice, bob, env.seq(alice));
|
||||||
env(create(alice, bob, USD(1000), settleDelay, pk), ter(tecFROZEN));
|
env(create(alice, bob, USD(1000), settleDelay, pk), ter(tecFROZEN));
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
env(fclear(gw, asfGlobalFreeze));
|
env(fclear(gw, asfGlobalFreeze));
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
chan = channel(alice, bob, env.seq(alice));
|
chan = channel(alice, bob, env.seq(alice));
|
||||||
env(create(alice, bob, USD(1000), settleDelay, pk));
|
env(create(alice, bob, USD(1000), settleDelay, pk));
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
env(fset(gw, asfGlobalFreeze));
|
env(fset(gw, asfGlobalFreeze));
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
auto chanBal = channelBalance(*env.current(), chan);
|
auto chanBal = channelBalance(*env.current(), chan);
|
||||||
auto chanAmt = channelAmount(*env.current(), chan);
|
auto chanAmt = channelAmount(*env.current(), chan);
|
||||||
|
|
||||||
auto const delta = USD(10);
|
auto const delta = USD(10);
|
||||||
auto reqBal = chanBal + delta;
|
auto reqBal = chanBal + delta;
|
||||||
auto authAmt = reqBal + USD(100);
|
auto authAmt = reqBal + USD(100);
|
||||||
// alice cannot claim - tl global freeze
|
|
||||||
env(claim(alice, chan, reqBal, authAmt), ter(tecFROZEN));
|
env(claim(alice, chan, reqBal, authAmt), ter(tecFROZEN));
|
||||||
// bob cannot claim - tl global freeze
|
|
||||||
auto sig = signClaimICAuth(alice.pk(), alice.sk(), chan, authAmt);
|
auto sig = signClaimICAuth(alice.pk(), alice.sk(), chan, authAmt);
|
||||||
env(claim(bob, chan, reqBal, authAmt, Slice(sig), alice.pk()),
|
env(claim(bob, chan, reqBal, authAmt, Slice(sig), alice.pk()),
|
||||||
ter(tecFROZEN));
|
ter(tecFROZEN));
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
env(fclear(gw, asfGlobalFreeze));
|
env(fclear(gw, asfGlobalFreeze));
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
// alice can claim
|
|
||||||
env(claim(alice, chan, reqBal, authAmt));
|
env(claim(alice, chan, reqBal, authAmt));
|
||||||
env.close();
|
env.close();
|
||||||
|
|
||||||
// update channel values for claim
|
|
||||||
chanBal = channelBalance(*env.current(), chan);
|
chanBal = channelBalance(*env.current(), chan);
|
||||||
chanAmt = channelAmount(*env.current(), chan);
|
chanAmt = channelAmount(*env.current(), chan);
|
||||||
reqBal = chanBal + delta;
|
reqBal = chanBal + delta;
|
||||||
authAmt = reqBal + USD(100);
|
authAmt = reqBal + USD(100);
|
||||||
// bob can claim
|
|
||||||
sig = signClaimICAuth(alice.pk(), alice.sk(), chan, authAmt);
|
sig = signClaimICAuth(alice.pk(), alice.sk(), chan, authAmt);
|
||||||
env(claim(bob, chan, reqBal, authAmt, Slice(sig), alice.pk()));
|
env(claim(bob, chan, reqBal, authAmt, Slice(sig), alice.pk()));
|
||||||
env.close();
|
env.close();
|
||||||
@@ -5042,6 +5149,41 @@ struct PayChan_test : public beast::unit_test::suite
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
testICMismatchFunding(FeatureBitset features)
|
||||||
|
{
|
||||||
|
testcase("IC Mismatch Funding");
|
||||||
|
using namespace test::jtx;
|
||||||
|
using namespace std::literals;
|
||||||
|
|
||||||
|
auto const alice = Account("alice");
|
||||||
|
auto const bob = Account("bob");
|
||||||
|
auto const gw = Account{"gateway"};
|
||||||
|
auto const USD = gw["USD"];
|
||||||
|
auto const USDC = gw["USDC"];
|
||||||
|
|
||||||
|
{
|
||||||
|
Env env(*this, features);
|
||||||
|
env.fund(XRP(10000), alice, bob, gw);
|
||||||
|
env.close();
|
||||||
|
env.trust(USD(100000), alice);
|
||||||
|
env.trust(USD(100000), bob);
|
||||||
|
env.trust(USDC(100000), alice);
|
||||||
|
env.close();
|
||||||
|
env(pay(gw, alice, USD(10000)));
|
||||||
|
env(pay(gw, bob, USD(10000)));
|
||||||
|
env(pay(gw, alice, USDC(10000)));
|
||||||
|
env.close();
|
||||||
|
|
||||||
|
auto const pk = alice.pk();
|
||||||
|
auto const settleDelay = 100s;
|
||||||
|
auto const chan = channel(alice, bob, env.seq(alice));
|
||||||
|
env(create(alice, bob, USD(1000), settleDelay, pk));
|
||||||
|
env.close();
|
||||||
|
env(fund(alice, chan, USDC(1000)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
testWithFeats(FeatureBitset features)
|
testWithFeats(FeatureBitset features)
|
||||||
{
|
{
|
||||||
@@ -5085,7 +5227,9 @@ struct PayChan_test : public beast::unit_test::suite
|
|||||||
testICUsingTickets(features);
|
testICUsingTickets(features);
|
||||||
testICAutoTL(features);
|
testICAutoTL(features);
|
||||||
testICGateway(features);
|
testICGateway(features);
|
||||||
|
testICLockedRate(features);
|
||||||
testICTLFeatures(features);
|
testICTLFeatures(features);
|
||||||
|
testICMismatchFunding(features);
|
||||||
}
|
}
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
|||||||
Reference in New Issue
Block a user