Skip to content

Commit 322f473

Browse files
author
Ludo Galabru
committed
feat: add command to check stacks db integrity
1 parent 6dacc3a commit 322f473

File tree

1 file changed

+61
-12
lines changed
  • components/chainhook-cli/src/cli

1 file changed

+61
-12
lines changed

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

+61-12
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,9 @@ use crate::config::{Config, PredicatesApi};
44
use crate::scan::bitcoin::scan_bitcoin_chainstate_via_rpc_using_predicate;
55
use crate::scan::stacks::scan_stacks_chainstate_via_csv_using_predicate;
66
use crate::service::Service;
7+
use crate::storage::{
8+
get_last_block_height_inserted, is_stacks_block_present, open_readonly_stacks_db_conn,
9+
};
710

811
use chainhook_sdk::bitcoincore_rpc::{Auth, Client, RpcApi};
912
use chainhook_sdk::chainhooks::types::{
@@ -59,9 +62,12 @@ enum Command {
5962
/// Run a service streaming blocks and evaluating registered predicates
6063
#[clap(subcommand)]
6164
Service(ServiceCommand),
62-
/// Explore the Ordinal Theory
65+
/// Ordinals related subcommands
6366
#[clap(subcommand)]
6467
Hord(HordCommand),
68+
/// Stacks related subcommands
69+
#[clap(subcommand)]
70+
Stacks(StacksCommand),
6571
}
6672

6773
#[derive(Subcommand, PartialEq, Clone, Debug)]
@@ -192,14 +198,14 @@ struct StartCommand {
192198
enum HordCommand {
193199
/// Db maintenance related commands
194200
#[clap(subcommand)]
195-
Db(DbCommand),
201+
Db(HordDbCommand),
196202
/// Db maintenance related commands
197203
#[clap(subcommand)]
198204
Scan(ScanCommand),
199205
}
200206

201207
#[derive(Subcommand, PartialEq, Clone, Debug)]
202-
enum DbCommand {
208+
enum HordDbCommand {
203209
/// Rewrite hord db
204210
#[clap(name = "rewrite", bin_name = "rewrite")]
205211
Rewrite(UpdateHordDbCommand),
@@ -211,7 +217,7 @@ enum DbCommand {
211217
Drop(DropHordDbCommand),
212218
/// Check integrity
213219
#[clap(name = "check", bin_name = "check")]
214-
Check(CheckHordDbCommand),
220+
Check(CheckDbCommand),
215221
/// Patch DB
216222
#[clap(name = "patch", bin_name = "patch")]
217223
Patch(PatchHordDbCommand),
@@ -220,6 +226,20 @@ enum DbCommand {
220226
Migrate(MigrateHordDbCommand),
221227
}
222228

229+
#[derive(Subcommand, PartialEq, Clone, Debug)]
230+
enum StacksCommand {
231+
/// Db maintenance related commands
232+
#[clap(subcommand)]
233+
Db(StacksDbCommand),
234+
}
235+
236+
#[derive(Subcommand, PartialEq, Clone, Debug)]
237+
enum StacksDbCommand {
238+
/// Check integrity
239+
#[clap(name = "check", bin_name = "check")]
240+
Check(CheckDbCommand),
241+
}
242+
223243
#[derive(Subcommand, PartialEq, Clone, Debug)]
224244
enum ScanCommand {
225245
/// Compute ordinal number of the 1st satoshi of the 1st input of a given transaction
@@ -348,7 +368,7 @@ struct MigrateHordDbCommand {
348368
}
349369

350370
#[derive(Parser, PartialEq, Clone, Debug)]
351-
struct CheckHordDbCommand {
371+
struct CheckDbCommand {
352372
/// Load config file path
353373
#[clap(long = "config-path")]
354374
pub config_path: Option<String>,
@@ -752,7 +772,7 @@ async fn handle_command(opts: Opts, ctx: Context) -> Result<(), String> {
752772
}
753773
},
754774
Command::Hord(HordCommand::Db(subcmd)) => match subcmd {
755-
DbCommand::Sync(cmd) => {
775+
HordDbCommand::Sync(cmd) => {
756776
let config = Config::default(false, false, false, &cmd.config_path)?;
757777
if let Some((start_block, end_block)) = should_sync_hord_db(&config, &ctx)? {
758778
if start_block == 0 {
@@ -778,7 +798,7 @@ async fn handle_command(opts: Opts, ctx: Context) -> Result<(), String> {
778798
info!(ctx.expect_logger(), "Database hord up to date");
779799
}
780800
}
781-
DbCommand::Rewrite(cmd) => {
801+
HordDbCommand::Rewrite(cmd) => {
782802
let config = Config::default(false, false, false, &cmd.config_path)?;
783803
// Delete data, if any
784804
{
@@ -805,15 +825,15 @@ async fn handle_command(opts: Opts, ctx: Context) -> Result<(), String> {
805825
)
806826
.await?;
807827
}
808-
DbCommand::Check(cmd) => {
828+
HordDbCommand::Check(cmd) => {
809829
let config = Config::default(false, false, false, &cmd.config_path)?;
810830
// Delete data, if any
811831
{
812832
let blocks_db_rw =
813833
open_readwrite_hord_db_conn_rocks_db(&config.expected_cache_path(), &ctx)?;
814834

815835
let mut missing_blocks = vec![];
816-
for i in 1..=780000 {
836+
for i in 1..=790000 {
817837
if find_lazy_block_at_block_height(i, 3, &blocks_db_rw).is_none() {
818838
println!("Missing block {i}");
819839
missing_blocks.push(i);
@@ -822,7 +842,7 @@ async fn handle_command(opts: Opts, ctx: Context) -> Result<(), String> {
822842
println!("{:?}", missing_blocks);
823843
}
824844
}
825-
DbCommand::Drop(cmd) => {
845+
HordDbCommand::Drop(cmd) => {
826846
let config = Config::default(false, false, false, &cmd.config_path)?;
827847
let blocks_db =
828848
open_readwrite_hord_db_conn_rocks_db(&config.expected_cache_path(), &ctx)?;
@@ -842,13 +862,42 @@ async fn handle_command(opts: Opts, ctx: Context) -> Result<(), String> {
842862
cmd.end_block - cmd.start_block + 1
843863
);
844864
}
845-
DbCommand::Patch(_cmd) => {
865+
HordDbCommand::Patch(_cmd) => {
846866
unimplemented!()
847867
}
848-
DbCommand::Migrate(_cmd) => {
868+
HordDbCommand::Migrate(_cmd) => {
849869
unimplemented!()
850870
}
851871
},
872+
Command::Stacks(StacksCommand::Db(StacksDbCommand::Check(cmd))) => {
873+
let config = Config::default(false, false, false, &cmd.config_path)?;
874+
// Delete data, if any
875+
{
876+
let stacks_db = open_readonly_stacks_db_conn(&config.expected_cache_path(), &ctx)?;
877+
let mut missing_blocks = vec![];
878+
if let Some(tip) = get_last_block_height_inserted(&stacks_db, &ctx) {
879+
for index in 1..=tip {
880+
let block_identifier = BlockIdentifier {
881+
index: i,
882+
hash: "".into(),
883+
};
884+
if !is_stacks_block_present(&block_identifier, 3, &stacks_db) {
885+
missing_blocks.push(i);
886+
}
887+
}
888+
}
889+
if missing_blocks.is_empty() {
890+
info!(ctx.expect_logger(), "Stacks db successfully checked");
891+
} else {
892+
warn!(
893+
ctx.expect_logger(),
894+
"Stacks db includes {} missing entries: {:?}",
895+
missing_blocks.len(),
896+
missing_blocks
897+
);
898+
}
899+
}
900+
}
852901
}
853902
Ok(())
854903
}

0 commit comments

Comments
 (0)