gitoxide_core/repository/
verify.rs

1use std::sync::atomic::AtomicBool;
2
3use crate::{pack, OutputFormat};
4
5/// A general purpose context for many operations provided here
6pub struct Context {
7    /// If set, provide statistics to `out` in the given format
8    pub output_statistics: Option<OutputFormat>,
9    /// If set, don't use more than this amount of threads.
10    /// Otherwise, usually use as many threads as there are logical cores.
11    /// A value of 0 is interpreted as no-limit
12    pub thread_limit: Option<usize>,
13    pub verify_mode: pack::verify::Mode,
14    pub algorithm: pack::verify::Algorithm,
15}
16
17pub const PROGRESS_RANGE: std::ops::RangeInclusive<u8> = 1..=3;
18
19pub fn integrity(
20    repo: gix::Repository,
21    mut out: impl std::io::Write,
22    mut progress: impl gix::NestedProgress + 'static,
23    should_interrupt: &AtomicBool,
24    Context {
25        output_statistics,
26        thread_limit,
27        verify_mode,
28        algorithm,
29    }: Context,
30) -> anyhow::Result<()> {
31    #[cfg_attr(not(feature = "serde"), allow(unused))]
32    let outcome = repo.objects.store_ref().verify_integrity(
33        &mut progress,
34        should_interrupt,
35        gix::odb::pack::index::verify::integrity::Options {
36            verify_mode,
37            traversal: algorithm.into(),
38            thread_limit,
39            // TODO: a way to get the pack cache from a handle
40            make_pack_lookup_cache: || gix::odb::pack::cache::Never,
41        },
42    )?;
43    if let Some(index) = repo.worktree().map(|wt| wt.index()).transpose()? {
44        index.verify_integrity()?;
45        index.verify_entries()?;
46        index.verify_extensions(true, repo.objects)?;
47        progress.info(format!("Index at '{}' OK", index.path().display()));
48    }
49    match output_statistics {
50        Some(OutputFormat::Human) => writeln!(out, "Human output is currently unsupported, use JSON instead")?,
51        #[cfg(feature = "serde")]
52        Some(OutputFormat::Json) => {
53            serde_json::to_writer_pretty(
54                out,
55                &serde_json::json!({
56                    "index_statistics" : outcome.index_statistics,
57                    "loose_object-stores" : outcome.loose_object_stores
58                }),
59            )?;
60        }
61        None => {}
62    }
63    Ok(())
64}