Git 與遠端分支

peterjxl發表於2024-09-27

90.遠端倉庫和分支

我們經常需要對遠端倉庫裡的分支進行更新。

當從遠端庫 clone 時,預設情況下,只會拉取 master ​分支,並且會將本地的 master 分支和遠端的 master 分支關聯起來:

$ git branch
* master

推送本地分支

推送分支,就是把該分支上的所有本地提交推送到遠端庫。本地新建的分支如果不推送到遠端,對其他人就是不可見的。

推送時,要指定本地分支,這樣,Git 就會把該分支推送到遠端庫對應的遠端分支上:

$ git push origin master

如果要推送其他分支,比如 dev​,就改成:

$ git push origin dev

實踐(先確保工作區是 clean 的):

$ git switch -c remotebranch
Switched to a new branch 'remotebranch'

# 建立一個新的資料夾
$ mkdir 4-remotebranch

$ echo "remote branch" >> ./4-remotebranch/remote.txt
$ git add .
$ git commit -m "add remote.txt"
$ git push gitee remotebranch

然後我們在另一個目錄裡克隆該專案:

$ git clone git@gitee.com:peterjxl/LearnGit.git

$ ls
Mode                 LastWriteTime         Length Name
----                 -------------         ------ ----
d-----        2023-01-15     12:03                1-diffAndPath
d-----        2023-01-15     12:03                2-versionControl
d-----        2023-01-15     12:03                4-diff
-a----        2023-01-15     12:03              9 .gitignore
-a----        2023-01-15     12:03             34 readme.md

可以看到是沒有 4-remotebranch 這個資料夾的。

注意:

  1. origin 和分支名請修改為自己的
  2. 並不是一定要把所有本地分支往遠端推送,這取決於該分支是否要和其他小夥伴合作開發

拉取遠端分支

多人協作時,大家都會往 master ​和 dev ​分支上推送各自的修改。我們一般會定期(比如每天)從分支上拉取最新的程式碼。

如何檢視遠端分支上有什麼分支呢?可以用 git branch -r​:

$ git branch -r
  gitee/feature
  gitee/master
  github/feature
  github/master

如果涉及到多人開發一個分支,但我們從遠端倉庫 clone 的時候,只有 master 分支;

這時就得拉取遠端 origin ​的 dev ​分支到本地,並關聯起來:

$ git switch -c dev origin/dev

這樣,我們就可以在 dev ​上繼續修改,並時不時地把 dev ​分支 push ​到遠端:

$ git add env.txt
$ git commit -m "add env"
$ git push origin dev

而其他開發 dev 分支的小夥伴,則需要定期從 dev 分支拉取更新:

$ git pull

拉取的時候可能會有衝突,需要手動解決,參考前幾篇部落格。

如果 git pull ​提示 no tracking information​,則說明本地分支和遠端分支的連結關係沒有建立,用命令 git branch --set-upstream-to <branch-name> origin/<branch-name>​。

實踐:我們接著上面的例子來,建立一個分支並關聯:

$ git switch -c remotebranch origin/remotebranch
Switched to a new branch 'remotebranch'
branch 'remotebranch' set up to track 'origin/remotebranch'.


$ ls
Mode                 LastWriteTime         Length Name
----                 -------------         ------ ----
d-----        2023-01-15     12:03                2-versionControl
d-----        2023-01-15     12:03                3-branch
d-----        2023-01-15     12:03                4-diff
d-----        2023-01-15     12:03                4-remotebranch
-a----        2023-01-15     12:03              9 .gitignore
-a----        2023-01-15     12:03             34 readme.md

此時我們可以看到,當前目錄下有 4-remotebranch 這個資料夾了。

注意:在拉取遠端分支之前,最好先 git pull 一下。不然可能找不到該分支。

git fetch

git fetch ​是將遠端主機的最新內容拉到本地倉庫

git pull​ 則是將遠端主機的最新內容拉下來後直接合並,即:git pull = git fetch + git merge​,這樣可能會產生衝突,需要手動解決。

相比之下,git fetch 是一個更安全的選擇,因為它從你的遠端倉庫拉入所有的提交,但不會對你的本地檔案做任何修改。你可以在合併前檢查哪些檔案有變化,哪些檔案可能導致衝突。

分支改名

之前我們說過了怎麼修改分支名:

$ git branch -m <old_branch_name> <new_branch_name>

