Git学习笔记

2019/06/16

Tags: Git

摘要:学习Git的一些笔记,记录了Git的一些常见命令,以及Git中文件的生命周期。


git文件状态变化

状态说明:

Untracked: 刚新加的文件,还没有纳入git管理范围

UnModified: 已经committed的文件

Modified: 已经committed的文件,通过vi等修改后,就变成Modified

Staged: git add 后的文件

状态转换:

Untracked->Staged: 通过git add 来完成

UnModified->Modified: 修改文件内容来完成,比如vi命令

Modified->Staged: 通过git add 来完成

UnModified->Untracked: 通过git rm 来完成

Staged->UnModified: 通过git commit 来完成

正常流程

git clone 从远程拉一个工程下来

$ git clone git@github.com:sotrip/gittest.git         
Cloning into 'gittest'...
warning: You appear to have cloned an empty repository.
Checking connectivity... done. 

增加一个文件

$ vi 1.txt  #里面内容如下:
the first line 

git status 查看状态

$ git status
On branch master            #表示我们目前在master分支上
Initial commit
Untracked files:            #有哪些文件是Untracked状态,有1.txt
(use "git add ..." to include in what will be committed)
1.txt
nothing added to commit but untracked files present (use "git add" to track)

git add 把文件从Untracked–>Staged

$ git add 1.txt  #成功后,没有输出
$ git status     #再次查看
On branch master
Initial commit
Changes to be committed:       #表示1.txt已经是staged了,可以被提交了
(use "git rm --cached ..." to unstage)  #如果不想提交了,可以用git rm --cached 1.txt
new file:   1.txt

git rm –cached

文件已经是staged了,但想要退回原来的状态

$ git rm --cached 1.txt
rm '1.txt'

$ git status       # 再来看又回来2.3这一步了
On branch master
Initial commit
Untracked files:
(use "git add ..." to include in what will be committed)
1.txt

$ git add 1.txt  # 我们还是再加上
$ git status
On branch master
Initial commit
Changes to be committed:     # 1.txt 又改为staged状态 准备提交
(use "git rm --cached ..." to unstage)
new file:   1.txt

git commit 提交

$ git commit -m "first commit"          #-m后面是我们这一次提交的注释
[master (root-commit) e6b0e7d] first commit
1 file changed, 1 insertion(+)
create mode 100644 1.txt

git push 把master分支的内容提交到远端

$ git push origin master
Warning: Permanently added the RSA host key for IP address '*.*.*.*' to the list of known hosts.
Counting objects: 3, done.
Writing objects: 100% (3/3), 214 bytes | 0 bytes/s, done.
Total 3 (delta 0), reused 0 (delta 0)
To git@github.com:sotrip/gittest.git
* [new branch]      master -> master 

git diff 查看变化

命令概括

git diff           #查看 Modified的文件,做了哪些修改
git diff --staged  # 查看 Staged的文件,做了哪些修改

操作实例

$ vi 1.txt   #在后面增加一行,变成如下
the first line
the second line

$ git status    
On branch master
Your branch is up-to-date with 'origin/master'.
Changes not staged for commit:       #这个表示1.txt已经变为Modified了,not staged
(use "git add ..." to update what will be committed)
(use "git checkout -- ..." to discard changes in working directory)
modified:   1.txt
no changes added to commit (use "git add" and/or "git commit -a")

$ git diff      #查看Modified的文件,修改了哪些地方
diff --git a/1.txt b/1.txt
index 137b7fd..067030b 100644
--- a/1.txt
+++ b/1.txt
@@ -1 +1,2 @@
the first line
+the second line

$ git add 1.txt       #把1.txt加入到staged中
$ git status
On branch master
Your branch is up-to-date with 'origin/master'.
Changes to be committed:
(use "git reset HEAD ..." to unstage)
modified:   1.txt

$ git diff  #这个时候不会输出任何东西,因为没有Modified的文件了    
$ git diff --staged    #查看staged的文件和上一次commit有哪些修改
diff --git a/1.txt b/1.txt
index 137b7fd..067030b 100644
--- a/1.txt
+++ b/1.txt
@@ -1 +1,2 @@
the first line
+the second line

回滚还没有commit的文件

命令概括

$ git reset HEAD 1.txt    #文件已经Staged的了,用这个来回滚到Modified状态,但是内容不会回滚
$ git checkout 1.txt      #如果文件是Modified,不想做修改了,恢复原样,使用这个

操作实例

$ git status
On branch master
Your branch is up-to-date with 'origin/master'.
Changes to be committed:
(use "git reset HEAD ..." to unstage)
modified:   1.txt

$ git diff --staged
diff --git a/1.txt b/1.txt
index 137b7fd..067030b 100644
--- a/1.txt
+++ b/1.txt
@@ -1 +1,2 @@
the first line
+the second line    

$ git reset HEAD 1.txt        #把1.txt 的状态由Staged变为Staged, 但是1.txt的内容不会变
Unstaged changes after reset:
M1.txt

$ git status
On branch master
Your branch is up-to-date with 'origin/master'.
Changes not staged for commit:            #可以看出1.txt 由Staged变为Modified
(use "git add ..." to update what will be committed)
(use "git checkout -- ..." to discard changes in working directory)
modified:   1.txt
no changes added to commit (use "git add" and/or "git commit -a")

$ cat 1.txt            #查看内容,发现 1.txt的内容并没有回滚
the first line
the second line

