wallet: only request spend notification for our outputs

We would previously request spend notifications for all transaction
outputs, leading to irrelevant transactions being found in the wallet's
transaction store.
This commit is contained in:
Wilmer Paulino 2020-08-25 11:35:49 -07:00
parent ca24ed58cf
commit 682bd8d33e
No known key found for this signature in database
GPG key ID: 6DF57B9F9514972F

View file

@ -3447,7 +3447,35 @@ func (w *Wallet) reliablyPublishTransaction(tx *wire.MsgTx,
if err != nil {
return nil, err
}
// Along the way, we'll extract our relevant destination addresses from
// the transaction.
var ourAddrs []btcutil.Address
err = walletdb.Update(w.db, func(dbTx walletdb.ReadWriteTx) error {
txmgrNs := dbTx.ReadWriteBucket(wtxmgrNamespaceKey)
for _, txOut := range tx.TxOut {
_, addrs, _, err := txscript.ExtractPkScriptAddrs(
txOut.PkScript, w.chainParams,
)
if err != nil {
// Non-standard outputs can safely be skipped because
// they're not supported by the wallet.
continue
}
for _, addr := range addrs {
// Skip any addresses which are not relevant to
// us.
_, err := w.Manager.Address(txmgrNs, addr)
if waddrmgr.IsError(err, waddrmgr.ErrAddressNotFound) {
continue
}
if err != nil {
return err
}
ourAddrs = append(ourAddrs, addr)
}
}
if err := w.addRelevantTx(dbTx, txRec, nil); err != nil {
return err
}
@ -3459,7 +3487,6 @@ func (w *Wallet) reliablyPublishTransaction(tx *wire.MsgTx,
// If there is a label we should write, get the namespace key
// and record it in the tx store.
txmgrNs := dbTx.ReadWriteBucket(wtxmgrNamespaceKey)
return w.TxStore.PutTxLabel(txmgrNs, tx.TxHash(), label)
})
if err != nil {
@ -3469,27 +3496,8 @@ func (w *Wallet) reliablyPublishTransaction(tx *wire.MsgTx,
// We'll also ask to be notified of the transaction once it confirms
// on-chain. This is done outside of the database transaction to prevent
// backend interaction within it.
//
// NOTE: In some cases, it's possible that the transaction to be
// broadcast is not directly relevant to the user's wallet, e.g.,
// multisig. In either case, we'll still ask to be notified of when it
// confirms to maintain consistency.
//
// TODO(wilmer): import script as external if the address does not
// belong to the wallet to handle confs during restarts?
for _, txOut := range tx.TxOut {
_, addrs, _, err := txscript.ExtractPkScriptAddrs(
txOut.PkScript, w.chainParams,
)
if err != nil {
// Non-standard outputs can safely be skipped because
// they're not supported by the wallet.
continue
}
if err := chainClient.NotifyReceived(addrs); err != nil {
return nil, err
}
if err := chainClient.NotifyReceived(ourAddrs); err != nil {
return nil, err
}
return w.publishTransaction(tx)