Allow filter show_transfers by multiple arguments

- Allow show_transfers to filter by stake
- Allow combining show_transfer arguments to get a composition of
arguments specifying transfer type
- Transfer type arguments in RPC call are defaulted to true
This commit is contained in:
Doyle 2019-11-25 14:44:44 +11:00
parent f3767a5d7e
commit f218d6cf45
5 changed files with 57 additions and 31 deletions

View File

@ -205,7 +205,7 @@ namespace
const char* USAGE_CHECK_SPEND_PROOF("check_spend_proof <txid> <signature_file> [<message>]");
const char* USAGE_GET_RESERVE_PROOF("get_reserve_proof (all|<amount>) [<message>]");
const char* USAGE_CHECK_RESERVE_PROOF("check_reserve_proof <address> <signature_file> [<message>]");
const char* USAGE_SHOW_TRANSFERS("show_transfers [in|out|all|pending|failed|coinbase] [index=<N1>[,<N2>,...]] [<min_height> [<max_height>]]");
const char* USAGE_SHOW_TRANSFERS("show_transfers [in] [out] [stake] [all] [pending] [failed] [coinbase] [index=<N1>[,<N2>,...]] [<min_height> [<max_height>]]");
const char* USAGE_EXPORT_TRANSFERS("export_transfers [in|out|all|pending|failed] [index=<N1>[,<N2>,...]] [<min_height> [<max_height>]] [output=<path>]");
const char* USAGE_UNSPENT_OUTPUTS("unspent_outputs [index=<N1>[,<N2>,...]] [<min_amount> [<max_amount>]]");
const char* USAGE_RESCAN_BC("rescan_bc [hard|soft|keep_ki] [start_height=0]");
@ -2813,10 +2813,10 @@ simple_wallet::simple_wallet()
tr(R"(Show the incoming/outgoing transfers within an optional height range.
Output format:
In or Coinbase: Block Number, "block"|"in", Time, Amount, Transaction Hash, Payment ID, Subaddress Index, "-", Note
Out: Block Number, "out", Time, Amount*, Transaction Hash, Payment ID, Fee, Destinations, Input addresses**, "-", Note
Pool: "pool", "in", Time, Amount, Transaction Hash, Payment ID, Subaddress Index, "-", Note, Double Spend Note
Pending or Failed: "failed"|"pending", "out", Time, Amount*, Transaction Hash, Payment ID, Fee, Input addresses**, "-", Note
In or Coinbase: Block Number, "block"|"in", Lock, Checkpointed, Time, Amount, Transaction Hash, Payment ID, Subaddress Index, "-", Note
Out: Block Number, "out", Lock, Checkpointed, Time, Amount*, Transaction Hash, Payment ID, Fee, Destinations, Input addresses**, "-", Note
Pool: "pool", "in", Lock, Checkpointed, Time, Amount, Transaction Hash, Payment ID, Subaddress Index, "-", Note, Double Spend Note
Pending or Failed: "failed"|"pending", "out", Lock, Checkpointed, Time, Amount*, Transaction Hash, Payment ID, Fee, Input addresses**, "-", Note
* Excluding change and fee.
** Set of address indices used as inputs in this transfer.)"));
@ -8048,35 +8048,44 @@ bool simple_wallet::check_reserve_proof(const std::vector<std::string> &args)
static bool parse_get_transfers_args(std::vector<std::string>& local_args, tools::wallet2::get_transfers_args_t& args)
{
// optional in/out selector
if (local_args.size() > 0) {
while (local_args.size() > 0)
{
if (local_args[0] == "in" || local_args[0] == "incoming") {
args.out = args.pending = args.failed = false;
args.in = args.coinbase = true;
local_args.erase(local_args.begin());
}
else if (local_args[0] == "out" || local_args[0] == "outgoing") {
args.in = args.pool = args.coinbase = false;
args.out = args.stake = true;
local_args.erase(local_args.begin());
}
else if (local_args[0] == "pending") {
args.in = args.out = args.failed = args.coinbase = false;
args.pending = true;
local_args.erase(local_args.begin());
}
else if (local_args[0] == "failed") {
args.in = args.out = args.pending = args.pool = args.coinbase = false;
args.failed = true;
local_args.erase(local_args.begin());
}
else if (local_args[0] == "pool") {
args.in = args.out = args.pending = args.failed = args.coinbase = false;
args.pool = true;
local_args.erase(local_args.begin());
}
else if (local_args[0] == "coinbase") {
args.in = args.out = args.pending = args.failed = args.pool = false;
args.coinbase = true;
local_args.erase(local_args.begin());
}
else if (local_args[0] == "all" || local_args[0] == "both") {
else if (local_args[0] == "stake") {
args.stake = true;
local_args.erase(local_args.begin());
}
else if (local_args[0] == "all" || local_args[0] == "both") {
args.in = args.out = args.stake = args.pending = args.failed = args.pool = args.coinbase = true;
local_args.erase(local_args.begin());
}
else
{
break;
}
}
// subaddr_index
@ -8120,7 +8129,7 @@ static bool parse_get_transfers_args(std::vector<std::string>& local_args, tools
// mutates local_args as it parses and consumes arguments
bool simple_wallet::get_transfers(std::vector<std::string>& local_args, std::vector<tools::transfer_view>& transfers)
{
tools::wallet2::get_transfers_args_t args;
tools::wallet2::get_transfers_args_t args = {};
if (!parse_get_transfers_args(local_args, args))
{
return false;

View File

@ -6065,6 +6065,9 @@ void wallet2::get_transfers(get_transfers_args_t args, std::vector<transfer_view
args.max_height = std::min<uint64_t>(args.max_height, CRYPTONOTE_MAX_BLOCK_NUMBER);
}
int args_count = args.in + args.out + args.stake + args.pending + args.failed + args.pool + args.coinbase;
if (args_count == 0) args.in = args.out = args.stake = args.pending = args.failed = args.pool = args.coinbase = true;
std::list<std::pair<crypto::hash, tools::wallet2::payment_details>> in;
std::list<std::pair<crypto::hash, tools::wallet2::confirmed_transfer_details>> out;
std::list<std::pair<crypto::hash, tools::wallet2::unconfirmed_transfer_details>> pending_or_failed;
@ -6080,7 +6083,7 @@ void wallet2::get_transfers(get_transfers_args_t args, std::vector<transfer_view
size += in.size();
}
if (args.out)
if (args.out || args.stake)
{
get_payments_out(out, args.min_height, args.max_height, account_index, args.subaddr_indices);
size += out.size();
@ -6103,7 +6106,14 @@ void wallet2::get_transfers(get_transfers_args_t args, std::vector<transfer_view
for (const auto &i : in)
transfers.push_back(make_transfer_view(i.second.m_tx_hash, i.first, i.second));
for (const auto &o : out)
transfers.push_back(make_transfer_view(o.first, o.second));
{
bool add_entry = true;
if (args.stake && args_count == 1)
add_entry = o.second.m_pay_type == tools::pay_type::stake;
if (add_entry)
transfers.push_back(make_transfer_view(o.first, o.second));
}
for (const auto &pof : pending_or_failed)
{
bool is_failed = pof.second.m_state == tools::wallet2::unconfirmed_transfer_details::failed;

View File

@ -1013,12 +1013,13 @@ private:
struct get_transfers_args_t
{
bool in = true;
bool out = true;
bool pending = true;
bool failed = true;
bool pool = true;
bool coinbase = true;
bool in = false;
bool out = false;
bool stake = false;
bool pending = false;
bool failed = false;
bool pool = false;
bool coinbase = false;
bool filter_by_height = false;
uint64_t min_height = 0;
uint64_t max_height = CRYPTONOTE_MAX_BLOCK_NUMBER;

View File

@ -2324,12 +2324,13 @@ namespace tools
return false;
}
wallet2::get_transfers_args_t args;
wallet2::get_transfers_args_t args = {};
args.in = req.in;
args.out = req.out;
args.pending = req.pending;
args.failed = req.failed;
args.pool = req.pool;
args.stake = req.stake;
args.filter_by_height = req.filter_by_height;
args.min_height = req.min_height;
args.max_height = req.max_height;
@ -2351,7 +2352,7 @@ namespace tools
{
res.in.push_back(entry);
}
else if (entry.pay_type == tools::pay_type::out)
else if (entry.pay_type == tools::pay_type::out || entry.pay_type == tools::pay_type::stake)
{
res.out.push_back(entry);
}
@ -2377,10 +2378,11 @@ namespace tools
wallet2::get_transfers_args_t args;
args.in = req.in;
args.out = req.out;
args.stake = req.stake;
args.pending = req.pending;
args.failed = req.failed;
args.pool = req.pool;
// args.coinbase = req.coinbase;
args.coinbase = req.coinbase;
args.filter_by_height = req.filter_by_height;
args.min_height = req.min_height;
args.max_height = req.max_height;

View File

@ -1561,16 +1561,18 @@ namespace wallet_rpc
};
LOKI_RPC_DOC_INTROSPECT
// Returns a list of transfers.
// Returns a list of transfers, by default all transfer types are included. If all requested type fields are false, then all transfers will be queried.
struct COMMAND_RPC_GET_TRANSFERS
{
struct request_t
{
bool in; // (Optional) Include incoming transfers.
bool out; // (Optional) Include outgoing transfers.
bool stake; // (Optional) Include outgoing stakes.
bool pending; // (Optional) Include pending transfers.
bool failed; // (Optional) Include failed transfers.
bool pool; // (Optional) Include transfers from the daemon's transaction pool.
bool coinbase; // (Optional) Include transfers from the daemon's transaction pool.
bool filter_by_height; // (Optional) Filter transfers by block height.
uint64_t min_height; // (Optional) Minimum block height to scan for transfers, if filtering by height is enabled.
@ -1580,11 +1582,13 @@ namespace wallet_rpc
bool all_accounts; // If true, return transfers for all accounts, subaddr_indices and account_index are ignored
BEGIN_KV_SERIALIZE_MAP()
KV_SERIALIZE(in);
KV_SERIALIZE(out);
KV_SERIALIZE(pending);
KV_SERIALIZE(failed);
KV_SERIALIZE(pool);
KV_SERIALIZE_OPT(in, true);
KV_SERIALIZE_OPT(out, true);
KV_SERIALIZE_OPT(stake, true);
KV_SERIALIZE_OPT(pending, true);
KV_SERIALIZE_OPT(failed, true);
KV_SERIALIZE_OPT(pool, true);
KV_SERIALIZE_OPT(coinbase, true);
KV_SERIALIZE(filter_by_height);
KV_SERIALIZE(min_height);
KV_SERIALIZE_OPT(max_height, (uint64_t)CRYPTONOTE_MAX_BLOCK_NUMBER);