$ git checkout 1.txt   #回滚
$ git status
On branch master
Your branch is up-to-date with 'origin/master'.
nothing to commit, working directory clean

$ cat 1.txt           #内容已经回滚
the first line

回滚某个提交

命令概括

$ git revert HEAD         #回滚上一次提交
$ git revert HEAD^        #回滚上上次提交
$ git revert #commit no#  #回滚某一次提交
$ git revert -m 1 #commit no#  #回滚某一次merge提交

操作实例

增加了2.txt 并提交了,现在想回滚

$ vi 2.txt  #在里面增加内容
$ git add 2.txt    #把文件由Untracked 变为 Staged
$ git commit -m "2.txt commit"  #提交
$ git log   查看提交日志
commit 710c5e84bd02e5d041b537b8732b9e80fee257a1    #这个是我们2.txt的提交
Author: xxx 
Date:   Thu Apr 7 22:10:00 2016 +0800
2.txt commit
commit e6b0e7d844154d5473a37baed2ef56807dca16b3
Author: xxx 
Date:   Wed Apr 6 22:42:44 2016 +0800
first commit

$ git show   710c5e84bd02e5d041b537b8732b9e80fee257a1  #可以查看这次修改的内容     
$ git revert 710c5e84bd02e5d041b537b8732b9e80fee257a1  #回滚提交
[master d3ab103] Revert "2.txt commit"
1 file changed, 1 deletion(-)
delete mode 100644 2.txt    
$ git revert -m 1 9d55502f0e05bef943d6b4e7cf57aafe08e42d63  #保留master,去除别的分支提交过来的

分支操作

查看分支

$ git branch    #查看目前有哪些分支
* master       #只有一个分支,"*"表示当前是在master分支上

创建分支

$ git branch first-branch  #打出第一个分支,名字是first-branch
$ git branch
first-branch   # 分支已经有了
* master         #"*"表示当前是在master分支上

$ git checkout first-branch
Switched to branch 'first-branch'

$ git branch
* first-branch    #已经成功切换到自己打的分支上了
master

分支上增加内容

$ vi 2.txt
$ cat 2.txt         #增加的内容如下
edit in first-branch

$ git add 2.txt
$ git commit -m "2.txt commit in first-branch"      #在分支上提交
[first-branch 9abd8f2] 2.txt commit in first-branch
1 file changed, 2 insertions(+)
create mode 100644 2.txt

推送分支到远程

推送到远程分支需要添加一个远程地址, 同时设置用户和邮箱

git remote add origin xxx.git

# 设置用户
git config user.name "foo" 
# 设置邮箱
git config user.email "bar@mail.com"

# 如果加上 --global 参数, 则是全局配置, 否则是设置当前project的的配置
git config --global
$ git push origin first-branch
Counting objects: 7, done.
Delta compression using up to 4 threads.
Compressing objects: 100% (5/5), done.
Writing objects: 100% (7/7), 692 bytes | 0 bytes/s, done.
Total 7 (delta 0), reused 0 (delta 0)
To git@github.com:sotrip/gittest.git
* [new branch]      first-branch -> first-branch

两个分支进行比较

$ git diff master first-branch    # 比较master与first-branch
diff --git a/2.txt b/2.txt
new file mode 100644
index 0000000..b09edf1
--- /dev/null
+++ b/2.txt              # 表示first-branch上多了一个2.txt
@@ -0,0 +1,2 @@
+edit in first-branch+

分支合并到master上

$ git checkout master
$ git merge first-branch    #把first-branch的内容合并到master上
Updating d3ab103..9abd8f2
Fast-forward
2.txt | 2 ++
1 file changed, 2 insertions(+)
create mode 100644 2.txt    

$ ls
1.txt    2.txt 
$ cat 2.txt
edit in first-branch 
$ git log
commit 9abd8f2d8fe7c08ca246464552dae25397694582
Author: xxx 
Date:   Thu Apr 7 22:26:26 2016 +0800
2.txt commit in first-branch         #在first-branch上提交的内容也显示在日志中

从远程拉一个分支

有两个办法,第一种是:

$ git fecth origin 
$ git checkout first-branch
Branch first-branch set up to track remote branch first-branch from origin.
Switched to a new branch 'first-branch'

第二个办法:

$ git checkout -t origin/first-branch
Branch first-branch set up to track remote branch first-branch from origin.
Switched to a new branch 'first-branch'

tag操作

tag一般维护一个只读的版本,不再进行修改

$ git tag -a v1.0 -m "v1.0 ready for  publish"    #创建一个tag ,名字是"v1.0"
$ git tag   #查看tag 
v1.0  

$ git push origin v1.0            #推送tag 到github上
Counting objects: 1, done.
Writing objects: 100% (1/1), 162 bytes | 0 bytes/s, done.
Total 1 (delta 0), reused 0 (delta 0)
To git@github.com:sotrip/gittest.git
* [new tag]         v1.0 -> v1.0    
$ git checkout v1.0   #切换到这个tag 上

注意 最好不要在tag进行修改东西,就把tag维护成一个只读的版本

其他

$ git rm 2.txt  #删除2.txt 这个文件
$ git remote -v   #可以查看远程的git的地址

git覆盖本地修改,pull 远程

$ git fetch --all
$ git reset --hard origin/master 
$ git pull

git修改上一次commit message

$ git commit --amend

git重命名分支

$ git branch -m oldname newname
$ git push origin :oldbranch # 此命令会在origin仓库中匹配oldbranch分支,然后删除它。