Push new block and mempool synchronized.
Measure projected block accuracy. refs #47
This commit is contained in:
		
							parent
							
								
									9bf38da470
								
							
						
					
					
						commit
						f0b0fc3f4b
					
				@ -15,7 +15,7 @@ class ElectrsApi {
 | 
			
		||||
        } else if (res.statusCode !== 200) {
 | 
			
		||||
          reject(response);
 | 
			
		||||
        } else {
 | 
			
		||||
          if (!response.count) {
 | 
			
		||||
          if (typeof response.count !== 'number') {
 | 
			
		||||
            reject('Empty data');
 | 
			
		||||
            return;
 | 
			
		||||
          }
 | 
			
		||||
 | 
			
		||||
@ -1,13 +1,26 @@
 | 
			
		||||
const config = require('../../mempool-config.json');
 | 
			
		||||
import { MempoolBlock, TransactionExtended } from '../interfaces';
 | 
			
		||||
import { MempoolBlock, TransactionExtended, MempoolBlockWithTransactions } from '../interfaces';
 | 
			
		||||
import { Common } from './common';
 | 
			
		||||
 | 
			
		||||
class MempoolBlocks {
 | 
			
		||||
  private mempoolBlocks: MempoolBlock[] = [];
 | 
			
		||||
  private mempoolBlocks: MempoolBlockWithTransactions[] = [];
 | 
			
		||||
 | 
			
		||||
  constructor() {}
 | 
			
		||||
 | 
			
		||||
  public getMempoolBlocks(): MempoolBlock[] {
 | 
			
		||||
    return this.mempoolBlocks.map((block) => {
 | 
			
		||||
      return {
 | 
			
		||||
        blockSize: block.blockSize,
 | 
			
		||||
        blockVSize: block.blockVSize,
 | 
			
		||||
        nTx: block.nTx,
 | 
			
		||||
        totalFees: block.totalFees,
 | 
			
		||||
        medianFee: block.medianFee,
 | 
			
		||||
        feeRange: block.feeRange,
 | 
			
		||||
      };
 | 
			
		||||
    });
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  public getMempoolBlocksWithTransactions(): MempoolBlockWithTransactions[] {
 | 
			
		||||
    return this.mempoolBlocks;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
@ -24,8 +37,8 @@ class MempoolBlocks {
 | 
			
		||||
    this.mempoolBlocks = this.calculateMempoolBlocks(transactionsSorted);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  private calculateMempoolBlocks(transactionsSorted: TransactionExtended[]): MempoolBlock[] {
 | 
			
		||||
    const mempoolBlocks: MempoolBlock[] = [];
 | 
			
		||||
  private calculateMempoolBlocks(transactionsSorted: TransactionExtended[]): MempoolBlockWithTransactions[] {
 | 
			
		||||
    const mempoolBlocks: MempoolBlockWithTransactions[] = [];
 | 
			
		||||
    let blockVSize = 0;
 | 
			
		||||
    let blockSize = 0;
 | 
			
		||||
    let transactions: TransactionExtended[] = [];
 | 
			
		||||
@ -48,7 +61,7 @@ class MempoolBlocks {
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  private dataToMempoolBlocks(transactions: TransactionExtended[],
 | 
			
		||||
    blockSize: number, blockVSize: number, blocksIndex: number): MempoolBlock {
 | 
			
		||||
    blockSize: number, blockVSize: number, blocksIndex: number): MempoolBlockWithTransactions {
 | 
			
		||||
    let rangeLength = 4;
 | 
			
		||||
    if (blocksIndex === 0) {
 | 
			
		||||
      rangeLength = 8;
 | 
			
		||||
@ -65,6 +78,7 @@ class MempoolBlocks {
 | 
			
		||||
      totalFees: transactions.reduce((acc, cur) => acc + cur.fee, 0),
 | 
			
		||||
      medianFee: Common.median(transactions.map((tx) => tx.feePerVsize)),
 | 
			
		||||
      feeRange: Common.getFeesInRange(transactions, rangeLength),
 | 
			
		||||
      transactionIds: transactions.map((tx) => tx.txid),
 | 
			
		||||
    };
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@ -1,7 +1,7 @@
 | 
			
		||||
const config = require('../../mempool-config.json');
 | 
			
		||||
 | 
			
		||||
import * as WebSocket from 'ws';
 | 
			
		||||
import { Block, TransactionExtended, Statistic, WebsocketResponse } from '../interfaces';
 | 
			
		||||
import { Block, TransactionExtended, Statistic, WebsocketResponse, MempoolBlock } from '../interfaces';
 | 
			
		||||
import blocks from './blocks';
 | 
			
		||||
import memPool from './mempool';
 | 
			
		||||
import backendInfo from './backend-info';
 | 
			
		||||
@ -215,6 +215,32 @@ class WebsocketHandler {
 | 
			
		||||
      throw new Error('WebSocket.Server is not set');
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // Check how many transactions in the new block matches the latest projected mempool block
 | 
			
		||||
    // If it's more than 0, recalculate the mempool blocks and send to client in the same update
 | 
			
		||||
    let mBlocks: undefined | MempoolBlock[];
 | 
			
		||||
    let matchRate = 0;
 | 
			
		||||
    const _mempoolBlocks = mempoolBlocks.getMempoolBlocksWithTransactions();
 | 
			
		||||
    if (_mempoolBlocks[0]) {
 | 
			
		||||
      const matches: string[] = [];
 | 
			
		||||
      for (const txId of txIds) {
 | 
			
		||||
        if (_mempoolBlocks[0].transactionIds.indexOf(txId) > -1) {
 | 
			
		||||
          matches.push(txId);
 | 
			
		||||
        }
 | 
			
		||||
      }
 | 
			
		||||
 | 
			
		||||
      matchRate = Math.ceil((matches.length / txIds.length) * 100);
 | 
			
		||||
      if (matchRate > 0) {
 | 
			
		||||
        const currentMemPool = memPool.getMempool();
 | 
			
		||||
        for (const txId of matches) {
 | 
			
		||||
          delete currentMemPool[txId];
 | 
			
		||||
        }
 | 
			
		||||
        mempoolBlocks.updateMempoolBlocks(currentMemPool);
 | 
			
		||||
        mBlocks = mempoolBlocks.getMempoolBlocks();
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    block.matchRate = matchRate;
 | 
			
		||||
 | 
			
		||||
    this.wss.clients.forEach((client) => {
 | 
			
		||||
      if (client.readyState !== WebSocket.OPEN) {
 | 
			
		||||
        return;
 | 
			
		||||
@ -228,6 +254,10 @@ class WebsocketHandler {
 | 
			
		||||
        'block': block
 | 
			
		||||
      };
 | 
			
		||||
 | 
			
		||||
      if (mBlocks && client['want-mempool-blocks']) {
 | 
			
		||||
        response['mempool-blocks'] = mBlocks;
 | 
			
		||||
      }
 | 
			
		||||
 | 
			
		||||
      if (client['track-tx'] && txIds.indexOf(client['track-tx']) > -1) {
 | 
			
		||||
        client['track-tx'] = null;
 | 
			
		||||
        response['txConfirmed'] = true;
 | 
			
		||||
 | 
			
		||||
@ -16,6 +16,12 @@ export interface MempoolBlock {
 | 
			
		||||
  feeRange: number[];
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
export interface MempoolBlockWithTransactions extends MempoolBlock {
 | 
			
		||||
  transactionIds: string[];
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
export interface Transaction {
 | 
			
		||||
  txid: string;
 | 
			
		||||
  version: number;
 | 
			
		||||
@ -107,6 +113,7 @@ export interface Block {
 | 
			
		||||
  feeRange?: number[];
 | 
			
		||||
  reward?: number;
 | 
			
		||||
  coinbaseTx?: Transaction;
 | 
			
		||||
  matchRate?: number;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
export interface Address {
 | 
			
		||||
 | 
			
		||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user