Что скачивает GIT? - PullRequest
       4

Что скачивает GIT?

0 голосов
/ 07 сентября 2018

Если я клонирую репозиторий с 3 ветками. Является ли GIT достаточно умным, чтобы загружать только изменения между ветвями, или он загружает все файлы повторно для всех ветвей? А также, загружает ли он все данные из всех веток в начале или ждет, пока я переключу ветку?

Ответы [ 3 ]

0 голосов
/ 07 сентября 2018

git clone загрузит достаточно контента, чтобы вы могли достичь любого коммита в истории любой ветки.

Если вы хотите загрузить только верхний коммит каждой ветви или только часть истории каждой ветки (скажем, последние 10 коммитов), посмотрите следующие опции:

  • --depth=x
  • --shallow-since=date
  • --shallow-exclude=revision

Эти опции также могут быть переданы git fetch или git pull.


Обратите внимание, однако, что git предназначен для эффективной передачи всего контента:

  • если файл не изменен (между двумя коммитами), он загружается только один раз
  • весь загруженный контент сжат (используя zlib)
  • имеет множество функций, позволяющих обнаруживать, что 2 файла очень похожи, и загружать только diff (вместо двойного целого содержимого)
0 голосов
/ 07 сентября 2018

Принятый в настоящее время ответ вводит в заблуждение, и многое из того, что он говорит, на самом деле не решает вопрос.

Для переноса между репозиториями используется только упакованное представление [1], поэтому обычно можно предположить, что вы получите (разумно) минимальное представление запрошенной вами информации.

Сказать, что он «загружает только коммиты», вводит в заблуждение по нескольким причинам. В основном это способствует неправильному представлению о том, что коммиты сами по себе являются списками изменений - а это не так. Коммиты - это снимки проекта [2]. «Загружать коммиты» означает, грубо говоря, «скачивает все».

Какой хороший переход к ...

По умолчанию git clone загружает всю историю всех веток. Вы можете задать ему параметры, чтобы загружать меньше, если вы знаете, что вам нужно меньше, но по умолчанию загружается все, чтобы впоследствии вы могли выполнять любые операции управления исходным кодом (кроме синхронизации изменений с другим репо) без каких-либо необходимых подключений. Подробнее о параметрах см. В git clone docs (https://git -scm.com / docs / git-clone ), особенно --single-branch, --depth и --shallow-*.

Ничто из этого не имеет ничего общего с представлением DAG. Это действительно важно только тогда, когда вы думаете о том, как перемещаться по объектам в git, и на самом деле ошибочно думать о дельтах как о DAG, поскольку вы, как правило, получаете его задом наперед.


[1] Есть два формата, в которых git хранит объекты, составляющие историю проекта. Когда новый материал фиксируется, он сохраняется в незакрепленных объектах - полных копиях каждой версии каждого файла - но даже в этом случае git никогда не сохраняет одинаковое содержимое дважды. Таким образом, если файл не изменяется в течение 10 коммитов, то сохраняется одна копия этого файла. Кроме того, даже в свободном виде данные сжимаются.

Позже объекты можно переключать в «упакованное» представление. Одной из оптимизаций, выполняемых при упаковке, является поиск похожих объектов и представление более старых из двух как дельта из более новых .


[2] Некоторые команды, такие как rebase, работают с патчем между коммитом и его родителем, а документация (как и большая часть документации git) немного сложна с терминологией вокруг этих команд. , Так что, к сожалению, легко заблуждение, что коммит - это список распространяемых изменений.

Но даже если некоторые из объектов, составляющих более старый коммит, могут быть внутренне представлены в виде дельт от других объектов из более новых коммитов, концептуально коммит является снимком. Если вы скажете git, например с опциями --depth, чтобы загрузить только часть определенных коммитов, вы все равно получите весь снимок, а не только патчи относительно предыдущих коммитов. Любое подмножество репо, которое содержит частичные дельты без достаточной информации для восстановления моментального снимка (т.е. фиксация), будет считаться поврежденным.

0 голосов
/ 07 сентября 2018

Достаточно ли умен GIT, чтобы загружать только изменения между ветвями, или он загружает все файлы повторно для всех ветвей?

Самое лучшее в git (из всех, которые были до git) - это использование DAG для отслеживания изменений. То есть, когда вы git pull или git fetch загружает только diff с.
Итак, чтобы ответить на ваш вопрос: он загружает только 3 коммита, которые вы сделали. Тогда просто сделайте местный DAG для вас. Посмотрите здесь для быстрого ознакомления с основами.

А также, загружает ли он все данные из всех веток в начале или ждет, пока я переключу ветку?

Когда вы делаете git clone, вы загружаете весь репозиторий, это делается для создания DAG. Затем он загружает только те, о которых вы просили, используя git fetch и git pull.

git fetch загружает изменения с пульта и сохраняет их в .git/refs/remotes/<remote>/. Таким образом, вы не будете напрямую вносить это в ваш working directory. (Прочтите git baiscs, если вы не знаете, что такое working directory).
git pull делает git fetch и git merge в одной команде.

Обратитесь к этому другому ТАК вопрос при получении против тяги.

Несколько материалов для чтения
Git больше похож на дерево, чем на график. ТАК вопрос
Простое введение в Git с объяснением того, как и почему мы используем DAG Link

...