wip
This commit is contained in:
parent
eb39e5bf19
commit
17bbfcc6ce
@ -570,14 +570,14 @@ BlockService.prototype._onBlock = function(block) {
|
||||
// 3. store the block for safe keeping
|
||||
this._cacheBlock(block);
|
||||
|
||||
// don't process any more blocks if we are currently in a reorg
|
||||
// 4. don't process any more blocks if we are currently in a reorg
|
||||
if (this._reorging) {
|
||||
return;
|
||||
}
|
||||
// 4. determine block state, reorg, outoforder, normal
|
||||
// 5. determine block state, reorg, outoforder, normal
|
||||
var blockState = this._determineBlockState(block);
|
||||
|
||||
// 5. update internal data structures depending on blockstate
|
||||
// 6. update internal data structures depending on blockstate
|
||||
this._updateChainInfo(block, blockState);
|
||||
|
||||
// 7. react to state of block
|
||||
|
||||
@ -1,74 +1,28 @@
|
||||
'use strict';
|
||||
|
||||
var bitcore = require('bitcore-lib');
|
||||
var BufferReader = bitcore.encoding.BufferReader;
|
||||
var tx = require('bcoin').tx;
|
||||
|
||||
function Encoding(servicePrefix) {
|
||||
this.servicePrefix = servicePrefix;
|
||||
}
|
||||
|
||||
Encoding.prototype.encodeMempoolAddressIndexKey = function(address, txid) {
|
||||
var prefix = new Buffer('00', 'hex');
|
||||
var buffers = [this.servicePrefix, prefix];
|
||||
|
||||
var addressSizeBuffer = new Buffer(1);
|
||||
addressSizeBuffer.writeUInt8(address.length);
|
||||
buffers.push(addressSizeBuffer);
|
||||
var addressBuffer = new Buffer(address, 'utf8');
|
||||
buffers.push(addressBuffer);
|
||||
|
||||
var txidBuffer = new Buffer(txid, 'hex');
|
||||
buffers.push(txidBuffer);
|
||||
|
||||
return Buffer.concat(buffers);
|
||||
};
|
||||
|
||||
Encoding.prototype.decodeMempoolAddressIndexKey = function(buffer) {
|
||||
var reader = new BufferReader(buffer);
|
||||
reader.read(3);
|
||||
|
||||
var addressSize = reader.readUInt8();
|
||||
var address = reader.read(addressSize).toString('utf8');
|
||||
var txid = reader.read(32).toString('hex');
|
||||
|
||||
return {
|
||||
address: address,
|
||||
txid: txid
|
||||
};
|
||||
};
|
||||
|
||||
Encoding.prototype.encodeMempoolTransactionKey = function(txid) {
|
||||
var prefix = new Buffer('01', 'hex');
|
||||
var buffers = [this.servicePrefix, prefix];
|
||||
var buffers = [this.servicePrefix];
|
||||
var txidBuffer = new Buffer(txid, 'hex');
|
||||
buffers.push(txidBuffer);
|
||||
return Buffer.concat(buffers);
|
||||
};
|
||||
|
||||
Encoding.prototype.decodeMempoolTransactionKey = function(buffer) {
|
||||
return buffer.slice(4).toString('hex');
|
||||
return buffer.slice(2).toString('hex');
|
||||
};
|
||||
|
||||
Encoding.prototype.encodeMempoolTransactionValue = function(transaction) {
|
||||
var inputValues = transaction.__inputValues || [];
|
||||
var inputValuesBuffer = new Buffer(8 * inputValues.length);
|
||||
for(var i = 0; i < inputValues.length; i++) {
|
||||
inputValuesBuffer.writeDoubleBE(inputValues[i], i * 8);
|
||||
}
|
||||
var inputValuesLengthBuffer = new Buffer(2);
|
||||
inputValuesLengthBuffer.writeUInt16BE(inputValues.length * 8);
|
||||
return new Buffer.concat([inputValuesLengthBuffer, inputValuesBuffer, transaction.toBuffer()]);
|
||||
return transaction.toRaw();
|
||||
};
|
||||
|
||||
Encoding.prototype.decodeMempoolTransactionValue = function(buffer) {
|
||||
var inputValues = [];
|
||||
var inputValuesLength = buffer.readUInt16BE();
|
||||
for(var i = 0; i < inputValuesLength / 8; i++) {
|
||||
inputValues.push(buffer.readDoubleBE(i * 8 + 2));
|
||||
}
|
||||
var transaction = new bitcore.Transaction(buffer.slice(inputValues.length * 8 + 2));
|
||||
transaction.__inputValues = inputValues;
|
||||
return transaction;
|
||||
return tx.fromRaw(buffer);
|
||||
};
|
||||
|
||||
module.exports = Encoding;
|
||||
|
||||
@ -4,279 +4,89 @@ var util = require('util');
|
||||
var Encoding = require('./encoding');
|
||||
var index = require('../../index');
|
||||
var log = index.log;
|
||||
var async = require('async');
|
||||
|
||||
var MempoolService = function(options) {
|
||||
BaseService.call(this, options);
|
||||
this.node = options.node;
|
||||
this.name = options.name;
|
||||
this._txIndex = {};
|
||||
this._addressIndex = {};
|
||||
this.db = this.node.services.db;
|
||||
this._handleBlocks = false;
|
||||
this._db = this.node.services.db;
|
||||
this._tx = this.node.services.transaction;
|
||||
};
|
||||
|
||||
util.inherits(MempoolService, BaseService);
|
||||
|
||||
MempoolService.dependencies = ['db'];
|
||||
|
||||
|
||||
MempoolService.prototype.getPublishEvents = function() {
|
||||
return [];
|
||||
};
|
||||
|
||||
MempoolService.prototype.getAPIMethods = function() {
|
||||
return [];
|
||||
var methods = [
|
||||
['getTransaction', this, this.getTransaction, 1]
|
||||
];
|
||||
return methods;
|
||||
};
|
||||
|
||||
MempoolService.prototype.start = function(callback) {
|
||||
var self = this;
|
||||
|
||||
self.node.services.db.getPrefix(self.name, function(err, servicePrefix) {
|
||||
self._db.getPrefix(self.name, function(err, prefix) {
|
||||
if(err) {
|
||||
return callback(err);
|
||||
}
|
||||
self.servicePrefix = servicePrefix;
|
||||
self._encoding = new Encoding(self.servicePrefix);
|
||||
self._setListeners();
|
||||
self._encoding = new Encoding(prefix);
|
||||
self._startSubscriptions();
|
||||
callback();
|
||||
});
|
||||
};
|
||||
|
||||
MempoolService.prototype._setListeners = function() {
|
||||
this._startSubscriptions();
|
||||
MempoolService.prototype._startSubscriptions = function() {
|
||||
|
||||
if (this._subscribed) {
|
||||
return;
|
||||
}
|
||||
|
||||
this._subscribed = true;
|
||||
if (!this._bus) {
|
||||
this._bus = this.node.openBus({remoteAddress: 'localhost'});
|
||||
}
|
||||
|
||||
this._bus.on('p2p/block', this._onBlock.bind(this));
|
||||
this._bus.on('p2p/transaction', this._onTransaction.bind(this));
|
||||
|
||||
this._bus.subscribe('p2p/block');
|
||||
this._bus.subscribe('p2p/transaction');
|
||||
};
|
||||
|
||||
MempoolService.prototype._startSubscriptions = function() {
|
||||
var bus = this.node.openBus({ remoteAddress: 'localhost' });
|
||||
bus.on('p2p/transaction', this._onTransaction.bind(this));
|
||||
bus.subscribe('p2p/transaction');
|
||||
MempoolService.prototype._onBlock = function(block) {
|
||||
// remove this block's txs from mempool
|
||||
var ops = block.transactions.map(function(tx) {
|
||||
return {
|
||||
type: 'del',
|
||||
key: tx.id
|
||||
};
|
||||
});
|
||||
this._db.batch(ops);
|
||||
};
|
||||
|
||||
MempoolService.prototype._onTransaction = function(tx) {
|
||||
var txOps = this._getTxOperation(tx);
|
||||
this._db.batch(txOps);
|
||||
};
|
||||
|
||||
MempoolService.prototype._getTxOperations = function(tx) {
|
||||
var inputValues = this._tx.getInputValues(tx);
|
||||
tx.__inputValues = inputValues;
|
||||
return {
|
||||
type: 'put',
|
||||
key: this._encoding.encodeMempoolTransactionKey(tx.id),
|
||||
value: this._encoding.encodeMempoolTransactionValue(tx)
|
||||
};
|
||||
};
|
||||
|
||||
MempoolService.prototype.getTransaction = function(txid, callback) {
|
||||
this._db.get(this._encoding.encodeMempoolTransactionKey(txid), callback);
|
||||
};
|
||||
|
||||
MempoolService.prototype.stop = function(callback) {
|
||||
callback();
|
||||
};
|
||||
|
||||
MempoolService.prototype.setupRoutes = function() {
|
||||
};
|
||||
|
||||
MempoolService.prototype.getRoutePrefix = function() {
|
||||
return this.name;
|
||||
};
|
||||
|
||||
MempoolService.prototype._getTransactionAddressDetailOperations = function(tx, action) {
|
||||
var self = this;
|
||||
|
||||
if(tx.isCoinbase()) {
|
||||
return [];
|
||||
}
|
||||
var operations = [];
|
||||
|
||||
var txid = tx.id;
|
||||
var inputs = tx.inputs;
|
||||
var outputs = tx.outputs;
|
||||
|
||||
var outputLength = outputs.length;
|
||||
for (var outputIndex = 0; outputIndex < outputLength; outputIndex++) {
|
||||
var output = outputs[outputIndex];
|
||||
|
||||
var script = output.script;
|
||||
|
||||
if(!script) {
|
||||
log.debug('Invalid script');
|
||||
continue;
|
||||
}
|
||||
|
||||
var address = self.getAddressString(script);
|
||||
|
||||
if(!address) {
|
||||
continue;
|
||||
}
|
||||
|
||||
var key = self.encoding.encodeMempoolAddressIndexKey(address, txid);
|
||||
operations.push({
|
||||
type: action,
|
||||
key: key
|
||||
});
|
||||
|
||||
}
|
||||
|
||||
//TODO deal with P2PK
|
||||
for(var i = 0; i < inputs.length; i++) {
|
||||
var input = inputs[i];
|
||||
if(!input.script) {
|
||||
log.debug('Invalid script');
|
||||
continue;
|
||||
}
|
||||
|
||||
var inputAddress = self.getAddressString(input.script);
|
||||
|
||||
if(!inputAddress) {
|
||||
continue;
|
||||
}
|
||||
|
||||
var inputKey = self.encodeMempoolAddressIndexKey(inputAddress, txid);
|
||||
|
||||
operations.push({
|
||||
type: action,
|
||||
key: inputKey
|
||||
});
|
||||
}
|
||||
return operations;
|
||||
};
|
||||
|
||||
MempoolService.prototype.getAddressString = function(script, output) {
|
||||
var address = script.toAddress();
|
||||
if(address) {
|
||||
return address.toString();
|
||||
}
|
||||
|
||||
try {
|
||||
var pubkey = script.getPublicKey();
|
||||
if(pubkey) {
|
||||
return pubkey.toString('hex');
|
||||
}
|
||||
} catch(e) {
|
||||
}
|
||||
|
||||
if(output && output.script && output.script.isPublicKeyOut()) {
|
||||
return output.script.getPublicKey().toString('hex');
|
||||
}
|
||||
|
||||
return null;
|
||||
};
|
||||
|
||||
MempoolService.prototype._getInputValues = function(tx, callback) {
|
||||
var self = this;
|
||||
|
||||
if (tx.isCoinbase()) {
|
||||
return callback(null, []);
|
||||
}
|
||||
|
||||
async.mapLimit(tx.inputs, this.concurrency, function(input, next) {
|
||||
self.getTransaction(input.prevTxId.toString('hex'), {}, function(err, prevTx) {
|
||||
if(err) {
|
||||
return next(err);
|
||||
}
|
||||
if (!prevTx) {
|
||||
return next(null, 0);
|
||||
}
|
||||
if (!prevTx.outputs[input.outputIndex]) {
|
||||
return next(new Error('Input did not have utxo.'));
|
||||
}
|
||||
var satoshis = prevTx.outputs[input.outputIndex].satoshis;
|
||||
next(null, satoshis);
|
||||
});
|
||||
}, callback);
|
||||
};
|
||||
|
||||
|
||||
MempoolService.prototype._updateCache = function(operation) {
|
||||
if (operation.type === 'del') {
|
||||
return this._cache.del(operation.key);
|
||||
}
|
||||
this._cache.set(operation.key, operation.value);
|
||||
};
|
||||
|
||||
MempoolService.prototype.getTransaction = function(txid, callback) {
|
||||
var self = this;
|
||||
var key = self._encoding.encodeMempoolTransactionKey(txid);
|
||||
var txBuffer = self._cache.get(key);
|
||||
if (txBuffer) {
|
||||
return setImmediate(function() {
|
||||
callback(null, self._encoding.decodeMempoolTransactionValue(txBuffer));
|
||||
});
|
||||
}
|
||||
self.db.get(key, function(err, value) {
|
||||
if(err) {
|
||||
return callback(err);
|
||||
}
|
||||
callback(null, self._encoding.decodeMempoolTransactionValue(value));
|
||||
});
|
||||
};
|
||||
|
||||
MempoolService.prototype._getTransactionOperation = function(tx, action, callback) {
|
||||
var self = this;
|
||||
self._getInputValues(tx, function(err, inputValues) {
|
||||
if(err) {
|
||||
return callback(err);
|
||||
}
|
||||
tx.__inputValues = inputValues;
|
||||
var operation = {
|
||||
type: action,
|
||||
key: self._encoding.encodeMempoolTransactionKey(tx.id),
|
||||
value: self._encoding.encodeMempoolTransactionValue(tx)
|
||||
};
|
||||
callback(null, operation);
|
||||
});
|
||||
};
|
||||
|
||||
MempoolService.prototype._updateMempool = function(tx, action, callback) {
|
||||
var self = this;
|
||||
self._getTransactionOperation(tx, action, function(err, operation) {
|
||||
if(err) {
|
||||
return callback(err);
|
||||
}
|
||||
var operations = [operation].concat(self._getTransactionAddressDetailOperations(tx, action));
|
||||
self.db.batch(operations, function(err) {
|
||||
if(err) {
|
||||
log.error('batch operation for updating Mempool failed.');
|
||||
return;
|
||||
}
|
||||
operations.forEach(self._updateCache);
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
MempoolService.prototype.getTransactionsByAddress = function(address, callback) {
|
||||
var self = this;
|
||||
var txids = [];
|
||||
var maxTxid = new Buffer(new Array(65).join('f'), 'hex');
|
||||
var start = self._encoding.encodeMempoolAddressKey(address);
|
||||
var end = Buffer.concat([self._encoding.encodeMempoolAddressKey(address), maxTxid]);
|
||||
var stream = self.db.createKeyStream({
|
||||
gte: start,
|
||||
lte: end
|
||||
});
|
||||
var streamErr;
|
||||
stream.on('error', function(err) {
|
||||
streamErr = err;
|
||||
});
|
||||
stream.on('data', function(data) {
|
||||
var key = self._encoding.decodeMempoolAddressKey(data);
|
||||
txids.push(key.txid);
|
||||
});
|
||||
stream.on('end', function() {
|
||||
async.mapLimit(txids, 10, function(txid, next) {
|
||||
self.getTransaction(txid, next);
|
||||
}, callback);
|
||||
});
|
||||
};
|
||||
|
||||
MempoolService.prototype.getTransactionsByAddresses = function(addresses, callback) {
|
||||
var self = this;
|
||||
var transactions = {};
|
||||
async.eachLimit(addresses, 10, function(address, next) {
|
||||
self.getTransactionsByAddress(address, function(err, txs) {
|
||||
if(err) {
|
||||
return next(err);
|
||||
}
|
||||
txs.forEach(function(tx) {
|
||||
transactions[tx.id] = tx;
|
||||
});
|
||||
next();
|
||||
});
|
||||
}, function(err) {
|
||||
if(err) {
|
||||
return callback(err);
|
||||
}
|
||||
callback(null, Object.values(transactions));
|
||||
});
|
||||
};
|
||||
|
||||
module.exports = MempoolService;
|
||||
|
||||
|
||||
@ -9,28 +9,6 @@ var BaseService = require('../../service');
|
||||
var assert = require('assert');
|
||||
var Bcoin = require('./bcoin');
|
||||
|
||||
/*
|
||||
|
||||
1. getAddressSummary
|
||||
2. getAddressUnspentOutputs
|
||||
3. bitcoind.height
|
||||
4. getBlockHeader
|
||||
5. getDetailedTransaction
|
||||
6. getTransaction
|
||||
7. sendTransaction
|
||||
8. getInfo
|
||||
9. bitcoind.tiphash
|
||||
10. getBestBlockHash
|
||||
11. isSynced
|
||||
12. getAddressHistory
|
||||
13. getBlock
|
||||
14. getRawBlock
|
||||
15. getBlockHashesByTimestamp
|
||||
16. estimateFee
|
||||
17. getBlockOverview
|
||||
18. syncPercentage
|
||||
|
||||
*/
|
||||
var P2P = function(options) {
|
||||
|
||||
if (!(this instanceof P2P)) {
|
||||
@ -85,14 +63,8 @@ P2P.prototype.getHeaders = function(filter) {
|
||||
|
||||
P2P.prototype.getInfo = function(callback) {
|
||||
callback(null, {
|
||||
version: '4.0',
|
||||
protocolversion: 'latest',
|
||||
blocks: this._getBestHeight(),
|
||||
timeoffset: 0,
|
||||
connections: this._pool.numberConnected,
|
||||
difficulty: 0,
|
||||
testnet: false,
|
||||
relayfee: 0
|
||||
connections: this._pool.numberConnected
|
||||
});
|
||||
};
|
||||
|
||||
@ -245,7 +217,8 @@ P2P.prototype._initPool = function() {
|
||||
if (this._configPeers) {
|
||||
opts.addrs = this._configPeers;
|
||||
}
|
||||
opts.dnsSeed = false;
|
||||
// TODO: bcoin stuff goes here
|
||||
opts.dnsSeed = false; // do not set to true unless you want to be pwned
|
||||
opts.maxPeers = this._maxPeers;
|
||||
opts.network = this.node.getNetworkName();
|
||||
this._pool = new p2p.Pool(opts);
|
||||
@ -258,7 +231,6 @@ P2P.prototype._initPubSub = function() {
|
||||
this.subscriptions.transaction = [];
|
||||
};
|
||||
|
||||
|
||||
P2P.prototype._onPeerBlock = function(peer, message) {
|
||||
this._broadcast(this.subscriptions.block, 'p2p/block', message.block);
|
||||
};
|
||||
|
||||
@ -206,7 +206,7 @@ TimestampService.prototype._onReorg = function(oldBlockList, newBlockList, commo
|
||||
}
|
||||
|
||||
// set the tip to the common ancestor in case something goes wrong with the reorg
|
||||
var tipOps = utils.encodeTip({ height: commonAncestor.header.height });
|
||||
var tipOps = utils.encodeTip({ hash: commonAncestor.hash, height: commonAncestor.header.height }, this.name);
|
||||
|
||||
var removalOps = [{
|
||||
type: 'put',
|
||||
|
||||
@ -35,7 +35,8 @@ TransactionService.prototype.getAPIMethods = function() {
|
||||
['getTransaction', this, this.getTransaction, 1],
|
||||
['getDetailedTransaction', this, this.getDetailedTransaction, 1],
|
||||
['sendTransaction', this, this.sendTransaction, 1],
|
||||
['syncPercentage', this, this.syncPercentage, 0]
|
||||
['syncPercentage', this, this.syncPercentage, 0],
|
||||
['getInputValues', this, this._getInputValues, 1]
|
||||
];
|
||||
};
|
||||
|
||||
@ -140,9 +141,9 @@ TransactionService.prototype._getBlockTimestamp = function(hash) {
|
||||
return this._timestamp.getTimestamp(hash);
|
||||
};
|
||||
|
||||
TransactionService.prototype._getInputValues = function(tx, opts) {
|
||||
TransactionService.prototype._getInputValues = function(tx) {
|
||||
|
||||
return tx.inputs.forEach(function(input) {
|
||||
return tx.inputs.map(function(input) {
|
||||
var value = this._inputValuesCache.get(input.prevTxId);
|
||||
if (value) {
|
||||
return value[input.outputIndex];
|
||||
|
||||
41
test/services/mempool/encoding.unit.js
Normal file
41
test/services/mempool/encoding.unit.js
Normal file
@ -0,0 +1,41 @@
|
||||
'use strict';
|
||||
|
||||
var should = require('chai').should();
|
||||
var tx = require('bcoin').tx;
|
||||
|
||||
var Encoding = require('../../../lib/services/mempool/encoding');
|
||||
|
||||
describe('Block service encoding', function() {
|
||||
|
||||
var servicePrefix = new Buffer('0000', 'hex');
|
||||
|
||||
var encoding = new Encoding(servicePrefix);
|
||||
var hash = '25e28f9fb0ada5353b7d98d85af5524b2f8df5b0b0e2d188f05968bceca603eb';
|
||||
var txString = '0100000004de9b4bb17f627096a9ee0b4528e4eae17df5b5c69edc29704c2e84a7371db29f010000006b483045022100f5b1a0d33b7be291c3953c25f8ae39d98601aa7099a8674daf638a08b86c7173022006ce372da5ad088a1cc6e5c49c2760a1b6f085eb1b51b502211b6bc9508661f9012102ec5e3731e54475dd2902326f43602a03ae3d62753324139163f81f20e787514cffffffff7a1d4e5fc2b8177ec738cd723a16cf2bf493791e55573445fc0df630fe5e2d64010000006b483045022100cf97f6cb8f126703e9768545dfb20ffb10ba78ae3d101aa46775f5a239b075fc02203150c4a89a11eaf5e404f4f96b62efa4455e9525765a025525c7105a7e47b6db012102c01e11b1d331f999bbdb83e8831de503cd52a01e3834a95ccafd615c67703d77ffffffff9e52447116415ca0d0567418a1a4ef8f27be3ff5a96bf87c922f3723d7db5d7c000000006b483045022100f6c117e536701be41a6b0b544d7c3b1091301e4e64a6265b6eb167b15d16959d022076916de4b115e700964194ce36a24cb9105f86482f4abbc63110c3f537cd5770012102ddf84cc7bee2d6a82ac09628a8ad4a26cd449fc528b81e7e6cc615707b8169dfffffffff5815d9750eb3572e30d6fd9df7afb4dbd76e042f3aa4988ac763b3fdf8397f80010000006a473044022028f4402b736066d93d2a32b28ccd3b7a21d84bb58fcd07fe392a611db94cdec5022018902ee0bf2c3c840c1b81ead4e6c87c88c48b2005bf5eea796464e561a620a8012102b6cdd1a6cd129ef796faeedb0b840fcd0ca00c57e16e38e46ee7028d59812ae7ffffffff0220a10700000000001976a914c342bcd1a7784d9842f7386b8b3b8a3d4171a06e88ac59611100000000001976a91449f8c749a9960dc29b5cbe7d2397cea7d26611bb88ac00000000'
|
||||
|
||||
describe('Mempool', function() {
|
||||
|
||||
it('should encode mempool transaction key', function() {
|
||||
encoding.encodeMempoolTransactionKey(hash).should.deep.equal(Buffer.concat([ servicePrefix, new Buffer(hash, 'hex') ]));
|
||||
});
|
||||
|
||||
it('should decode mempool transaction key', function() {
|
||||
encoding.decodeMempoolTransactionKey(Buffer.concat([ servicePrefix, new Buffer(hash, 'hex') ])).should.deep.equal(hash);
|
||||
});
|
||||
|
||||
it('should encode mempool transaction value', function() {
|
||||
var mytx = tx.fromRaw(txString, 'hex');
|
||||
mytx.__inputValues = [1012955, 447698, 446664, 391348];
|
||||
encoding.encodeMempoolTransactionValue(mytx).should.deep.equal(new Buffer(txString, 'hex'));
|
||||
});
|
||||
|
||||
it('should decode mempool transaction value', function() {
|
||||
var mytx = encoding.decodeMempoolTransactionValue(new Buffer(txString, 'hex'));
|
||||
mytx.should.deep.equal(tx.fromRaw(txString, 'hex'));
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
|
||||
50
test/services/mempool/index.unit.js
Normal file
50
test/services/mempool/index.unit.js
Normal file
@ -0,0 +1,50 @@
|
||||
'use strict';
|
||||
|
||||
var expect = require('chai').expect;
|
||||
var MempoolService = require('../../../lib/services/mempool');
|
||||
var sinon = require('sinon');
|
||||
var Encoding = require('../../../lib/services/block/encoding');
|
||||
var Tx = require('bcoin').tx;
|
||||
|
||||
describe('Mempool Service', function() {
|
||||
|
||||
var mempoolService;
|
||||
var sandbox;
|
||||
var tx = Tx.fromRaw( '0100000004de9b4bb17f627096a9ee0b4528e4eae17df5b5c69edc29704c2e84a7371db29f010000006b483045022100f5b1a0d33b7be291c3953c25f8ae39d98601aa7099a8674daf638a08b86c7173022006ce372da5ad088a1cc6e5c49c2760a1b6f085eb1b51b502211b6bc9508661f9012102ec5e3731e54475dd2902326f43602a03ae3d62753324139163f81f20e787514cffffffff7a1d4e5fc2b8177ec738cd723a16cf2bf493791e55573445fc0df630fe5e2d64010000006b483045022100cf97f6cb8f126703e9768545dfb20ffb10ba78ae3d101aa46775f5a239b075fc02203150c4a89a11eaf5e404f4f96b62efa4455e9525765a025525c7105a7e47b6db012102c01e11b1d331f999bbdb83e8831de503cd52a01e3834a95ccafd615c67703d77ffffffff9e52447116415ca0d0567418a1a4ef8f27be3ff5a96bf87c922f3723d7db5d7c000000006b483045022100f6c117e536701be41a6b0b544d7c3b1091301e4e64a6265b6eb167b15d16959d022076916de4b115e700964194ce36a24cb9105f86482f4abbc63110c3f537cd5770012102ddf84cc7bee2d6a82ac09628a8ad4a26cd449fc528b81e7e6cc615707b8169dfffffffff5815d9750eb3572e30d6fd9df7afb4dbd76e042f3aa4988ac763b3fdf8397f80010000006a473044022028f4402b736066d93d2a32b28ccd3b7a21d84bb58fcd07fe392a611db94cdec5022018902ee0bf2c3c840c1b81ead4e6c87c88c48b2005bf5eea796464e561a620a8012102b6cdd1a6cd129ef796faeedb0b840fcd0ca00c57e16e38e46ee7028d59812ae7ffffffff0220a10700000000001976a914c342bcd1a7784d9842f7386b8b3b8a3d4171a06e88ac59611100000000001976a91449f8c749a9960dc29b5cbe7d2397cea7d26611bb88ac00000000', 'hex');
|
||||
beforeEach(function() {
|
||||
sandbox = sinon.sandbox.create();
|
||||
mempoolService = new MempoolService({
|
||||
node: {
|
||||
getNetworkName: function() { return 'regtest'; },
|
||||
services: []
|
||||
}
|
||||
});
|
||||
mempoolService._encoding = new Encoding(new Buffer('0000', 'hex'));
|
||||
});
|
||||
|
||||
afterEach(function() {
|
||||
sandbox.restore();
|
||||
});
|
||||
|
||||
describe('#start', function() {
|
||||
|
||||
it('should get the db prefix', function(done) {
|
||||
var getPrefix = sandbox.stub().callsArgWith(1, null, new Buffer('0001', 'hex'));
|
||||
var startSubs = sandbox.stub(mempoolService, '_startSubscriptions');
|
||||
mempoolService._db = { getPrefix: getPrefix };
|
||||
|
||||
mempoolService.start(function() {
|
||||
expect(getPrefix.calledOnce).to.be.true;
|
||||
expect(startSubs.calledOnce).to.be.true;
|
||||
done();
|
||||
});
|
||||
});
|
||||
|
||||
describe('#getTransaction', function(done) {
|
||||
var get = sandbox.stub().callsArgWith(1, null, tx.toJSON());
|
||||
});
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user