mirror of
https://github.com/Qortal/altcoinj.git
synced 2025-01-31 15:22:16 +00:00
Merge branch 'master' of https://code.google.com/p/bitcoinj
This commit is contained in:
commit
3eb12c8e97
2
pom.xml
2
pom.xml
@ -254,6 +254,7 @@
|
|||||||
</execution>
|
</execution>
|
||||||
</executions>
|
</executions>
|
||||||
</plugin>
|
</plugin>
|
||||||
|
<!--
|
||||||
<plugin>
|
<plugin>
|
||||||
<groupId>org.codehaus.mojo</groupId>
|
<groupId>org.codehaus.mojo</groupId>
|
||||||
<artifactId>build-helper-maven-plugin</artifactId>
|
<artifactId>build-helper-maven-plugin</artifactId>
|
||||||
@ -273,6 +274,7 @@
|
|||||||
</execution>
|
</execution>
|
||||||
</executions>
|
</executions>
|
||||||
</plugin>
|
</plugin>
|
||||||
|
-->
|
||||||
|
|
||||||
</plugins>
|
</plugins>
|
||||||
</build>
|
</build>
|
||||||
|
@ -22,7 +22,7 @@ import org.slf4j.LoggerFactory;
|
|||||||
import java.io.*;
|
import java.io.*;
|
||||||
import java.math.BigInteger;
|
import java.math.BigInteger;
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
|
|
||||||
import static com.google.bitcoin.core.Utils.*;
|
import static com.google.bitcoin.core.Utils.*;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -56,15 +56,9 @@ public class Transaction extends ChildMessage implements Serializable {
|
|||||||
|
|
||||||
private long lockTime;
|
private long lockTime;
|
||||||
|
|
||||||
// This is only stored in Java serialization. It records which blocks (and their height + work) the transaction
|
// This is being migrated to appearsInHashes
|
||||||
// has been included in. For most transactions this set will have a single member. In the case of a chain split a
|
|
||||||
// transaction may appear in multiple blocks but only one of them is part of the best chain. It's not valid to
|
|
||||||
// have an identical transaction appear in two blocks in the same chain but this invariant is expensive to check,
|
|
||||||
// so it's not directly enforced anywhere.
|
|
||||||
//
|
|
||||||
// If this transaction is not stored in the wallet, appearsIn is null.
|
|
||||||
Set<StoredBlock> appearsIn;
|
Set<StoredBlock> appearsIn;
|
||||||
|
|
||||||
// Stored only in Java serialization. This is either the time the transaction was broadcast as measured from the
|
// Stored only in Java serialization. This is either the time the transaction was broadcast as measured from the
|
||||||
// local clock, or the time from the block in which it was included. Note that this can be changed by re-orgs so
|
// local clock, or the time from the block in which it was included. Note that this can be changed by re-orgs so
|
||||||
// the wallet may update this field. Old serialized transactions don't have this field, thus null is valid.
|
// the wallet may update this field. Old serialized transactions don't have this field, thus null is valid.
|
||||||
@ -78,6 +72,15 @@ public class Transaction extends ChildMessage implements Serializable {
|
|||||||
// Data about how confirmed this tx is. Serialized, may be null.
|
// Data about how confirmed this tx is. Serialized, may be null.
|
||||||
private TransactionConfidence confidence;
|
private TransactionConfidence confidence;
|
||||||
|
|
||||||
|
// This records which blocks the transaction
|
||||||
|
// has been included in. For most transactions this set will have a single member. In the case of a chain split a
|
||||||
|
// transaction may appear in multiple blocks but only one of them is part of the best chain. It's not valid to
|
||||||
|
// have an identical transaction appear in two blocks in the same chain but this invariant is expensive to check,
|
||||||
|
// so it's not directly enforced anywhere.
|
||||||
|
//
|
||||||
|
// If this transaction is not stored in the wallet, appearsInHashes is null.
|
||||||
|
Set<Sha256Hash> appearsInHashes;
|
||||||
|
|
||||||
public Transaction(NetworkParameters params) {
|
public Transaction(NetworkParameters params) {
|
||||||
super(params);
|
super(params);
|
||||||
version = 1;
|
version = 1;
|
||||||
@ -190,8 +193,21 @@ public class Transaction extends ChildMessage implements Serializable {
|
|||||||
* Returns a set of blocks which contain the transaction, or null if this transaction doesn't have that data
|
* Returns a set of blocks which contain the transaction, or null if this transaction doesn't have that data
|
||||||
* because it's not stored in the wallet or because it has never appeared in a block.
|
* because it's not stored in the wallet or because it has never appeared in a block.
|
||||||
*/
|
*/
|
||||||
public Set<StoredBlock> getAppearsIn() {
|
public Collection<Sha256Hash> getAppearsInHashes() {
|
||||||
return appearsIn;
|
if (appearsInHashes != null)
|
||||||
|
return appearsInHashes;
|
||||||
|
|
||||||
|
if (appearsIn != null) {
|
||||||
|
assert appearsInHashes == null;
|
||||||
|
log.info("Migrating a tx to appearsInHashes");
|
||||||
|
appearsInHashes = new HashSet<Sha256Hash>(appearsIn.size());
|
||||||
|
for (StoredBlock block : appearsIn) {
|
||||||
|
appearsInHashes.add(block.getHeader().getHash());
|
||||||
|
}
|
||||||
|
appearsIn = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
return appearsInHashes;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -207,31 +223,36 @@ public class Transaction extends ChildMessage implements Serializable {
|
|||||||
* used by the wallet to ensure transactions that appear on side chains are recorded properly even though the
|
* used by the wallet to ensure transactions that appear on side chains are recorded properly even though the
|
||||||
* block stores do not save the transaction data at all.<p>
|
* block stores do not save the transaction data at all.<p>
|
||||||
*
|
*
|
||||||
* If there is a re-org this will be called once for each block that was previously seen, to update which block
|
* <p>If there is a re-org this will be called once for each block that was previously seen, to update which block
|
||||||
* is the best chain. The best chain block is guaranteed to be called last. So this must be idempotent.
|
* is the best chain. The best chain block is guaranteed to be called last. So this must be idempotent.
|
||||||
*
|
*
|
||||||
|
* <p>Sets updatedAt to be the earliest valid block time where this tx was seen
|
||||||
|
*
|
||||||
* @param block The {@link StoredBlock} in which the transaction has appeared.
|
* @param block The {@link StoredBlock} in which the transaction has appeared.
|
||||||
* @param bestChain whether to set the updatedAt timestamp from the block header (only if not already set)
|
* @param bestChain whether to set the updatedAt timestamp from the block header (only if not already set)
|
||||||
*/
|
*/
|
||||||
public void setBlockAppearance(StoredBlock block, boolean bestChain) {
|
public void setBlockAppearance(StoredBlock block, boolean bestChain) {
|
||||||
if (bestChain && updatedAt == null) {
|
long blockTime = block.getHeader().getTimeSeconds() * 1000;
|
||||||
updatedAt = new Date(block.getHeader().getTimeSeconds() * 1000);
|
if (bestChain && (updatedAt == null || updatedAt.getTime() == 0 || updatedAt.getTime() > blockTime)) {
|
||||||
|
updatedAt = new Date(blockTime);
|
||||||
}
|
}
|
||||||
if (appearsIn == null) {
|
|
||||||
appearsIn = new HashSet<StoredBlock>();
|
addBlockAppearance(block.getHeader().getHash());
|
||||||
}
|
|
||||||
appearsIn.add(block);
|
|
||||||
|
|
||||||
if (bestChain) {
|
if (bestChain) {
|
||||||
if (updatedAt == null) {
|
|
||||||
updatedAt = new Date(block.getHeader().getTimeSeconds() * 1000);
|
|
||||||
}
|
|
||||||
// This can cause event listeners on TransactionConfidence to run. After this line completes, the wallets
|
// This can cause event listeners on TransactionConfidence to run. After this line completes, the wallets
|
||||||
// state may have changed!
|
// state may have changed!
|
||||||
getConfidence().setAppearedAtChainHeight(block.getHeight());
|
getConfidence().setAppearedAtChainHeight(block.getHeight());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void addBlockAppearance(final Sha256Hash blockHash) {
|
||||||
|
if (appearsInHashes == null) {
|
||||||
|
appearsInHashes = new HashSet<Sha256Hash>();
|
||||||
|
}
|
||||||
|
appearsInHashes.add(blockHash);
|
||||||
|
}
|
||||||
|
|
||||||
/** Called by the wallet once a re-org means we don't appear in the best chain anymore. */
|
/** Called by the wallet once a re-org means we don't appear in the best chain anymore. */
|
||||||
void notifyNotOnBestChain() {
|
void notifyNotOnBestChain() {
|
||||||
getConfidence().setConfidenceType(TransactionConfidence.ConfidenceType.NOT_IN_BEST_CHAIN);
|
getConfidence().setConfidenceType(TransactionConfidence.ConfidenceType.NOT_IN_BEST_CHAIN);
|
||||||
@ -324,26 +345,12 @@ public class Transaction extends ChildMessage implements Serializable {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the earliest time at which the transaction was seen (broadcast or included into the chain),
|
* Returns the earliest time at which the transaction was seen (broadcast or included into the chain),
|
||||||
* or null if that information isn't available.
|
* or the epoch if that information isn't available.
|
||||||
*/
|
*/
|
||||||
public Date getUpdateTime() {
|
public Date getUpdateTime() {
|
||||||
if (updatedAt == null) {
|
if (updatedAt == null) {
|
||||||
// Older wallets did not store this field. If we can, fill it out based on the block pointers. We might
|
// Older wallets did not store this field. Set to the epoch.
|
||||||
// "guess wrong" in the case of transactions appearing on chain forks, but this is unlikely to matter in
|
updatedAt = new Date(0);
|
||||||
// practice. Note, some patched copies of BitCoinJ store dates in this field that do not correspond to any
|
|
||||||
// block but rather broadcast time.
|
|
||||||
if (appearsIn == null || appearsIn.size() == 0) {
|
|
||||||
// Transaction came from somewhere that doesn't provide time info.
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
long earliestTimeSecs = Long.MAX_VALUE;
|
|
||||||
// We might return a time that is different to the best chain, as we don't know here which block is part
|
|
||||||
// of the active chain and which are simply inactive. We just ignore this for now.
|
|
||||||
// TODO: At some point we'll want to store storing full block headers in the wallet. Remove at that time.
|
|
||||||
for (StoredBlock b : appearsIn) {
|
|
||||||
earliestTimeSecs = Math.min(b.getHeader().getTimeSeconds(), earliestTimeSecs);
|
|
||||||
}
|
|
||||||
updatedAt = new Date(earliestTimeSecs * 1000);
|
|
||||||
}
|
}
|
||||||
return updatedAt;
|
return updatedAt;
|
||||||
}
|
}
|
||||||
|
@ -1158,10 +1158,18 @@ public class Wallet implements Serializable {
|
|||||||
//
|
//
|
||||||
// receive() has been called on the block that is triggering the re-org before this is called.
|
// receive() has been called on the block that is triggering the re-org before this is called.
|
||||||
|
|
||||||
|
List<Sha256Hash> oldBlockHashes = new ArrayList<Sha256Hash>(oldBlocks.size());
|
||||||
|
List<Sha256Hash> newBlockHashes = new ArrayList<Sha256Hash>(newBlocks.size());
|
||||||
log.info("Old part of chain (top to bottom):");
|
log.info("Old part of chain (top to bottom):");
|
||||||
for (StoredBlock b : oldBlocks) log.info(" {}", b.getHeader().getHashAsString());
|
for (StoredBlock b : oldBlocks) {
|
||||||
|
log.info(" {}", b.getHeader().getHashAsString());
|
||||||
|
oldBlockHashes.add(b.getHeader().getHash());
|
||||||
|
}
|
||||||
log.info("New part of chain (top to bottom):");
|
log.info("New part of chain (top to bottom):");
|
||||||
for (StoredBlock b : newBlocks) log.info(" {}", b.getHeader().getHashAsString());
|
for (StoredBlock b : newBlocks) {
|
||||||
|
log.info(" {}", b.getHeader().getHashAsString());
|
||||||
|
newBlockHashes.add(b.getHeader().getHash());
|
||||||
|
}
|
||||||
|
|
||||||
// Transactions that appear in the old chain segment.
|
// Transactions that appear in the old chain segment.
|
||||||
Map<Sha256Hash, Transaction> oldChainTransactions = new HashMap<Sha256Hash, Transaction>();
|
Map<Sha256Hash, Transaction> oldChainTransactions = new HashMap<Sha256Hash, Transaction>();
|
||||||
@ -1177,12 +1185,12 @@ public class Wallet implements Serializable {
|
|||||||
all.putAll(spent);
|
all.putAll(spent);
|
||||||
all.putAll(inactive);
|
all.putAll(inactive);
|
||||||
for (Transaction tx : all.values()) {
|
for (Transaction tx : all.values()) {
|
||||||
Set<StoredBlock> appearsIn = tx.getAppearsIn();
|
Collection<Sha256Hash> appearsIn = tx.getAppearsInHashes();
|
||||||
assert appearsIn != null;
|
assert appearsIn != null;
|
||||||
// If the set of blocks this transaction appears in is disjoint with one of the chain segments it means
|
// If the set of blocks this transaction appears in is disjoint with one of the chain segments it means
|
||||||
// the transaction was never incorporated by a miner into that side of the chain.
|
// the transaction was never incorporated by a miner into that side of the chain.
|
||||||
boolean inOldSection = !Collections.disjoint(appearsIn, oldBlocks);
|
boolean inOldSection = !Collections.disjoint(appearsIn, oldBlockHashes);
|
||||||
boolean inNewSection = !Collections.disjoint(appearsIn, newBlocks);
|
boolean inNewSection = !Collections.disjoint(appearsIn, newBlockHashes);
|
||||||
boolean inCommonSection = !inNewSection && !inOldSection;
|
boolean inCommonSection = !inNewSection && !inOldSection;
|
||||||
|
|
||||||
if (inCommonSection) {
|
if (inCommonSection) {
|
||||||
|
@ -16,21 +16,9 @@
|
|||||||
|
|
||||||
package com.google.bitcoin.store;
|
package com.google.bitcoin.store;
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
import java.io.OutputStream;
|
|
||||||
import java.math.BigInteger;
|
|
||||||
import java.util.Date;
|
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.Map;
|
|
||||||
|
|
||||||
import org.bitcoinj.wallet.Protos;
|
|
||||||
|
|
||||||
import com.google.bitcoin.core.AddressFormatException;
|
|
||||||
import com.google.bitcoin.core.ECKey;
|
import com.google.bitcoin.core.ECKey;
|
||||||
import com.google.bitcoin.core.NetworkParameters;
|
import com.google.bitcoin.core.NetworkParameters;
|
||||||
import com.google.bitcoin.core.Sha256Hash;
|
import com.google.bitcoin.core.Sha256Hash;
|
||||||
import com.google.bitcoin.core.StoredBlock;
|
|
||||||
import com.google.bitcoin.core.Transaction;
|
import com.google.bitcoin.core.Transaction;
|
||||||
import com.google.bitcoin.core.TransactionInput;
|
import com.google.bitcoin.core.TransactionInput;
|
||||||
import com.google.bitcoin.core.TransactionOutPoint;
|
import com.google.bitcoin.core.TransactionOutPoint;
|
||||||
@ -40,6 +28,16 @@ import com.google.bitcoin.core.WalletTransaction;
|
|||||||
import com.google.protobuf.ByteString;
|
import com.google.protobuf.ByteString;
|
||||||
import com.google.protobuf.TextFormat;
|
import com.google.protobuf.TextFormat;
|
||||||
|
|
||||||
|
import org.bitcoinj.wallet.Protos;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.io.InputStream;
|
||||||
|
import java.io.OutputStream;
|
||||||
|
import java.math.BigInteger;
|
||||||
|
import java.util.Date;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Serialize and de-serialize a wallet to a protobuf stream.
|
* Serialize and de-serialize a wallet to a protobuf stream.
|
||||||
*
|
*
|
||||||
@ -59,7 +57,7 @@ public class WalletProtobufSerializer {
|
|||||||
walletProto.writeTo(output);
|
walletProto.writeTo(output);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static String walletToText(Wallet wallet) throws IOException {
|
public static String walletToText(Wallet wallet) {
|
||||||
Protos.Wallet walletProto = walletToProto(wallet);
|
Protos.Wallet walletProto = walletToProto(wallet);
|
||||||
|
|
||||||
return TextFormat.printToString(walletProto);
|
return TextFormat.printToString(walletProto);
|
||||||
@ -128,23 +126,23 @@ public class WalletProtobufSerializer {
|
|||||||
if (spentBy != null) {
|
if (spentBy != null) {
|
||||||
outputBuilder
|
outputBuilder
|
||||||
.setSpentByTransactionHash(ByteString.copyFrom(spentBy.getParentTransaction().getHash().getBytes()))
|
.setSpentByTransactionHash(ByteString.copyFrom(spentBy.getParentTransaction().getHash().getBytes()))
|
||||||
.setSpentByTransactionIndex((int)spentBy.getParentTransaction().getInputs().indexOf(spentBy)); // FIXME
|
.setSpentByTransactionIndex(spentBy.getParentTransaction().getInputs().indexOf(spentBy));
|
||||||
}
|
}
|
||||||
txBuilder.addTransactionOutput(outputBuilder);
|
txBuilder.addTransactionOutput(outputBuilder);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Handle which blocks tx was seen in
|
// Handle which blocks tx was seen in
|
||||||
if (tx.getAppearsIn() != null) {
|
if (tx.getAppearsInHashes() != null) {
|
||||||
for (StoredBlock block : tx.getAppearsIn()) {
|
for (Sha256Hash hash : tx.getAppearsInHashes()) {
|
||||||
txBuilder.addBlockHash(ByteString.copyFrom(block.getHeader().getHash().getBytes()));
|
txBuilder.addBlockHash(ByteString.copyFrom(hash.getBytes()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return txBuilder.build();
|
return txBuilder.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Wallet readWallet(InputStream input, NetworkParameters params, BlockStore store)
|
public static Wallet readWallet(InputStream input, NetworkParameters params)
|
||||||
throws IOException, AddressFormatException, BlockStoreException {
|
throws IOException {
|
||||||
WalletProtobufSerializer serializer = new WalletProtobufSerializer();
|
WalletProtobufSerializer serializer = new WalletProtobufSerializer();
|
||||||
Protos.Wallet walletProto = Protos.Wallet.parseFrom(input);
|
Protos.Wallet walletProto = Protos.Wallet.parseFrom(input);
|
||||||
if (!params.getId().equals(walletProto.getNetworkIdentifier()))
|
if (!params.getId().equals(walletProto.getNetworkIdentifier()))
|
||||||
@ -164,7 +162,7 @@ public class WalletProtobufSerializer {
|
|||||||
|
|
||||||
// Read all transactions and create outputs
|
// Read all transactions and create outputs
|
||||||
for (Protos.Transaction txProto : walletProto.getTransactionList()) {
|
for (Protos.Transaction txProto : walletProto.getTransactionList()) {
|
||||||
serializer.readTransaction(txProto, params, store);
|
serializer.readTransaction(txProto, params);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Create transactions inputs pointing to transactions
|
// Create transactions inputs pointing to transactions
|
||||||
@ -188,8 +186,7 @@ public class WalletProtobufSerializer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private void readTransaction(Protos.Transaction txProto,
|
private void readTransaction(Protos.Transaction txProto, NetworkParameters params) {
|
||||||
NetworkParameters params, BlockStore store) throws BlockStoreException {
|
|
||||||
Transaction tx = new Transaction(params, txProto.getVersion(), new Sha256Hash(txProto.getHash().toByteArray()));
|
Transaction tx = new Transaction(params, txProto.getVersion(), new Sha256Hash(txProto.getHash().toByteArray()));
|
||||||
if (txProto.hasUpdatedAt())
|
if (txProto.hasUpdatedAt())
|
||||||
tx.setUpdateTime(new Date(txProto.getUpdatedAt()));
|
tx.setUpdateTime(new Date(txProto.getUpdatedAt()));
|
||||||
@ -207,7 +204,7 @@ public class WalletProtobufSerializer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
for (ByteString blockHash : txProto.getBlockHashList()) {
|
for (ByteString blockHash : txProto.getBlockHashList()) {
|
||||||
tx.setBlockAppearance(store.get(new Sha256Hash(blockHash.toByteArray())), false);
|
tx.addBlockAppearance(new Sha256Hash(blockHash.toByteArray()));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (txProto.hasLockTime()) {
|
if (txProto.hasLockTime()) {
|
||||||
|
@ -23,6 +23,7 @@ import org.junit.Before;
|
|||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
|
|
||||||
import java.math.BigInteger;
|
import java.math.BigInteger;
|
||||||
|
import java.util.HashSet;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import static com.google.bitcoin.core.TestUtils.createFakeBlock;
|
import static com.google.bitcoin.core.TestUtils.createFakeBlock;
|
||||||
@ -460,12 +461,10 @@ public class WalletTest {
|
|||||||
// Verify we can handle the case of older wallets in which the timestamp is null (guessed from the
|
// Verify we can handle the case of older wallets in which the timestamp is null (guessed from the
|
||||||
// block appearances list).
|
// block appearances list).
|
||||||
tx1.updatedAt = null;
|
tx1.updatedAt = null;
|
||||||
tx2.updatedAt = null;
|
tx3.updatedAt = null;
|
||||||
// Check we got them back in order.
|
// Check we got them back in order.
|
||||||
transactions = wallet.getTransactionsByTime();
|
transactions = wallet.getTransactionsByTime();
|
||||||
assertEquals(tx3, transactions.get(0));
|
assertEquals(tx2, transactions.get(0));
|
||||||
assertEquals(tx2, transactions.get(1));
|
|
||||||
assertEquals(tx1, transactions.get(2));
|
|
||||||
assertEquals(3, transactions.size());
|
assertEquals(3, transactions.size());
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -482,5 +481,18 @@ public class WalletTest {
|
|||||||
wallet.addKey(new ECKey());
|
wallet.addKey(new ECKey());
|
||||||
assertEquals(now + 60, wallet.getEarliestKeyCreationTime());
|
assertEquals(now + 60, wallet.getEarliestKeyCreationTime());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void transactionAppearsInMigration() throws Exception {
|
||||||
|
// Test migration from appearsIn to appearsInHashes
|
||||||
|
Transaction tx1 = createFakeTx(params, Utils.toNanoCoins(1, 0), myAddress);
|
||||||
|
StoredBlock b1 = createFakeBlock(params, blockStore, tx1).storedBlock;
|
||||||
|
tx1.appearsIn = new HashSet<StoredBlock>();
|
||||||
|
tx1.appearsIn.add(b1);
|
||||||
|
assertEquals(1, tx1.getAppearsInHashes().size());
|
||||||
|
assertTrue(tx1.getAppearsInHashes().contains(b1.getHeader().getHash()));
|
||||||
|
assertNull(tx1.appearsIn);
|
||||||
|
}
|
||||||
|
|
||||||
// Support for offline spending is tested in PeerGroupTest
|
// Support for offline spending is tested in PeerGroupTest
|
||||||
}
|
}
|
||||||
|
@ -3,18 +3,9 @@ package com.google.bitcoin.store;
|
|||||||
|
|
||||||
import static com.google.bitcoin.core.TestUtils.createFakeTx;
|
import static com.google.bitcoin.core.TestUtils.createFakeTx;
|
||||||
import static com.google.bitcoin.core.Utils.toNanoCoins;
|
import static com.google.bitcoin.core.Utils.toNanoCoins;
|
||||||
|
import static org.junit.Assert.*;
|
||||||
import java.io.ByteArrayInputStream;
|
|
||||||
import java.io.ByteArrayOutputStream;
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.math.BigInteger;
|
|
||||||
|
|
||||||
import org.bitcoinj.wallet.Protos;
|
|
||||||
import org.junit.Before;
|
|
||||||
import org.junit.Test;
|
|
||||||
|
|
||||||
import com.google.bitcoin.core.Address;
|
import com.google.bitcoin.core.Address;
|
||||||
import com.google.bitcoin.core.AddressFormatException;
|
|
||||||
import com.google.bitcoin.core.BlockChain;
|
import com.google.bitcoin.core.BlockChain;
|
||||||
import com.google.bitcoin.core.ECKey;
|
import com.google.bitcoin.core.ECKey;
|
||||||
import com.google.bitcoin.core.NetworkParameters;
|
import com.google.bitcoin.core.NetworkParameters;
|
||||||
@ -22,14 +13,20 @@ import com.google.bitcoin.core.Transaction;
|
|||||||
import com.google.bitcoin.core.Utils;
|
import com.google.bitcoin.core.Utils;
|
||||||
import com.google.bitcoin.core.Wallet;
|
import com.google.bitcoin.core.Wallet;
|
||||||
|
|
||||||
import static org.junit.Assert.*;
|
import org.bitcoinj.wallet.Protos;
|
||||||
|
import org.junit.Before;
|
||||||
|
import org.junit.Test;
|
||||||
|
|
||||||
|
import java.io.ByteArrayInputStream;
|
||||||
|
import java.io.ByteArrayOutputStream;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.math.BigInteger;
|
||||||
|
|
||||||
public class WalletProtobufSerializerTest {
|
public class WalletProtobufSerializerTest {
|
||||||
static final NetworkParameters params = NetworkParameters.unitTests();
|
static final NetworkParameters params = NetworkParameters.unitTests();
|
||||||
private ECKey myKey;
|
private ECKey myKey;
|
||||||
private Address myAddress;
|
private Address myAddress;
|
||||||
private Wallet wallet;
|
private Wallet wallet;
|
||||||
private MemoryBlockStore blockStore;
|
|
||||||
|
|
||||||
@Before
|
@Before
|
||||||
public void setUp() throws Exception {
|
public void setUp() throws Exception {
|
||||||
@ -37,7 +34,6 @@ public class WalletProtobufSerializerTest {
|
|||||||
myAddress = myKey.toAddress(params);
|
myAddress = myKey.toAddress(params);
|
||||||
wallet = new Wallet(params);
|
wallet = new Wallet(params);
|
||||||
wallet.addKey(myKey);
|
wallet.addKey(myKey);
|
||||||
blockStore = new MemoryBlockStore(params);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@ -101,11 +97,11 @@ public class WalletProtobufSerializerTest {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private Wallet roundTrip(Wallet wallet) throws IOException, AddressFormatException, BlockStoreException {
|
private Wallet roundTrip(Wallet wallet) throws IOException {
|
||||||
ByteArrayOutputStream output = new ByteArrayOutputStream();
|
ByteArrayOutputStream output = new ByteArrayOutputStream();
|
||||||
//System.out.println(WalletProtobufSerializer.walletToText(wallet));
|
//System.out.println(WalletProtobufSerializer.walletToText(wallet));
|
||||||
WalletProtobufSerializer.writeWallet(wallet, output);
|
WalletProtobufSerializer.writeWallet(wallet, output);
|
||||||
ByteArrayInputStream input = new ByteArrayInputStream(output.toByteArray());
|
ByteArrayInputStream input = new ByteArrayInputStream(output.toByteArray());
|
||||||
return WalletProtobufSerializer.readWallet(input, params, blockStore);
|
return WalletProtobufSerializer.readWallet(input, params);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user