簡體   English   中英

如何克隆包含所有分支的 git 存儲庫?

[英]How to clone a git repository with all branches?

我有一個服務器,其中包含一個帶有多個分支的 git 存儲庫。 我用“git branch -r”檢查了服務器 git,它顯示:
起源/頭部
起源/發展
起源/整潔的用戶界面
來源/iOS
...還有更多

如果我使用以下命令克隆此存儲庫:“git clone [path_to_server]/ATS ATS”,我會收到一個僅包含“develop”的存儲庫。 “git branch -a”顯示:
* 開發
遙控器/起源/HEAD -> 起源/開發
遙控器/起源/開發

所有其他分支都丟失了。

如果我使用 --mirror 選項克隆存儲庫,所有分支都存在,但我無法使用它們。 “git branch -a”顯示:
遙控器/原點/頭
遙控器/起源/開發
遙控器/起源/neatUI
遙控器/起源/iOS
...和 rest

如果我嘗試檢查一個分支 git 告訴我“致命的:這個操作必須在工作樹中運行”

我還嘗試了“SourceTree”來克隆存儲庫,但 SourceTree 也只創建了“開發”分支。

有人有想法嗎?

這里有幾個獨立但又相互交織的關鍵概念。

首先,雖然 Git 有分支名稱,但這並不是 Git 的全部(就此而言,術語分支是模棱兩可的:另請參閱我們所說的“分支”究竟是什么意思? )。 Git 也有標簽和 Git 稱之為遠程跟蹤分支名稱的東西,這些都屬於一個稱為引用的一般類別。

  • master這樣的分支名稱只是一個名以refs/heads/開頭的引用。

  • origin/iOS這樣的遠程跟蹤分支名稱是一個引用,其名以refs/remotes/開頭,后跟遠程本身的名稱 ( origin ) 和另一個斜杠。 最后一部分iOS是您的 Git 通常從另一個 Git 復制的內容

    遠程部分是一個幾乎任意的字符串。您可以發明自己的遠程名稱。但是,遠程名稱之后添加斜杠這一事實與您應該小心在您的遠程名稱。)

  • 為了完成這個特定的列表,像v1.0這樣的標簽名稱只是一個參考,其名以refs/tags/開頭。 還有更多形式的引用( refs/notes/用於 Git 的git notes ,例如 GitHub 使用refs/pull/ )但是分支、標簽和遠程跟蹤分支都是內置的,並且是標准的,最重要的是,高度可見 - 所以你應該了解它們。

當您運行git branch ,Git 會找到您所有的refs/heads/引用名稱並顯示它們並去除refs/heads/ 當您運行git branch -r ,Git 會找到您所有的refs/remotes/引用並顯示它們並刪除refs/remotes/ 當您運行git branch -a ,Git 會同時找到兩者,並顯示第一個帶有refs/heads/剝離,但顯示第二個僅refs/剝離。 (為什么?誰知道呢!Git 是 gitty。:-))

這解釋了為什么你看到你所看到的,而不是git clone --mirror會發生什么,也解釋了為什么你可以git checkout iOS突然有了一個新的refs/heads/iOS 為此,我們還需要兩個項目,關於refspecs (與git fetchgit push ),以及關於Git 在git checkout調用DWIM或 Do What I Mean 的內容

