Commit ec6bfdf3 authored by Georges Racinet's avatar Georges Racinet 🦑
Browse files

RefService.FindLocalBranches: fixing discrepancies with Gitaly

The expected response was actually in full ref form (as `refs/heads`).
It is probable that the Rails app is resilient with respect to that.

Gitaly response is sorted (bad for perf, but nothing obvious we can
do, GitLab 14.2 will even introduce different sorting criteria).

This RPC method was implemented before we had Gitaly Comparison tests,
this underlines once more how crucial they are.

branch : stable
parent ef460712b08d
Pipeline #27738 passed with stage
in 2 minutes and 58 seconds
......@@ -172,6 +172,18 @@ def iter_gitlab_branches_as_refs(repo):
yield gitlab_branch_ref(branch), ctx
def sorted_gitlab_branches_as_refs(repo):
"""Return all visible, GitLab branches, sorted.
By default GitLab sorts branches lexicographically.
Since Heptapod is using `/` separated special names,
it would make sense to perform a variation over that
(named branches first, then topics, lexicographically sorted
for each, of course).
return sorted(iter_gitlab_branches_as_refs(repo))
def ensure_gitlab_branches_state_file(repo):
"""Make sure that the GitLab branches state file exists.
......@@ -79,6 +79,7 @@ from ..branch import (
from ..gitlab_ref import (
......@@ -232,7 +233,7 @@ class RefServicer(RefServiceServicer, HGitalyServicer):
context) -> FindLocalBranchesResponse:
logger.debug("Processing %r", message.Logging(request))
repo = self.load_repo(request.repository, context)
for chunk in chunked(iter_gitlab_branches(repo)):
for chunk in chunked(sorted_gitlab_branches_as_refs(repo)):
yield FindLocalBranchesResponse(
branches=(find_local_branch_response(name, head)
for name, head in chunk),
......@@ -146,7 +146,7 @@ def test_find_branch(grpc_channel, server_repos_root):
branches = [br for chunk in resp for br in chunk.branches]
assert len(branches) == 1
assert branches[0].name == b'branch/default'
assert branches[0].name == b'refs/heads/branch/default'
assert branches[0].commit == branch.target_commit
assert branches[0].commit_subject == b"Ze subject"
......@@ -13,6 +13,7 @@ from hgext3rd.heptapod.special_ref import (
from hgitaly.stub.ref_pb2 import (
......@@ -57,6 +58,42 @@ def test_compare_find_branch(gitaly_comparison):
for resp in (hg_resp, git_resp))
def test_compare_find_local_branches(gitaly_comparison):
fixture = gitaly_comparison
wrapper = fixture.hg_repo_wrapper
for i in range(3):
wrapper.commit_file('foo', branch='br%02d' % i, return_ctx=False)
# mirror worked
assert set(fixture.git_repo.branch_titles().keys()) == {
b'branch/br%02d' % i for i in range(3)}
gitaly_ref_stub = RefServiceStub(fixture.gitaly_channel)
hgitaly_ref_stub = RefServiceStub(fixture.hgitaly_channel)
def flatten_branch_names(response):
return [ for chunk in response for br in chunk.branches]
def assert_compare():
hgitaly_request = FindLocalBranchesRequest(
gitaly_request = FindLocalBranchesRequest(
hg_resp = hgitaly_ref_stub.FindLocalBranches(hgitaly_request)
git_resp = gitaly_ref_stub.FindLocalBranches(gitaly_request)
# chunk size probably not the same between Gitaly and HGitaly
assert flatten_branch_names(hg_resp) == flatten_branch_names(git_resp)
# only one call to assert_compare(), looks weird (what's the point
# of the separate function), but that is to minimize conflicts with
# upcoming version for GitLab 14.2, with pagination and sort by.
def test_delete_refs(gitaly_comparison):
fixture = gitaly_comparison
grpc_repo = fixture.gitaly_repo
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment