3
0
mirror of https://github.com/Qortal/altcoinj.git synced 2025-01-30 23:02:15 +00:00

Make WalletEventListener an interface with a no-op implementation. Add an onChange() method to the default implementation that is called by the others, for cases where you don't care about what specifically changed, just that a change happened.

This commit is contained in:
Mike Hearn 2011-09-18 20:09:26 +00:00
parent 6f36e96f66
commit bbe133be88
6 changed files with 96 additions and 40 deletions

View File

@ -0,0 +1,80 @@
/**
* Copyright 2011 Google Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.google.bitcoin.core;
import java.math.BigInteger;
/**
* Implementing a subclass WalletEventListener allows you to learn when the contents of the wallet changes due to
* receiving money or a block chain re-organize. Methods are called with the event listener object locked so your
* implementation does not have to be thread safe. The default method implementations simply call onChange().
*/
public abstract class AbstractWalletEventListener implements WalletEventListener {
/**
* This is called on a Peer thread when a block is received that sends some coins to you. Note that this will
* also be called when downloading the block chain as the wallet balance catches up so if you don't want that
* register the event listener after the chain is downloaded. It's safe to use methods of wallet during the
* execution of this callback.
*
* @param wallet The wallet object that received the coins/
* @param tx The transaction which sent us the coins.
* @param prevBalance Balance before the coins were received.
* @param newBalance Current balance of the wallet.
*/
public void onCoinsReceived(Wallet wallet, Transaction tx, BigInteger prevBalance, BigInteger newBalance) {
onChange();
}
/**
* This is called on a Peer thread when a block is received that triggers a block chain re-organization.<p>
*
* A re-organize means that the consensus (chain) of the network has diverged and now changed from what we
* believed it was previously. Usually this won't matter because the new consensus will include all our old
* transactions assuming we are playing by the rules. However it's theoretically possible for our balance to
* change in arbitrary ways, most likely, we could lose some money we thought we had.<p>
*
* It is safe to use methods of wallet whilst inside this callback.
*
* TODO: Finish this interface.
*/
public void onReorganize() {
onChange();
}
/**
* This is called on a Peer thread when a transaction becomes <i>dead</i>. A dead transaction is one that has
* been overridden by a double spend from the network and so will never confirm no matter how long you wait.<p>
*
* A dead transaction can occur if somebody is attacking the network, or by accident if keys are being shared.
* You can use this event handler to inform the user of the situation. A dead spend will show up in the BitCoin
* C++ client of the recipient as 0/unconfirmed forever, so if it was used to purchase something,
* the user needs to know their goods will never arrive.
*
* @param deadTx The transaction that is newly dead.
* @param replacementTx The transaction that killed it.
*/
public void onDeadTransaction(Transaction deadTx, Transaction replacementTx) {
onChange();
}
/**
* Called by the other default method implementations when something (anything) changes in the wallet.
*/
public void onChange() {
}
}

View File

@ -18,14 +18,13 @@ package com.google.bitcoin.core;
import java.math.BigInteger;
// TODO: Make this be an interface with a convenience abstract impl.
/**
* Implementing a subclass WalletEventListener allows you to learn when the contents of the wallet changes due to
* Implementing WalletEventListener allows you to learn when the contents of the wallet changes due to
* receiving money or a block chain re-organize. Methods are called with the event listener object locked so your
* implementation does not have to be thread safe. The default method implementations do nothing.
* implementation does not have to be thread safe. It may be convenient to derive from
* {@link AbstractWalletEventListener} instead.
*/
public abstract class WalletEventListener {
public interface WalletEventListener {
/**
* This is called on a Peer thread when a block is received that sends some coins to you. Note that this will
* also be called when downloading the block chain as the wallet balance catches up so if you don't want that
@ -37,8 +36,7 @@ public abstract class WalletEventListener {
* @param prevBalance Balance before the coins were received.
* @param newBalance Current balance of the wallet.
*/
public void onCoinsReceived(Wallet wallet, Transaction tx, BigInteger prevBalance, BigInteger newBalance) {
}
void onCoinsReceived(Wallet wallet, Transaction tx, BigInteger prevBalance, BigInteger newBalance);
/**
* This is called on a Peer thread when a block is received that triggers a block chain re-organization.<p>
@ -52,9 +50,7 @@ public abstract class WalletEventListener {
*
* TODO: Finish this interface.
*/
public void onReorganize() {
}
void onReorganize();
/**
* This is called on a Peer thread when a transaction becomes <i>dead</i>. A dead transaction is one that has
@ -68,6 +64,5 @@ public abstract class WalletEventListener {
* @param deadTx The transaction that is newly dead.
* @param replacementTx The transaction that killed it.
*/
public void onDeadTransaction(Transaction deadTx, Transaction replacementTx) {
}
void onDeadTransaction(Transaction deadTx, Transaction replacementTx);
}

View File

@ -16,19 +16,7 @@
package com.google.bitcoin.examples;
import com.google.bitcoin.core.Address;
import com.google.bitcoin.core.BlockChain;
import com.google.bitcoin.core.DownloadListener;
import com.google.bitcoin.core.ECKey;
import com.google.bitcoin.core.NetworkParameters;
import com.google.bitcoin.core.PeerAddress;
import com.google.bitcoin.core.PeerGroup;
import com.google.bitcoin.core.ScriptException;
import com.google.bitcoin.core.Transaction;
import com.google.bitcoin.core.TransactionInput;
import com.google.bitcoin.core.Utils;
import com.google.bitcoin.core.Wallet;
import com.google.bitcoin.core.WalletEventListener;
import com.google.bitcoin.core.*;
import com.google.bitcoin.store.BlockStore;
import com.google.bitcoin.store.BoundedOverheadBlockStore;
@ -94,7 +82,7 @@ public class PingService {
peerGroup.start();
// We want to know when the balance changes.
wallet.addEventListener(new WalletEventListener() {
wallet.addEventListener(new AbstractWalletEventListener() {
@Override
public void onCoinsReceived(Wallet w, Transaction tx, BigInteger prevBalance, BigInteger newBalance) {
// Running on a peer thread.

View File

@ -16,14 +16,7 @@
package com.google.bitcoin.examples;
import com.google.bitcoin.core.BlockChain;
import com.google.bitcoin.core.DownloadListener;
import com.google.bitcoin.core.NetworkParameters;
import com.google.bitcoin.core.PeerAddress;
import com.google.bitcoin.core.PeerGroup;
import com.google.bitcoin.core.Transaction;
import com.google.bitcoin.core.Wallet;
import com.google.bitcoin.core.WalletEventListener;
import com.google.bitcoin.core.*;
import com.google.bitcoin.store.BlockStore;
import com.google.bitcoin.store.MemoryBlockStore;
@ -49,7 +42,7 @@ public class RefreshWallet {
peerGroup.addAddress(new PeerAddress(InetAddress.getLocalHost()));
peerGroup.start();
wallet.addEventListener(new WalletEventListener() {
wallet.addEventListener(new AbstractWalletEventListener() {
@Override
public void onCoinsReceived(Wallet w, Transaction tx, BigInteger prevBalance, BigInteger newBalance) {
System.out.println("\nReceived tx " + tx.getHashAsString());

View File

@ -51,7 +51,7 @@ public class ChainSplitTests {
// TODO: Change this test to not use coinbase transactions as they are special (maturity rules).
final boolean[] reorgHappened = new boolean[1];
reorgHappened[0] = false;
wallet.addEventListener(new WalletEventListener() {
wallet.addEventListener(new AbstractWalletEventListener() {
@Override
public void onReorganize() {
reorgHappened[0] = true;
@ -185,7 +185,7 @@ public class ChainSplitTests {
// double spend on the new best chain.
final boolean[] eventCalled = new boolean[1];
wallet.addEventListener(new WalletEventListener() {
wallet.addEventListener(new AbstractWalletEventListener() {
@Override
public void onDeadTransaction(Transaction deadTx, Transaction replacementTx) {
eventCalled[0] = true;
@ -225,7 +225,7 @@ public class ChainSplitTests {
final Transaction[] eventDead = new Transaction[1];
final Transaction[] eventReplacement = new Transaction[1];
wallet.addEventListener(new WalletEventListener() {
wallet.addEventListener(new AbstractWalletEventListener() {
@Override
public void onDeadTransaction(Transaction deadTx, Transaction replacementTx) {
eventDead[0] = deadTx;

View File

@ -101,7 +101,7 @@ public class WalletTest {
public void listeners() throws Exception {
final Transaction fakeTx = createFakeTx(params, Utils.toNanoCoins(1, 0), myAddress);
final boolean[] didRun = new boolean[1];
WalletEventListener listener = new WalletEventListener() {
WalletEventListener listener = new AbstractWalletEventListener() {
public void onCoinsReceived(Wallet w, Transaction tx, BigInteger prevBalance, BigInteger newBalance) {
assertTrue(prevBalance.equals(BigInteger.ZERO));
assertTrue(newBalance.equals(Utils.toNanoCoins(1, 0)));
@ -249,7 +249,7 @@ public class WalletTest {
// isn't tested because today BitCoinJ only learns about such transactions when they appear in the chain.
final Transaction[] eventDead = new Transaction[1];
final Transaction[] eventReplacement = new Transaction[1];
wallet.addEventListener(new WalletEventListener() {
wallet.addEventListener(new AbstractWalletEventListener() {
@Override
public void onDeadTransaction(Transaction deadTx, Transaction replacementTx) {
eventDead[0] = deadTx;