但這樣是僅能修改本地的分支名的,如果遠端倉庫上也有該分支,並且想要改名,還需進行以下步驟。

推送這個新分支,從而建立一個新的遠端分支:

$ git push origin <new_branch_name>

然後刪除遠端分支:

$ git push origin -d -f <old_branch_name>

同時推送多個倉庫

先前,我們新增了兩個遠端參考,一個 Gitee,一個 GitHub。如果我們要推送,需要分別推送分支到兩個倉庫上,有沒辦法一次性就推送兩次呢?有的。

比如,我們想推送到 Gitee 的時候,預設也推送到 GitHub,那麼可以給 gitee 新增一個遠端的 push 地址,這樣一次 push 就能同時 push 到兩個地址上面

語法格式:

$ git remote set-url --add 遠端倉庫名 另一個倉庫的push地址

例如:

$ git remote -v
gitee   git@gitee.com:peterjxl/LearnGit.git (fetch)
gitee   git@gitee.com:peterjxl/LearnGit.git (push)
github  git@github.com:Peter-JXL/LearnGit.git (fetch)
github  git@github.com:Peter-JXL/LearnGit.git (push)



git remote set-url --add gitee git@github.com:Peter-JXL/LearnGit.git


$ git remote -v //檢視是否多了一條push地址
gitee   git@gitee.com:peterjxl/LearnGit.git (fetch)
gitee   git@gitee.com:peterjxl/LearnGit.git (push)
gitee   git@github.com:Peter-JXL/LearnGit.git (push)
github  git@github.com:Peter-JXL/LearnGit.git (fetch)
github  git@github.com:Peter-JXL/LearnGit.git (push)

至此,我們就可以直接一個 push,同時推送到兩個 git 地址。我們來測試下:

$ echo "test push two repository" >> 4-diff/testDiff.txt
$ git add 4-diff/testDiff.txt
$ git commit -m "add test push two repository"

$ git push gitee
Enumerating objects: 13, done.
Counting objects: 100% (13/13), done.
Delta compression using up to 20 threads
Compressing objects: 100% (6/6), done.
Writing objects: 100% (12/12), 946 bytes | 946.00 KiB/s, done.
Total 12 (delta 3), reused 0 (delta 0), pack-reused 0
remote: Powered by GITEE.COM [GNK-6.4]
To gitee.com:peterjxl/LearnGit.git
   378332f..5ba73a6  master -> master
Enumerating objects: 13, done.
Counting objects: 100% (13/13), done.
Delta compression using up to 20 threads
Compressing objects: 100% (6/6), done.
Writing objects: 100% (12/12), 946 bytes | 946.00 KiB/s, done.
Total 12 (delta 3), reused 0 (delta 0), pack-reused 0
remote: Resolving deltas: 100% (3/3), completed with 1 local object.
To github.com:Peter-JXL/LearnGit.git
   378332f..5ba73a6  master -> master

可以看到 git push 的輸出中,既有 Gitee 的輸出,也有 GitHub 的輸出。

如果不想同時推送多個倉庫,可刪除 push 地址:

$ git remote set-url --delete origin 地址

以上配置是在 .git/config ​檔案裡儲存的。我們也可以透過直接修改該檔案來達到配置的效果

原始內容:

[core]
        repositoryformatversion = 0
        filemode = false
        bare = false
        logallrefupdates = true
        symlinks = false
        ignorecase = true
[remote "gitee"]
        url = git@gitee.com:peterjxl/LearnGit.git
        fetch = +refs/heads/*:refs/remotes/gitee/*
[branch "master"]
        remote = gitee
        merge = refs/heads/master
[remote "github"]
        url = git@github.com:Peter-JXL/LearnGit.git
        fetch = +refs/heads/*:refs/remotes/github/*

我們在 Gitee 裡,新增一行:

url = git@github.com:Peter-JXL/LearnGit.git

修改後:

[core]
        repositoryformatversion = 0
        filemode = false
        bare = false
        logallrefupdates = true
        symlinks = false
        ignorecase = true
[remote "gitee"]
        url = git@gitee.com:peterjxl/LearnGit.git
        fetch = +refs/heads/*:refs/remotes/gitee/*
        url = git@github.com:Peter-JXL/LearnGit.git
[branch "master"]
        remote = gitee
        merge = refs/heads/master
[remote "github"]
        url = git@github.com:Peter-JXL/LearnGit.git
        fetch = +refs/heads/*:refs/remotes/github/*

相關文章