1
0
Fork 0
mirror of https://github.com/BlueWallet/BlueWallet.git synced 2025-03-26 08:55:56 +01:00

WIP: HD wallet

This commit is contained in:
Overtorment 2018-07-31 23:37:35 +01:00
parent 7e84bf6374
commit 73c3281cbf
4 changed files with 48 additions and 2 deletions

View file

@ -38,6 +38,8 @@ it('can create a Segwit HD (BIP49)', async function() {
// checking that internal pointer and async address getter return the same address
let freeAddress = await hd.getAddressAsync();
assert.equal(hd._getExternalAddressByIndex(hd.next_free_address_index), freeAddress);
let freeChangeAddress = await hd.getChangeAddressAsync();
assert.equal(hd._getInternalAddressByIndex(hd.next_free_change_address_index), freeChangeAddress);
});
it('can generate Segwit HD (BIP49)', async () => {

View file

@ -102,9 +102,10 @@ export class AbstractHDWallet extends LegacyWallet {
// looking for free external address
let freeAddress = '';
let c;
for (c = -1; c < 5; c++) {
for (c = 0; c < 5; c++) {
if (this.next_free_address_index + c < 0) continue;
let address = this._getExternalAddressByIndex(this.next_free_address_index + c);
this.external_addresses_cache[this.next_free_address_index + c] = address; // updating cache just for any case
let WatchWallet = new WatchOnlyWallet();
WatchWallet.setSecret(address);
await WatchWallet.fetchTransactions();
@ -125,6 +126,42 @@ export class AbstractHDWallet extends LegacyWallet {
return freeAddress;
}
/**
* Derives from hierarchy, returns next free CHANGE address
* (the one that has no transactions). Looks for several,
* gives up if none found, and returns the used one
*
* @return {Promise.<string>}
*/
async getChangeAddressAsync() {
// looking for free internal address
let freeAddress = '';
let c;
for (c = 0; c < 5; c++) {
if (this.next_free_change_address_index + c < 0) continue;
let address = this._getInternalAddressByIndex(this.next_free_change_address_index + c);
this.internal_addresses_cache[this.next_free_change_address_index + c] = address; // updating cache just for any case
let WatchWallet = new WatchOnlyWallet();
WatchWallet.setSecret(address);
await WatchWallet.fetchTransactions();
if (WatchWallet.transactions.length === 0) {
// found free address
freeAddress = WatchWallet.getAddress();
this.next_free_change_address_index += c; // now points to _this one_
break;
}
}
if (!freeAddress) {
// could not find in cycle above, give up
freeAddress = this._getExternalAddressByIndex(this.next_free_address_index + c); // we didnt check this one, maybe its free
this.next_free_address_index += c + 1; // now points to the one _after_
}
return freeAddress;
}
/**
* Should not be used in HD wallets
*

View file

@ -157,6 +157,8 @@ export class HDSegwitP2SHWallet extends AbstractHDWallet {
}
let addresses = this.usedAddresses.join('|');
addresses += '|' + this._getExternalAddressByIndex(this.next_free_address_index)
addresses += '|' + this._getInternalAddressByIndex(this.next_free_change_address_index)
const api = new Frisbee({ baseURI: 'https://blockchain.info' });
this.transactions = [];

View file

@ -255,7 +255,12 @@ export class LegacyWallet extends AbstractWallet {
hashPresent[tx.hash] = 1;
if (tx.block_height && tx.block_height === -1) {
// unconfirmed
txsUnconf.push(tx);
console.log(tx);
if ((+new Date(tx.received)) < ((+new Date()) - 3600*24*1000)) {
// nop, too old unconfirmed tx - skipping it
} else {
txsUnconf.push(tx);
}
} else {
txs.push(tx);
}