Skip to content

Commit 2d7d173

Browse files
authored
Use gitoxide in get_commit_info (#2654)
* Implement From<gix::ObjectId> for CommitId * Use gitoxide in get_commit_info
1 parent 7625277 commit 2d7d173

File tree

5 files changed

+78
-13
lines changed

5 files changed

+78
-13
lines changed

Cargo.lock

Lines changed: 13 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

asyncgit/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ git2-hooks = { path = "../git2-hooks", version = ">=0.4" }
2727
gix = { version = "0.71.0", default-features = false, features = [
2828
"max-performance",
2929
"revision",
30+
"mailmap"
3031
] }
3132
log = "0.4"
3233
# git2 = { path = "../../extern/git2-rs", features = ["vendored-openssl"]}

asyncgit/src/error.rs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -113,6 +113,16 @@ pub enum Error {
113113
#[error("gix::revision::walk error: {0}")]
114114
GixRevisionWalk(#[from] gix::revision::walk::Error),
115115

116+
///
117+
#[error("gix::objs::decode::Error error: {0}")]
118+
GixObjsDecode(#[from] gix::objs::decode::Error),
119+
120+
///
121+
#[error("gix::object::find::existing::with_conversion::Error error: {0}")]
122+
GixObjectFindExistingWithConversionError(
123+
#[from] gix::object::find::existing::with_conversion::Error,
124+
),
125+
116126
///
117127
#[error("amend error: config commit.gpgsign=true detected.\ngpg signing is not supported for amending non-last commits")]
118128
SignAmendNonLastCommit,

asyncgit/src/sync/commits_info.rs

Lines changed: 53 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,21 @@ impl From<Oid> for CommitId {
8484
}
8585
}
8686

87+
impl From<gix::ObjectId> for CommitId {
88+
fn from(object_id: gix::ObjectId) -> Self {
89+
#[allow(clippy::expect_used)]
90+
let oid = Oid::from_bytes(object_id.as_bytes()).expect("`Oid::from_bytes(object_id.as_bytes())` is expected to never fail");
91+
92+
Self::new(oid)
93+
}
94+
}
95+
96+
impl From<CommitId> for gix::ObjectId {
97+
fn from(id: CommitId) -> Self {
98+
Self::from_bytes_or_panic(id.0.as_bytes())
99+
}
100+
}
101+
87102
///
88103
#[derive(Debug, Clone)]
89104
pub struct CommitInfo {
@@ -142,24 +157,35 @@ pub fn get_commit_info(
142157
) -> Result<CommitInfo> {
143158
scope_time!("get_commit_info");
144159

145-
let repo = repo(repo_path)?;
146-
let mailmap = repo.mailmap()?;
160+
let repo: gix::Repository =
161+
gix::ThreadSafeRepository::discover_with_environment_overrides(repo_path.gitpath())
162+
.map(Into::into)?;
163+
let mailmap = repo.open_mailmap();
164+
165+
let commit = repo.find_commit(*commit_id)?;
166+
let commit_ref = commit.decode()?;
167+
168+
let message = gix_get_message(&commit_ref, None);
147169

148-
let commit = repo.find_commit((*commit_id).into())?;
149-
let author = get_author_of_commit(&commit, &mailmap);
170+
let author = commit_ref.author();
171+
172+
let author = mailmap.try_resolve(author).map_or_else(
173+
|| author.name.into(),
174+
|signature| signature.name,
175+
);
150176

151177
Ok(CommitInfo {
152-
message: commit.message().unwrap_or("").into(),
153-
author: author.name().unwrap_or("<unknown>").into(),
154-
time: commit.time().seconds(),
155-
id: CommitId(commit.id()),
178+
message,
179+
author: author.to_string(),
180+
time: commit_ref.time().seconds,
181+
id: commit.id().detach().into(),
156182
})
157183
}
158184

159185
/// if `message_limit` is set the message will be
160186
/// limited to the first line and truncated to fit
161187
pub fn get_message(
162-
c: &Commit,
188+
c: &git2::Commit,
163189
message_limit: Option<usize>,
164190
) -> String {
165191
let msg = String::from_utf8_lossy(c.message_bytes());
@@ -174,6 +200,24 @@ pub fn get_message(
174200
)
175201
}
176202

203+
/// if `message_limit` is set the message will be
204+
/// limited to the first line and truncated to fit
205+
pub fn gix_get_message(
206+
commit_ref: &gix::objs::CommitRef,
207+
message_limit: Option<usize>,
208+
) -> String {
209+
let message = commit_ref.message.to_string();
210+
let message = message.trim();
211+
212+
message_limit.map_or_else(
213+
|| message.to_string(),
214+
|limit| {
215+
let message = message.lines().next().unwrap_or_default();
216+
message.unicode_truncate(limit).0.to_string()
217+
},
218+
)
219+
}
220+
177221
#[cfg(test)]
178222
mod tests {
179223
use super::get_commits_info;

asyncgit/src/sync/logwalker.rs

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -161,10 +161,7 @@ impl<'a> LogWalkerWithoutFilter<'a> {
161161
let mut count = 0_usize;
162162

163163
while let Some(Ok(info)) = self.walk.next() {
164-
let bytes = info.id.as_bytes();
165-
let commit_id: CommitId = Oid::from_bytes(bytes)?.into();
166-
167-
out.push(commit_id);
164+
out.push(info.id.into());
168165

169166
count += 1;
170167

0 commit comments

Comments
 (0)