Skip to content

Commit

Permalink
feat: Reference::remote_name() now also provides valid remote names…
Browse files Browse the repository at this point in the history
… for local tracking branches.
  • Loading branch information
Byron committed Aug 7, 2024
1 parent c612440 commit 6ac2867
Show file tree
Hide file tree
Showing 4 changed files with 64 additions and 3 deletions.
30 changes: 27 additions & 3 deletions gix/src/reference/remote.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
use crate::bstr::ByteSlice;
use crate::repository::{branch_remote_ref_name, branch_remote_tracking_ref_name};
use crate::{remote, Reference};
use gix_ref::FullNameRef;
use gix_ref::{Category, FullNameRef};
use std::borrow::Cow;

/// Remotes
Expand All @@ -9,8 +10,31 @@ impl<'repo> Reference<'repo> {
/// Return `None` if no remote is configured.
///
/// See also [`Repository::branch_remote_name()`](crate::Repository::branch_remote_name()) for more details.
pub fn remote_name(&self, direction: remote::Direction) -> Option<remote::Name<'repo>> {
self.repo.branch_remote_name(self.name().shorten(), direction)
pub fn remote_name(&self, direction: remote::Direction) -> Option<remote::Name<'_>> {
let (category, shortname) = self.name().category_and_short_name()?;
match category {
Category::RemoteBranch => {
if shortname.find_iter("/").take(2).count() == 1 {
let slash_pos = shortname.find_byte(b'/').expect("it was just found");
shortname[..slash_pos]
.as_bstr()
.to_str()
.ok()
.map(|n| remote::Name::Symbol(n.into()))
} else {
let remotes = self.repo.remote_names();
for slash_pos in shortname.rfind_iter("/") {
let candidate = shortname[..slash_pos].as_bstr();
if remotes.contains(candidate) {
return candidate.to_str().ok().map(|n| remote::Name::Symbol(n.into()));
}
}
None
}
}
Category::LocalBranch => self.repo.branch_remote_name(shortname, direction),
_ => None,
}
}

/// Find the remote along with all configuration associated with it suitable for handling this reference.
Expand Down
Binary file not shown.
10 changes: 10 additions & 0 deletions gix/tests/fixtures/make_remote_config_repos.sh
Original file line number Diff line number Diff line change
Expand Up @@ -131,3 +131,13 @@ EOF
pushDefault = push-origin
EOF
)

git clone fetch multiple-remotes
(cd multiple-remotes
git remote add other ../fetch && git fetch other
git remote add with/two/slashes ../fetch && git fetch with/two/slashes
git remote add with/two ../fetch && git fetch with/two

git checkout -b main --track origin/main
git checkout -b other-main --track other/main
)
27 changes: 27 additions & 0 deletions gix/tests/reference/mod.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use gix::remote::Direction;

mod log {

#[test]
Expand All @@ -17,6 +19,31 @@ mod log {
);
}
}

#[test]
fn remote_name() -> crate::Result {
let repo = crate::named_subrepo_opts(
"make_remote_config_repos.sh",
"multiple-remotes",
gix::open::Options::isolated(),
)?;
for (ref_name, expected_remote) in [
("main", "origin"),
("other-main", "other"),
("refs/remotes/origin/main", "origin"),
("refs/remotes/other/main", "other"),
("with/two/slashes/main", "with/two/slashes"),
("with/two/main", "with/two"),
] {
let r = repo.find_reference(ref_name)?;
assert_eq!(
r.remote_name(Direction::Fetch).map(|name| name.as_bstr().to_owned()),
Some(expected_remote.into())
);
}
Ok(())
}

mod find {
use gix_ref as refs;
use gix_ref::{FullName, FullNameRef, Target};
Expand Down

0 comments on commit 6ac2867

Please sign in to comment.