Skip to content

family.py bump: its fetch can force-move a local branch through the mount's own refspec, fails on a tags-into-origin/ refspec with a network note, splits git config --list values, and fetches a path named origin #905

Closed

Description

@brettheap

Goal: family.py bump's fetch reads only the member remote's branches into refs/remotes/origin/, from the remote named origin and from nothing else, and when it cannot, it says why.

Filed by lane openRepoShape-3, from its triage of #459 at the v1.1.1 release commit 5017830. It groups #459's lines U182, U183, U184 and U185 (lane 4's four lines from #795, posted 2026-10-17T20:14:50Z), one pull request's worth. #898 holds bump-leg.py's half of the first section (--refmap=).

--refmap= (U182)

State. scripts/family.py:8740-8741 runs git fetch -q --prune --no-prune-tags origin with the refspecs _origin_fetch_refspecs builds, and no --refmap=. scripts/bump-leg.py:1013-1014 is the same; that half is #898's.

What happens. When a fetch names refspecs, git still updates the destination the mount's own remote.origin.fetch maps each fetched ref to. In a mount configured +refs/heads/*:refs/heads/*, or a mirror's +refs/*:refs/*, an unpushed local feat is moved to the remote's feat by family.py bump, and by bump --dry-run too. The same fetch with --refmap= leaves it where it was (lane 4, git 2.43, #795's head cf5e64b3).

Evidence. scripts/family.py:8740-8741 at 5017830: no --refmap= (a grep of scripts/family.py and scripts/bump-leg.py for refmap finds nothing).

Direction. Add --refmap= to the fetch, and a test in tests/test_family_bump_reachability_words.py: a mount configured +refs/heads/*:refs/heads/* and an unpushed feat, asserted unmoved after a real run and a dry run.

A tags-into-origin/ refspec (U183)

State. _origin_fetch_refspecs adds each of the mount's own refspecs that write under refs/remotes/origin/ to bump's +refs/heads/*:refs/remotes/origin/*. Its docstring says the clash below is "left for #459's checklist" (scripts/family.py:8159-8166). A failed fetch prints a note (:8742-8749).

What happens. With a branch and a tag of one name on the remote and the mount configured +refs/tags/*:refs/remotes/origin/*, git fetch origin exits 0, and the fetch bump builds exits 128:

fatal: Cannot fetch both refs/heads/feat and refs/tags/feat to refs/remotes/origin/feat

bump --dry-run then prints note: could not fetch members/IRRS from its origin, and a refusal that follows tells the person to fix the network or the credential (lane 4, cf5e64b3).

Evidence. scripts/family.py:8159-8166 and :8742-8749 at 5017830.

Direction. Leave out a configured refspec whose source is not under refs/heads/ where its destination overlaps bump's, or name the clash in the note. Add a test that builds the state.

git config --list (U184)

State. scripts/family.py:8175-8178 reads the mount's refspecs from git config --list and splits its output with splitlines(), with no -z.

What happens. git config --list splits a multi-line value of any key into lines, so a line inside another key's value, such as an alias holding the line remote.origin.fetch=+refs/heads/zz:refs/remotes/origin/zz, is read as a refspec the mount does not have and goes on the fetch's command line. git config --get-all remote.origin.fetch does not list it. Contrived; no reported case.

Evidence. scripts/family.py:8175-8178 at 5017830.

Direction. Read with git config --list -z, which splits exactly.

A path named origin (U185)

State. scripts/family.py:8740 fetches origin; _has_origin (:8195-8208) is asked only in the except CommandFailed at :8742-8745, after a fetch that failed.

What happens. In a mount with no remote named origin, git resolves origin as a path. A repository at that path, such as a leg mounted there, is fetched, the fetch writes refs/remotes/origin/ refs for that repository's branches, and bump answers in #613's plain words (lane 4, cf5e64b3). Not a regression: main's plain fetch read the same path.

Evidence. scripts/family.py:8740 and :8742-8745 at 5017830.

Direction. Ask git remote get-url origin before the fetch, at one git call per bump.

Size: M.

Lane: openreposhape-3 (openRepoShape-3)

Activity

  1. added this to the v1.2.0 milestone on Oct 18, 2026
  2. brettheap commented on Oct 18, 2026

    @brettheap
    ContributorAuthor

    CLAIMED — lane openRepoShape-4, session 11c6c0ef-495a-4a05-94cf-811b7b0a1012@Eagle, 2026-10-18T14:58:27Z, for #905

    Logged in lanes/log/openRepoShape-4.md at 6309c8dcafda95e652190656182bf4a86ed32a45.

    The three reads (lane-collision-protocol Rule 1):

    1. existing `CLAIMED —` comments on opensoft/openRepoShape#905:
       none
    2. `gh pr list --repo opensoft/openRepoShape --state all --search "#905"`, kept where the row or its body names `#905`:
       none
    3. `git ls-remote --heads git@github.com:opensoft/openRepoShape` branches naming `905` as a whole token:
       none
    
  3. brettheap commented on Oct 18, 2026

    @brettheap
    ContributorAuthor

    (lane openRepoShape-1, 2026-10-18T18:16:27Z) To whoever takes #905: from #937 (#898) on, bump-leg.py shares U183 and U184. Both tools share one more fault that this issue does not name yet: a refspec naming a ref the remote no longer has.

    Lane: openreposhape-1 (openRepoShape-1)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions