使用Git管理源码时,如果项目需要和他人协作,通常需要一个或多个远程仓库(remote repository)。
远程仓库作为项目的版本库,可以托管在自己搭建的Git服务器上的,也可以是托管在互联网上的(例如GitHub、AzureDevops等)。
1. 管理远程仓库
1.1. 查看远程仓库
-
git remote -v
:查看本地仓库所有的远程仓库。仍然以gitsample为例:
$ git remote -v
origin https://github.com/efreykongcn/gitsample (fetch)
origin https://github.com/efreykongcn/gitsample (push)
命令返回了两行信息,分别列出了fetch和push命令的对应remote。这两个命令随后会介绍。
每一行信息的第一列为远程仓库的别名(默认为origin),第二列为远程仓库的地址。
为什么我们并没有对gitsample添加过任何远程仓库,而仓库里就已经由远程仓库了?这是因为项目是从github clone初始的,clone的时候git会自动将被clone的源设置为本地仓库的remote。
-
git remote show <远程仓库别名>
查看指定远程仓库。现在查看下origin
$ git remote show origin
* remote origin
Fetch URL: https://github.com/efreykongcn/gitsample
Push URL: https://github.com/efreykongcn/gitsample
HEAD branch: master
Remote branch:
master tracked
Local branch configured for 'git pull':
master merges with remote master
Local ref configured for 'git push':
master pushes to master (fast-forwardable)
1.2. 移除远程仓库
-
git remote rm <远程仓库别名>
命令可以移除指定的远程仓库。
现在我们来将gitsample默认添加的remote移除:
$ git remote rm origin
再来查看远程仓库:
$ git remote -v
命令返回的结果是空的,可以确认
1.3. 为本地仓库添加远程仓库
-
git remote add <远程仓库别名> <远程仓库url>
命令可以添加远程仓库。
现在我们将github上的远程库添加回来:
$ git remote add githubek git@github.com:efreykongcn/gitsample.git
再查看远程仓库:
$ git remote -v
githubek origin git@github.com:efreykongcn/gitsample.git (fetch)
githubek origin git@github.com:efreykongcn/gitsample.git (push)
1.4. 修改远程仓库
-
git remote rename <当前远程仓库的别名> <想要改成的别名>
:修改远程仓库的别名。
远程仓库又添加回来了,只是这次的别名为“githubek”。通常推荐默认同步的仓库别名为origin,现在我们将别名改回来:
$ git remote rename githubek origin
-
git remote set-url <远程仓库别名> <远程仓库url>
:修改远程仓库的url。
另外这次添加的远程仓库使用的是ssh,现在改回https:
$ git remote set-url origin https://github.com/efreykongcn/gitsample.git
再来查看:
$ git remote -v
origin https://github.com/efreykongcn/gitsample.git (fetch)
origin https://github.com/efreykongcn/gitsample.git (push)
2. 同远程仓库同步数据
2.1. 向远程仓库推送更新
使用git push
命令可以向远程仓库推送更新。常见的几种用法如下:
git push origin master
将本地当前分支的更新推送到远程仓库origin的master分支。使用这个命令时,如果分之间没有建立跟踪关系会报错:fatal: The current branch master has no upstream branch.git push --set-upstream <远程仓库别名> <远程分支名>
为本地的分支同远程仓库的分支建立跟踪关系并将本地分支的更新(提交)推送到远程仓库关联的分支。git push <远程仓库别名> <本地分支名>:<远程分支名>
将指定的本地分支的更新推送到远程仓库的指定分支。这个命令不需要本地分支和远程分支建立跟踪关系。git push origin --delete feature-c3
删除远程仓库orgin的feature-c3分支。效果等同于git push origin :feature-c3
(推送空的库到远程仓库)。如果远程仓库只有一个分支(默认分支),那么这个分支不允许被删除,使用推送删除命令时git会报错。
git push --all origin
将本地所有的分支推送到远程仓库,包括本地新建但还没有推送到远程仓库的分支。git push -f origin master
:强制将本地的更新推送到远程仓库origin的master分支。例如,当本地发生过提交的回撤时(被本地回撤的递交已经被推送到远程仓库),需要使用-f
这个强制参数,否则不会成功。git push origin --tags
将本地的tag推送到远程仓库。需要注意的是,在使用push命令但是没有指定--tags
参数的情况下,git是不会将tag推送到到远程仓库的。
接下来将本地的更新推送到远程仓库:
$ git push --set-upstream origin master
Enumerating objects: 14, done.
Counting objects: 100% (14/14), done.
Delta compression using up to 8 threads
Compressing objects: 100% (11/11), done.
Writing objects: 100% (12/12), 1.22 KiB | 249.00 KiB/s, done.
Total 12 (delta 3), reused 0 (delta 0)
remote: Resolving deltas: 100% (3/3), done.
To https://github.com/efreykongcn/gitsample.git
4a567b9..23b2190 master -> master
Branch 'master' set up to track remote branch 'master' from 'origin'.
2.2. 从远程仓库获取更新
使用git fetch
和git pull
都可以从远程仓库获取更新(commit)。不同的是fetch操作只获取更新,但是不会将远程仓库的更新合并到本地仓库。pull操作获取更新然后将更新合并到本地仓库,并且会用合并的结果更新暂存区和工作区。
一般推荐使用git fetch
+ git merge
的方式来获取更新并合并到本地。这两个命令组合使用效果等同于git pull
,但是fetch和merge之间可以通过diff来查看差异,确认没有问题了再merge。
2.2.1. git fetch
-
git fetch <远程仓库别名> [<远程分支名>]
:从远程仓库获取更新到本地仓库,但是不更新暂存区和工作区。如果不指定分支名则获取全部分支的更新。这个命令通常用来查看远程仓库的更新情况。
从远程仓库获取了更新后,可以使用git diff <本地分支名> <远程仓库别名>/<远程仓库分支名>
命令来查看本地分支和远程分支的差异。
如果本地分支同远程分支的提交有差异,可以使用git merge [<本地分支名>] <远程仓库别名>/<分支名>
命令将远程分支的提交合并到本地的分支。
示例:
$ git fetch origin #获取origin全部分支的更新
$ git fetch origin master #获取origin master分支的更新
$ git diff master origin/master
$ git merge origin/master #省略本地分支名,则会将origin/master合并到当前签出的本地分支。
2.2.2. git pull
-
git pull <远程仓库别名> <远程分支名>[:<本地分支名>]
从远程仓库指定分支拉取更细并合并到本地指定的分支。如果不指定本地分支名,则默认合并到当前签出的分支。
示例:
$ git pull origin master
From https://github.com/efreykongcn/gitsample
* branch master -> FETCH_HEAD
Already up to date.