Git HEAD: The Definitive Guide


This is the most complete guide about Git HEAD.

So if you want to Learn :

  • Git HEAD and how to view Git HEAD
  • Git reset HEAD
  • Git detached HEAD
  • and about Git merge HEAD and more...

then you’ll love this detailed guide.

Let’s dive right in.

Don't have time to read 
the full Guide!

No Problem, I've created a pdf so you can read when it's convenient. And to get the PDF version of this guide, click on the button below.

Download Git Head Complete Guide

CHAPTER 1 :
Git HEAD Fundamentals


Git Head is an important term (everything has a head).

In this chapter, you will learn about - 

  • What is Git HEAD?
  • Git HEAD Fundamentals
  • Important terminology and more...

So let's start.

Git HEAD fundamentals [Updated]

What is Git HEAD?

The Git HEAD is a pointer to the last commit snapshot.

HEAD is a direct or indirect reference (symbolic reference) to the current commit.

In simple words - HEAD is a special pointer. And it points to that local branch in which you are currently working.

The HEAD identifies the most recent commit in the current checkout branch.

What is the current HEAD in Git ?

When using Git, You may switch to any branch.

And the checkout branch is known as the HEAD branch.  Also known as the "active" or "current" branch.

I will cover how you can view the Git HEAD in the next chapter.

And this chapter is all about the fundamentals of Git HEAD and other related terms.

HEAD (uppercase) vs. head (lowercase)

HEAD

Once again, HEAD is a special pointer. And it points to that local branch in which you are currently working. 

The HEAD refers to the commit or branch that you are now viewing.

I've used all capital letters to indicate this status.

head

A repository can have several heads but only one HEAD. 

For example, "main" is a "head" since it refers to a branch.

In other words, A "head" (in lowercase letters) refers to a head that you are not viewing.

HEAD (in all uppercase) relates to a commit or branch in your repository that you are viewing. It refers to the presently active head alone.

Git HEAD^ (caret) and HEAD~ (tilde)

In Git, you can use any of the signs - caret or tilde to go backward.

You can use the caret sign for the merge commits (as there may be two or more parents of a commit).


Use the tilde sign most of the time to go back in a straight line.

Git HEAD^

 In Git HEAD^, the caret sign (^) denotes the parent of a specific commit.

The parent of the current HEAD commit is referred to as HEAD^.

You can optionally include a number after the caret sign (^) to indicate which parent you want.

And HEAD^ is shorthand for HEAD^1.

HEAD^2 is NOT equivalent to HEAD^^

This technique is only helpful for merge commits with more than one parent.

Here is the two-parent of the merge commit.

  • The first parent is from the branch you were on (source branch) when you merged (often the main branch).
  • And the second parent is from the target branch that was merged (like feature branch)

Git HEAD~

Most of the time, you can use a tilde sign to go back several generations.

HEAD~ (with a tilde sign) appears virtually linear and wishes to travel backward in a straight path.

You may get the parents of any commit, not only the HEAD.

You can use the tilde sign with a branch to find its parent.

For example, feature_branch~2 refers to the grandparent of the feature_branch.

Git HEAD^ vs. HEAD~

Most of the time, you can use ~ (tilde sign). It refers to previous commits to the current branch.


And ^ (caret) refers to parent.

HEAD~ is always the same as HEAD^
HEAD~~ is always the same as HEAD^^
HEAD~~~ is always the same as HEAD^^^
HEAD~~~~ is always the same as HEAD^^^^

 
and so on…


But HEAD~2 is not the same as HEAD^2.

When there are several carets (^) in a row, the tilde (~) is a shortcut character.

HEAD~2 is equivalent to HEAD^^
HEAD~3 is equivalent to HEAD^^^
HEAD~4 is equivalent to HEAD^^^^
and so on…


I prefer to use the tilde(~) is best practices over the caret (^), like HEAD~2, HEAD~3, etc.

Git HEAD vs Git index

Git Head and Git Index are different concepts.

From Git’s point of view the journey of a file goes from three areas.

  • Working directory
  • Staging area and
  • Repository
Three Trees in Git


When you use  git add command, you can say you have added files in the Git index area or Git staging area.

Git HEAD

You already know about the Git HEAD; It's a special pointer.

And it points to that local branch in which you are currently working.

Git Index (or Staging area)

The Git index is a staging region that sits between your working directory and your repository.

Technically, it's a file called index, which you can see in your special folder - .git (it's a hidden folder starting with a dot).

The Git Index is an area where you put files that you want to commit to your git repository.

