Skip to content

Commit d071484

Browse files
author
Ludo Galabru
committed
feat: polish hord find sat_point command
1 parent c49b54d commit d071484

File tree

3 files changed

+90
-53
lines changed

3 files changed

+90
-53
lines changed

components/chainhook-cli/src/cli/mod.rs

+57-43
Original file line numberDiff line numberDiff line change
@@ -13,8 +13,8 @@ use chainhook_event_observer::chainhooks::types::{
1313
StacksPrintEventBasedPredicate,
1414
};
1515
use chainhook_event_observer::hord::db::{
16-
fetch_and_cache_blocks_in_hord_db, find_inscriptions_at_wached_outpoint, initialize_hord_db,
17-
open_readonly_hord_db_conn, open_readwrite_hord_db_conn,
16+
fetch_and_cache_blocks_in_hord_db, find_inscriptions_at_wached_outpoint,
17+
find_latest_compacted_block_known, open_readonly_hord_db_conn, open_readwrite_hord_db_conn,
1818
retrieve_satoshi_point_using_local_storage,
1919
};
2020
use chainhook_event_observer::observer::BitcoinConfig;
@@ -203,8 +203,6 @@ struct FindSatPointCommand {
203203
pub block_height: u64,
204204
/// Txid
205205
pub txid: String,
206-
/// Output index
207-
pub output_index: usize,
208206
/// Target Devnet network
209207
#[clap(
210208
long = "devnet",
@@ -455,6 +453,21 @@ async fn handle_command(opts: Opts, ctx: Context) -> Result<(), String> {
455453
FindCommand::SatPoint(cmd) => {
456454
let config =
457455
Config::default(cmd.devnet, cmd.testnet, cmd.mainnet, &cmd.config_path)?;
456+
457+
info!(
458+
ctx.expect_logger(),
459+
"Computing satoshi number for satoshi at offet 0 in 1st output of transaction {} (block ${})", cmd.txid, cmd.block_height
460+
);
461+
462+
let hord_db_conn =
463+
open_readonly_hord_db_conn(&config.expected_cache_path(), &ctx).unwrap();
464+
465+
let tip_height = find_latest_compacted_block_known(&hord_db_conn) as u64;
466+
467+
if cmd.block_height > tip_height {
468+
perform_hord_db_update(tip_height, cmd.block_height, 8, &config, &ctx).await?;
469+
}
470+
458471
let transaction_identifier = TransactionIdentifier {
459472
hash: cmd.txid.clone(),
460473
};
@@ -463,10 +476,7 @@ async fn handle_command(opts: Opts, ctx: Context) -> Result<(), String> {
463476
hash: "".into(),
464477
};
465478

466-
let hord_db_conn =
467-
open_readonly_hord_db_conn(&config.expected_cache_path(), &ctx).unwrap();
468-
469-
let (block_height, offset, ordinal_number) =
479+
let (block_height, offset, ordinal_number, hops) =
470480
retrieve_satoshi_point_using_local_storage(
471481
&hord_db_conn,
472482
&block_identifier,
@@ -475,7 +485,7 @@ async fn handle_command(opts: Opts, ctx: Context) -> Result<(), String> {
475485
)?;
476486
info!(
477487
ctx.expect_logger(),
478-
"Block: {block_height}, Offset {offset}:, Ordinal number: {ordinal_number}",
488+
"Satoshi #{ordinal_number} was minted in block #{block_height} at offset {offset} and was transferred {hops} times.",
479489
);
480490
}
481491
FindCommand::Inscription(cmd) => {
@@ -491,14 +501,6 @@ async fn handle_command(opts: Opts, ctx: Context) -> Result<(), String> {
491501
Command::Hord(HordCommand::Db(subcmd)) => match subcmd {
492502
DbCommand::Init(cmd) => {
493503
let config = Config::default(false, false, false, &cmd.config_path)?;
494-
495-
let bitcoin_config = BitcoinConfig {
496-
username: config.network.bitcoin_node_rpc_username.clone(),
497-
password: config.network.bitcoin_node_rpc_password.clone(),
498-
rpc_url: config.network.bitcoin_node_rpc_url.clone(),
499-
network: config.network.bitcoin_network.clone(),
500-
};
501-
502504
let auth = Auth::UserPass(
503505
config.network.bitcoin_node_rpc_username.clone(),
504506
config.network.bitcoin_node_rpc_password.clone(),
@@ -521,38 +523,16 @@ async fn handle_command(opts: Opts, ctx: Context) -> Result<(), String> {
521523
}
522524
};
523525

524-
let rw_hord_db_conn = initialize_hord_db(&config.expected_cache_path(), &ctx);
525-
526-
let _ = fetch_and_cache_blocks_in_hord_db(
527-
&bitcoin_config,
528-
&rw_hord_db_conn,
529-
0,
530-
end_block,
531-
&ctx,
532-
cmd.network_threads,
533-
)
534-
.await?;
526+
perform_hord_db_update(0, end_block, cmd.network_threads, &config, &ctx).await?;
535527
}
536528
DbCommand::Update(cmd) => {
537529
let config = Config::default(false, false, false, &cmd.config_path)?;
538-
539-
let bitcoin_config = BitcoinConfig {
540-
username: config.network.bitcoin_node_rpc_username.clone(),
541-
password: config.network.bitcoin_node_rpc_password.clone(),
542-
rpc_url: config.network.bitcoin_node_rpc_url.clone(),
543-
network: config.network.bitcoin_network.clone(),
544-
};
545-
546-
let rw_hord_db_conn =
547-
open_readwrite_hord_db_conn(&config.expected_cache_path(), &ctx)?;
548-
549-
let _ = fetch_and_cache_blocks_in_hord_db(
550-
&bitcoin_config,
551-
&rw_hord_db_conn,
530+
perform_hord_db_update(
552531
cmd.start_block,
553532
cmd.end_block,
554-
&ctx,
555533
cmd.network_threads,
534+
&config,
535+
&ctx,
556536
)
557537
.await?;
558538
}
@@ -561,6 +541,40 @@ async fn handle_command(opts: Opts, ctx: Context) -> Result<(), String> {
561541
Ok(())
562542
}
563543

544+
pub async fn perform_hord_db_update(
545+
start_block: u64,
546+
end_block: u64,
547+
network_threads: usize,
548+
config: &Config,
549+
ctx: &Context,
550+
) -> Result<(), String> {
551+
info!(
552+
ctx.expect_logger(),
553+
"Syncing hord_db: {} blocks to download ({start_block}: {end_block}), using {network_threads} network threads", end_block - start_block
554+
);
555+
556+
let bitcoin_config = BitcoinConfig {
557+
username: config.network.bitcoin_node_rpc_username.clone(),
558+
password: config.network.bitcoin_node_rpc_password.clone(),
559+
rpc_url: config.network.bitcoin_node_rpc_url.clone(),
560+
network: config.network.bitcoin_network.clone(),
561+
};
562+
563+
let rw_hord_db_conn = open_readwrite_hord_db_conn(&config.expected_cache_path(), &ctx)?;
564+
565+
let _ = fetch_and_cache_blocks_in_hord_db(
566+
&bitcoin_config,
567+
&rw_hord_db_conn,
568+
start_block,
569+
end_block,
570+
&ctx,
571+
network_threads,
572+
)
573+
.await?;
574+
575+
Ok(())
576+
}
577+
564578
#[allow(dead_code)]
565579
pub fn install_ctrlc_handler(terminate_tx: Sender<DigestingCommand>, ctx: Context) {
566580
ctrlc::set_handler(move || {

components/chainhook-event-observer/src/hord/db/mod.rs

+30-7
Original file line numberDiff line numberDiff line change
@@ -302,7 +302,23 @@ pub fn update_transfered_inscription(
302302
}
303303
}
304304

305-
pub fn find_last_inscription_number(
305+
pub fn find_latest_inscription_block_height(
306+
hord_db_conn: &Connection,
307+
_ctx: &Context,
308+
) -> Result<u64, String> {
309+
let args: &[&dyn ToSql] = &[];
310+
let mut stmt = hord_db_conn
311+
.prepare("SELECT block_height FROM inscriptions ORDER BY block_height DESC LIMIT 1")
312+
.unwrap();
313+
let mut rows = stmt.query(args).unwrap();
314+
while let Ok(Some(row)) = rows.next() {
315+
let block_height: u64 = row.get(0).unwrap();
316+
return Ok(block_height);
317+
}
318+
Ok(0)
319+
}
320+
321+
pub fn find_latest_inscription_number(
306322
hord_db_conn: &Connection,
307323
_ctx: &Context,
308324
) -> Result<u64, String> {
@@ -513,7 +529,7 @@ pub async fn fetch_and_cache_blocks_in_hord_db(
513529
let (block_compressed_tx, block_compressed_rx) = crossbeam_channel::unbounded();
514530
let first_inscription_block_height = 767430;
515531

516-
for block_cursor in start_block..end_block {
532+
for block_cursor in start_block..=end_block {
517533
let block_height = block_cursor.clone();
518534
let block_hash_tx = block_hash_tx.clone();
519535
let config = bitcoin_config.clone();
@@ -573,7 +589,8 @@ pub async fn fetch_and_cache_blocks_in_hord_db(
573589
.expect("unable to spawn thread");
574590

575591
let mut blocks_stored = 0;
576-
let mut cursor = first_inscription_block_height;
592+
let mut cursor = find_latest_inscription_block_height(&rw_hord_db_conn, &ctx)
593+
.unwrap_or(first_inscription_block_height) as usize;
577594
let mut inbox = HashMap::new();
578595

579596
while let Ok(Some((block_height, compacted_block, raw_block))) = block_compressed_rx.recv() {
@@ -582,7 +599,7 @@ pub async fn fetch_and_cache_blocks_in_hord_db(
582599
insert_entry_in_blocks(block_height, &compacted_block, &rw_hord_db_conn, &ctx);
583600

584601
// Early return, only considering blocks after 1st inscription
585-
if raw_block.height < first_inscription_block_height {
602+
if raw_block.height < cursor {
586603
continue;
587604
}
588605
let block_height = raw_block.height;
@@ -645,16 +662,17 @@ pub fn retrieve_satoshi_point_using_local_storage(
645662
block_identifier: &BlockIdentifier,
646663
transaction_identifier: &TransactionIdentifier,
647664
ctx: &Context,
648-
) -> Result<(u64, u64, u64), String> {
665+
) -> Result<(u64, u64, u64, u32), String> {
649666
let mut ordinal_offset = 0;
650667
let mut ordinal_block_number = block_identifier.index as u32;
651668
let txid = {
652669
let bytes = hex::decode(&transaction_identifier.hash[2..]).unwrap();
653670
[bytes[0], bytes[1], bytes[2], bytes[3]]
654671
};
655672
let mut tx_cursor = (txid, 0);
656-
673+
let mut hops: u32 = 0;
657674
loop {
675+
hops += 1;
658676
let res = match find_compacted_block_at_block_height(ordinal_block_number, &hord_db_conn) {
659677
Some(res) => res,
660678
None => {
@@ -776,5 +794,10 @@ pub fn retrieve_satoshi_point_using_local_storage(
776794
let height = Height(ordinal_block_number.into());
777795
let ordinal_number = height.starting_sat().0 + ordinal_offset;
778796

779-
Ok((ordinal_block_number.into(), ordinal_offset, ordinal_number))
797+
Ok((
798+
ordinal_block_number.into(),
799+
ordinal_offset,
800+
ordinal_number,
801+
hops,
802+
))
780803
}

components/chainhook-event-observer/src/hord/mod.rs

+3-3
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ use crate::{
1313
hord::{
1414
db::{
1515
find_inscription_with_ordinal_number, find_inscriptions_at_wached_outpoint,
16-
find_last_inscription_number, insert_entry_in_blocks,
16+
find_latest_inscription_number, insert_entry_in_blocks,
1717
retrieve_satoshi_point_using_local_storage, store_new_inscription,
1818
update_transfered_inscription, CompactedBlock,
1919
},
@@ -98,7 +98,7 @@ pub fn update_hord_db_and_augment_bitcoin_block(
9898
new_tx.metadata.ordinal_operations.iter_mut().enumerate()
9999
{
100100
if let OrdinalOperation::InscriptionRevealed(inscription) = ordinal_event {
101-
let (ordinal_block_height, ordinal_offset, ordinal_number) = {
101+
let (ordinal_block_height, ordinal_offset, ordinal_number, _) = {
102102
// Are we looking at a re-inscription?
103103
let res = retrieve_satoshi_point_using_local_storage(
104104
&rw_hord_db_conn,
@@ -140,7 +140,7 @@ pub fn update_hord_db_and_augment_bitcoin_block(
140140
inscription.ordinal_block_height = ordinal_block_height;
141141
inscription.ordinal_number = ordinal_number;
142142
inscription.inscription_number =
143-
match find_last_inscription_number(&rw_hord_db_conn, &ctx) {
143+
match find_latest_inscription_number(&rw_hord_db_conn, &ctx) {
144144
Ok(inscription_number) => inscription_number,
145145
Err(e) => {
146146
ctx.try_log(|logger| {

0 commit comments

Comments
 (0)