How to know if there is a git rebase in progress?

2019-01-16 23:10发布

问题:

When I start a git rebase -i, I can issue commands like git rebase --continue, or git rebase --abort. Those commands only work if a rebase is in progress.

How can I know if there is a rebase in progress?

(I would greatly appreciate some details on how rebase works internally; what does git do to a repo that gives it the "rebase in progress" status,?)

回答1:

For one thing, there is a ORIG_HEAD in place during a rebase (but that is not limited to the rebase command)

But you can also look at the 2010 Git 1.7.0 git-rebase.sh script itself (which is as "internal" as you can get ;) ).
Lines like those can give you another clue:

dotest="$GIT_DIR"/rebase-merge
test -d "$dotest" -o -d "$GIT_DIR"/rebase-apply || die "No rebase in progress?"

sabgenton comments:

  • The folder rebase-apply seems to appear with rebase,
  • but a folder rebase-merge shows up only with with rebase -i.

And hippy also comments, in 2017, that:

The coding guidelines discourage the usage of -o (see Documentation/CodingGuidelines), so the correct way now (2017, but also since 2011, Git 1.7.6) is:

(test -d ".git/rebase-merge" || test -d ".git/rebase-apply") || die "No rebase in progress?"

Jelaby suggests in the comments:

(test -d "$(git rev-parse --git-path rebase-merge)" || \
 test -d "$(git rev-parse --git-path rebase-apply)" )

This correctly handles worktrees and unusual or non-standard layouts that don't have a .git directory, and also allows you to run this test from a subdir of the working directory.

That is because the git rev-parse --git-path <path>: does resolve "$GIT_DIR/<path>".


Git 2.6+ (Q3 2015) will print more information during a rebase:

See commit 592e412, commit 84e6fb9 (06 Jul 2015), commit 84e6fb9 (06 Jul 2015), and commit df25e94, commit 05eb563 (30 Jun 2015) by Guillaume Pagès (gitster).
(Merged by Junio C Hamano -- gitster -- in commit 178d2c7, 03 Aug 2015)

status: give more information during rebase -i

git status gives more information during rebase -i, about the list of commands that are done during the rebase.
It displays:

  • the last two commands executed and
  • the next two lines to be executed.

It also gives hints to find the whole files in .git directory.



回答2:

You can also check how such detection is done in __git_ps1 function in contrib/completion/git-prompt.sh, which can be used for git-aware bash prompt:

                if [ -f "$g/rebase-merge/interactive" ]; then
                        r="|REBASE-i"
                        b="$(cat "$g/rebase-merge/head-name")"
                elif [ -d "$g/rebase-merge" ]; then
                        r="|REBASE-m"
                        b="$(cat "$g/rebase-merge/head-name")"
                else
                        if [ -d "$g/rebase-apply" ]; then
                                if [ -f "$g/rebase-apply/rebasing" ]; then
                                        r="|REBASE"
                                elif [ -f "$g/rebase-apply/applying" ]; then
                                        r="|AM"
                                else
                                        r="|AM/REBASE"
                                fi


回答3:

If you have EasyGit, eg status will tell you:

$ eg status
(Not currently on any branch.)
(YOU ARE IN THE MIDDLE OF A INTERACTIVE REBASE; RUN 'eg help topic middle-of-rebase' FOR MORE INFO.)
Changes ready to be committed ("staged"):
    modified:   .gitmodules
    renamed:    config_loader.rb -> code/config_loader.rb
Newly created unknown files:
    vendor/
(YOU ARE IN THE MIDDLE OF A INTERACTIVE REBASE; RUN 'eg help topic middle-of-rebase' FOR MORE INFO.)

In a colored terminal, the notification is very prominent:

(eg help topic middle-of-rebase displays the documentation “How to resolve or abort an incomplete rebase”.)



回答4:

If there’s an interactive rebase in progress, this will tell you where you are in the process:

$ cat .git/rebase-merge/done 
pick 786139e lrg
edit 668b8a6 ktio
$ 

Right now I’m editing the “ktio” patch in an interactive rebase.

If there’s no rebase going on, it will look like this:

$ cat .git/rebase-merge/done 
cat: .git/rebase-merge/done: No such file or directory
$ 


回答5:

From a bash command line:

ls `git rev-parse --git-dir` | grep rebase

That will return exit code 0 (success) if there is a rebase folder, and it will output the rebase folder to STDOUT. If you are not in the middle of a rebase, then it will output nothing and return non-0 exit code. So you could even do something like this:

ls `git rev-parse --git-dir` | grep rebase || echo no rebase


回答6:

I am using this command is_rebase=$(git status | grep "rebasing" | wc -l)