It is a final preview to add and remove files before your changes go into your local repository.

Git HEAD vs Git Origin

There is a concept of remote in Git. 

And you can connect with several remote repositories.

Git HEAD vs Git Origin [updated]

Origin is the default name of your default remote repository. Origin is the repository from where you have cloned your local copy (of your repo).


How does Git know about your local and remote repositories?

From .git/config.

The. git folder contains all of the information required for your project's version control. It also records information on commits, remote repository addresses, and so on.

Git origin config file

You can check the list of how many remotes you have set up in your local repository with the git remote -v command.

Git remote command to view origin

Git HEAD vs. Main(or Master)

Master is the name of the default branch that Git creates when you first create a repository. 

 In simple words - master is the principal branch.

GitHub recently changed the master branch to main. (in case you have old repo still you can rename your branch to main)

In Github master in main branch now

So master and main is a name of your primary Git branch.

CHAPTER 2 :
View Git HEAD


This chapter is all about how you can view Git HEAD.

In this chapter, I will show you how you can view the Git HEAD of your remote and local branch. 

Also, I will show you how you can view the detached HEAD.

So let's dive in.

view Git HEAD main


In the previous chapter I shared about head (lowercase) and HEAD (uppercase).

There can be many heads but only one HEAD.

And again - HEAD is a special pointer to the current branch in which you are working) 

You can check the status of HEAD with a few simple git commands. 

1. Git branch

You can simply run the git branch command and it will display your local branches. 

But It will mark the active branch on which you are currently working on with an asterisk.

Here is the syntax and a screen shot.

Syntax - $ git branch  

Git show HEAD with git branch command

2. Git branch --show-current

If you want to display only your current branch name you can use --show-current flag with your Git branch command. 

The - -show-current option will simply tell you your active branch. 

Syntax:  $git branch  --show-current

Git show head with git branch --show-current

3. Git name-rev

You can use the git name-rev command to find the HEAD

This command will find symbolic names appropriate for human digestion.

Syntax: $git name-rev --name-only HEAD

Git head  with git name-rev  --name-only HEAD

4. Git symbolic-ref

Another quick and easy approach is to use the git-symbolic-ref command to show a brief symbolic reference to the current branch's HEAD, which is simply the current branch name.

Syntax : $git symbolic-ref --short HEAD

Git show HEAD with git symbolic-ref

5. git show HEAD

You can check the status of a HEAD with a simple command. Also, the command will tell you the status of HEAD.

$ git show HEAD

And you can get a view of something like this

git show HEAD command with git

You can see the commit id of the HEAD.

And also, you can see the branch name to which HEAD is currently pointing to.

In this case, the HEAD points to the main branch.

6. Git show-ref

This command is super helpful if you need the current commit Id of HEAD.

You can view the Git HEAD SHA of all your local branches with the following command.

$ git show-ref --head

Here the --head option shows the HEAD reference

Git show HEAD with git show-ref --head

In the above output windows, the last line shows the commit Id of remote HEAD (refs/remotes) 

7. View Detached HEAD

You can see what HEAD points to by 

cat .git/HEAD

And normally you will get something like this (branch name)

ref: refs/heads/bug-login-page-css

View Detached HEAD in Git

But if you are in detached head mode you will get hash value

70460b4b4aece5915caf5c68d12f560a9fe3e4

View Detached HEAD

It tells you that the HEAD is pointing to a commit ( instead of a branch).

How can you fix detached HEAD issues? I have covered everything in the next lesson.

And for now, how you can check if you are running in the detached HEAD issue.

CHAPTER 3 :
Git HEAD reset

In this chapter, I will share with you what the purpose of Git HEAD reset is?

Why you need a detached HEAD in the first place, and How you can fix it.

Also, later in this chapter, you will learn about Git hard and soft reset with examples.

So let's dive in.

Git HEAD reset main

Why do you need to use Git reset command?

Git reset is a powerful command.

The primary purpose of the Git reset command is -

  • To move the current Git HEAD to the commit specified.
  • Undo local changes of your Git repo.

In simple words, Git reset command will fix un-committed mistakes.

Git Reset Command

Git Reset

There are three Git reset options that you can use for your three trees.

Before I dive in, let me explain what are the three trees in Git.

  • Your working Area (Working directory )
  • Staging Area (Staging Index)
  • The commit History (HEAD)
three trees in Git- HEAD, INDEX and Working Dir

Now back to three Git reset options -

  1. 1
    Soft
  2. 2
    Hard
  3. 3
    Mixed (default option)
Three Git reset Options

Git Reset Soft

