Index asciiScriptSig and display it in /mining/blocks

This commit is contained in:
nymkappa 2022-03-15 23:33:51 +01:00
parent 9c60c7ba79
commit 94dbec46cf
No known key found for this signature in database
GPG Key ID: E155910B16E8BD04
8 changed files with 59 additions and 17 deletions

View File

@ -108,9 +108,7 @@ class Blocks {
const blockExtended: BlockExtended = Object.assign({ extras: {} }, block);
blockExtended.extras.reward = transactions[0].vout.reduce((acc, curr) => acc + curr.value, 0);
blockExtended.extras.coinbaseTx = transactionUtils.stripCoinbaseTransaction(transactions[0]);
const coinbaseRaw: IEsploraApi.Transaction = await bitcoinApi.$getRawTransaction(transactions[0].txid, true, false, block.id);
blockExtended.extras.coinbaseRaw = coinbaseRaw.hex;
blockExtended.extras.coinbaseRaw = transactionUtils.hex2ascii(blockExtended.extras.coinbaseTx.vin[0].scriptsig);
if (block.height === 0) {
blockExtended.extras.medianFee = 0; // 50th percentiles
@ -410,6 +408,7 @@ class Blocks {
weight: block.weight,
previousblockhash: block.previousblockhash,
extras: {
coinbaseRaw: block.coinbase_raw ?? block.extras.coinbaseRaw,
medianFee: block.medianFee ?? block.median_fee ?? block.extras?.medianFee,
feeRange: block.feeRange ?? block.fee_range ?? block?.extras?.feeSpan,
reward: block.reward ?? block?.extras?.reward,

View File

@ -6,7 +6,7 @@ import logger from '../logger';
const sleep = (ms: number) => new Promise(res => setTimeout(res, ms));
class DatabaseMigration {
private static currentVersion = 14;
private static currentVersion = 15;
private queryTimeout = 120000;
private statisticsAddedIndexed = false;
@ -175,6 +175,12 @@ class DatabaseMigration {
await this.$executeQuery(connection, 'ALTER TABLE `hashrates` MODIFY `pool_id` SMALLINT UNSIGNED NOT NULL DEFAULT "0"');
}
if (databaseSchemaVersion < 15 && isBitcoin === true) {
logger.warn(`'blocks' table has been truncated. Re-indexing from scratch.`);
await this.$executeQuery(connection, 'TRUNCATE blocks;'); // Need to re-index
await this.$executeQuery(connection, 'ALTER TABLE `blocks` MODIFY `coinbase_raw` TEXT COLLATE "utf8mb4_general_ci" NULL ');
}
connection.release();
} catch (e) {
connection.release();

View File

@ -45,12 +45,21 @@ class TransactionUtils {
return transactionExtended;
}
public hex2ascii(hex: string) {
let str = '';
for (let i = 0; i < hex.length; i += 2) {
str += String.fromCharCode(parseInt(hex.substr(i, 2), 16));
public hex2ascii(hex: string): string {
const opPush = hex.split(' ').filter((_, i, a) => i > 0 && /^OP_PUSH/.test(a[i - 1]));
if (opPush[0]) {
hex = opPush[0];
}
return str;
if (!hex) {
return '';
}
const bytes: number[] = [];
for (let i = 0; i < hex.length; i += 2) {
bytes.push(parseInt(hex.substr(i, 2), 16));
}
return new TextDecoder('utf8').decode(Uint8Array.from(bytes));
}
}

View File

@ -32,7 +32,7 @@ class BlocksRepository {
block.size,
block.weight,
block.tx_count,
block.extras.coinbaseRaw,
connection.escape(block.extras.coinbaseRaw),
block.difficulty,
block.extras.pool?.id, // Should always be set to something
block.extras.totalFees,
@ -56,7 +56,7 @@ class BlocksRepository {
logger.debug(`$saveBlockInDatabase() - Block ${block.height} has already been indexed, ignoring`);
} else {
connection.release();
logger.err('$saveBlockInDatabase() error' + (e instanceof Error ? e.message : e));
logger.err('$saveBlockInDatabase() error: ' + (e instanceof Error ? e.message : e));
throw e;
}
}

View File

@ -24,11 +24,14 @@
}}</a>
</td>
<td class="pool text-left" [class]="widget ? 'widget' : ''">
<a class="clear-link" [routerLink]="[('/mining/pool/' + block.extras.pool.id) | relativeUrl]">
<img width="25" height="25" src="{{ block.extras.pool['logo'] }}"
onError="this.src = './resources/mining-pools/default.svg'">
<span class="pool-name">{{ block.extras.pool.name }}</span>
</a>
<div class="tooltip-custom">
<a class="clear-link" [routerLink]="[('/mining/pool/' + block.extras.pool.id) | relativeUrl]">
<img width="25" height="25" src="{{ block.extras.pool['logo'] }}"
onError="this.src = './resources/mining-pools/default.svg'">
<span class="pool-name">{{ block.extras.pool.name }}</span>
</a>
<span class="tooltiptext">{{ block.extras.coinbaseRaw }}</span>
</div>
</td>
<td class="timestamp" *ngIf="!widget">
&lrm;{{ block.timestamp * 1000 | date:'yyyy-MM-dd HH:mm' }}

View File

@ -122,3 +122,27 @@ td {
display: none;
}
}
/* Tooltip text */
.tooltip-custom {
position: relative;
}
.tooltip-custom .tooltiptext {
visibility: hidden;
background-color: black;
color: #fff;
text-align: center;
padding: 5px 0;
border-radius: 6px;
position: absolute;
z-index: 1;
// width: 120px;
top: -40px;
left: 0;
}
/* Show the tooltip text when you mouse over the tooltip container */
.tooltip-custom:hover .tooltiptext {
visibility: visible;
}

View File

@ -102,6 +102,7 @@ export interface BlockExtension {
feeRange?: number[];
reward?: number;
coinbaseTx?: Transaction;
coinbaseRaw?: string;
matchRate?: number;
pool?: {
id: number;

View File

@ -15,7 +15,7 @@ export class Hex2asciiPipe implements PipeTransform {
if (!hex) {
return '';
}
let bytes: number[] = [];
const bytes: number[] = [];
for (let i = 0; i < hex.length; i += 2) {
bytes.push(parseInt(hex.substr(i, 2), 16));
}