2016-10-26 6 views
0

У меня есть одно репо. Мне нужно переместить некоторые файлы и каталоги в другое репо. Мне удалось извлечь каталог, используя git filter-branch --subdirectory-filter config/deploy -- --all.Переместить файл в другой репозиторий Git с историей

Мне также нужно переместить файл config/deploy.rb.

Как это сделать?

+1

Если вы перемещаете файл на совершенно другое репо, как может история с ним пойти? –

+0

@TimBiegeleisen История в одном репо может быть скопирована на другое репо в виде серии патчей. Они сохранят даты авторизации. – willkil

+1

Ключ здесь в том, что * файлы * на самом деле не имеют * истории в Git. * Commits * имеют историю, а точнее, * являются историей. И, конечно, у коммитов есть файлы. Так что это совсем наоборот: это не то, что у файлов есть история, это история, в которой есть файлы! В конце концов, когда вы хотите скопировать или добавить некоторую историю из репо A в репо B, это означает, что вы хотите скопировать * commit * из A в B. (Как и с 'git filter-branch', вы можете захотеть изменить коммиты в процессе копирования.) – torek

ответ

0

«Переместить» История

После завершения git filter-branch, ветви содержат только фильтрованную историю. Теперь вы можете просто нажать на ветвь к другому хранилищу:

git init --bare ../elsewhere 
git push ../elsewhere master branch1 branch2 branch3 

Теперь у вас есть голый репозиторий с отфильтрованной историей, из которого вы можете клонировать новые репозитории.

Включить другой файл

Если вам не хватает одного файла в отфильтрованной истории, вы должны повторить фильтрацию, так что не исключен.

+0

Итак, проблема заключается в том, как фильтровать только этот файл с помощью 'filter-branch' –

+0

@Alex, тогда это другой вопрос. – j6t

1

Скопируйте исправления.

Как заметил комментатор, история с гитом технически не может быть перенесена из одного репо в другое. Однако, поскольку вы все равно переписываете историю, вы, очевидно, хотите скопировать историю файла в свое новое репо.

У меня есть несколько сценариев, которые делают это, и работают нормально со следующими оговорками:

  • файлы не были переименованы.
  • Каждое исполнение создает новые коммиты.

Для краткости я только перечисляя мясо сценариев:

# git-cp-history 
OTHER_REPO_DIR="$1" 
FILES="[email protected]" 
git-export-history "$FILES" | git-import-history "$OTHER_REPO_DIR" 

# git-export-history 
FIRST_COMMIT=`git log --format=%H --reverse -- "${FILES[@]}" | head -n1` 
git format-patch --stdout "$FIRST_COMMIT"^..HEAD -- "${FILES[@]}" 

# git-import-history 
cd "$1" 
git am 

Поскольку скрипты называются «git- *» и в моей PATH, я использую их, как это:

git cp-history ../other-repo local/repo/file.txt 
+0

'FIRST_COMMIT = 00000000000000000000000000000000000000000000; git format-patch --stdout "$ FIRST_COMMIT"^.. HEAD - config/deploy.rb' возвращает 'fatal: bad revision '00000000000000000000000000000000000000000000^.. HEAD'' –

+0

@AlexTonkonozhenko Был ли файл добавлен в первую фиксацию филиала? Мы всегда добавляем либо пустую фиксацию, либо пустой файл .gitignore в качестве корня в наши репозитории, чтобы избежать особых комков корневого кода.Если файл был добавлен в корневом коммите, вы можете использовать 'git format-patch -stdout -root HEAD -" $ {FILES [@]} "' (untested, HEAD, вероятно, необязательный). Подробнее читайте 'git help format-patch'. Основной 'git format-patch | (cd; git am) 'процесс должен работать, но вам, возможно, придется возиться с деталями для вашего конкретного случая. – willkil