Bitcoin ABC 0.30.5
P2P Digital Currency
transactionrecord.cpp
Go to the documentation of this file.
1// Copyright (c) 2011-2016 The Bitcoin Core developers
2// Distributed under the MIT software license, see the accompanying
3// file COPYING or http://www.opensource.org/licenses/mit-license.php.
4
6
7#include <cashaddrenc.h>
8#include <chain.h> // For MAX_BLOCK_TIME_GAP
9#include <chainparams.h> // For Params()
10#include <interfaces/wallet.h>
11#include <key_io.h>
12#include <wallet/ismine.h>
13
14#include <QDateTime>
15
16#include <cstdint>
17#include <variant>
18
23 // There are currently no cases where we hide transactions, but we may want
24 // to use this in the future for things like RBF.
25 return true;
26}
27
31QList<TransactionRecord>
33 QList<TransactionRecord> parts;
34 int64_t nTime = wtx.time;
35 Amount nCredit = wtx.credit;
36 Amount nDebit = wtx.debit;
37 Amount nNet = nCredit - nDebit;
38 const TxId &txid = wtx.tx->GetId();
39 std::map<std::string, std::string> mapValue = wtx.value_map;
40
41 if (nNet > Amount::zero() || wtx.is_coinbase) {
42 //
43 // Credit
44 //
45 for (size_t i = 0; i < wtx.tx->vout.size(); i++) {
46 const CTxOut &txout = wtx.tx->vout[i];
47 isminetype mine = wtx.txout_is_mine[i];
48 if (mine) {
49 TransactionRecord sub(txid, nTime);
50 sub.idx = i; // vout index
51 sub.credit = txout.nValue;
53 if (wtx.txout_address_is_mine[i]) {
54 // Received by Bitcoin Address
56 sub.address =
58 } else {
59 // Received by IP connection (deprecated features), or a
60 // multisignature or other non-simple transaction
62 sub.address = mapValue["from"];
63 }
64 if (wtx.is_coinbase) {
65 // Generated
67 }
68
69 parts.append(sub);
70 }
71 }
72 } else {
73 bool involvesWatchAddress = false;
74 isminetype fAllFromMe = ISMINE_SPENDABLE;
75 for (const isminetype mine : wtx.txin_is_mine) {
76 if (mine & ISMINE_WATCH_ONLY) {
78 }
79 if (fAllFromMe > mine) {
80 fAllFromMe = mine;
81 }
82 }
83
85 for (const isminetype mine : wtx.txout_is_mine) {
86 if (mine & ISMINE_WATCH_ONLY) {
88 }
89 if (fAllToMe > mine) {
90 fAllToMe = mine;
91 }
92 }
93
94 if (fAllFromMe && fAllToMe) {
95 // Payment to self
96 std::string address;
97 for (auto it = wtx.txout_address.begin();
98 it != wtx.txout_address.end(); ++it) {
99 if (it != wtx.txout_address.begin()) {
100 address += ", ";
101 }
102 address += EncodeCashAddr(*it, Params());
103 }
104 Amount nChange = wtx.change;
105 parts.append(TransactionRecord(
107 -(nDebit - nChange), nCredit - nChange));
108
109 // maybe pass to TransactionRecord as constructor argument
110 parts.last().involvesWatchAddress = involvesWatchAddress;
111 } else if (fAllFromMe) {
112 //
113 // Debit
114 //
115 Amount nTxFee = nDebit - wtx.tx->GetValueOut();
116
117 for (size_t nOut = 0; nOut < wtx.tx->vout.size(); nOut++) {
118 const CTxOut &txout = wtx.tx->vout[nOut];
119 TransactionRecord sub(txid, nTime);
120 sub.idx = nOut;
122
123 if (wtx.txout_is_mine[nOut]) {
124 // Ignore parts sent to self, as this is usually the change
125 // from a transaction sent back to our own address.
126 continue;
127 }
128
129 if (!std::get_if<CNoDestination>(&wtx.txout_address[nOut])) {
130 // Sent to Bitcoin Address
132 sub.address =
133 EncodeCashAddr(wtx.txout_address[nOut], Params());
134 } else {
135 // Sent to IP, or other non-address transaction like OP_EVAL
137 sub.address = mapValue["to"];
138 }
139
140 Amount nValue = txout.nValue;
141 /* Add fee to first output */
142 if (nTxFee > Amount::zero()) {
143 nValue += nTxFee;
144 nTxFee = Amount::zero();
145 }
146 sub.debit = -1 * nValue;
147
148 parts.append(sub);
149 }
150 } else {
151 //
152 // Mixed debit transaction, can't break down payees
153 //
154 parts.append(TransactionRecord(txid, nTime,
155 TransactionRecord::Other, "", nNet,
156 Amount::zero()));
157 parts.last().involvesWatchAddress = involvesWatchAddress;
158 }
159 }
160
161 return parts;
162}
163
165 const BlockHash &block_hash, int numBlocks,
166 int64_t block_time) {
167 // Determine transaction status
168
169 // Sort order, unrecorded transactions sort to the top
170 status.sortKey = strprintf("%010d-%01d-%010u-%03d", wtx.block_height,
171 wtx.is_coinbase ? 1 : 0, wtx.time_received, idx);
174 status.m_cur_block_hash = block_hash;
175
177 // For generated transactions, determine maturity
178 if (wtx.blocks_to_maturity > 0) {
180
181 if (wtx.is_in_main_chain) {
183 } else {
185 }
186 } else {
188 }
189 } else {
190 if (status.depth < 0) {
192 } else if (status.depth == 0) {
194 if (wtx.is_abandoned) {
196 }
199 } else {
201 }
202 }
203}
204
206 assert(!block_hash.IsNull());
207 return status.m_cur_block_hash != block_hash;
208}
209
211 return QString::fromStdString(txid.ToString());
212}
213
215 return idx;
216}
std::string EncodeCashAddr(const CTxDestination &dst, const CChainParams &params)
Definition: cashaddrenc.cpp:90
const CChainParams & Params()
Return the currently selected parameters.
Definition: chainparams.cpp:19
An output of a transaction.
Definition: transaction.h:128
Amount nValue
Definition: transaction.h:130
UI model for a transaction.
int idx
Subtransaction index, for sort key.
static QList< TransactionRecord > decomposeTransaction(const interfaces::WalletTx &wtx)
Decompose CWallet transaction to model transaction records.
static const int RecommendedNumConfirmations
Number of confirmation recommended for accepting a transaction.
static bool showTransaction()
Decompose CWallet transaction to model transaction records.
TransactionStatus status
Status: can change with block chain update.
int getOutputIndex() const
Return the output index of the subtransaction
void updateStatus(const interfaces::WalletTxStatus &wtx, const BlockHash &block_hash, int numBlocks, int64_t block_time)
Update status from core wallet tx.
bool statusUpdateNeeded(const BlockHash &block_hash) const
Return whether a status update is needed.
QString getTxID() const
Return the unique identifier for this transaction (part)
bool involvesWatchAddress
Whether the transaction was sent/received with a watch-only address.
bool countsForBalance
Transaction counts towards available balance.
BlockHash m_cur_block_hash
Current block hash (to know whether cached status is still valid)
@ Confirmed
Have 6 or more confirmations (normal tx) or fully mature (mined tx)
@ Unconfirmed
Normal (sent/received) transactions.
@ Immature
Generated (mined) transactions.
@ Confirming
Confirmed, but waiting for the recommended number of confirmations.
@ NotAccepted
Mined but not accepted.
@ Conflicted
Conflicts with other transaction or mempool.
@ Abandoned
Abandoned from the wallet.
std::string sortKey
Sorting key based on status.
std::string ToString() const
Definition: uint256.h:80
bool IsNull() const
Definition: uint256.h:32
isminetype
IsMine() return codes.
Definition: ismine.h:18
@ ISMINE_SPENDABLE
Definition: ismine.h:21
@ ISMINE_WATCH_ONLY
Definition: ismine.h:20
Definition: amount.h:19
static constexpr Amount zero() noexcept
Definition: amount.h:32
A BlockHash is a unqiue identifier for a block.
Definition: blockhash.h:13
A TxId is the identifier of a transaction.
Definition: txid.h:14
std::vector< CTxDestination > txout_address
Definition: wallet.h:372
std::vector< isminetype > txout_is_mine
Definition: wallet.h:371
CTransactionRef tx
Definition: wallet.h:369
std::map< std::string, std::string > value_map
Definition: wallet.h:378
std::vector< isminetype > txout_address_is_mine
Definition: wallet.h:373
std::vector< isminetype > txin_is_mine
Definition: wallet.h:370
Updated transaction status.
Definition: wallet.h:383
unsigned int time_received
Definition: wallet.h:387
#define strprintf
Format arguments and return the string or write to given std::ostream (see tinyformat::format doc for...
Definition: tinyformat.h:1202
assert(!tx.IsCoinBase())