Git reset soft option only changes the HEAD.

And it does not change staged files in the index or in the working directory.

When can you use Git reset soft in the real world?

Imagine you need to undo your last commit.

You can use git reset with the soft option.

$ git reset --soft HEAD~1

git reset soft option

This command will move the head to the one before the current revision.

And all your changes will stay. And you can check your changes with the Git status command.

Once you execute the Git reset command with the soft option. You can see your changes in your working directory.

Also, you can see the changes still exist in your index. So you can commit your changes if you want. Git reset command only removed your last commit.

Git Reset Hard

Git reset HARD option will move the HEAD and update index and working directory. 

It might cause data loss.

Let's try to remove the last commit with the HARD option.

Git reset hard option on the git bash

$ git reset --hard HEAD~1

As mentioned, it will remove all your changes from your working directory and index. 

After executing this command, you try to view git status. You will get a message like nothing to commit, working tree clean.

Git Reset Mixed

Git reset mixed option will move the HEAD.

It also updated the index (where HEAD points).

Git reset mixed is the default option.

It means if you write only Git reset, it will execute with the mixed option.

Let's take the same scenario, undo your last commit with the default option (--mixed)

$ git reset --mixed HEAD~1

Git reset mixed command will remove your change from the Git index. But you still can see your changes in the working directory.

Git reset mixed (default) option on the git bash

Later in this chapter I will share how Git reset is different Git revert and from Git rebase. But for now let's try to understand a little bit deeper about Git Reset.

Git reset HEAD delete files

Sometimes you want to remove all your changes. 

It's easy with Git reset HARD  

$ git reset --HARD 

It will delete all of your local changes in your current branch. 

Git reset option

Reset a local branch to match remote repository HEAD

You might need to do it often.

Why?

You made some changes in a branch. And in the meanwhile, your teammates push changes in the same branch.

Now you want to discard your changes and make sure you are in sync with the remote repository.

Reset a local branch to match remote repository HEAD

It is a two-step process 

  • Fetch all the changes from remote - $ git fetch origin
  • Remove  your changes - $ git reset --hard origin/main

Here main is the name of your default primary branch. It might be a master for your project. 

In case you want to save your changes before you fetch, you can set up your local branch.

$ git commit -a -m "Saving temp work."
$ git branch your-temp-work

And after saving your work, you can reset your local branch.

Git reset HEAD vs. Git revert

You can use both of these commands to undo some work, but they work differently.

Git revert 

As I mentioned earlier, git revert used to undo your changes. It adds a new commit that undoes the changes from a previous commit.

This command adds a new history to your project.

Git revert command add a new commit

When will you use Git revert?

Let’s say you made a change in your project repository. And later, you figure out the commit is not valid. 

Then you can use the Git revert command to undo the modifications added by the bad commit. And Git revert command to record a new undo commit in the history.

Git revert commit

With the Git revert, you can undo your single commit or set of commits. 

It's super easy to undo your commit on the CLI with the following command.

$ git revert <your unwanted commit hash>

There is another way as well. You can use the branch name with the tilde sign ~, followed by a number that indicates commit behind the head commit.

$ git revert main~3

In this example, the target commit is three, behind the head commit on the main branch (your checked-out branch).

How do you revert multiple commits in Git?

You can use two dots to select multiple commits. 

When you revert multiple commits, the older commit should come first and then the newer commit.

For example 

$ git revert HEAD~7..HEAD~3

The above command will revert these two commits. And also every other commit in between them.

Git reset 

If you use Git reset command, it might alter the history.

Let’s take an example - you made a lousy commit in your local repository (and did not share with others). And now you want to get rid of that lousy commit.

Git reset command

In this case, you can use the Git reset command. And it will remove that commit from history.

This is about Git HEAD reset, Its time dive deeper in more advanced concepts.

CHAPTER 4 :
Git Rebase vs. Git Merge (HEAD)

In this chapter you will learn two more advanced concepts

  • Git rebase & Git merge HEAD

Also, you will learn where Git merge head and how you can remove it.

So let's dive in.

Git Merge and MERGE_HEAD in Git

Before going into the MERGE_HEAD explanation, let's understand what Git merge.

Git Merge

Git merge is a command that allows you to merge branches in Git. When you do git merge, only the target branch will change.

Git merge example

Git merge adds your current branch changes into the target branch.

MERGE_HEAD 

Linux Kernel Git documentation for Git revisions says. MERGE_HEAD records the commit(s) you are merging into your branch when you run git merge.

In simple words, - While doing a merge, MERGE_HEAD is the SHA of the branch, you are merging into your changes.

