Как мне преобразовать пустой git-репозиторий в обычный (на месте)?
У меня есть пустой репозиторий git, но мне нужно получить доступ и просмотреть его содержимое по ssh (в файловом менеджере, например, в пользовательском интерфейсе).
Я полагаю, я мог бы клонировать это:
git clone -l <path_to_bare_repo> <new_normal_repo>
Тем не менее, мой репозиторий имеет размер около 20 ГБ, и у меня нет места для его дублирования. Есть ли способ конвертировать пустой репозиторий на месте, чтобы получить рабочую копию?
9 ответов
Примечание: я проверил это в очень простом репозитории с 1 коммитом. Дважды проверьте это, прочитайте справочные страницы и всегда будьте счастливы, что вы сделали резервную копию, прежде чем следовать советам, которые вы нашли в Stackru. (Вы делаете резервную копию, верно?)
Чтобы преобразовать --bare
хранилище для не голого:
- Делать
.git
папка на верхнем уровне вашего хранилища. - Переместить вещи управления хранилищем (
HEAD branches config description hooks info objects refs
и т. д.) в.git
Вы только что создали. - Бежать
git config --local --bool core.bare false
конвертировать локальный git-репозиторий в non-bare. - (через комментарий Tamás Pap) После шага № 3 вы увидите, что находитесь на ветке
master
(или в зависимости от того, какая у вас основная ветка), и все ваши файлы будут удалены, и удаление будет подготовлено. Это нормально. Просто вручную оформить заказmaster
или сделатьgit reset --hard
и все готово. - (чтобы решить проблему, сообщенную Royi) Править
.git/config
строка добавления файлаfetch = +refs/heads/*:refs/remotes/origin/*
послеurl = <...>
в[remote "origin"]
раздел. Иначеgit fetch
не увидитorigin/master
и другие ветви происхождения.
Эти шаги направлены в противоположном направлении от этого вопроса, "git-convert normal to bare repository" - в частности, обратите внимание на этот ответ, в котором говорится, что вышеуказанные шаги (я полагаю, в любом направлении) отличаются от выполнения git-clone
, Не уверен, что это имеет отношение к вам, но вы упомянули git clone
в вопросе.
У меня был немного другой сценарий:
- не репо ( пройти через тарбол из github)
- необходимость восстановления полного репо из этого контента.
Решение:
- клонировать голое репо в этом контенте, в
.git
реж:git clone --bare https://github.com/user/project .git
- Пометить это как не обнаженное репо:
git config --local --bool core.bare false
- сбросить индекс (в противном случае он считает, что все было удалено, так как
.git
голое репо не содержит файлindex
".)git reset HEAD -- .
Это восстанавливает.git/index
,
Я фактически превратил голое репо в не голое, сохранив контент, который получил ранее.
Полный сценарий, который я использовал в течение многих лет, включает следующие шаги:
cd /path/to/current/worktree
# That creates a .git directly at the right place
git clone --bare /url/of/repo .git
# restore the link between the local repo and its upstream remote repo
git config --local --bool core.bare false
git config --local remote.origin.fetch +refs/heads/*:refs/remotes/origin/*
git fetch origin
git branch -u origin/master master
# reset the index (not the working tree)
git reset HEAD -- .
Но я делаю пересмотр принятого решения (с полезным git reset
шаг добавлен по ADTC) проще.
Вопрос оригинального плаката о том, что не хватает места, чтобы делать вещи простым способом. Для тех, у кого достаточно места, ответ гораздо проще:
git clone foo.git foo
Чтобы упростить и объединить информацию в ответах:
Есть два отличия, которые отличают репо от обычной папки.git:
- core.bare имеет значение true в конфигурационном файле
- индексный файл и рабочее дерево не существует
Таким образом, вы можете просто переместить ваш репозиторий в подпапку.git новой папки,
mkdir clone
mv bare.git clone/.git
Измените core.bare:
cd clone
git config --local --bool core.bare false
И сгенерируйте индексный файл и рабочее дерево:
git checkout master
рекомендую git checkout
скорее, чем git reset
генерировать файлы, если они случайно введены не в том месте.
Перейди на голый репо и сделай
git config core.bare false
git reset --hard
или же
git clone X.git X
(даст вам регулярное Git-репо с именем X)
Если у вас мало места на диске, расширение рабочего дерева путем преобразования в обычный репозиторий будет проблемой, но вы можете просматривать содержимое чистого репозитория без его преобразования. использование git cat-file -p <commit-sha>
на любом коммите, чтобы увидеть дерево, к которому оно относится. использование git cat-file -p <blob-sha>
чтобы увидеть содержимое файла, на который ссылается BLOB-объект. использование git show <sha>:path
где sha - это либо коммит, либо дерево, чтобы увидеть содержимое BLOB-объекта в path.
Если вы не против работать на другом рабочем дереве, тогда
git worktree add ../repo2
cd ..
git status # now works fine
Обратите внимание, что это не клон.
Еще один случай windows 10
В моем случае я бы даже не инициализировал новый репозиторий с рабочим деревом по другому пути для последующего клонирования.(BARE:main)
remository, потому что это не был репозиторий, а также я не смог найти папку .git , потому что не смог создать ее после запуска
git init
Итак, моя проблема заключалась в переменных системной среды , где был другой путь, связанный с моим git. Мне просто нужно удалить эту переменную, и тогда я смогу запуститьgit init
Я приложу изображение, на котором вы можете получить доступ к переменным среды системы.
Нажимай-Deploy
Вместо того, чтобы преобразовывать пустой пульт дистанционного управления в стандартный репозиторий, вы можете использовать сценарий post-receive в каталоге hooks, чтобы развернуть репозиторий в каталог развертывания.
Вот хороший пример настройки Push-to-Deploy
Для простоты, это пример содержания скрипта из ссылки выше. Он будет развертывать только толчки из "основной" ветви в каталог с именем "deploy", который находится на том же уровне, что и родительский каталог репозитория:
#!/usr/bin/env ruby
# post-receive
# 1. Read STDIN (Format: "from_commit to_commit branch_name")
from, to, branch = ARGF.read.split " "
# 2. Only deploy if master branch was pushed
if (branch =~ /master$/) == nil
puts "Received branch #{branch}, not deploying."
exit
end
# 3. Copy files to deploy directory
deploy_to_dir = File.expand_path('../deploy')
`GIT_WORK_TREE="#{deploy_to_dir}" git checkout -f master`
puts "DEPLOY: master(#{to}) copied to '#{deploy_to_dir}'"