1
1
pub(crate) mod function {
2
-
use std::{borrow::Cow, ffi::OsString};
3
-
2
+
use crate::OutputFormat;
4
3
use anyhow::{bail, Context};
4
+
use gix::odb::store::RefreshMode;
5
+
use gix::revision::plumbing::Spec;
5
6
use gix::{prelude::ObjectIdExt, revision::walk::Sorting};
6
-
7
-
use crate::OutputFormat;
7
+
use std::fmt::Formatter;
8
+
use std::{borrow::Cow, ffi::OsString};
8
9
9
10
pub fn list(
10
11
mut repo: gix::Repository,
11
12
spec: OsString,
12
13
mut out: impl std::io::Write,
14
+
long_hashes: bool,
13
15
format: OutputFormat,
14
16
) -> anyhow::Result<()> {
15
17
if format != OutputFormat::Human {
16
18
bail!("Only human output is currently supported");
17
19
}
18
20
let graph = repo
19
-
.commit_graph()
21
+
.commit_graph_if_enabled()
20
22
.context("a commitgraph is required, but none was found")?;
21
23
repo.object_cache_size_if_unset(4 * 1024 * 1024);
24
+
repo.objects.refresh = RefreshMode::Never;
22
25
23
26
let spec = gix::path::os_str_into_bstr(&spec)?;
24
-
let id = repo
25
-
.rev_parse_single(spec)
26
-
.context("Only single revisions are currently supported")?;
27
-
let commits = id
28
-
.object()?
29
-
.peel_to_kind(gix::object::Kind::Commit)
30
-
.context("Need committish as starting point")?
31
-
.id()
32
-
.ancestors()
33
-
.sorting(Sorting::ByCommitTime(Default::default()))
34
-
.all()?;
27
+
let spec = repo.rev_parse(spec)?.detach();
28
+
let commits = match spec {
29
+
Spec::Include(id) => connected_commit_id(&repo, id)?
30
+
.ancestors()
31
+
.sorting(Sorting::ByCommitTime(Default::default()))
32
+
.all()?,
33
+
Spec::Range { from, to } => connected_commit_id(&repo, to)?
34
+
.ancestors()
35
+
.sorting(Sorting::ByCommitTime(Default::default()))
36
+
.with_hidden(Some(connected_commit_id(&repo, from)?))
37
+
.all()?,
38
+
Spec::Exclude(_) | Spec::Merge { .. } | Spec::IncludeOnlyParents(_) | Spec::ExcludeParents(_) => {
39
+
bail!("The spec isn't currently supported: {spec:?}")
40
+
}
41
+
};
35
42
for commit in commits {
36
43
let commit = commit?;
37
44
writeln!(
38
45
out,
39
46
"{} {} {} {}",
40
-
commit.id().shorten_or_id(),
47
+
HexId::new(commit.id(), long_hashes),
41
48
commit.commit_time.expect("traversal with date"),
42
49
commit.parent_ids.len(),
43
-
graph.commit_by_id(commit.id).map_or_else(
44
-
|| Cow::Borrowed("<NOT IN GRAPH-CACHE>"),
45
-
|c| Cow::Owned(format!(
46
-
"{} {}",
47
-
c.root_tree_id().to_owned().attach(&repo).shorten_or_id(),
48
-
c.generation()
50
+
graph
51
+
.as_ref()
52
+
.map_or(Cow::Borrowed(""), |graph| graph.commit_by_id(commit.id).map_or_else(
53
+
|| Cow::Borrowed("<NOT IN GRAPH-CACHE>"),
54
+
|c| Cow::Owned(format!(
55
+
"{} {}",
56
+
HexId::new(c.root_tree_id().to_owned().attach(&repo), long_hashes),
57
+
c.generation()
58
+
))
49
59
))
50
-
)
51
60
)?;
52
61
}
53
62
Ok(())
54
63
}
64
+
65
+
fn connected_commit_id(repo: &gix::Repository, id: gix::ObjectId) -> anyhow::Result<gix::Id<'_>> {
66
+
Ok(id
67
+
.attach(repo)
68
+
.object()?
69
+
.peel_to_kind(gix::object::Kind::Commit)
70
+
.context("Need committish as starting point")?
71
+
.id())
72
+
}
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
+
}
55
92
}
RetroSearch is an open source project built by @garambo | Open a GitHub Issue
Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo
HTML:
3.2
| Encoding:
UTF-8
| Version:
0.7.4