How can I list all branches that are ancestors of a commit?

I want to see all branches that are ancestors of commit abcdef1234 .

This is sort of the inverse of:

git branch --contains abcdef1234

The above command would list all branches that are descendants of abcdef1234 . I want to see a list of all branches that are ancestors of abcdef1234 .

I am also interested the equivalent for tags.

UPDATE

To be extra clear, I mean I want to see a list of all commits that meet 2 criteria:

  • They are ancestors of abcdef1234
  • They are currently pointed to by (local or remote) branches.
  • Obviously most commits at some point had a branch pointing to them when they were brand new. I am only interested in whether they are branches at this particular moment.


    git branch --merged abcdef1234 should do what you want. It lists all branches that are merged into the named commit (and thus are ancestors of it), ie those whose tip commits are reachable from the named commit.


    Here's what I suggested as a comment, in expanded form. (I think this is what you're asking for.)

    We set K to your chosen commit ( abcdefg1234 in your example). Then, we want to iterate through all labels L where L has the form refs/heads/* or refs/remotes/* (all branches and remote-tracking branches). Each label L points to some specific commit C. If C is an ancestor of K, print label L.

    [ Edit : as sschuberth answered, this is just git branch --merged ; the new feature I was thinking of is that git for-each-ref also now implements --merged , which means you can script things more easily, but if all you want is the names, git branch does it. If you do want tags, see git tag --merged , if available. If your version of Git is too old, read on to the script. :-) ]

    Here is a shell script (untested!) that implements this. Note that git for-each-ref has new capabilities in later versions of Git that would simplify this, but this should work all the way back to 1.6-ish—maybe 1.7-ish; I forget when git merge-base acquired --is-ancestor .

    #! /bin/sh
    
    # find branches and remote-tracking branches that targt
    # ancestors of $1.
    showthem() {
        local tgt label lbltgt
        tgt=$(git rev-parse "$1") || return $?
        git for-each-ref --format='%(refname:short) %(objectname)' 
                refs/heads refs/remotes |
            while read label lbltgt; do
                if git merge-base --is-ancestor $lbltgt $tgt; then
                    echo "$label"
                fi
            done
        return 0
    }
    
    case $# in
    0) usage 1>&2; exit 1;;
    1) showthem "$1";;
    *) for i do "echo ${i}:"; showthem "$i" || exit; done
    esac
    

    (You may want to tweak this slightly, eg, to discard symbolic refs like origin/HEAD .)


    comm -23 <(git branch -a | sort) <(git branch -a --contains abcdefg1234 | sort)
    

    This will give you all the branches that do not have commit abcdefg1234 ; it's the output of git branch -a minus the output of git branch -a --contains abcdefg1234 .

    链接地址: http://www.djcxy.com/p/26056.html

    上一篇: 混帐清理旧分支

    下一篇: 我如何列出作为提交祖先的所有分支?