txdb: details and pathinfo.
This commit is contained in:
parent
759365ca25
commit
914bc8435d
@ -311,7 +311,7 @@ Input.prototype.getRedeem = function getRedeem() {
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
Input.prototype.getSubtype = function getSubtype() {
|
Input.prototype.getSubtype = function getSubtype() {
|
||||||
var redeem;
|
var redeem, type;
|
||||||
|
|
||||||
if (this.isCoinbase())
|
if (this.isCoinbase())
|
||||||
return;
|
return;
|
||||||
@ -321,7 +321,9 @@ Input.prototype.getSubtype = function getSubtype() {
|
|||||||
if (!redeem)
|
if (!redeem)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
return redeem.getType();
|
type = redeem.getType();
|
||||||
|
|
||||||
|
return constants.scriptTypesByVal[type].toLowerCase();
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@ -2334,6 +2334,196 @@ MapMember.fromPath = function fromPath(path) {
|
|||||||
return new MapMember().fromPath(path);
|
return new MapMember().fromPath(path);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
function PathInfo(tx, table) {
|
||||||
|
// All relevant Wallet-ID/Accounts for
|
||||||
|
// inputs and outputs (for database indexing).
|
||||||
|
this.keys = [];
|
||||||
|
|
||||||
|
// All output paths (for deriving during sync).
|
||||||
|
this.paths = [];
|
||||||
|
|
||||||
|
// All output wallet IDs (for balance & syncing).
|
||||||
|
this.wallets = [];
|
||||||
|
|
||||||
|
// Map of address hashes->paths (for everything).
|
||||||
|
this.table = {};
|
||||||
|
|
||||||
|
if (tx)
|
||||||
|
this.fromTX(tx, table);
|
||||||
|
}
|
||||||
|
|
||||||
|
PathInfo.prototype.fromTX = function fromTX(tx, table) {
|
||||||
|
var i, j, keys, wallets, hashes, hash, paths, path, key;
|
||||||
|
|
||||||
|
this.table = table;
|
||||||
|
|
||||||
|
keys = {};
|
||||||
|
hashes = Object.keys(table);
|
||||||
|
|
||||||
|
for (i = 0; i < hashes.length; i++) {
|
||||||
|
hash = hashes[i];
|
||||||
|
paths = table[hash];
|
||||||
|
for (j = 0; j < paths.length; j++) {
|
||||||
|
path = paths[j];
|
||||||
|
key = path.id + '/' + path.account;
|
||||||
|
keys[key] = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
this.keys = Object.keys(keys);
|
||||||
|
|
||||||
|
wallets = {};
|
||||||
|
hashes = tx.getOutputHashes('hex');
|
||||||
|
|
||||||
|
for (i = 0; i < hashes.length; i++) {
|
||||||
|
hash = hashes[i];
|
||||||
|
paths = table[hash];
|
||||||
|
for (j = 0; j < paths.length; j++) {
|
||||||
|
path = paths[j];
|
||||||
|
this.paths.push(path);
|
||||||
|
wallets[path.id] = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
this.wallets = Object.keys(wallets);
|
||||||
|
};
|
||||||
|
|
||||||
|
PathInfo.fromTX = function fromTX(tx, table) {
|
||||||
|
return new PathInfo().fromTX(tx, table);
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Test whether the map has paths
|
||||||
|
* for a given address hash.
|
||||||
|
* @param {Hash} address
|
||||||
|
* @returns {Boolean}
|
||||||
|
*/
|
||||||
|
|
||||||
|
PathInfo.prototype.hasPaths = function hasPaths(address) {
|
||||||
|
var paths;
|
||||||
|
|
||||||
|
if (!address)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
paths = this.table[address];
|
||||||
|
|
||||||
|
return paths && paths.length !== 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get paths for a given address hash.
|
||||||
|
* @param {Hash} address
|
||||||
|
* @returns {Path[]|null}
|
||||||
|
*/
|
||||||
|
|
||||||
|
PathInfo.prototype.getPaths = function getPaths(address) {
|
||||||
|
var paths;
|
||||||
|
|
||||||
|
if (!address)
|
||||||
|
return;
|
||||||
|
|
||||||
|
paths = this.table[address];
|
||||||
|
|
||||||
|
if (!paths || paths.length === 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
return paths;
|
||||||
|
};
|
||||||
|
|
||||||
|
function Details(tx, id, table) {
|
||||||
|
this.hash = tx.hash('hex');
|
||||||
|
this.height = tx.height;
|
||||||
|
this.block = tx.block;
|
||||||
|
this.index = tx.index;
|
||||||
|
this.confirmations = tx.getConfirmations();
|
||||||
|
this.ts = tx.ts;
|
||||||
|
this.ps = tx.ps;
|
||||||
|
this.fee = tx.getFee();
|
||||||
|
this.tx = tx;
|
||||||
|
this.inputs = [];
|
||||||
|
this.outputs = [];
|
||||||
|
|
||||||
|
if (id)
|
||||||
|
this.init(id, table);
|
||||||
|
}
|
||||||
|
|
||||||
|
Details.prototype._insert = function _insert(vector, target, id, table) {
|
||||||
|
var i, j, io, address, hash, paths, path, member;
|
||||||
|
|
||||||
|
for (i = 0; i < vector.length; i++) {
|
||||||
|
io = vector[i];
|
||||||
|
member = new DetailsMember();
|
||||||
|
|
||||||
|
if (io instanceof bcoin.input)
|
||||||
|
member.value = io.coin ? io.coin.value : 0;
|
||||||
|
else
|
||||||
|
member.value = io.value;
|
||||||
|
|
||||||
|
address = io.getAddress();
|
||||||
|
|
||||||
|
if (address) {
|
||||||
|
member.address = address;
|
||||||
|
|
||||||
|
hash = address.getHash('hex');
|
||||||
|
paths = table[hash];
|
||||||
|
|
||||||
|
for (j = 0; j < paths.length; j++) {
|
||||||
|
path = paths[j];
|
||||||
|
if (path.id === id) {
|
||||||
|
member.path = path;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
target.push(member);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
Details.prototype.init = function init(id, table) {
|
||||||
|
this._insert(this.tx.inputs, this.inputs, id, table);
|
||||||
|
this._insert(this.tx.outputs, this.outputs, id, table);
|
||||||
|
};
|
||||||
|
|
||||||
|
Details.prototype.toJSON = function toJSON() {
|
||||||
|
return {
|
||||||
|
hash: utils.revHex(this.hash),
|
||||||
|
height: this.height,
|
||||||
|
block: this.block ? utils.revHex(this.block) : null,
|
||||||
|
ts: this.ts,
|
||||||
|
ps: this.ps,
|
||||||
|
index: this.index,
|
||||||
|
fee: utils.btc(this.fee),
|
||||||
|
confirmations: this.confirmations,
|
||||||
|
inputs: this.inputs.map(function(input) {
|
||||||
|
return input.toJSON();
|
||||||
|
}),
|
||||||
|
outputs: this.outputs.map(function(output) {
|
||||||
|
return output.toJSON();
|
||||||
|
}),
|
||||||
|
tx: this.tx.toRaw().toString('hex')
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
function DetailsMember() {
|
||||||
|
this.value = 0;
|
||||||
|
this.address = null;
|
||||||
|
this.path = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
DetailsMember.prototype.toJSON = function toJSON() {
|
||||||
|
return {
|
||||||
|
value: utils.btc(this.value),
|
||||||
|
address: this.address
|
||||||
|
? this.address.toBase58()
|
||||||
|
: null,
|
||||||
|
path: this.path
|
||||||
|
? this.path.toJSON()
|
||||||
|
: null
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Expose
|
* Expose
|
||||||
*/
|
*/
|
||||||
|
|||||||
@ -2192,7 +2192,7 @@ utils.toMap = function toMap(obj) {
|
|||||||
/**
|
/**
|
||||||
* Reverse a map.
|
* Reverse a map.
|
||||||
* @param {Object} map
|
* @param {Object} map
|
||||||
* @param {Object} Reversed map.
|
* @returns {Object} Reversed map.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
utils.revMap = function revMap(map) {
|
utils.revMap = function revMap(map) {
|
||||||
@ -2208,6 +2208,25 @@ utils.revMap = function revMap(map) {
|
|||||||
return reversed;
|
return reversed;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get object values.
|
||||||
|
* @param {Object} map
|
||||||
|
* @returns {Array} Values.
|
||||||
|
*/
|
||||||
|
|
||||||
|
utils.values = function values(map) {
|
||||||
|
var keys = Object.keys(map);
|
||||||
|
var out = [];
|
||||||
|
var i, key;
|
||||||
|
|
||||||
|
for (i = 0; i < keys.length; i++) {
|
||||||
|
key = keys[i];
|
||||||
|
out.push(map[key]);
|
||||||
|
}
|
||||||
|
|
||||||
|
return out;
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Perform a binary search on a sorted array.
|
* Perform a binary search on a sorted array.
|
||||||
* @param {Array} items
|
* @param {Array} items
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user