While doing a merge, ORIG_HEAD is the SHA of the branch you are merging from your changes.

What is HEAD in Git Rebase

Git rebase command also tries to integrate changes from one branch to another branch.  

Git rebase command, with the example, is in the Git commands post. So here we will dive deeper to understand HEAD in the Git rebase.

When you use git rebase, you have two option for the new base

  1. The features parent branch (example - main branch) 
  2. Earlier commit in your feature branch 
git rebase example

The following command begins an interactive rebase 

$ git checkout feature git rebase -i HEAD~3

Here you are specifying the HEAD~3 as the new base.

You are not moving the feature branch but rewriting four commits that follow it.

You may also run into the detached HEAD when you are rebasing. And you may check out a specific commit. 

I have covered the detached HEAD in detail in the next chapter. For now, let's see if you run into a problem while rebasing what you can do.

If you feel something went wrong with Git rebase, you can cancel it with the following command.

 $ Git rebase --abort

It will abort the rebase without doing anything.

Git Rebase vs. Git Merge

Git rebase and git merge; both commands help you integrate your changes. Both take changes from one branch to another. 

The real difference is how they do. 

Git merge

They both use different ways to do the same thing.

Let's see how Git Merge command work

  • Git merge takes your changes from one branch.
  • And then merges them into another branch in one single commit.

Rebase move/combine sequence of commit to a new base commit. 

In the public repo, do not use Git rebase. It is a good option if you are working alone or in a small team.

CHAPTER 5 :
Detached HEAD

In this last chapter, you will learn about the detached HEAD. 

First I will share what is detached HEAD, why it happens for you in the first place and then how you can get rid of detached HEAD problems.

So let's dive into more details.

What is detached HEAD in Git

Most of the time, the head points to the latest commit in your current branch. But keep in mind that is not the case all the time.

Suppose Git HEAD is pointing only to a commit ( and not branch associated). And when HEAD pointing to a commit, it's known as a detached head state.

A detached HEAD means you are not on any branch.

In this mode, you can not update any branch as no active branch with HEAD.

How to enter in a detached HEAD state?

A detached HEAD does not mean you did something wrong. Also, it does not say that you break your code or repository.

There are a few common scenarios why you might have detached HEAD issues.

  • If you check out a remote branch without tracking it first, you may end up with a detached HEAD.
  • And when you try to check out a commit (instead of a branch), you will enter into a detached HEAD state.

Let's try to understand with an example.

git log command to see branch HEAD

As you can see, after running the Git log command, I am in the main branch, and I have a few commits.

Now to check out a commit dfb57db, where I’ve updated the index file.

git checkout commit sha to enter in detached HEAD

After executing that command, you can see the message says -

You are in a 'detached HEAD' state.

Why do you need detached HEAD?

Most of the time, you do not need it. It might happen accidentally with you.

And if you need, you can enter into the detached HEAD state yourself as mentioned above.

There are a few reasons behind that.

  • You have to look around and make experimental adjustments when you need to. 
  • If you want to test how at a certain point, your project was going.

Most of the time, developers check out an older commit to test the project state at that point. 

How do you fix a detached HEAD?

There are few quick ways to fix the detached HEAD issue.

Case 1: If you want to delete changes associated with detached HEAD

The easiest way is to check out some branch, and it will move the HEAD to that branch.

$ git checkout <branch name>

And in this case, your changes will be lost (if you made some).

If you entered into the detached HEAD by mistake, chances are you have some changes.

And to keep those, and you can use the next case.

Case 2: If you want to keep changes associated with a detached HEAD

To keep changes that you have made while in a detached HEAD state are not hard.

You can use the following steps.

  1. 1
    Git branch <new branch name> 
    $ git branch temp
    This git command will save your changes in the temp branch
  2. 2
    Switch to some other branch or to main branch
    $ git checkout master
  3. 3
    And if you want to incorporate your changes into the main branch you can merge those changes. 

    Run the command $ git merge temp from your main branch.

Conclusion

In this definitive guide, I share all the important aspects of Git HEAD. 

Now you know all the core concepts about git HEAD.

What Do you like about Git?   

Did I miss anything? 

Either way, share your thought.

Git HEAD Conclusion


Leave a Reply

Your email address will not be published. Required fields are marked

{"email":"Email address invalid","url":"Website address invalid","required":"Required field missing"}

Related Posts

Git in PowerShell: Get Productive Results (in 2021)

31 Advanced Git Tips (Boost your Productivity)

51+ Best Git Commands : Definitive Guide