Skip to content

Commit 9470892

Browse files
committed
feat: gix revision list --long-hashes for faster iteration.
The performance of the short-hash generation was improved as well.
1 parent b8f2ab6 commit 9470892

File tree

5 files changed

+52
-38
lines changed

5 files changed

+52
-38
lines changed

gitoxide-core/src/repository/commitgraph/list.rs

Lines changed: 1 addition & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
11
pub(crate) mod function {
2+
use crate::repository::HexId;
23
use crate::OutputFormat;
34
use anyhow::{bail, Context};
45
use gix::odb::store::RefreshMode;
56
use gix::revision::plumbing::Spec;
67
use gix::{prelude::ObjectIdExt, revision::walk::Sorting};
7-
use std::fmt::Formatter;
88
use std::{borrow::Cow, ffi::OsString};
99

1010
pub fn list(
@@ -70,23 +70,4 @@ pub(crate) mod function {
7070
.context("Need committish as starting point")?
7171
.id())
7272
}
73-
74-
struct HexId<'a>(gix::Id<'a>, bool);
75-
76-
impl<'a> HexId<'a> {
77-
pub fn new(id: gix::Id<'a>, long_hex: bool) -> Self {
78-
HexId(id, long_hex)
79-
}
80-
}
81-
82-
impl std::fmt::Display for HexId<'_> {
83-
fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
84-
let HexId(id, long_hex) = self;
85-
if *long_hex {
86-
id.fmt(f)
87-
} else {
88-
id.shorten_or_id().fmt(f)
89-
}
90-
}
91-
}
9273
}

gitoxide-core/src/repository/mod.rs

Lines changed: 34 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1,22 +1,9 @@
1+
use std::fmt::Formatter;
12
use std::path::PathBuf;
23

34
use anyhow::{Context as AnyhowContext, Result};
45
use gix::bstr::BString;
56

6-
pub fn init(directory: Option<PathBuf>) -> Result<gix::discover::repository::Path> {
7-
gix::create::into(
8-
directory.unwrap_or_default(),
9-
gix::create::Kind::WithWorktree,
10-
gix::create::Options::default(),
11-
)
12-
.with_context(|| "Repository initialization failed")
13-
}
14-
15-
pub enum PathsOrPatterns {
16-
Paths(Box<dyn std::iter::Iterator<Item = BString>>),
17-
Patterns(Vec<BString>),
18-
}
19-
207
#[cfg(feature = "archive")]
218
pub mod archive;
229
pub mod cat;
@@ -60,3 +47,36 @@ pub mod submodule;
6047
pub mod tree;
6148
pub mod verify;
6249
pub mod worktree;
50+
51+
pub fn init(directory: Option<PathBuf>) -> Result<gix::discover::repository::Path> {
52+
gix::create::into(
53+
directory.unwrap_or_default(),
54+
gix::create::Kind::WithWorktree,
55+
gix::create::Options::default(),
56+
)
57+
.with_context(|| "Repository initialization failed")
58+
}
59+
60+
pub enum PathsOrPatterns {
61+
Paths(Box<dyn std::iter::Iterator<Item = BString>>),
62+
Patterns(Vec<BString>),
63+
}
64+
65+
struct HexId<'a>(gix::Id<'a>, bool);
66+
67+
impl<'a> HexId<'a> {
68+
pub fn new(id: gix::Id<'a>, long_hex: bool) -> Self {
69+
HexId(id, long_hex)
70+
}
71+
}
72+
73+
impl std::fmt::Display for HexId<'_> {
74+
fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
75+
let HexId(id, long_hex) = self;
76+
if *long_hex {
77+
id.fmt(f)
78+
} else {
79+
id.shorten_or_id().fmt(f)
80+
}
81+
}
82+
}

gitoxide-core/src/repository/revision/list.rs

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ pub struct Context {
77
pub spec: OsString,
88
pub format: OutputFormat,
99
pub text: Format,
10+
pub long_hashes: bool,
1011
}
1112

1213
pub enum Format {
@@ -16,16 +17,17 @@ pub enum Format {
1617
pub const PROGRESS_RANGE: std::ops::RangeInclusive<u8> = 0..=2;
1718

1819
pub(crate) mod function {
20+
use crate::repository::HexId;
21+
use crate::{repository::revision::list::Format, OutputFormat};
1922
use anyhow::{bail, Context};
23+
use gix::odb::store::RefreshMode;
2024
use gix::{hashtable::HashMap, revision::walk::Sorting, Progress};
2125
use layout::{
2226
backends::svg::SVGWriter,
2327
core::{base::Orientation, geometry::Point, style::StyleAttr},
2428
std_shapes::shapes::{Arrow, Element, ShapeKind},
2529
};
2630

27-
use crate::{repository::revision::list::Format, OutputFormat};
28-
2931
pub fn list(
3032
mut repo: gix::Repository,
3133
mut progress: impl Progress,
@@ -35,12 +37,14 @@ pub(crate) mod function {
3537
format,
3638
text,
3739
limit,
40+
long_hashes,
3841
}: super::Context,
3942
) -> anyhow::Result<()> {
4043
if format != OutputFormat::Human {
4144
bail!("Only human output is currently supported");
4245
}
4346
repo.object_cache_size_if_unset(4 * 1024 * 1024);
47+
repo.objects.refresh = RefreshMode::Never;
4448

4549
let spec = gix::path::os_str_into_bstr(&spec)?;
4650
let id = repo
@@ -101,7 +105,7 @@ pub(crate) mod function {
101105
writeln!(
102106
out,
103107
"{} {} {}",
104-
commit.id().shorten_or_id(),
108+
HexId::new(commit.id(), long_hashes),
105109
commit.commit_time.expect("traversal with date"),
106110
commit.parent_ids.len()
107111
)?;

src/plumbing/main.rs

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1148,7 +1148,12 @@ pub fn main() -> Result<()> {
11481148
},
11491149
),
11501150
Subcommands::Revision(cmd) => match cmd {
1151-
revision::Subcommands::List { spec, svg, limit } => prepare_and_run(
1151+
revision::Subcommands::List {
1152+
spec,
1153+
svg,
1154+
limit,
1155+
long_hashes,
1156+
} => prepare_and_run(
11521157
"revision-list",
11531158
trace,
11541159
auto_verbose,
@@ -1164,6 +1169,7 @@ pub fn main() -> Result<()> {
11641169
limit,
11651170
spec,
11661171
format,
1172+
long_hashes,
11671173
text: svg.map_or(core::repository::revision::list::Format::Text, |path| {
11681174
core::repository::revision::list::Format::Svg { path }
11691175
}),

src/plumbing/options/mod.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -996,6 +996,9 @@ pub mod revision {
996996
/// List all commits reachable from the given rev-spec.
997997
#[clap(visible_alias = "l")]
998998
List {
999+
/// Display long hashes, instead of expensively shortened versions for best performance.
1000+
#[clap(long, short = 'l')]
1001+
long_hashes: bool,
9991002
/// How many commits to list at most.
10001003
#[clap(long, short = 'l')]
10011004
limit: Option<usize>,

0 commit comments

Comments
 (0)