git 学习笔记 - git add/commit/log 等基本操作介绍
这里是将原来的两篇博文做了拆分.感觉之前一篇文章中涵盖的东西太多,看起来容易让人失去信心,主题也不是很明确.经过拆分后,这篇文章主要记录 git 进行本地操作时的基本命令,包括 git add/commit/log等,也就是介绍涉及本地修改/提交等操作的命令.这些命令在 git 本地仓库中使用.关于git 中仓库和文件状态的基本概念可以参见拆分出来的另一篇博文git 学习记录—— git 中的仓库、文件状态等概念介绍.
通过 git status 查看当前目录下各个文件的状态。git status 还会给出各种状态下文件可以使用的操作指令。
git status //查看当前文件夹下各个文件的状态 git status -s //查看各文件状态,使用字母简单表示文件状态
一个 git 仓库下文件的状态主要有 (对应git 学习记录—— git 中的仓库、文件状态等概念介绍):
Untracked files : 对应并未被 git 追踪记录的文件,当通过 git init 初始化一个目录时,是初始化了一个空的 git 目录,所有该目录下的文件均处于未被 git 追踪记录的状态。新建文件的状态也属于此类;
changes not staged for commit : 仅限于已经被 git 追踪记录( tracked )的文件。若这些文件发生了修改,但还没有被通过 git add 加入需要进行提交的状态( staged ),则处于此状态;
changes to be committed : 仅限于已经被 git 追踪记录( tracked )的文件。当这些文件发生了修改,且已经通过 git add 加入需要进行提交的状态,则处于此状态。通过 git commit 提交的修改即为处于该状态的文件的修改;
笔者进行实践时新建 test 目录,其中仅包含一个 hello.cpp 文件,在通过 git init 初始化后,即生成一个空的 git repository,git status 的结果如下图,可以看到此时的 hello.cpp 处于 Untracked 状态。
通过 git add 添加文件至待提交的状态( changes to be committed )。git add 主要有两个功能: a.将未被 git 追踪记录( untracked )的文件"加入" git 仓库的记录中; b.将处于 changes not staged for commit 状态下的文件的修改添加至需要进行提交的状态( staged )。这两个功能均会将文件变为 changes to be committed 状态。
git add file-list //将 file-list 指定的文件添加至 changes to be committed 状态 git add . //将当前目录下所有的文件添加至 changes to be committed 状态
用户可通过 git add 命令将当前目录下处于 untracked 状态下的文件"添加"至 git 仓库中。在笔者的实践中,即通过 git add hello.cpp 将 hello.cpp 加入 changes to be committed 状态,也可使用 git add . 命令将当前目录下所有文件变为 changes to be committed 状态。
通过指令 git commit 提交所有处于 staged 状态的文件。注意使用上述命令只会提交使用 git add 命令标记为 staged 状态的文件。
通过指令 git commit 提交时 Git 会通过默认编辑器显示一个编辑界面,用户需编辑提交信息(commit message),用于标识该次提交。其中 # 开始的行表示注释,用户编辑结束退出后,Git会使用该提交信息创建新的提交(即生成新的快照)。默认的显示内容包括最近一次 git status 命令显示的结果(注释),使用提交时加入参数 -v 则会将 git diff 指令的结果也包含在显示内容中,用户可以通过取消注释或编辑新内容来修改提交信息( Ubuntu 系统下运行结果 )。
用户也可以使用 git commit -m "commit message" 命令来直接指定提交信息,可用于提交流程更简洁的情况。
git commit -m "test" //使用提交信息 "test" 提交所有 staged 的修改 git commit --allow-empty //允许无内容的提交 git commit -am "test" //直接将所有被修改的文件提交,相当于先 git add 再 commit
当用户提交了最近的一次 commit后,发现仍有一些内容被遗漏,如存在已被修改的文件没有通过 git add 加入 staged 状态从而没有被正确提交,或者在提交后发现存在一些小错误故而进行了修改,此时已经提交的 commit 中并不包含这些记录.此时可通过 git commit 命令的 --amend 选项将当前 staged 状态下的修改合并进最新的一次提交的修改中.注意,只有当前被 staged 状态的修改会被合并,所以在 git commit 之后立即运行 git commit --amend 命令并不会产生变化(因为不存在被 staged 的修改).该命令实际上创建了一个新的 commit 提交,该提交会基于最近一次提交的基本信息生成,并合并了该次 commit 和当前被 staged 的修改.
git commit --amend //合并最近一次 commit 和当前处于 staged 状态的修改
注意:git commit 保存的数据仅保存在本地仓库中,若需要同步至远端仓库,需要使用 git 支持的远程仓库操作。同时,第一次使用 git commit 进行提交时需要设置好用户的用户名和邮箱,可以查看后文的 git 设置部分。
在 git 中,删除一个文件包括取消文件的 tracked 状态,之后再进行提交,可通过命令 git rm 完成上述操作。更具体描述可以参考这里。
git rm a.c 会将文件a.c 删除,并将删除这个"修改"标记为 staged 状态。当使用 git commit 命令之后,a.c 文件就会从工作目录中消失,并不再为 tracked 状态。这样可以保证不会在之后的操作中将该文件视为 untracked 文件再次进行处理。
注意:常规的删除操作如 rm,会使得删除的文件处于 Changes not staged for commit 状态,而 git rm 的删除操作使得被删除文件处于 Changed to be commited 状态。对于后者,用户提交之后,被删除的文件之后不再被 git 记录,而前者由于并不会被提交,会一直保持该状态。
对于已经修改并被加入staged状态的文件来说,通过 git rm 删除该文件需要使用 -f 参数,以避免删除 git 尚未记录的文件和其他误操作。
使用参数 git rm --cached xxx 可以使得文件不再被 git 记录,但继续存在于工作目录下,作用与 .gitignore 文件类似。
对于本地创建的或自其他仓库克隆的具有多次提交记录的项目,可以通过 git log 命令查看历史的提交记录。
默认情况, git log 会根据提交顺序的逆序排列(即最近的提交最先显示), git log 会显示提交顺序及其对应的SHA-1哈希值,以及作者、邮箱、提交日期和提交信息等内容。
git log 有一些常用的参数可以用于更精确的显示需要的内容。
-p //在 log 条目中加入每次提交的修改信息 -n //仅显示最近的n个提交条目 --stat //显示每次提交被修改的文件的信息 --pretty=options //options可以为online、short等,也可以自行指定输出的格式信息,可以参考这里 --graph //输出字符树的形式显示提交记录
通过指令 git status 可以得知当前各个文件所处的状态(是否发生改变等),通过指令 git diff可以得知某一文件发生的怎样的改变。
git diff //查看那些再次修改但尚未被staged的文件修改情况,如 git add a.c 命令之后,再次对 a.c 所做的(而又未被staged)的修改 git diff --stat // 显示对当前修改的统计描述 git diff --stage //查看当前staged状态下的文件较之原始(未修改状态下,也就是上一次提交时)的文件的修改情况 git diff commit1 commit2 //比较两次提交之间的差别
git diff 会将当前工作目录下的文件与处于staged状态的文件进行比较,并将差异结果显示出来。可以视为显示自上一次 git add 后进行的修改情况。
git diff --stage会将当前处于staged状态的文件与上一次提交的结果进行比较,并将结果显示出来。可以视为显示自上一次 git commit 后进行的修改情况。
注意:指令 git diff 只会显示还未被staged的修改,即之前已经通过 git add 命令加入staged状态的修改是不被显示的。使用参数 --staged或--cached显示当前已经处于staged状态的修改,即与上一次提交进行比较的结果。
撤销与修改操作
(1)针对提交过程:若发现存在部分文件未正确提交(未加入 staged 状态)或提交信息有疏漏,可以先将需要补充提交的文件加入 staged 状态,再使用 git commit --amend 命令,则本次提交会取代上一次的提交,在此过程中,也可以修改提交信息;
(2)针对 staged 状态的文件:使用命令 git reset HEAD filename 可以将 filename 文件从 staged 状态中恢复至一般修改状态;
(3)针对已经修改的文件:若想要将已经修改的文件恢复至未修改的状态,可以使用 git checkout --filename,则会将对应文件从之前的提交记录中恢复,而简单的丢弃对其的修改;
事实上,通过 git status 命令获得当前工作目录中文件的状态信息时,针对每种文件状态会有相应的 git 操作提示。用户可以直接使用 git status 命令查看特定的文件类型如何进行操作。
其他
(1)跳过 staged area 状态:在命令 git commit 中加入 -a 参数,git 会直接将所有 tracked 文件提交,而不再需要使用 git add 将其转换为 staged 状态。
(2)可创建一个 .gitignore 文件,来设置不需要 Git 进行显示和提交的文件(处理时直接忽略),最简单的 .gitignore 文件的写入就是每个文件/文件夹占一行,所有被包含在其中的内容都被 git 所忽略。具体的写法可参考这里。
git 通过其携带的工具 git config 来对修改配置变量从而对应用进行个性化设置,个性化设置的变量可能会被存储在三个不同的位置,各自有着不同的作用域( Ubuntu 环境下目录结构 )。
(1) /etc/gitconfig,全局的 git 变量设置。其中的设置会应用到系统所有用户和 git 仓库。通过 git config 的 --system 参数进行设置。
(2) ~/.gitconfig或~/.config/git/config,用户个人的 git 变量设置,该设置应用于该用户的所有操作。通过 --global 参数进行设置。
(3) git目录中的 config 文件(下文的.config目录中),记录对该 git 目录的一些配置变量。
每一层设置的配置变量的值会覆盖上一层的设置值,故而 git 目录中的 config 文件中特定设置的效果会掩盖 /etc/gitconfig 中的对应的设置效果。
设置个人信息
设置个人有关的信息,包括用户名和 email,在进行提交之前,必须进行用户名和邮箱名的设置。这是与单个用户相关的设置,故而使用参数 --global。
git config --global user.name "xxx" git config --global user.email email_address
设置默认编辑器
git config --global core.editor vim //在 Ubuntu 环境下设置编辑器为 vim
查看设置
可以通过以下命令对 git 的配置参数进行查看
git config --list //查看当前已经设置的所有变量值,会从以上三个文件中读取,故而特定变量可能出现多次,其最后出现的值为 git 实际使用的值 git config key_name //查看Git当前使用的特定变量的值,如 git config user.name
git 帮助
用户可以通过命令行方式获得帮助,包括如下命令,可以通过帮助信息和网络资源理解 git 相关命令的功能。
git help <action> //如通过 git help config 来过得对config操作的相关帮助 man git-行为名 //如通过 man git-config 来获得帮助 git command -h //获得简略的帮助提示,如 git config -h
参考和学习资源: