Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add blockchain.getBlockStats, blockchain.getBestBlockHash RPC #256

Merged
merged 14 commits into from
May 27, 2021
Merged
Original file line number Diff line number Diff line change
Expand Up @@ -314,4 +314,67 @@ describe('masternode', () => {
})
})
})

describe('getBlockStats', () => {
it('should get blockchain stats and return all values', async () => {
const blockHash = await waitForBlockHash(1)
const stats = await client.blockchain.getBlockStats(blockHash)
siradji marked this conversation as resolved.
Show resolved Hide resolved

expect(stats.height).toStrictEqual(1)
expect(stats.minfee).toBeLessThanOrEqual(stats.medianfee)
expect(stats.medianfee).toBeLessThanOrEqual(stats.maxfee)
expect(stats.mediantxsize).toBeLessThanOrEqual(stats.maxtxsize)
expect(stats.avgfeerate).toBeLessThanOrEqual(stats.maxfeerate)
expect(stats.minfeerate).toBeLessThanOrEqual(stats.maxfeerate)
expect(stats.mintxsize).toBeLessThanOrEqual(stats.mediantxsize)
expect(stats.utxo_increase).toStrictEqual(stats.outs - stats.ins)

expect(typeof stats.utxo_size_inc).toStrictEqual('number')
expect(typeof stats.avgfee).toStrictEqual('number')
expect(typeof stats.avgtxsize).toStrictEqual('number')
expect(typeof stats.blockhash).toStrictEqual('string')
expect(typeof stats.outs).toStrictEqual('number')
expect(typeof stats.totalfee).toStrictEqual('number')
expect(typeof stats.total_out).toStrictEqual('number')
expect(typeof stats.total_size).toStrictEqual('number')
expect(typeof stats.total_weight).toStrictEqual('number')
expect(typeof stats.time).toStrictEqual('number')
expect(typeof stats.swtotal_size).toStrictEqual('number')
expect(typeof stats.swtxs).toStrictEqual('number')
expect(typeof stats.swtxs).toStrictEqual('number')
expect(typeof stats.swtotal_weight).toStrictEqual('number')
expect(typeof stats.subsidy).toStrictEqual('number')
expect(typeof stats.txs).toStrictEqual('number')
expect(typeof stats.minfeerate).toStrictEqual('number')

expect(stats.feerate_percentiles.length).toStrictEqual(5)
expect(stats.feerate_percentiles[0]).toBeLessThanOrEqual(stats.feerate_percentiles[1])
expect(stats.feerate_percentiles[1]).toBeLessThanOrEqual(stats.feerate_percentiles[2])
expect(stats.feerate_percentiles[2]).toBeLessThanOrEqual(stats.feerate_percentiles[3])
expect(stats.feerate_percentiles[3]).toBeLessThanOrEqual(stats.feerate_percentiles[4])
})

it('should get blockchain stats with specific values', async () => {
const blockHash = await waitForBlockHash(1)
const stats = await client.blockchain.getBlockStats(blockHash, ['avgfee', 'height'])

expect('height' in stats).toStrictEqual(true)
expect('avgfee' in stats).toStrictEqual(true)
expect(stats.height).toStrictEqual(1)
expect(Object.keys(stats).length).toStrictEqual(2)
})

it('should fail when a negative height is provided', async () => {
const promise = client.blockchain.getBlockStats(-1, ['avgfee', 'height'])
await expect(promise).rejects.toThrow('Target block height -1 is negative')
})
})
fuxingloh marked this conversation as resolved.
Show resolved Hide resolved

describe('getBestBlockHash', () => {
it('should get hash of best block and return a string', async () => {
const bestBlockHash = await client.blockchain.getBestBlockHash()

expect(typeof bestBlockHash).toStrictEqual('string')
})
})
})
52 changes: 52 additions & 0 deletions packages/jellyfish-api-core/src/category/blockchain.ts
Original file line number Diff line number Diff line change
Expand Up @@ -152,6 +152,26 @@ export class Blockchain {
async getRawMempool (verbose: boolean): Promise<string[] | MempoolTx> {
return await this.client.call('getrawmempool', [verbose], 'bignumber')
}

/**
* Get block statistics for a given window.
*
* @param {number} hashOrHeight The block hash or height of the target block.
siradji marked this conversation as resolved.
Show resolved Hide resolved
* @param {Array<keyof BlockStats>} stats Default = all values. See BlockStats Interface.
* @return {Promise<BlockStats>}
*/
async getBlockStats (hashOrHeight: number | string, stats?: Array<keyof BlockStats>): Promise<BlockStats> {
return await this.client.call('getblockstats', [hashOrHeight, stats], 'number')
}

siradji marked this conversation as resolved.
Show resolved Hide resolved
/**
* Get the hash of the best (tip) block in the most-work fully-validated chain.
*
* @returns {Promise<string>}
*/
async getBestBlockHash (): Promise<string> {
return await this.client.call('getbestblockhash', [], 'number')
}
}

/**
Expand Down Expand Up @@ -306,3 +326,35 @@ export interface MempoolTx {
'bip125-replaceable': boolean
}
}

siradji marked this conversation as resolved.
Show resolved Hide resolved
export interface BlockStats {
siradji marked this conversation as resolved.
Show resolved Hide resolved
avgfee: number
avgfeerate: number
avgtxsize: number
blockhash: string
height: number
ins: number
maxfee: number
maxfeerate: number
maxtxsize: number
medianfee: number
mediantime: number
mediantxsize: number
minfee: number
minfeerate: number
mintxsize: number
outs: number
subsidy: number
swtxs: number
time: number
totalfee: number
txs: number
swtotal_size: number
swtotal_weight: number
total_out: number
total_size: number
total_weight: number
utxo_increase: number
utxo_size_inc: number
feerate_percentiles: [number, number, number, number, number]
}
54 changes: 54 additions & 0 deletions website/docs/jellyfish/api/blockchain.md
Original file line number Diff line number Diff line change
Expand Up @@ -257,3 +257,57 @@ interface MempoolTx {
}
}
```

## getBlockStats

Get block statistics for a given window. Returns all stats values if nothing is passed in the second param.


canonbrother marked this conversation as resolved.
Show resolved Hide resolved
```ts title="client.blockchain.getBlockStats()"
interface blockchain {
getBlockStats(hashOrHeight: number | string): Promise<BlockStats>
getBlockStats(hashOrHeight: number | string, stats: Array<keyof BlockStats>): Promise<BlockStats>
}

interface BlockStats {
avgfee: number
avgfeerate: number
avgtxsize: number
blockhash: string
height: number
ins: number
maxfee: number
maxfeerate: number
maxtxsize: number
medianfee: number
mediantime: number
mediantxsize: number
minfee: number
minfeerate: number
mintxsize: number
outs: number
subsidy: number
swtxs: number
time: number
totalfee: number
txs: number
swtotal_size: number
swtotal_weight: number
total_out: number
total_size: number
total_weight: number
utxo_increase: number
utxo_size_inc: number
feerate_percentiles: [number, number, number, number, number]
}
```

## getBestBlockHash

Get the hash of the best (tip) block in the most-work fully-validated chain.

```ts title="client.blockchain.getBestBlockHash()"
interface blockchain {
getBestBlockHash (): Promise<string>
}
```