rpctest: Update to use new filtered block ntfns.
This modifies the rpctest harness and its associated memwallet to make use of the new filter-based notifications since the old notifications are now deprecated. It also updates the glide.lock file to require the necessary btcrpcclient version.
This commit is contained in:
parent
6a54323258
commit
554460feda
3 changed files with 47 additions and 39 deletions
4
glide.lock
generated
4
glide.lock
generated
|
@ -1,10 +1,10 @@
|
|||
hash: ea6e6ffa31517aacb35de06b097975229096253bf658d302f2d6652fde91b3f1
|
||||
updated: 2017-01-11T15:54:00.925235328-05:00
|
||||
updated: 2017-01-27T20:06:58.5779336-06:00
|
||||
imports:
|
||||
- name: github.com/btcsuite/btclog
|
||||
version: 73889fb79bd687870312b6e40effcecffbd57d30
|
||||
- name: github.com/btcsuite/btcrpcclient
|
||||
version: 5ce0ed600997eafaed25ad4936c1d84ec6ad2b5a
|
||||
version: abcdfb702a7ca67e4a32c10be380c63216bd69fe
|
||||
- name: github.com/btcsuite/btcutil
|
||||
version: 86346b5a958c0cf94186b87855469ae991be501c
|
||||
subpackages:
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
// Copyright (c) 2016 The btcsuite developers
|
||||
// Copyright (c) 2016-2017 The btcsuite developers
|
||||
// Use of this source code is governed by an ISC
|
||||
// license that can be found in the LICENSE file.
|
||||
|
||||
|
@ -9,7 +9,6 @@ import (
|
|||
"encoding/binary"
|
||||
"fmt"
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"github.com/btcsuite/btcd/blockchain"
|
||||
"github.com/btcsuite/btcd/btcec"
|
||||
|
@ -55,8 +54,8 @@ func (u *utxo) isMature(height int32) bool {
|
|||
// used to sync up the memWallet each time a new block is connected to the main
|
||||
// chain.
|
||||
type chainUpdate struct {
|
||||
blockHash *chainhash.Hash
|
||||
blockHeight int32
|
||||
filteredTxns []*btcutil.Tx
|
||||
}
|
||||
|
||||
// undoEntry is functionally the opposite of a chainUpdate. An undoEntry is
|
||||
|
@ -179,11 +178,11 @@ func (m *memWallet) SetRPCClient(rpcClient *btcrpcclient.Client) {
|
|||
// IngestBlock is a call-back which is to be triggered each time a new block is
|
||||
// connected to the main chain. Ingesting a block updates the wallet's internal
|
||||
// utxo state based on the outputs created and destroyed within each block.
|
||||
func (m *memWallet) IngestBlock(blockHash *chainhash.Hash, height int32, t time.Time) {
|
||||
func (m *memWallet) IngestBlock(height int32, header *wire.BlockHeader, filteredTxns []*btcutil.Tx) {
|
||||
// Append this new chain update to the end of the queue of new chain
|
||||
// updates.
|
||||
m.chainMtx.Lock()
|
||||
m.chainUpdates = append(m.chainUpdates, &chainUpdate{blockHash, height})
|
||||
m.chainUpdates = append(m.chainUpdates, &chainUpdate{height, filteredTxns})
|
||||
m.chainMtx.Unlock()
|
||||
|
||||
// Launch a goroutine to signal the chainSyncer that a new update is
|
||||
|
@ -210,21 +209,16 @@ func (m *memWallet) chainSyncer() {
|
|||
m.chainUpdates = m.chainUpdates[1:]
|
||||
m.chainMtx.Unlock()
|
||||
|
||||
// Fetch the new block so we can process it shortly below.
|
||||
block, err := m.rpc.GetBlock(update.blockHash)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
// Update the latest synced height, then process each
|
||||
// transaction in the block creating and destroying utxos
|
||||
// within the wallet as a result.
|
||||
// Update the latest synced height, then process each filtered
|
||||
// transaction in the block creating and destroying utxos within
|
||||
// the wallet as a result.
|
||||
m.Lock()
|
||||
m.currentHeight = update.blockHeight
|
||||
undo := &undoEntry{
|
||||
utxosDestroyed: make(map[wire.OutPoint]*utxo),
|
||||
}
|
||||
for _, mtx := range block.Transactions {
|
||||
for _, tx := range update.filteredTxns {
|
||||
mtx := tx.MsgTx()
|
||||
isCoinbase := blockchain.IsCoinBaseTx(mtx)
|
||||
txHash := mtx.TxHash()
|
||||
m.evalOutputs(mtx.TxOut, &txHash, isCoinbase, undo)
|
||||
|
@ -293,7 +287,7 @@ func (m *memWallet) evalInputs(inputs []*wire.TxIn, undo *undoEntry) {
|
|||
// UnwindBlock is a call-back which is to be executed each time a block is
|
||||
// disconnected from the main chain. Unwinding a block undoes the effect that a
|
||||
// particular block had on the wallet's internal utxo state.
|
||||
func (m *memWallet) UnwindBlock(hash *chainhash.Hash, height int32, t time.Time) {
|
||||
func (m *memWallet) UnwindBlock(height int32, header *wire.BlockHeader) {
|
||||
m.Lock()
|
||||
defer m.Unlock()
|
||||
|
||||
|
@ -310,7 +304,9 @@ func (m *memWallet) UnwindBlock(hash *chainhash.Hash, height int32, t time.Time)
|
|||
delete(m.reorgJournal, height)
|
||||
}
|
||||
|
||||
// newAddress returns a new address from the wallet's hd key chain.
|
||||
// newAddress returns a new address from the wallet's hd key chain. It also
|
||||
// loads the address into the RPC client's transaction filter to ensure any
|
||||
// transactions that involve it are delivered via the notifications.
|
||||
func (m *memWallet) newAddress() (btcutil.Address, error) {
|
||||
index := m.hdIndex
|
||||
|
||||
|
@ -328,6 +324,11 @@ func (m *memWallet) newAddress() (btcutil.Address, error) {
|
|||
return nil, err
|
||||
}
|
||||
|
||||
err = m.rpc.LoadTxFilter(false, []btcutil.Address{addr}, nil)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
m.addrs[index] = addr
|
||||
|
||||
m.hdIndex++
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
// Copyright (c) 2016 The btcsuite developers
|
||||
// Copyright (c) 2016-2017 The btcsuite developers
|
||||
// Use of this source code is governed by an ISC
|
||||
// license that can be found in the LICENSE file.
|
||||
|
||||
|
@ -160,28 +160,28 @@ func New(activeNet *chaincfg.Params, handlers *btcrpcclient.NotificationHandlers
|
|||
handlers = &btcrpcclient.NotificationHandlers{}
|
||||
}
|
||||
|
||||
// If a handler for the OnBlockConnected/OnBlockDisconnected callback
|
||||
// has already been set, then we create a wrapper callback which
|
||||
// executes both the currently registered callback, and the mem
|
||||
// wallet's callback.
|
||||
if handlers.OnBlockConnected != nil {
|
||||
obc := handlers.OnBlockConnected
|
||||
handlers.OnBlockConnected = func(hash *chainhash.Hash, height int32, t time.Time) {
|
||||
wallet.IngestBlock(hash, height, t)
|
||||
obc(hash, height, t)
|
||||
// If a handler for the OnFilteredBlock{Connected,Disconnected} callback
|
||||
// callback has already been set, then create a wrapper callback which
|
||||
// executes both the currently registered callback and the mem wallet's
|
||||
// callback.
|
||||
if handlers.OnFilteredBlockConnected != nil {
|
||||
obc := handlers.OnFilteredBlockConnected
|
||||
handlers.OnFilteredBlockConnected = func(height int32, header *wire.BlockHeader, filteredTxns []*btcutil.Tx) {
|
||||
wallet.IngestBlock(height, header, filteredTxns)
|
||||
obc(height, header, filteredTxns)
|
||||
}
|
||||
} else {
|
||||
// Otherwise, we can claim the callback ourselves.
|
||||
handlers.OnBlockConnected = wallet.IngestBlock
|
||||
handlers.OnFilteredBlockConnected = wallet.IngestBlock
|
||||
}
|
||||
if handlers.OnBlockDisconnected != nil {
|
||||
obd := handlers.OnBlockConnected
|
||||
handlers.OnBlockDisconnected = func(hash *chainhash.Hash, height int32, t time.Time) {
|
||||
wallet.UnwindBlock(hash, height, t)
|
||||
obd(hash, height, t)
|
||||
if handlers.OnFilteredBlockDisconnected != nil {
|
||||
obd := handlers.OnFilteredBlockDisconnected
|
||||
handlers.OnFilteredBlockDisconnected = func(height int32, header *wire.BlockHeader) {
|
||||
wallet.UnwindBlock(height, header)
|
||||
obd(height, header)
|
||||
}
|
||||
} else {
|
||||
handlers.OnBlockDisconnected = wallet.UnwindBlock
|
||||
handlers.OnFilteredBlockDisconnected = wallet.UnwindBlock
|
||||
}
|
||||
|
||||
h := &Harness{
|
||||
|
@ -220,8 +220,15 @@ func (h *Harness) SetUp(createTestChain bool, numMatureOutputs uint32) error {
|
|||
|
||||
h.wallet.Start()
|
||||
|
||||
// Ensure the btcd properly dispatches our registered call-back for
|
||||
// each new block. Otherwise, the memWallet won't function properly.
|
||||
// Filter transactions that pay to the coinbase associated with the
|
||||
// wallet.
|
||||
filterAddrs := []btcutil.Address{h.wallet.coinbaseAddr}
|
||||
if err := h.Node.LoadTxFilter(true, filterAddrs, nil); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
// Ensure btcd properly dispatches our registered call-back for each new
|
||||
// block. Otherwise, the memWallet won't function properly.
|
||||
if err := h.Node.NotifyBlocks(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue