3#include <xrpl/ledger/helpers/TokenHelpers.h>
4#include <xrpl/protocol/SField.h>
5#include <xrpl/protocol/jss.h>
33 for (
auto const& h : holders)
35 if (accounts.
find(h.human()) != accounts.
cend())
36 Throw<std::runtime_error>(
"Duplicate holder");
43 : env_(env), issuer_(issuer), holders_(makeHolders(arg.holders)), close_(arg.close)
59 Throw<std::runtime_error>(
"Issuer can't be holder");
73 : env_(env), issuer_(issuer), holders_(makeHolders(holders)), id_(id), close_(close)
109 Throw<std::runtime_error>(
"MPT has not been created");
110 return MPT(
"", *id_);
117 Throw<std::runtime_error>(
"MPTTester::createJV: issuer is not set");
119 jv[sfAccount] = arg.
issuer->human();
132 jv[sfTransactionType] = jss::MPTokenIssuanceCreate;
141 Throw<std::runtime_error>(
"MPT can't be reused");
162 auto authAndPay = [&](
auto const& accts,
auto const&& getAcct) {
163 for (
auto const& it : accts)
168 if (arg.
pay && arg.
pay->first.empty())
173 for (
auto const& p : arg.
pay->first)
181 authAndPay(
holders_, [](
auto const& it) {
return it.second; });
185 authAndPay(*arg.
authorize, [](
auto const& it) { return it; });
190 if (arg.
pay->first.empty())
192 authAndPay(
holders_, [](
auto const& it) {
return it.second; });
196 authAndPay(arg.
pay->first, [](
auto const& it) { return it; });
207 Throw<std::runtime_error>(
"MPTTester::destroyJV: issuer/id is not set");
208 jv[sfAccount] = arg.
issuer->human();
210 jv[sfTransactionType] = jss::MPTokenIssuanceDestroy;
219 Throw<std::runtime_error>(
"MPT has not been created");
228 auto const& it =
holders_.find(holder_);
230 Throw<std::runtime_error>(
"Holder is not found");
239 Throw<std::runtime_error>(
"MPTTester::authorizeJV: account/id is not set");
240 jv[sfAccount] = arg.
account->human();
243 jv[sfHolder] = arg.
holder->human();
244 jv[sfTransactionType] = jss::MPTokenAuthorize;
253 Throw<std::runtime_error>(
"MPT has not been created");
314 for (
auto const&
holder : holders)
325 Throw<std::runtime_error>(
"MPTTester::setJV: account and/or id is not set");
326 jv[sfAccount] = arg.
account->human();
331 [&jv]<
typename T>(T
const&
holder) {
345 jv[sfDelegate] = arg.
delegate->human();
354 jv[sfTransactionType] = jss::MPTokenIssuanceSet;
363 Throw<std::runtime_error>(
"MPT has not been created");
381 if (*arg.
flags & tfMPTLock)
383 flags |= lsfMPTLocked;
385 else if (*arg.
flags & tfMPTUnlock)
387 flags &= ~lsfMPTLocked;
395 flags |= lsfMPTCanLock;
399 flags &= ~lsfMPTCanLock;
404 flags |= lsfMPTRequireAuth;
408 flags &= ~lsfMPTRequireAuth;
413 flags |= lsfMPTCanEscrow;
417 flags &= ~lsfMPTCanEscrow;
422 flags |= lsfMPTCanClawback;
426 flags &= ~lsfMPTCanClawback;
431 flags |= lsfMPTCanTrade;
435 flags &= ~lsfMPTCanTrade;
440 flags |= lsfMPTCanTransfer;
444 flags &= ~lsfMPTCanTransfer;
463 Throw<std::runtime_error>(
"MPT has not been created");
465 if (
auto const sle =
env_.
le(key))
474 if (sle->isFieldPresent(sfDomainID))
475 return expected == sle->getFieldH256(sfDomainID);
484 [&](
SLEP const& sle) {
return expectedAmount == (*sle)[sfMPTAmount]; }, holder_);
491 [&](
SLEP const& sle) {
return expectedAmount == (*sle)[sfOutstandingAmount]; });
504 if (sle->isFieldPresent(sfMPTokenMetadata))
505 return strHex(sle->getFieldVL(sfMPTokenMetadata)) ==
strHex(metadata);
514 [&](
SLEP const& sle) ->
bool {
return sle->isFieldPresent(sfMPTokenMetadata); });
521 if (sle->isFieldPresent(sfTransferFee))
522 return sle->getFieldU16(sfTransferFee) == transferFee;
530 return forObject([&](
SLEP const& sle) ->
bool {
return sle->isFieldPresent(sfTransferFee); });
542 Throw<std::runtime_error>(
"MPT has not been created");
593 Throw<std::runtime_error>(
"MPT has not been created");
610 Throw<std::runtime_error>(
"MPT has not been created");
615operator
Asset()
const
618 Throw<std::runtime_error>(
"MPT has not been created");
626 Throw<std::runtime_error>(
"MPT has not been created");
630 return sle->getFieldU64(sfOutstandingAmount);
635 return sle->getFieldU64(sfMPTAmount);
645 [&](
SLEP const& sle) {
646 flags = sle->getFlags();
650 Throw<std::runtime_error>(
"Failed to get the flags");
bool expect(Condition const &shouldBeTrue)
Evaluate a test condition.
constexpr value_type value() const
Returns the underlying value.
Immutable cryptographic account descriptor.
std::string const & human() const
Returns the human readable public key.
std::string const & name() const
Return the name.
AccountID id() const
Returns the Account ID.
A transaction testing environment.
bool close(NetClock::time_point closeTime, std::optional< std::chrono::milliseconds > consensusDelay=std::nullopt)
Close and advance the ledger.
TER ter() const
Return the TER for the last JTx.
std::shared_ptr< SLE const > le(Account const &account) const
Return an account root.
void fund(bool setDefaultRipple, STAmount const &amount, Account const &account)
std::uint32_t seq(Account const &account) const
Returns the next sequence number on account.
beast::unit_test::suite & test
void require(Args const &... args)
Check a set of requirements.
std::shared_ptr< OpenView const > current() const
Returns the current ledger.
std::unordered_map< std::string, Account > const holders_
MPTTester(Env &env, Account const &issuer, MPTInit const &constr={})
bool forObject(std::function< bool(SLEP const &sle)> const &cb, std::optional< Account > const &holder=std::nullopt) const
void set(MPTSet const &set={})
bool checkMPTokenAmount(Account const &holder, std::int64_t expectedAmount) const
std::optional< MPTID > id_
void pay(Account const &src, Account const &dest, std::int64_t amount, std::optional< TER > err=std::nullopt, std::optional< std::vector< std::string > > credentials=std::nullopt)
Account const & holder(std::string const &h) const
void create(MPTCreate const &arg=MPTCreate{})
bool isTransferFeePresent() const
bool checkMetadata(std::string const &metadata) const
bool checkFlags(uint32_t const expectedFlags, std::optional< Account > const &holder=std::nullopt) const
bool isMetadataPresent() const
MPT operator[](std::string const &name) const
void authorizeHolders(Holders const &holders)
static Json::Value authorizeJV(MPTAuthorize const &arg=MPTAuthorize{})
Account const & issuer() const
void authorize(MPTAuthorize const &arg=MPTAuthorize{})
MPTID const & issuanceID() const
static Json::Value destroyJV(MPTDestroy const &arg=MPTDestroy{})
std::int64_t getBalance(Account const &account) const
static Json::Value createJV(MPTCreate const &arg=MPTCreate{})
void claw(Account const &issuer, Account const &holder, std::int64_t amount, std::optional< TER > err=std::nullopt)
TER submit(A const &arg, Json::Value const &jv)
PrettyAmount mpt(std::int64_t amount) const
void destroy(MPTDestroy const &arg=MPTDestroy{})
bool checkTransferFee(std::uint16_t transferFee) const
static Json::Value setJV(MPTSet const &set={})
bool checkDomainID(std::optional< uint256 > expected) const
PrettyAmount operator()(std::int64_t amount) const
std::uint32_t getFlags(std::optional< Account > const &holder) const
static std::unordered_map< std::string, Account > makeHolders(std::vector< Account > const &holders)
bool checkMPTokenOutstandingAmount(std::int64_t expectedAmount) const
Converts to MPT Issue or STAmount.
MPTTester const & tester_
std::int64_t const amount_
void operator()(Env &env) const
std::optional< Account > holder_
void operator()(Env &env) const
Match the number of items in the account's owner directory.
std::function< bool()> cb_
void operator()(Env &env) const
Check a set of conditions.
Set the expected result code for a JTx The test will fail if the code doesn't match.
Keylet mptIssuance(std::uint32_t seq, AccountID const &issuer) noexcept
Keylet mptoken(MPTID const &issuanceID, AccountID const &holder) noexcept
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)
Json::Value claw(Account const &account, STAmount const &amount, std::optional< Account > const &mptHolder)
static MPTCreate makeMPTCreate(MPTInitDef const &arg)
void fund(jtx::Env &env, jtx::Account const &gw, std::vector< jtx::Account > const &accounts, std::vector< STAmount > const &amts, Fund how)
Json::Value pay(AccountID const &account, AccountID const &to, AnyAmount amount)
Create a payment.
Use hash_* containers for keys that do not need a cryptographically secure hashing algorithm.
constexpr FlagValue tmfMPTSetCanLock
constexpr FlagValue tmfMPTSetCanClawback
std::string to_string(base_uint< Bits, Tag > const &a)
std::string strHex(FwdIt begin, FwdIt end)
constexpr FlagValue tmfMPTClearCanTrade
std::string toBase58(AccountID const &v)
Convert AccountID to base58 checked string.
constexpr FlagValue tmfMPTSetCanTrade
constexpr FlagValue tmfMPTClearCanLock
constexpr FlagValue tmfMPTClearCanEscrow
STAmount multiply(STAmount const &amount, Rate const &rate)
constexpr FlagValue tmfMPTSetCanTransfer
constexpr FlagValue tmfMPTSetCanEscrow
constexpr FlagValue tmfMPTClearCanTransfer
Rate transferRate(ReadView const &view, AccountID const &issuer)
Returns IOU issuer transfer fee as Rate.
bool isTesSuccess(TER x) noexcept
constexpr FlagValue tmfMPTClearRequireAuth
constexpr FlagValue tmfMPTClearCanClawback
MPTID makeMptID(std::uint32_t sequence, AccountID const &account)
constexpr FlagValue tmfMPTSetRequireAuth
std::optional< Account > holder
std::optional< Account > account
std::optional< MPTID > id
std::optional< std::uint32_t > flags
std::optional< std::uint8_t > assetScale
std::optional< std::uint32_t > mutableFlags
std::optional< std::string > metadata
std::optional< std::uint32_t > flags
std::optional< uint256 > domainID
std::optional< std::uint64_t > maxAmt
std::optional< Account > issuer
std::optional< std::pair< std::vector< Account >, std::uint64_t > > pay
std::optional< std::uint16_t > transferFee
std::optional< std::vector< Account > > authorize
std::optional< Account > issuer
std::optional< MPTID > id
std::uint16_t transferFee
std::optional< std::uint64_t > maxAmt
std::optional< std::uint64_t > pay
std::optional< MPTCreate > create
PrettyAmount const xrpHolders
std::optional< uint256 > domainID
std::optional< Account > account
std::optional< MPTID > id
std::optional< std::uint16_t > transferFee
std::optional< std::uint32_t > flags
std::optional< std::variant< Account, AccountID > > holder
std::optional< std::uint32_t > mutableFlags
std::optional< std::string > metadata
std::optional< Account > delegate
Represents an XRP or IOU quantity This customizes the string conversion and supports XRP conversions ...