Git 是目前世界上被最广泛使用的现代软件版本管理系统。Git 本身亦是一个成熟并处于活跃开发状态的开源项目,它最初是由 Linux 操作系统内核的创造者 Linus Torvalds 在 2005 年创造。今天惊人数量的软件项目依赖 Git 进行版本管理,这些项目包括开源以及各种商业软件。Git 在职业软件开发者中拥有良好的声誉,Git 目前支持绝大多数的操作系统以及 IDE(Integrated Development Environments)。
将远端的仓库克隆到本地
可以cd进入想将项目放入的文件夹,然后输入如下命令克隆项目。
# 将远端的仓库克隆到本地
git clone https://github.com/Geek-monk/studyeveryday_for_python.git
创建新仓库
进入本地的项目文件夹,将其创建为一个Git仓库,方便使用Git命令进行管理。目的是将一个不是仓库的文件夹变成Git仓库。此命令会在文件夹中创建一个.git文件夹。
# 创建新仓库
git init
# 创建空仓库,只有.git,没有工作目录,名为<directory>
git init --bare <directory>
如果没有从远程克隆仓库到本地,并想将本地仓库连接到某个远程服务器(公司d代码管理平台,github等),使用如下命令添加。
# 连接远程仓库
git remote add origin <server>
添加与提交
修改或者新增代码,要将其先从本地工作空间添加到缓冲区,再提交到本地仓库。一个项目的编写离不开这个基本模式:编辑、缓存和提交。首先,你在工作目录下编辑你的文件。当你想要备份当前的项目状态时,你使用 git add 缓存更改。当你觉得这个被缓存的副本已经就绪,你使用 git commit 将它提交到项目历史。git reset 命令用于撤销提交或被缓存的快照。缓存允许你把紧密相关的几份更改合并成一份快照,而不是直接提交所有新的更改。也就是说你可以同时进行多个无关的更改,最后分成几次将相关更改添加到缓存区并提交。
# 第一步:添加到缓冲区
git add .
git add <文件名称>
# 第二步:提交到本地仓库,-m 的意思是添加备注。建议必须添加备注,方便协作。
git commit -m "本次提交代码的备注,说明有哪些修改"
提交到远程仓库
前两步的操作只是将代码提交到了HEAD,并没有提交到远程的仓库,例如公司的代码管理平台,或者github、gitlab等。
# 第三步:提交到远程仓库master,master可以替换成其他分支,origin是远程仓库的名字,也可以自定义
git push origin master
Git的配置
git config 在命令行中配置你的 Git 的信息。这个命令定义了所有配置,从用户信息到仓库行为等等。一些常见的配置命令如下所列。
# 告诉Git你是谁
git config --global user.name "Geekmonk"
git config --global user.email Geekmonk@example.com
# 选择你喜欢的文本编辑器
git config --global core.editor vim
# 添加一些快捷方式(别名)
git config --global alias.st status
git config --global alias.co checkout
git config --global alias.br branch
git config --global alias.up rebase
git config --global alias.ci commit
检查仓库状态
- git status 命令显示工作目录和缓存区的状态。你可以看到哪些更改被缓存了,哪些还没有,以及哪些还未被 Git 追踪。status 的输出 不会 告诉你任何已提交到项目历史的信息。如果你想看的话,应该使用 git log 命令。
# 列出已缓存、未缓存、未追踪的文件。
git status
- git log 命令显示已提交的快照。你可以列出项目历史,筛选,以及搜索特定更改。git status 允许你查看工作目录和缓存区,而 git log 只作用于提交的项目历史。
# 使用默认格式显示完整地项目历史。如果输出超过一屏,你可以用 空格键 来滚动,按 q 退出。
git log
#用 <limit> 限制提交的数量。比如 git log -n 3 只会显示 3 个提交。
git log -n <limit>
#将每个提交压缩到一行。当你需要查看项目历史的上层情况时这会很有用。
git log --oneline
#除了 git log 信息之外,包含哪些文件被更改了,以及每个文件相对的增删行数。
git log --stat
#显示代表每个提交的一堆信息。显示每个提交全部的差异(diff),这也是项目历史中最详细的视图。
git log -p
#搜索特定作者的提交。<pattern> 可以是字符串或正则表达式。
git log --author="<pattern>"
#搜索提交信息匹配特定 <pattern> 的提交。<pattern> 可以是字符串或正则表达式。
git log --grep="<pattern>"
#只显示发生在 <since> 和 <until> 之间的提交。两个参数可以是提交 ID、分支名、HEAD 或是任何一种引用。
git log <since>..<until>
#只显示包含特定文件的提交。查找特定文件的历史这样做会很方便。
git log <file>
#还有一些有用的选项。--graph 标记会绘制一幅字符组成的图形,左边是提交,右边是提交信息。--decorate 标记会加上提交所在的分支名称和标签。--oneline 标记将提交信息显示在同一行,一目了然。
git log --graph --decorate --oneline
checkout 之前的提交
- checkout的三种用法:
- 检出文件
- 检出提交
- 检出分支
# 回到 master 分支。只需要将它视为回到项目「当前」状态的一种方式。
git checkout master
# 查看文件之前的版本。它将工作目录中的 <file> 文件变成 <commit> 中那个文件的拷贝,并将它加入缓存区。
git checkout <commit> <file>
# 更新工作目录中的所有文件,使得和某个特定提交中的文件一致。你可以将提交的哈希字串,或是标签作为 <commit> 参数。这会使你处在分离 HEAD 的状态。
git checkout <commit>
回滚错误的修改
git revert 命令用来撤销一个已经提交的快照。但是,它是通过搞清楚如何撤销这个提交引入的更改,然后在最后加上一个撤销了更改的 新 提交,而不是从项目历史中移除这个提交。这避免了Git丢失项目历史,这一点对于你的版本历史和协作的可靠性来说是很重要的。
# 生成一个撤消了 <commit> 引入的修改的新提交,然后应用到当前分支。
git reset <file>
如果说 git revert 是一个撤销更改安全的方式,你可以将 git reset 看做一个 危险 的方式。当你用 git reset 来重设更改时(提交不再被任何引用或引用日志所引用),我们无法获得原来的样子——这个撤销是永远的。使用这个工具的时候务必要小心,因为这是少数几个可能会造成工作丢失的命令之一。
和 git checkout 一样,git reset 有很多种用法。它可以被用来移除提交快照,尽管它通常被用来撤销缓存区和工作目录的修改。不管是哪种情况,它应该只被用于 本地 修改——你永远不应该重设和其他开发者共享的快照。
# 从缓存区移除特定文件,但不改变工作目录。它会取消这个文件的缓存,而不覆盖任何更改。
git revert <commit>
#重设缓冲区,匹配最近的一次提交,但工作目录不变。它会取消 所有 文件的缓存,而不会覆盖任何修改,给你了一个重设缓存快照的机会。
git reset
# 重设缓冲区和工作目录,匹配最近的一次提交。除了取消缓存之外,--hard 标记告诉 Git 还要重写所有工作目录中的更改。换句话说:它清除了所有未提交的更改,所以在使用前确定你想扔掉你所有本地的开发。
git reset --hard
# 将当前分支的末端移到 <commit>,将缓存区重设到这个提交,但不改变工作目录。所有 <commit> 之后的更改会保留在工作目录中,这允许你用更干净、原子性的快照重新提交项目历史。
git reset <commit>
# 将当前分支的末端移到 <commit>,将缓存区和工作目录都重设到这个提交。它不仅清除了未提交的更改,同时还清除了 <commit> 之后的所有提交。
git reset --hard <commit>
git clean 命令将未跟踪的文件从你的工作目录中移除。它只是提供了一条捷径,因为用 git status 查看哪些文件还未跟踪然后手动移除它们也很方便。和一般的 rm 命令一样,git clean 是无法撤消的,所以在删除未跟踪的 文件之前想清楚,你是否真的要这么做。
git clean 命令经常和 git reset --hard 一起使用。记住,reset 只影响被跟踪的文件,所以还需要一个单独的命令来清理未被跟踪的文件。这个两个命令相结合,你就可以将工作目录回到之前特定提交时的状态。
# 执行一次git clean的『演习』。它会告诉你那些文件在命令执行后会被移除,而不是真的删除它。
git clean -n
# 移除当前目录下未被跟踪的文件。-f(强制)标记是必需的,除非 clean.requireForce 配置项被设为了 false(默认为 true)。它 不会 删除 .gitignore 中指定的未跟踪的文件。
git clean -f
# 移除未跟踪的文件,但限制在某个路径下。
git clean -f <path>
# 移除未跟踪的文件,以及目录。
git clean -df
# 移除当前目录下未跟踪的文件,以及 Git 一般忽略的文件。
git clean -xf