日常工作中,因为都是团队协作,且涉及版本管理,所以git是绕不开的技能。
可能你也会用可视化工具来管理代码,但跨工具时你可能就不会用了。且处理复杂的版本管理问题时,还是命令更加清晰!
一:基本概念
关于基础概念与名称,推荐一个清晰明了的文档:Git 基本操作 | 菜鸟教程
首先普及下git里面的4个概念,
- workspace:工作区
- staging area:暂存区/缓存区
- local repository:版本库或本地仓库
- remote repository:远程仓库
我们的本地修改叫做工作区,git add后添加到缓存区,git commit后添加到本地仓库,git push后推到远程仓库
二:Git命令
1、获取代码
git clone url LocalPath // url为git地址,LocalPath是代码要存在本机的位置
举例:
git clone https://github.com/SunQQQ/SunQBlog-UserSide D://code/SunQBlog-UserSide
如果报错,信息如下
Git:Host key verification failed
大概意思是远端库关键信息失败,需设置提交人名称、邮箱等。提交人设置方法具体见下文
2、更新本地代码:
git pull
3、提交本地代码:
$ git commit -m 提交的描述信息
$ git push
4、合并分支
git branch -a // 展示所有分支
q // 退出分支列表
git checkout 某分支 // 切换到某个分支
git merge 以上某一个分支 // 将某分支合并到本分支
// 如果手动解决冲突后,需要commit操作
git push
合并分支时,发现有冲突需要解决,且冲突你不知道怎么解决。此刻git一直停留在冲突阶段无法使用,异常尴尬,此时你只需要取消合并即可
git merge --abort // 放弃合并操作,恢复到原本分支状态
5、git add . 和 git add * 区别
- git add . 会把本地所有untrack的文件都加入暂存区,并且会根据.gitignore做过滤,
- 但是git add * 会忽略.gitignore把任何文件都加入
6、暂存代码
拉取代码有冲突时,需要先把改动暂存,再拉下代码,处理冲突。然后add、commit、push
如下是一个常用的,当拉取代码有冲突时的操作场景:
git stash save 备注信息 // 暂存修改
git pull // 拉取代码
git stash pop // 恢复暂存的修改 这个指令将缓存堆栈中的第一个stash删除,并将对应修改应用到当前的工作目录下。
如下是暂存常用到命令:
git stash save "message"
: 保存当前的工作成果并添加一个描述性文字。
git stash pop
: 将最近的存储应用到当前分支并从列表中删除它。
git stash list
: 列出当前所有已保存但未恢复的存储。
git stash apply
: 将最近的存储应用到当前分支。
git stash apply 'stash@{2}'
: 应用特定编号的存储到当前分支。
git stash drop 'stash@{0}'
: 从列表中永久删除一个存储。
git stash clear
:删除所有存储。
7、回退版本
git reset 命令用于回退版本,可以指定退回某一次提交的版本。git reset 命令语法格式如下:
git reset [--soft | --mixed | --hard] [HEAD]
--mixed 为默认,可以不用带该参数,用于重置暂存区的文件与上一次的提交(commit)保持一致,工作区文件内容保持不变。
git reset [HEAD]
// 实例:
$ git reset HEAD^ # 回退所有内容到上一个版本
$ git reset HEAD^ hello.php # 回退 hello.php 文件的版本到上一个版本
$ git reset 052e # 回退到指定版本
--hard 参数撤销工作区中所有未提交的修改内容,将暂存区与工作区都回到上一次版本,并删除之前的所有信息提交:
git reset --hard HEAD
// 实例:
$ git reset -–hard HEAD~3 # 回退上上上一个版本
$ git reset –-hard bae128 # 回退到某个版本回退点之前的所有信息。
$ git reset --hard origin/master # 将本地的状态回退到和远程的一样
注意:谨慎使用 -–hard 参数,它会删除回退点之前的所有信息。
回退后,因为本地版本落后于远程仓库,直接push提交不上去。需要git push -f,强制提交
8、删除/拉取分支
如果本地分支代码害怕有问题,那么删除该分支在本地代码后,从新拉取。以master为例
1、先切到别的分支,再git branch -d master,如果本地分支跟服务器不同需要-D
2、git checkout -b master origin/master // 拉取分支
9、提交记录
gitk
该命令会打开一个git自带的历史记录可视化工具,比我们从浏览器里再打开页面看提交记录更方便一些
10、设置提交人名称
git config user.name // 查询当前的提交人姓名
git config --global user.name sunquan // 把提交人姓名设置为sunquan
11、避免每次推送都输入密码
git config --global credential.helper store
12、获取当前 Git 仓库关联的远程仓库的 URL
git config --get remote.origin.url
该命令将返回当前 Git 仓库关联的远程仓库的 URL,也就是你的本地仓库代码是从哪个远程 Git 仓库拉取下来的。
13、关联本地代码与远程仓库
git remote add origin <remote-repository-URL>
14、关联本地分支到远程分支
如果未关联,pull时会提示
There is no tracking information for the current branch.
Please specify which branch you want to merge with.
See git-pull(1) for details.git pull <remote> <branch>
If you wish to set tracking information for this branch you can do so with:
git branch --set-upstream-to=origin/<branch> develop
解决方法:假如分支名为v2.0.0
git branch --set-upstream-to=origin/v2.0.0
三:从本地上传新项目
- 本地文件夹中,git init
- 在github上新建代码库
- 输入命令git add . 将该目录下所有文件添加到本地仓库;
- 输入命令git commit -m “描述” 将刚刚添加的文件提交到本地仓库;
- GitHub上新建的远程仓库建立连接:git remote add origin https://github.com/xxx/xxx
- git push
如遇到 OpenSSL SSL_read: Connection was reset, errno 10054的报错,可以把ssl验证关闭:git config --global http.sslVerify "false"
四:合并分支实操
大多时候公司都是分工合作,可能一人一个分支,各自在自己的分支上开发,然后开发完毕后合并到主分支(master)上线。这时就需要在master上将你的分支合并过来,有时别人分支如果也合并到master了,就需要你先在你的分支上把master上最新的代码合并到你的分支上,然后push;再去master上把你的分支合并过来,然后push。记着push,合并只是合并到本地了。
比如我们现在在dev分支上,想将dev分支合并到master分支,操作如下:
1、确认当前分支
git branch -a // 展示所有分支,高亮的为当前分支
2、首先切换到master分支上
git checkout master
3、如果是多人开发的话 需要把远程master上的代码pull下来
//如果是自己一个开发就没有必要了,为了保险期间还是pull
git pull origin master
4、然后我们把dev分支的代码合并到master上
git merge dev
5、然后查看状态及执行提交命令
git status
On branch master
Your branch is ahead of 'origin/master' by 12 commits.
(use "git push" to publish your local commits)
nothing to commit, working tree clean
//上面的意思就是你有12个commit,需要push到远程master上
6、最后执行提交命令
git push origin master
五:git不能先commit后再pull
今天遇到一个在使用git上的一个误区。具体的问题现象是:
我commit后再pull而不能在本地合并的情况,结果导致我的commit直接把同事的修改覆盖了。因为相对于我此次的commit的A版本是同事的提交的B版本的上一个C版本,我直接是对C版本进行的修改,就是因为我没有先把同事的B版本先pull下来在本地产生一个最新的版本的合并。
我一直都是先commit后再pull,这样能“避免”冲突,事实上这样肯定不行,这样会导致你的commit不是基于最新的版本来进行的,而是上一个版本,这其中有其他的提交而在服务器上产生了最新的版本。而这样避免冲突的方式是错误的,更像是躲开了冲突。正确的操作是先pull下来,再添加,然后冲突解决,然后提交推送.
下面有一个简单的图示:
六:.gitignore添加无效
有一些包含密码的文件我们不想上传git,这时大家都知道把文件路径添加到.gitignore中即可。
但是我在我的老项目中,尝试了几次都不起效果。原来是如果某些文件已经被纳入了版本管理中,在.gitignore中再声明也是不起作用的。
解决方法: git清除本地缓存(改变成未track状态),然后再提交:
1、git rm -r --cached .
2、将不需要上传git的文件添加到.gitignore
3、将所有文件再add commit push上去
gitignore中的文件在github等远程仓库上是没有的,当然本地仓库是有的
ignore的文件,本地代码中文件名称颜色会置灰,且无法记录改动
七:解决冲突
1、当我们pull代码,git命令提示pull失败,拉的代码会把本地代码覆盖。这就是因为有文件冲突
2、这时,我们把本地代码暂存(stash)下,然后再pull,即可拉去成功。
3、此时大概率有两位文件,
- 一类为须要我们手动合并,因为和别人改了同一行,可自行决定incoming那部分
- 一类在本地仓库中已自动合并,因为我们和别人改了同一个文件,但不是同一行,git已自动合并,且add到了暂存区
4、将手动解决冲突后的文件add到暂存区,然后连同自动合并的在暂存区里所有的文件都commit(我曾被同事将此部分代码舍弃导致代码丢失),然后push即可。如下为需要解决冲突的场景
5、以上为pull操作时的冲突场景,合并代码也会出现冲突的场景。跟上面一样操作即可。
如果合并代码出现冲突,手动解决了冲突,并add了该文件。这时后悔了,不想再合并了,只需要放弃暂存区里的更改即可,此时git status会发一切都没有改变。
这是因为虽然合并了冲突并且add到暂存区,但后来撤销了更改,最终是没有commit到本地仓库,且没有push到远程仓库。故一切都没有改变
八:命令行与开发工具区别?
存在在idea可视化配置好的git信息,在命令行中不能使用的情况。
比如idea可视化工具关联了本地代码与git url,且用工具可以正常进行pull/commit/push等操作。
但是在命令行中使用git status等命令时直接报错,报错信息如下
not a git repository( or ang of the parent directiories): .git
这种情况很可能是因为在当前命令行工作目录中不包含 Git 仓库,导致 Git 命令无法执行。而在 IDEA 中,你可能已经在打开的项目中正确地了 Git 仓库,并在连接到远程仓库时指定了凭证。
也就是说IDEA的git配置跟命令行的完全不相关
尝试在命令行工作目录中执行 git status
命令,如果命令行给出“Not a git repository”或类似的错误消息,那么说明该目录下没有正确的 Git 仓库。
你需要将工作目录切换到包含 .git 目录的项目路径,或使用 git clone
命令在命令行中克隆一个新的 Git 仓库。
如果你确信命令行工作目录中包含正确的 Git 仓库,那么还有一些其他原因也可能致出现上述错误,例如:
.git
目录被删除或损坏;- Git 配置中有一些错误的设置,如分支设置、远程仓库设置等;
- Git 某些版本的 bug 或故障。在解决这些问题之前,可以尝试使用
git init
命令重新初始化 Git 仓库,或者使用git clone
命令在命令行中重新克隆一个新的 Git 仓库。如果这些尝试都无法得到有效的结果,那么您可能需要对 Git 进行更详细的分析和故障排除,或者尝试使用 IDEA 排除出现问题的具体原因,以便找到解决方法。
如果感觉修复命令行git太麻烦,干脆直接使用编程工具来操作git吧
九:vscode中提示git不是命令
此时需要配置环境变量,然后重启vscode
PS:实践
1、SSL报错
克隆代码时,正常会自动弹框,要求我们输入git的账号密码。如果不弹出,且git报错如下
SSL certificate problem: self signed certificate
需要如下设置即可
git config --global http.sslVerify false
2、代码维护
我自己写了个个人网站:孙权的博客
前端后端都自己来,自己创建、上传、维护git,自己使用ftp部署服务器。
欢迎大家来玩~~~