use crate::cli::default_db_path;
use anyhow::Context;
use clap::Parser;
use fuel_core::{
combined_database::CombinedDatabase,
state::{
historical_rocksdb::StateRewindPolicy,
rocks_db::{
ColumnsPolicy,
DatabaseConfig,
},
},
};
use rlimit::{
getrlimit,
Resource,
};
use std::path::PathBuf;
#[derive(Debug, Clone, Parser)]
pub struct Command {
#[clap(
name = "DB_PATH",
long = "db-path",
value_parser,
default_value = default_db_path().into_os_string()
)]
pub database_path: PathBuf,
#[clap(
long = "rocksdb-max-fds",
env,
default_value = get_default_max_fds().to_string()
)]
pub rocksdb_max_fds: i32,
#[clap(long = "target-block-height")]
pub target_block_height: u32,
}
fn get_default_max_fds() -> i32 {
getrlimit(Resource::NOFILE)
.map(|(_, hard)| i32::try_from(hard.saturating_div(2)).unwrap_or(i32::MAX))
.expect("Our supported platforms should return max FD.")
}
pub async fn exec(command: Command) -> anyhow::Result<()> {
use crate::cli::ShutdownListener;
let path = command.database_path.as_path();
let db = CombinedDatabase::open(
path,
StateRewindPolicy::RewindFullRange,
DatabaseConfig {
cache_capacity: Some(64 * 1024 * 1024),
max_fds: command.rocksdb_max_fds,
columns_policy: ColumnsPolicy::Lazy,
},
)
.map_err(Into::<anyhow::Error>::into)
.context(format!("failed to open combined database at path {path:?}"))?;
let mut shutdown_listener = ShutdownListener::spawn();
let target_block_height = command.target_block_height.into();
db.rollback_to(target_block_height, &mut shutdown_listener)?;
Ok(())
}