Merge pull request #1537
c2135082
simplewallet: add a show_transfer <txid> command (moneromooo-monero)19c4041d
wallet_rpc_server: new RPC call to get a transfer by txid (moneromooo-monero)
This commit is contained in:
commit
59021496d8
|
@ -586,6 +586,7 @@ simple_wallet::simple_wallet()
|
||||||
m_cmd_binder.set_handler("import_key_images", boost::bind(&simple_wallet::import_key_images, this, _1), tr("Import signed key images list and verify their spent status"));
|
m_cmd_binder.set_handler("import_key_images", boost::bind(&simple_wallet::import_key_images, this, _1), tr("Import signed key images list and verify their spent status"));
|
||||||
m_cmd_binder.set_handler("export_outputs", boost::bind(&simple_wallet::export_outputs, this, _1), tr("Export a set of outputs owned by this wallet"));
|
m_cmd_binder.set_handler("export_outputs", boost::bind(&simple_wallet::export_outputs, this, _1), tr("Export a set of outputs owned by this wallet"));
|
||||||
m_cmd_binder.set_handler("import_outputs", boost::bind(&simple_wallet::import_outputs, this, _1), tr("Import set of outputs owned by this wallet"));
|
m_cmd_binder.set_handler("import_outputs", boost::bind(&simple_wallet::import_outputs, this, _1), tr("Import set of outputs owned by this wallet"));
|
||||||
|
m_cmd_binder.set_handler("show_transfer", boost::bind(&simple_wallet::show_transfer, this, _1), tr("Show information about a transfer to/from this address"));
|
||||||
m_cmd_binder.set_handler("help", boost::bind(&simple_wallet::help, this, _1), tr("Show this help"));
|
m_cmd_binder.set_handler("help", boost::bind(&simple_wallet::help, this, _1), tr("Show this help"));
|
||||||
}
|
}
|
||||||
//----------------------------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------------------------
|
||||||
|
@ -3998,6 +3999,128 @@ bool simple_wallet::import_outputs(const std::vector<std::string> &args)
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
//----------------------------------------------------------------------------------------------------
|
//----------------------------------------------------------------------------------------------------
|
||||||
|
bool simple_wallet::show_transfer(const std::vector<std::string> &args)
|
||||||
|
{
|
||||||
|
if (args.size() != 1)
|
||||||
|
{
|
||||||
|
fail_msg_writer() << tr("usage: show_transfer <txid>");
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
cryptonote::blobdata txid_data;
|
||||||
|
if(!epee::string_tools::parse_hexstr_to_binbuff(args.front(), txid_data))
|
||||||
|
{
|
||||||
|
fail_msg_writer() << tr("failed to parse txid");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
crypto::hash txid = *reinterpret_cast<const crypto::hash*>(txid_data.data());
|
||||||
|
|
||||||
|
std::list<std::pair<crypto::hash, tools::wallet2::payment_details>> payments;
|
||||||
|
m_wallet->get_payments(payments, 0);
|
||||||
|
for (std::list<std::pair<crypto::hash, tools::wallet2::payment_details>>::const_iterator i = payments.begin(); i != payments.end(); ++i) {
|
||||||
|
const tools::wallet2::payment_details &pd = i->second;
|
||||||
|
if (pd.m_tx_hash == txid) {
|
||||||
|
std::string payment_id = string_tools::pod_to_hex(i->first);
|
||||||
|
if (payment_id.substr(16).find_first_not_of('0') == std::string::npos)
|
||||||
|
payment_id = payment_id.substr(0,16);
|
||||||
|
success_msg_writer() << "Incoming transaction found";
|
||||||
|
success_msg_writer() << "txid: " << txid;
|
||||||
|
success_msg_writer() << "Height: " << pd.m_block_height;
|
||||||
|
success_msg_writer() << "Timestamp: " << get_human_readable_timestamp(pd.m_timestamp);
|
||||||
|
success_msg_writer() << "Amount: " << print_money(pd.m_amount);
|
||||||
|
success_msg_writer() << "Payment ID: " << payment_id;
|
||||||
|
success_msg_writer() << "Note: " << m_wallet->get_tx_note(txid);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
std::list<std::pair<crypto::hash, tools::wallet2::confirmed_transfer_details>> payments_out;
|
||||||
|
m_wallet->get_payments_out(payments_out, 0);
|
||||||
|
for (std::list<std::pair<crypto::hash, tools::wallet2::confirmed_transfer_details>>::const_iterator i = payments_out.begin(); i != payments_out.end(); ++i) {
|
||||||
|
if (i->first == txid)
|
||||||
|
{
|
||||||
|
const tools::wallet2::confirmed_transfer_details &pd = i->second;
|
||||||
|
uint64_t change = pd.m_change == (uint64_t)-1 ? 0 : pd.m_change; // change may not be known
|
||||||
|
uint64_t fee = pd.m_amount_in - pd.m_amount_out;
|
||||||
|
std::string dests;
|
||||||
|
for (const auto &d: pd.m_dests) {
|
||||||
|
if (!dests.empty())
|
||||||
|
dests += ", ";
|
||||||
|
dests += get_account_address_as_str(m_wallet->testnet(), d.addr) + ": " + print_money(d.amount);
|
||||||
|
}
|
||||||
|
std::string payment_id = string_tools::pod_to_hex(i->second.m_payment_id);
|
||||||
|
if (payment_id.substr(16).find_first_not_of('0') == std::string::npos)
|
||||||
|
payment_id = payment_id.substr(0,16);
|
||||||
|
success_msg_writer() << "Outgoing transaction found";
|
||||||
|
success_msg_writer() << "txid: " << txid;
|
||||||
|
success_msg_writer() << "Height: " << pd.m_block_height;
|
||||||
|
success_msg_writer() << "Timestamp: " << get_human_readable_timestamp(pd.m_timestamp);
|
||||||
|
success_msg_writer() << "Amount: " << print_money(pd.m_amount_in - change - fee);
|
||||||
|
success_msg_writer() << "Payment ID: " << payment_id;
|
||||||
|
success_msg_writer() << "Change: " << print_money(change);
|
||||||
|
success_msg_writer() << "Fee: " << print_money(fee);
|
||||||
|
success_msg_writer() << "Destinations: " << dests;
|
||||||
|
success_msg_writer() << "Note: " << m_wallet->get_tx_note(txid);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
m_wallet->update_pool_state();
|
||||||
|
std::list<std::pair<crypto::hash, tools::wallet2::payment_details>> pool_payments;
|
||||||
|
m_wallet->get_unconfirmed_payments(pool_payments);
|
||||||
|
for (std::list<std::pair<crypto::hash, tools::wallet2::payment_details>>::const_iterator i = pool_payments.begin(); i != pool_payments.end(); ++i) {
|
||||||
|
const tools::wallet2::payment_details &pd = i->second;
|
||||||
|
if (pd.m_tx_hash == txid)
|
||||||
|
{
|
||||||
|
std::string payment_id = string_tools::pod_to_hex(i->first);
|
||||||
|
if (payment_id.substr(16).find_first_not_of('0') == std::string::npos)
|
||||||
|
payment_id = payment_id.substr(0,16);
|
||||||
|
success_msg_writer() << "Unconfirmed incoming transaction found in the txpool";
|
||||||
|
success_msg_writer() << "txid: " << txid;
|
||||||
|
success_msg_writer() << "Timestamp: " << get_human_readable_timestamp(pd.m_timestamp);
|
||||||
|
success_msg_writer() << "Amount: " << print_money(pd.m_amount);
|
||||||
|
success_msg_writer() << "Payment ID: " << payment_id;
|
||||||
|
success_msg_writer() << "Note: " << m_wallet->get_tx_note(txid);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (...)
|
||||||
|
{
|
||||||
|
fail_msg_writer() << "Failed to get pool state";
|
||||||
|
}
|
||||||
|
|
||||||
|
std::list<std::pair<crypto::hash, tools::wallet2::unconfirmed_transfer_details>> upayments;
|
||||||
|
m_wallet->get_unconfirmed_payments_out(upayments);
|
||||||
|
for (std::list<std::pair<crypto::hash, tools::wallet2::unconfirmed_transfer_details>>::const_iterator i = upayments.begin(); i != upayments.end(); ++i) {
|
||||||
|
if (i->first == txid)
|
||||||
|
{
|
||||||
|
const tools::wallet2::unconfirmed_transfer_details &pd = i->second;
|
||||||
|
uint64_t amount = pd.m_amount_in;
|
||||||
|
uint64_t fee = amount - pd.m_amount_out;
|
||||||
|
std::string payment_id = string_tools::pod_to_hex(i->second.m_payment_id);
|
||||||
|
if (payment_id.substr(16).find_first_not_of('0') == std::string::npos)
|
||||||
|
payment_id = payment_id.substr(0,16);
|
||||||
|
bool is_failed = pd.m_state == tools::wallet2::unconfirmed_transfer_details::failed;
|
||||||
|
|
||||||
|
success_msg_writer() << (is_failed ? "Failed" : "Pending") << " outgoing transaction found";
|
||||||
|
success_msg_writer() << "txid: " << txid;
|
||||||
|
success_msg_writer() << "Timestamp: " << get_human_readable_timestamp(pd.m_timestamp);
|
||||||
|
success_msg_writer() << "Amount: " << print_money(amount - pd.m_change - fee);
|
||||||
|
success_msg_writer() << "Payment ID: " << payment_id;
|
||||||
|
success_msg_writer() << "Change: " << print_money(pd.m_change);
|
||||||
|
success_msg_writer() << "Fee: " << print_money(fee);
|
||||||
|
success_msg_writer() << "Note: " << m_wallet->get_tx_note(txid);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fail_msg_writer() << tr("Transaction ID not found");
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
//----------------------------------------------------------------------------------------------------
|
||||||
bool simple_wallet::process_command(const std::vector<std::string> &args)
|
bool simple_wallet::process_command(const std::vector<std::string> &args)
|
||||||
{
|
{
|
||||||
return m_cmd_binder.process_command_vec(args);
|
return m_cmd_binder.process_command_vec(args);
|
||||||
|
|
|
@ -157,6 +157,7 @@ namespace cryptonote
|
||||||
bool import_key_images(const std::vector<std::string> &args);
|
bool import_key_images(const std::vector<std::string> &args);
|
||||||
bool export_outputs(const std::vector<std::string> &args);
|
bool export_outputs(const std::vector<std::string> &args);
|
||||||
bool import_outputs(const std::vector<std::string> &args);
|
bool import_outputs(const std::vector<std::string> &args);
|
||||||
|
bool show_transfer(const std::vector<std::string> &args);
|
||||||
|
|
||||||
uint64_t get_daemon_blockchain_height(std::string& err);
|
uint64_t get_daemon_blockchain_height(std::string& err);
|
||||||
bool try_connect_to_daemon(bool silent = false);
|
bool try_connect_to_daemon(bool silent = false);
|
||||||
|
|
|
@ -201,6 +201,73 @@ namespace tools
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
//------------------------------------------------------------------------------------------------------------------------------
|
//------------------------------------------------------------------------------------------------------------------------------
|
||||||
|
void wallet_rpc_server::fill_transfer_entry(tools::wallet_rpc::transfer_entry &entry, const crypto::hash &txid, const crypto::hash &payment_id, const tools::wallet2::payment_details &pd)
|
||||||
|
{
|
||||||
|
entry.txid = string_tools::pod_to_hex(pd.m_tx_hash);
|
||||||
|
entry.payment_id = string_tools::pod_to_hex(payment_id);
|
||||||
|
if (entry.payment_id.substr(16).find_first_not_of('0') == std::string::npos)
|
||||||
|
entry.payment_id = entry.payment_id.substr(0,16);
|
||||||
|
entry.height = pd.m_block_height;
|
||||||
|
entry.timestamp = pd.m_timestamp;
|
||||||
|
entry.amount = pd.m_amount;
|
||||||
|
entry.fee = 0; // TODO
|
||||||
|
entry.note = m_wallet.get_tx_note(pd.m_tx_hash);
|
||||||
|
entry.type = "in";
|
||||||
|
}
|
||||||
|
//------------------------------------------------------------------------------------------------------------------------------
|
||||||
|
void wallet_rpc_server::fill_transfer_entry(tools::wallet_rpc::transfer_entry &entry, const crypto::hash &txid, const tools::wallet2::confirmed_transfer_details &pd)
|
||||||
|
{
|
||||||
|
entry.txid = string_tools::pod_to_hex(txid);
|
||||||
|
entry.payment_id = string_tools::pod_to_hex(pd.m_payment_id);
|
||||||
|
if (entry.payment_id.substr(16).find_first_not_of('0') == std::string::npos)
|
||||||
|
entry.payment_id = entry.payment_id.substr(0,16);
|
||||||
|
entry.height = pd.m_block_height;
|
||||||
|
entry.timestamp = pd.m_timestamp;
|
||||||
|
entry.fee = pd.m_amount_in - pd.m_amount_out;
|
||||||
|
uint64_t change = pd.m_change == (uint64_t)-1 ? 0 : pd.m_change; // change may not be known
|
||||||
|
entry.amount = pd.m_amount_in - change - entry.fee;
|
||||||
|
entry.note = m_wallet.get_tx_note(txid);
|
||||||
|
|
||||||
|
for (const auto &d: pd.m_dests) {
|
||||||
|
entry.destinations.push_back(wallet_rpc::transfer_destination());
|
||||||
|
wallet_rpc::transfer_destination &td = entry.destinations.back();
|
||||||
|
td.amount = d.amount;
|
||||||
|
td.address = get_account_address_as_str(m_wallet.testnet(), d.addr);
|
||||||
|
}
|
||||||
|
|
||||||
|
entry.type = "out";
|
||||||
|
}
|
||||||
|
//------------------------------------------------------------------------------------------------------------------------------
|
||||||
|
void wallet_rpc_server::fill_transfer_entry(tools::wallet_rpc::transfer_entry &entry, const crypto::hash &txid, const tools::wallet2::unconfirmed_transfer_details &pd)
|
||||||
|
{
|
||||||
|
bool is_failed = pd.m_state == tools::wallet2::unconfirmed_transfer_details::failed;
|
||||||
|
entry.txid = string_tools::pod_to_hex(txid);
|
||||||
|
entry.payment_id = string_tools::pod_to_hex(pd.m_payment_id);
|
||||||
|
entry.payment_id = string_tools::pod_to_hex(pd.m_payment_id);
|
||||||
|
if (entry.payment_id.substr(16).find_first_not_of('0') == std::string::npos)
|
||||||
|
entry.payment_id = entry.payment_id.substr(0,16);
|
||||||
|
entry.height = 0;
|
||||||
|
entry.timestamp = pd.m_timestamp;
|
||||||
|
entry.fee = pd.m_amount_in - pd.m_amount_out;
|
||||||
|
entry.amount = pd.m_amount_in - pd.m_change - entry.fee;
|
||||||
|
entry.note = m_wallet.get_tx_note(txid);
|
||||||
|
entry.type = is_failed ? "failed" : "pending";
|
||||||
|
}
|
||||||
|
//------------------------------------------------------------------------------------------------------------------------------
|
||||||
|
void wallet_rpc_server::fill_transfer_entry(tools::wallet_rpc::transfer_entry &entry, const crypto::hash &payment_id, const tools::wallet2::payment_details &pd)
|
||||||
|
{
|
||||||
|
entry.txid = string_tools::pod_to_hex(pd.m_tx_hash);
|
||||||
|
entry.payment_id = string_tools::pod_to_hex(payment_id);
|
||||||
|
if (entry.payment_id.substr(16).find_first_not_of('0') == std::string::npos)
|
||||||
|
entry.payment_id = entry.payment_id.substr(0,16);
|
||||||
|
entry.height = 0;
|
||||||
|
entry.timestamp = pd.m_timestamp;
|
||||||
|
entry.amount = pd.m_amount;
|
||||||
|
entry.fee = 0; // TODO
|
||||||
|
entry.note = m_wallet.get_tx_note(pd.m_tx_hash);
|
||||||
|
entry.type = "pool";
|
||||||
|
}
|
||||||
|
//------------------------------------------------------------------------------------------------------------------------------
|
||||||
bool wallet_rpc_server::on_getbalance(const wallet_rpc::COMMAND_RPC_GET_BALANCE::request& req, wallet_rpc::COMMAND_RPC_GET_BALANCE::response& res, epee::json_rpc::error& er)
|
bool wallet_rpc_server::on_getbalance(const wallet_rpc::COMMAND_RPC_GET_BALANCE::request& req, wallet_rpc::COMMAND_RPC_GET_BALANCE::response& res, epee::json_rpc::error& er)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
|
@ -1014,19 +1081,8 @@ namespace tools
|
||||||
std::list<std::pair<crypto::hash, tools::wallet2::payment_details>> payments;
|
std::list<std::pair<crypto::hash, tools::wallet2::payment_details>> payments;
|
||||||
m_wallet.get_payments(payments, min_height, max_height);
|
m_wallet.get_payments(payments, min_height, max_height);
|
||||||
for (std::list<std::pair<crypto::hash, tools::wallet2::payment_details>>::const_iterator i = payments.begin(); i != payments.end(); ++i) {
|
for (std::list<std::pair<crypto::hash, tools::wallet2::payment_details>>::const_iterator i = payments.begin(); i != payments.end(); ++i) {
|
||||||
res.in.push_back(wallet_rpc::COMMAND_RPC_GET_TRANSFERS::entry());
|
res.in.push_back(wallet_rpc::transfer_entry());
|
||||||
wallet_rpc::COMMAND_RPC_GET_TRANSFERS::entry &entry = res.in.back();
|
fill_transfer_entry(res.in.back(), i->second.m_tx_hash, i->first, i->second);
|
||||||
const tools::wallet2::payment_details &pd = i->second;
|
|
||||||
|
|
||||||
entry.txid = string_tools::pod_to_hex(pd.m_tx_hash);
|
|
||||||
entry.payment_id = string_tools::pod_to_hex(i->first);
|
|
||||||
if (entry.payment_id.substr(16).find_first_not_of('0') == std::string::npos)
|
|
||||||
entry.payment_id = entry.payment_id.substr(0,16);
|
|
||||||
entry.height = pd.m_block_height;
|
|
||||||
entry.timestamp = pd.m_timestamp;
|
|
||||||
entry.amount = pd.m_amount;
|
|
||||||
entry.fee = 0; // TODO
|
|
||||||
entry.note = m_wallet.get_tx_note(pd.m_tx_hash);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1035,27 +1091,8 @@ namespace tools
|
||||||
std::list<std::pair<crypto::hash, tools::wallet2::confirmed_transfer_details>> payments;
|
std::list<std::pair<crypto::hash, tools::wallet2::confirmed_transfer_details>> payments;
|
||||||
m_wallet.get_payments_out(payments, min_height, max_height);
|
m_wallet.get_payments_out(payments, min_height, max_height);
|
||||||
for (std::list<std::pair<crypto::hash, tools::wallet2::confirmed_transfer_details>>::const_iterator i = payments.begin(); i != payments.end(); ++i) {
|
for (std::list<std::pair<crypto::hash, tools::wallet2::confirmed_transfer_details>>::const_iterator i = payments.begin(); i != payments.end(); ++i) {
|
||||||
res.out.push_back(wallet_rpc::COMMAND_RPC_GET_TRANSFERS::entry());
|
res.out.push_back(wallet_rpc::transfer_entry());
|
||||||
wallet_rpc::COMMAND_RPC_GET_TRANSFERS::entry &entry = res.out.back();
|
fill_transfer_entry(res.out.back(), i->first, i->second);
|
||||||
const tools::wallet2::confirmed_transfer_details &pd = i->second;
|
|
||||||
|
|
||||||
entry.txid = string_tools::pod_to_hex(i->first);
|
|
||||||
entry.payment_id = string_tools::pod_to_hex(i->second.m_payment_id);
|
|
||||||
if (entry.payment_id.substr(16).find_first_not_of('0') == std::string::npos)
|
|
||||||
entry.payment_id = entry.payment_id.substr(0,16);
|
|
||||||
entry.height = pd.m_block_height;
|
|
||||||
entry.timestamp = pd.m_timestamp;
|
|
||||||
entry.fee = pd.m_amount_in - pd.m_amount_out;
|
|
||||||
uint64_t change = pd.m_change == (uint64_t)-1 ? 0 : pd.m_change; // change may not be known
|
|
||||||
entry.amount = pd.m_amount_in - change - entry.fee;
|
|
||||||
entry.note = m_wallet.get_tx_note(i->first);
|
|
||||||
|
|
||||||
for (const auto &d: pd.m_dests) {
|
|
||||||
entry.destinations.push_back(wallet_rpc::transfer_destination());
|
|
||||||
wallet_rpc::transfer_destination &td = entry.destinations.back();
|
|
||||||
td.amount = d.amount;
|
|
||||||
td.address = get_account_address_as_str(m_wallet.testnet(), d.addr);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1067,20 +1104,9 @@ namespace tools
|
||||||
bool is_failed = pd.m_state == tools::wallet2::unconfirmed_transfer_details::failed;
|
bool is_failed = pd.m_state == tools::wallet2::unconfirmed_transfer_details::failed;
|
||||||
if (!((req.failed && is_failed) || (!is_failed && req.pending)))
|
if (!((req.failed && is_failed) || (!is_failed && req.pending)))
|
||||||
continue;
|
continue;
|
||||||
std::list<wallet_rpc::COMMAND_RPC_GET_TRANSFERS::entry> &entries = is_failed ? res.failed : res.pending;
|
std::list<wallet_rpc::transfer_entry> &entries = is_failed ? res.failed : res.pending;
|
||||||
entries.push_back(wallet_rpc::COMMAND_RPC_GET_TRANSFERS::entry());
|
entries.push_back(wallet_rpc::transfer_entry());
|
||||||
wallet_rpc::COMMAND_RPC_GET_TRANSFERS::entry &entry = entries.back();
|
fill_transfer_entry(entries.back(), i->first, i->second);
|
||||||
|
|
||||||
entry.txid = string_tools::pod_to_hex(i->first);
|
|
||||||
entry.payment_id = string_tools::pod_to_hex(i->second.m_payment_id);
|
|
||||||
entry.payment_id = string_tools::pod_to_hex(i->second.m_payment_id);
|
|
||||||
if (entry.payment_id.substr(16).find_first_not_of('0') == std::string::npos)
|
|
||||||
entry.payment_id = entry.payment_id.substr(0,16);
|
|
||||||
entry.height = 0;
|
|
||||||
entry.timestamp = pd.m_timestamp;
|
|
||||||
entry.fee = pd.m_amount_in - pd.m_amount_out;
|
|
||||||
entry.amount = pd.m_amount_in - pd.m_change - entry.fee;
|
|
||||||
entry.note = m_wallet.get_tx_note(i->first);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1091,25 +1117,90 @@ namespace tools
|
||||||
std::list<std::pair<crypto::hash, tools::wallet2::payment_details>> payments;
|
std::list<std::pair<crypto::hash, tools::wallet2::payment_details>> payments;
|
||||||
m_wallet.get_unconfirmed_payments(payments);
|
m_wallet.get_unconfirmed_payments(payments);
|
||||||
for (std::list<std::pair<crypto::hash, tools::wallet2::payment_details>>::const_iterator i = payments.begin(); i != payments.end(); ++i) {
|
for (std::list<std::pair<crypto::hash, tools::wallet2::payment_details>>::const_iterator i = payments.begin(); i != payments.end(); ++i) {
|
||||||
res.pool.push_back(wallet_rpc::COMMAND_RPC_GET_TRANSFERS::entry());
|
res.pool.push_back(wallet_rpc::transfer_entry());
|
||||||
wallet_rpc::COMMAND_RPC_GET_TRANSFERS::entry &entry = res.pool.back();
|
fill_transfer_entry(res.pool.back(), i->first, i->second);
|
||||||
const tools::wallet2::payment_details &pd = i->second;
|
|
||||||
|
|
||||||
entry.txid = string_tools::pod_to_hex(pd.m_tx_hash);
|
|
||||||
entry.payment_id = string_tools::pod_to_hex(i->first);
|
|
||||||
if (entry.payment_id.substr(16).find_first_not_of('0') == std::string::npos)
|
|
||||||
entry.payment_id = entry.payment_id.substr(0,16);
|
|
||||||
entry.height = 0;
|
|
||||||
entry.timestamp = pd.m_timestamp;
|
|
||||||
entry.amount = pd.m_amount;
|
|
||||||
entry.fee = 0; // TODO
|
|
||||||
entry.note = m_wallet.get_tx_note(pd.m_tx_hash);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
//------------------------------------------------------------------------------------------------------------------------------
|
//------------------------------------------------------------------------------------------------------------------------------
|
||||||
|
bool wallet_rpc_server::on_get_transfer_by_txid(const wallet_rpc::COMMAND_RPC_GET_TRANSFER_BY_TXID::request& req, wallet_rpc::COMMAND_RPC_GET_TRANSFER_BY_TXID::response& res, epee::json_rpc::error& er)
|
||||||
|
{
|
||||||
|
if (m_wallet.restricted())
|
||||||
|
{
|
||||||
|
er.code = WALLET_RPC_ERROR_CODE_DENIED;
|
||||||
|
er.message = "Command unavailable in restricted mode.";
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
crypto::hash txid;
|
||||||
|
cryptonote::blobdata txid_blob;
|
||||||
|
if(!epee::string_tools::parse_hexstr_to_binbuff(req.txid, txid_blob))
|
||||||
|
{
|
||||||
|
er.code = WALLET_RPC_ERROR_CODE_WRONG_TXID;
|
||||||
|
er.message = "Transaction ID has invalid format";
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(sizeof(txid) == txid_blob.size())
|
||||||
|
{
|
||||||
|
txid = *reinterpret_cast<const crypto::hash*>(txid_blob.data());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
er.code = WALLET_RPC_ERROR_CODE_WRONG_TXID;
|
||||||
|
er.message = "Transaction ID has invalid size: " + req.txid;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::list<std::pair<crypto::hash, tools::wallet2::payment_details>> payments;
|
||||||
|
m_wallet.get_payments(payments, 0);
|
||||||
|
for (std::list<std::pair<crypto::hash, tools::wallet2::payment_details>>::const_iterator i = payments.begin(); i != payments.end(); ++i) {
|
||||||
|
if (i->first == txid)
|
||||||
|
{
|
||||||
|
fill_transfer_entry(res.transfer, i->second.m_tx_hash, i->first, i->second);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
std::list<std::pair<crypto::hash, tools::wallet2::confirmed_transfer_details>> payments_out;
|
||||||
|
m_wallet.get_payments_out(payments_out, 0);
|
||||||
|
for (std::list<std::pair<crypto::hash, tools::wallet2::confirmed_transfer_details>>::const_iterator i = payments_out.begin(); i != payments_out.end(); ++i) {
|
||||||
|
if (i->first == txid)
|
||||||
|
{
|
||||||
|
fill_transfer_entry(res.transfer, i->first, i->second);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
std::list<std::pair<crypto::hash, tools::wallet2::unconfirmed_transfer_details>> upayments;
|
||||||
|
m_wallet.get_unconfirmed_payments_out(upayments);
|
||||||
|
for (std::list<std::pair<crypto::hash, tools::wallet2::unconfirmed_transfer_details>>::const_iterator i = upayments.begin(); i != upayments.end(); ++i) {
|
||||||
|
if (i->first == txid)
|
||||||
|
{
|
||||||
|
fill_transfer_entry(res.transfer, i->first, i->second);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
m_wallet.update_pool_state();
|
||||||
|
|
||||||
|
std::list<std::pair<crypto::hash, tools::wallet2::payment_details>> pool_payments;
|
||||||
|
m_wallet.get_unconfirmed_payments(pool_payments);
|
||||||
|
for (std::list<std::pair<crypto::hash, tools::wallet2::payment_details>>::const_iterator i = pool_payments.begin(); i != pool_payments.end(); ++i) {
|
||||||
|
if (i->second.m_tx_hash == txid)
|
||||||
|
{
|
||||||
|
fill_transfer_entry(res.transfer, i->first, i->second);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
er.code = WALLET_RPC_ERROR_CODE_WRONG_TXID;
|
||||||
|
er.message = "Transaction not found.";
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
//------------------------------------------------------------------------------------------------------------------------------
|
||||||
bool wallet_rpc_server::on_export_key_images(const wallet_rpc::COMMAND_RPC_EXPORT_KEY_IMAGES::request& req, wallet_rpc::COMMAND_RPC_EXPORT_KEY_IMAGES::response& res, epee::json_rpc::error& er)
|
bool wallet_rpc_server::on_export_key_images(const wallet_rpc::COMMAND_RPC_EXPORT_KEY_IMAGES::request& req, wallet_rpc::COMMAND_RPC_EXPORT_KEY_IMAGES::response& res, epee::json_rpc::error& er)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
|
|
|
@ -78,6 +78,7 @@ namespace tools
|
||||||
MAP_JON_RPC_WE("set_tx_notes", on_set_tx_notes, wallet_rpc::COMMAND_RPC_SET_TX_NOTES)
|
MAP_JON_RPC_WE("set_tx_notes", on_set_tx_notes, wallet_rpc::COMMAND_RPC_SET_TX_NOTES)
|
||||||
MAP_JON_RPC_WE("get_tx_notes", on_get_tx_notes, wallet_rpc::COMMAND_RPC_GET_TX_NOTES)
|
MAP_JON_RPC_WE("get_tx_notes", on_get_tx_notes, wallet_rpc::COMMAND_RPC_GET_TX_NOTES)
|
||||||
MAP_JON_RPC_WE("get_transfers", on_get_transfers, wallet_rpc::COMMAND_RPC_GET_TRANSFERS)
|
MAP_JON_RPC_WE("get_transfers", on_get_transfers, wallet_rpc::COMMAND_RPC_GET_TRANSFERS)
|
||||||
|
MAP_JON_RPC_WE("get_transfer_by_txid", on_get_transfer_by_txid, wallet_rpc::COMMAND_RPC_GET_TRANSFER_BY_TXID)
|
||||||
MAP_JON_RPC_WE("sign", on_sign, wallet_rpc::COMMAND_RPC_SIGN)
|
MAP_JON_RPC_WE("sign", on_sign, wallet_rpc::COMMAND_RPC_SIGN)
|
||||||
MAP_JON_RPC_WE("verify", on_verify, wallet_rpc::COMMAND_RPC_VERIFY)
|
MAP_JON_RPC_WE("verify", on_verify, wallet_rpc::COMMAND_RPC_VERIFY)
|
||||||
MAP_JON_RPC_WE("export_key_images", on_export_key_images, wallet_rpc::COMMAND_RPC_EXPORT_KEY_IMAGES)
|
MAP_JON_RPC_WE("export_key_images", on_export_key_images, wallet_rpc::COMMAND_RPC_EXPORT_KEY_IMAGES)
|
||||||
|
@ -107,6 +108,7 @@ namespace tools
|
||||||
bool on_set_tx_notes(const wallet_rpc::COMMAND_RPC_SET_TX_NOTES::request& req, wallet_rpc::COMMAND_RPC_SET_TX_NOTES::response& res, epee::json_rpc::error& er);
|
bool on_set_tx_notes(const wallet_rpc::COMMAND_RPC_SET_TX_NOTES::request& req, wallet_rpc::COMMAND_RPC_SET_TX_NOTES::response& res, epee::json_rpc::error& er);
|
||||||
bool on_get_tx_notes(const wallet_rpc::COMMAND_RPC_GET_TX_NOTES::request& req, wallet_rpc::COMMAND_RPC_GET_TX_NOTES::response& res, epee::json_rpc::error& er);
|
bool on_get_tx_notes(const wallet_rpc::COMMAND_RPC_GET_TX_NOTES::request& req, wallet_rpc::COMMAND_RPC_GET_TX_NOTES::response& res, epee::json_rpc::error& er);
|
||||||
bool on_get_transfers(const wallet_rpc::COMMAND_RPC_GET_TRANSFERS::request& req, wallet_rpc::COMMAND_RPC_GET_TRANSFERS::response& res, epee::json_rpc::error& er);
|
bool on_get_transfers(const wallet_rpc::COMMAND_RPC_GET_TRANSFERS::request& req, wallet_rpc::COMMAND_RPC_GET_TRANSFERS::response& res, epee::json_rpc::error& er);
|
||||||
|
bool on_get_transfer_by_txid(const wallet_rpc::COMMAND_RPC_GET_TRANSFER_BY_TXID::request& req, wallet_rpc::COMMAND_RPC_GET_TRANSFER_BY_TXID::response& res, epee::json_rpc::error& er);
|
||||||
bool on_sign(const wallet_rpc::COMMAND_RPC_SIGN::request& req, wallet_rpc::COMMAND_RPC_SIGN::response& res, epee::json_rpc::error& er);
|
bool on_sign(const wallet_rpc::COMMAND_RPC_SIGN::request& req, wallet_rpc::COMMAND_RPC_SIGN::response& res, epee::json_rpc::error& er);
|
||||||
bool on_verify(const wallet_rpc::COMMAND_RPC_VERIFY::request& req, wallet_rpc::COMMAND_RPC_VERIFY::response& res, epee::json_rpc::error& er);
|
bool on_verify(const wallet_rpc::COMMAND_RPC_VERIFY::request& req, wallet_rpc::COMMAND_RPC_VERIFY::response& res, epee::json_rpc::error& er);
|
||||||
bool on_export_key_images(const wallet_rpc::COMMAND_RPC_EXPORT_KEY_IMAGES::request& req, wallet_rpc::COMMAND_RPC_EXPORT_KEY_IMAGES::response& res, epee::json_rpc::error& er);
|
bool on_export_key_images(const wallet_rpc::COMMAND_RPC_EXPORT_KEY_IMAGES::request& req, wallet_rpc::COMMAND_RPC_EXPORT_KEY_IMAGES::response& res, epee::json_rpc::error& er);
|
||||||
|
@ -117,6 +119,12 @@ namespace tools
|
||||||
//json rpc v2
|
//json rpc v2
|
||||||
bool on_query_key(const wallet_rpc::COMMAND_RPC_QUERY_KEY::request& req, wallet_rpc::COMMAND_RPC_QUERY_KEY::response& res, epee::json_rpc::error& er);
|
bool on_query_key(const wallet_rpc::COMMAND_RPC_QUERY_KEY::request& req, wallet_rpc::COMMAND_RPC_QUERY_KEY::response& res, epee::json_rpc::error& er);
|
||||||
|
|
||||||
|
// helpers
|
||||||
|
void fill_transfer_entry(tools::wallet_rpc::transfer_entry &entry, const crypto::hash &txid, const crypto::hash &payment_id, const tools::wallet2::payment_details &pd);
|
||||||
|
void fill_transfer_entry(tools::wallet_rpc::transfer_entry &entry, const crypto::hash &txid, const tools::wallet2::confirmed_transfer_details &pd);
|
||||||
|
void fill_transfer_entry(tools::wallet_rpc::transfer_entry &entry, const crypto::hash &txid, const tools::wallet2::unconfirmed_transfer_details &pd);
|
||||||
|
void fill_transfer_entry(tools::wallet_rpc::transfer_entry &entry, const crypto::hash &payment_id, const tools::wallet2::payment_details &pd);
|
||||||
|
|
||||||
wallet2& m_wallet;
|
wallet2& m_wallet;
|
||||||
std::string rpc_login_filename;
|
std::string rpc_login_filename;
|
||||||
std::atomic<bool> m_stop;
|
std::atomic<bool> m_stop;
|
||||||
|
|
|
@ -525,6 +525,31 @@ namespace wallet_rpc
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct transfer_entry
|
||||||
|
{
|
||||||
|
std::string txid;
|
||||||
|
std::string payment_id;
|
||||||
|
uint64_t height;
|
||||||
|
uint64_t timestamp;
|
||||||
|
uint64_t amount;
|
||||||
|
uint64_t fee;
|
||||||
|
std::string note;
|
||||||
|
std::list<transfer_destination> destinations;
|
||||||
|
std::string type;
|
||||||
|
|
||||||
|
BEGIN_KV_SERIALIZE_MAP()
|
||||||
|
KV_SERIALIZE(txid);
|
||||||
|
KV_SERIALIZE(payment_id);
|
||||||
|
KV_SERIALIZE(height);
|
||||||
|
KV_SERIALIZE(timestamp);
|
||||||
|
KV_SERIALIZE(amount);
|
||||||
|
KV_SERIALIZE(fee);
|
||||||
|
KV_SERIALIZE(note);
|
||||||
|
KV_SERIALIZE(destinations);
|
||||||
|
KV_SERIALIZE(type);
|
||||||
|
END_KV_SERIALIZE_MAP()
|
||||||
|
};
|
||||||
|
|
||||||
struct COMMAND_RPC_GET_TRANSFERS
|
struct COMMAND_RPC_GET_TRANSFERS
|
||||||
{
|
{
|
||||||
struct request
|
struct request
|
||||||
|
@ -551,36 +576,13 @@ namespace wallet_rpc
|
||||||
END_KV_SERIALIZE_MAP()
|
END_KV_SERIALIZE_MAP()
|
||||||
};
|
};
|
||||||
|
|
||||||
struct entry
|
|
||||||
{
|
|
||||||
std::string txid;
|
|
||||||
std::string payment_id;
|
|
||||||
uint64_t height;
|
|
||||||
uint64_t timestamp;
|
|
||||||
uint64_t amount;
|
|
||||||
uint64_t fee;
|
|
||||||
std::string note;
|
|
||||||
std::list<transfer_destination> destinations;
|
|
||||||
|
|
||||||
BEGIN_KV_SERIALIZE_MAP()
|
|
||||||
KV_SERIALIZE(txid);
|
|
||||||
KV_SERIALIZE(payment_id);
|
|
||||||
KV_SERIALIZE(height);
|
|
||||||
KV_SERIALIZE(timestamp);
|
|
||||||
KV_SERIALIZE(amount);
|
|
||||||
KV_SERIALIZE(fee);
|
|
||||||
KV_SERIALIZE(note);
|
|
||||||
KV_SERIALIZE(destinations);
|
|
||||||
END_KV_SERIALIZE_MAP()
|
|
||||||
};
|
|
||||||
|
|
||||||
struct response
|
struct response
|
||||||
{
|
{
|
||||||
std::list<entry> in;
|
std::list<transfer_entry> in;
|
||||||
std::list<entry> out;
|
std::list<transfer_entry> out;
|
||||||
std::list<entry> pending;
|
std::list<transfer_entry> pending;
|
||||||
std::list<entry> failed;
|
std::list<transfer_entry> failed;
|
||||||
std::list<entry> pool;
|
std::list<transfer_entry> pool;
|
||||||
|
|
||||||
BEGIN_KV_SERIALIZE_MAP()
|
BEGIN_KV_SERIALIZE_MAP()
|
||||||
KV_SERIALIZE(in);
|
KV_SERIALIZE(in);
|
||||||
|
@ -592,6 +594,27 @@ namespace wallet_rpc
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct COMMAND_RPC_GET_TRANSFER_BY_TXID
|
||||||
|
{
|
||||||
|
struct request
|
||||||
|
{
|
||||||
|
std::string txid;
|
||||||
|
|
||||||
|
BEGIN_KV_SERIALIZE_MAP()
|
||||||
|
KV_SERIALIZE(txid);
|
||||||
|
END_KV_SERIALIZE_MAP()
|
||||||
|
};
|
||||||
|
|
||||||
|
struct response
|
||||||
|
{
|
||||||
|
transfer_entry transfer;
|
||||||
|
|
||||||
|
BEGIN_KV_SERIALIZE_MAP()
|
||||||
|
KV_SERIALIZE(transfer);
|
||||||
|
END_KV_SERIALIZE_MAP()
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
struct COMMAND_RPC_SIGN
|
struct COMMAND_RPC_SIGN
|
||||||
{
|
{
|
||||||
struct request
|
struct request
|
||||||
|
|
Loading…
Reference in New Issue