Why does git detached HEAD even exist?

Our team recently moved to git, migrating from svn and hg. So when they checkout the tip of a tree, depending on the GUIs, they had a tendency to checkout a particular commit or local branch rather than a new tracking branch, without the understanding of how git really works.

So my question is why does detached HEAD even exist?
Why can’t it be defaulted to always checking out a new branch? (with my limited understanding of git)

  • How to specify CAFile path inline with the GIT command?
  • Is there any difference between `git gc` and `git repack -ad; git prune`?
  • How do I make git block commits if user email isn't set?
  • What constitutes a merge conflict in Git?
  • How to use git-replace to replace the tree of a commit
  • How to clone a remote git repository with Android Studio?
  • Education/Training definitely helped but there is always someone new to git…
    How do you guys manage it?

    By the way, I know how to fix them. I’ve read through a lot of posts on this site.
    This is more for knowledge sharing and how you prevent or manage.

    After reading the detailed explanations provided below, I now realized that my question should have been “Why does git give a detached HEAD when checking out a new remote branch?”. Regardless, the answer will give you a very good understanding!

  • What is the purpose of Perforce file “.perforce”?
  • How to disable git gpg signing
  • Import a bunch of files
  • Git pre-merge hooks?
  • Git flow share hotfix branch
  • How to maintain a Github fork of a popular project with submodules
  • 4 Solutions collect form web for “Why does git detached HEAD even exist?”

    […] why does detached HEAD even exist?
    Why can’t it be defaulted to always checking out a new branch?

    Let me try with the following metaphor. If you think of your Git repository as a photo album that chronicles the history of your repository…

    • You can think of branches as bookmarks; they mark points of interest in your history, snapshots you’re likely to go back to, at some stage… if only out of nostalgia 🙂
    • You can think of the HEAD reference as one of your fingers, keeping the book open at a particular page.

    Now, imagine if you were allowed to open the book only where there is already a bookmark. That would be very restrictive and unwieldy: you would have to create and use many bookmarks just in order to visit certain pages of your history:

    enter image description here

    Instead, Git allows you to flick through the book and open it on any page you fancy. Then, if you notice a particular snapshot that you’ve taken interest in, you can always create a new bookmark (branch) for it.

    In a nutshell, that’s why detached-HEAD state is useful. It allows you to check out any commit, even one which no branch currently points to. If you decide that you’d like to base brand new work on the commit in question, then it would make sense to create a new branch that points to that commit; but, otherwise, creating a new branch would be overkill.

    Why does git give a detached HEAD when checking out a new remote branch?

    I’m guessing you probably run

    git checkout <remote-branch>

    and are suprised that it detaches the HEAD. You need to be aware that Git distinguishes between

    • remote-tracking branches, which are local to your repository, but are only meant to reflect what a branch living in a remote repository looked like the last time you communicated with the server; you cannot work on such branches; and
    • (purely) local branches, which can work on.

    If you simply run

    git checkout <remote-branch>

    no local branch for you to play with will be created, and you will end up in detached-HEAD state. You may want to run

    git checkout -b <new-local-branch> <remote-branch>

    instead. That will create and check out a new local branch pointing at the same commit as the remote branch. No detached HEAD then.

    Simply put, a detached HEAD is your HEAD reference at somewhere other than the tip of your current branch.

    In layman’s terms, HEAD points to the latest commit in your repository; a detached HEAD points to somewhere that is not at the latest commit in your repository.

    It exists because going back to previous commits is very handy – notably when running git bisect, as Git has to go back in history to your earliest “good” check-in. It’s also good to be able to check out an arbitrary commit to run a smoke test on it (in case git bisect is too Byzantine), or check out a specific release version.

    Defaulting to creation of a branch is extremely confusing behavior, as there’s not much reason to create branches if you’re working on your own repository, or if everyone’s collaborative and commits to the same branch all the time (although this can lead to some heartache).

    The main things to remember:

    • To get out of a detached HEAD state, check out the current branch (git checkout master). This will move your HEAD pointer to the tip of master, for example.

    • To create a new branch, use git checkout -b <branch-name>. The -b flag on checkout indicates that you wish to create a new branch.

    • To update your local repository with changes from the server, use git pull. This will retrieve any remote changes, and advance your local branches’ tips to match that of the remote server.

    Because they are confused with the term “checkout”. They have different meaning in the two version control system.

    For your particular question, the simplest message to them is , “git pull” = “svn checkout”. So instead of doing checkout and think that they are trying to get the latest version from the server, they should use ‘pull’

    There is another common form of the checkout command that the other answers don’t mention.

    Form 1 – This will checkout an already existing local branch

    git checkout LOCAL_BRANCH

    Form 2 – Forcing detached HEAD

    git checkout REFERENCE

    Here, reference can be a remote branch reference, a tag, a sha, etc. A very common mistake is to type git checkout origin/some_branch and not realizing that will deference origin/some_branch to a SHA, and then put you in detached head.

    Form 3 – Simple form of checking out a remote branch

    git checkout REMOTE_BRANCH

    If REMOTE_BRANCH isn’t a local branch, but it is a valid branch on origin, then Git will create a local branch and setup tracking. so git checkout some_branch if “origin/some_branch” exists will work.

    Finally, you can checkout an arbitrary SHA/Ref and create a branch with git checkout -b LOCAL_BRANCH REF. If REF happens to be an a remote branch reference Git will automatically setup tracking for you (in this case you must explicitly put origin/ in the ref name). So git checkout -b my_some_branch origin/somebranch will create and checkoug my_some_branch and also enable tracking for it.

    Git Baby is a git and github fan, let's start git clone.