use anyhow::{Context, Result};
use clap::Parser;
use log::info;
#[derive(Parser, Debug)]
#[command(author, version, about, long_about = None)]
struct Args {
#[arg(short, long)]
input: String,
#[arg(short = 's', long)]
start_offset: u64,
#[arg(short = 'e', long)]
end_offset: u64,
#[arg(short, long)]
output: Option<String>,
#[arg(short, long, default_value = "fastq")]
format: String,
#[arg(short = 'l', long, default_value = "info")]
log_level: String,
}
fn main() -> Result<()> {
let args = Args::parse();
env_logger::Builder::from_env(env_logger::Env::default().default_filter_or(&args.log_level))
.init();
if args.start_offset >= args.end_offset {
anyhow::bail!(
"start_offset ({}) must be less than end_offset ({})",
args.start_offset,
args.end_offset
);
}
let mut writer: Box<dyn std::io::Write> = if let Some(output_path) = &args.output {
let file = std::fs::File::create(output_path)
.with_context(|| format!("Failed to create output file {output_path}"))?;
Box::new(std::io::BufWriter::new(file))
} else {
let stdout = std::io::stdout();
Box::new(std::io::BufWriter::new(stdout.lock()))
};
let format = match args.format.as_str() {
"fastq" => bamslice::OutputFormat::Fastq,
"bam" => bamslice::OutputFormat::Bam,
other => anyhow::bail!("Unknown format '{other}'. Expected 'fastq' or 'bam'."),
};
let processed_reads = bamslice::process_blocks(
&args.input,
args.start_offset,
args.end_offset,
&mut writer,
format,
)?;
info!("Total reads extracted: {processed_reads}");
Ok(())
}