At first, we need to be very clear about that all files in Git repository can be in one of two states: tracked or untracked.
Here are some references about tracked and untracked from 《Git pro》
Tacked file:
Tracked files are files that were in the last snapshot; they can be unmodified, modified, or staged. In simple term, tracked files are files that Git knows about.
Untacked file:
Untracked files are everything else — any files in your working directory that were not in your last snapshot and are not in your staging area.
(base) -a01:testGit$ git init
Initialized empty Git repository in /Users/GHIBLI/Desktop/testGit/.git/
(base) -a01:testGit$ touch test.txt
(base) -a01:testGit$ git status
On branch master
No commits yet
Untracked files:
(use "git add <file>..." to include in what will be committed)
test.txt
nothing added to commit but untracked files present (use "git add" to track)
Figure1.1
when you run git init
to initialize an empty git repository and make a new file without any subsequential git command like git add
, you can see from figure1.1 that this file is in untracked state.
(base) -a01:testGit$ git add test.txt
(base) -a01:testGit$ git status
On branch master
No commits yet
Changes to be committed:
(use "git rm --cached <file>..." to unstage)
new file: test.txt
Figure1.2
If you go with command git add test.txt
, and check its status, you can see a message ‘Changes to be committed’, it means this test.txt has been tracked and staged by git. So you can see what actually did the command ‘git add’ does for a untracked file:
test.txt(untracked) --> ‘git add’ -->test.txt(tracked and staged)
I want to use the same file to continue the following, so let’s do the commit action by running git commit -m 'first commit
, and the process will be like:
test.txt(untracked) --> ‘git add’ -->test.txt(tracked and staged) --> ‘git commit’–>test.txt(unmodified, tracked)
Now let’s do this process all over again but with a tracked file instead of a untracked file so we can see the difference between the tracked file and untracked file when run git add
.
(base) -a01:testGit$ vim test.txt
(base) -a01:testGit$ git status
On branch master
Changes not staged for commit:
(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)
modified: test.txt
no changes added to commit (use "git add" and/or "git commit -a")
I update this test.txt and check its status in Figure1.3, you can see the message ‘Changes not staged for commit’ .
(base) -a01:testGit $ git add test.txt
(base) -a01:testGit $ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)
modified: test.txt
Let’s see what will happen if we run git add
, a message ‘Changes to be committed’ comes out. That means this file has been modified and staged, totally waiting for your commit.
test.txt(modified, tracked, unstaged) --> ‘git add’ -->test.txt(modified, tracked ,staged)–>‘git commit’–>test.txt(unmodified, tracked)
For now, in fact we have seen the lifecycles of both tracked file and untracked file, at the same time we should also realize that git add
is a multipurpose command, the descripton from 《Git Por》is really clear:
git add is a multipurpose command — you use it to begin tracking new files, to stage files, and to do other things like marking merge-conflicted files as resolved. It may be helpful to think of it more as “add precisely this content to the next commit” rather than “add this file to the project”.
Also here is a very helpful picture from 《Pro Git》:
Figure 1.1
you can see lifecycles just as we found out:
untracked file:
test.txt(untracked) --> ‘git add’ -->test.txt(tracked and staged) --> ‘git commit’–>test.txt(unmodified, tracked)
tracked file:
test.txt(modified, tracked, unstaged) --> ‘git add’ -->test.txt(modified, tracked ,staged)–>‘git commit’–>test.txt(unmodified, tracked)