簡而言之: refspec只是一對引用,用冒號分隔,有時用*替換一部分。 例如, refs/heads/*:refs/remotes/origin/*是一個 refspec。 您也可以使用前導加號作為 refspec 的前綴; 這將設置--force標志。 git fetchgit push都與 refspecs 一起工作(並且它們都有自己的--force標志,這有效地為您在命令行上提供的任何 refspecs 添加了一個+ )。 冒號前的引用是,冒號后的引用是目標,這很重要,因為git fetchgit push涉及兩個git push :你的和其他一些 Git。

當你git fetch ,源引用是其他 Git 的引用,目標引用是你的。 當你git push ,源引用是你的,目標引用是他們的。

使用git clone --mirror告訴您的 Git 設置一個存儲庫(我將在此處未定義)並將+refs/*:refs/*設置為git fetch +refs/*:refs/*規范。 這會復制來自origin其他 Git 的所有引用,但這意味着您不能擁有自己的分支:您的 Git 現在是他們的一個精確副本,並且每次運行git fetch您都將擁有的所有內容替換為……一個精確的他們的副本,再次。

大多數git clone操作的要點是獲取“他們的 Git”的不精確副本。 這里的基本思想是您希望它們的所有分支名稱都成為您的遠程跟蹤分支名稱。 他們的master成為你的origin/master 他們的iOS成為你的origin/iOS

這沒有為它們的origin/*留下空間,因為你的不精確副本有它自己的origin/* 如果你想得到他們的遠程跟蹤分支,你可以——但你需要給他們起別的名字!

一旦你有你的(無反光鏡)克隆,他們whatever成為你的origin/ whatever ,你可以git checkout whatever我提到的(和鏈接)和DWIM行動上方進場時,創建一個新的地方whatever使用的是自己origin/ whatever你從他們的whatever復制的!

如果您使用git clone <url>克隆,請放心,所有分支都在您的工作樹中。 當您想簽入其他分支時,您只需要剝離 origin/ 。 例如,如果你想結帳iOS,請執行git checkout iOS

git branch -r顯示存儲庫上的所有遠程分支

git branch -a顯示遠程和本地分支(如果您在本地存儲庫中創建了任何分支)

我有同樣的問題。 我以前用--branch <branch-name>--depth 1選項克隆了我的--depth 1
這會將remote.origin.fetch的配置條目設置為+refs/heads/<branch-name>:refs/remotes/origin/<branch-name>+refs/heads/<default-branch>:refs/remotes/origin/<default-branch>

<default-branch>通常是mainmaster或者在 OP develop情況下。

您可以使用以下命令進行檢查:

git config --get remote.origin.fetch

如果您的遙控器名稱不同,請替換origin ,請參閱git remote -v

您可以使用以下命令更新設置

git config --replace-all remote.origin.fetch +refs/heads/*:refs/remotes/origin/*

您還可以使用git config -e在配置的編輯器中編輯git config -e

[remote "origin"]
    url = https://github.com/<some-user>/<some-repo>.git
    fetch = +refs/heads/*:refs/remotes/origin/*

現在git fetch應該獲取所有遠程分支(和相關標簽)。

有關詳細信息,請參閱@torek 的回答

我在github.com上有 2 個分支的 repo 有類似的問題。 下面的解決方案基於github.com上的演示存儲庫,該存儲庫專為本答案而創建。

demo.git repo 有兩個名為firstsecond的分支,只包含一個文件README.md ,每個分支的內容都不同。

克隆存儲庫,列出分支,切換到感興趣的分支。 注意:下面的附加評論以##為前綴

## clone demo repo to local machine
$ git clone git:github.com:ugmurthy/demo.git
Cloning into 'demo'...
remote: Enumerating objects: 9, done.
remote: Counting objects: 100% (9/9), done.
remote: Compressing objects: 100% (3/3), done.
remote: Total 9 (delta 0), reused 0 (delta 0), pack-reused 0
Receiving objects: 100% (9/9), done.

$ cd demo

## show local branches
$ git branch
* main

## show remote branches (github.com)
$ git branch -r
  origin/HEAD -> origin/main
  origin/first
  origin/main
  origin/second

## show both local and remote branches
$ git branch -a
* main
  remotes/origin/HEAD -> origin/main
  remotes/origin/first
  remotes/origin/main
  remotes/origin/second


$ cat README.md 
# Demo

## switching branch 
$ git switch first
Branch 'first' set up to track remote branch 'first' from 'origin'.
Switched to a new branch 'first'

## Note that we now have first as a local branch
$ git branch 
* first
  main

$ cat README.md
# Demo
## FIRST BRANCH

$ git switch second
Branch 'second' set up to track remote branch 'second' from 'origin'.
Switched to a new branch 'second'
$ cat README.md 
# Demo
## SECOND BRANCH

$ git branch 
  first
  main
* second

參考:

  1. git 參考
  2. 如何從 github 克隆特定分支

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM