Как вытащить один коммит за один раз из удаленного репозитория git? - PullRequest
9 голосов
/ 21 апреля 2010

Я пытаюсь настроить зеркало darcs из репозитория git. У меня есть кое-что, что работает хорошо, но есть существенная проблема: если я помещаю целую кучу коммитов в репозиторий git, эти коммиты объединяются в один набор патчей darcs. Я действительно хочу убедиться, что каждый коммит git настроен как отдельный набор патчей darcs. Могу поспорить, что это возможно, выполнив какой-то git fetch с последующим опросом локальной копии удаленной ветви, но мой мерзавец не подходит для этой работы.

Вот код (ksh), который я использую сейчас, более или менее:

git pull -v # pulls all the commits from remote --- bad!

# gets information about only the last commit pulled -- bad!
author="$(git log HEAD^..HEAD --pretty=format:"%an <%ae>")"
logfile=$(mktemp)
git log HEAD^..HEAD --pretty=format:"%s%n%b%n" > $logfile

# add all new files to darcs and record a patchset. this part is OK
darcs add -q --umask=0002 -r .
darcs record -a -A "$author" --logfile="$logfile"
darcs push -a
rm -f $logfile

Моя идея

  1. Попробуйте git fetch получить локальную копию удаленной ветви (точно не знаю, какие аргументы нужны)
  2. Каким-то образом опросить локальную копию, чтобы получить хэш для каждого коммита с момента последней операции зеркалирования (я понятия не имею, как это сделать)
  3. Переберите все хэши, извлеките только тот коммит и запишите соответствующий набор патчей (я уверен, что знаю, как это сделать, если я получу хэш)

Я бы приветствовал либо помощь в уточнении сценария выше , либо предложения о что-то еще, что я должен попробовать.

Идеи

Ответы [ 4 ]

2 голосов
/ 07 сентября 2010

Пробовали ли вы взглянуть на некоторые существующие решения для перемещения наборов изменений между системами контроля версий, такие как Tailor , в которых говорится, что он включает поддержку git и darcs? (На этой странице также есть предложения по аналогичным системам.)

В противном случае, если вы хотите использовать предложенный подход, вы можете использовать git checkout при каждом коммите после HEAD до origin/master, чтобы оформить этот коммит в режиме «detached HEAD». Например, чтобы изменить пример, который вы даете (и я боюсь, что в оболочке Bourne, так как я не использую ksh):

# Update all remote-tracking branches from origin
git fetch origin

for c in `git log --pretty=format:"%h" HEAD..origin/master`
do
     git checkout $c
     author=$(git log -1 --pretty=format:"%an <%ae>")
     logfile=$(mktemp)
     git log -1 --pretty=format:"%s%n%n%b%n" > $logfile

     darcs add -q --umask=0002 -r .
     darcs record -a -A "$author" --logfile="$logfile"
     darcs push -a
     rm -f $logfile         
done

# Now go back to master, and merge to keep your master branch up to date:
git checkout master
git merge origin/master

Обратите внимание, что это будет линеаризовать историю из git, что не будет тем, что я хотел лично. :) Я думаю, что для этого лучше всего использовать существующий инструмент, но вышеописанный подход можно использовать.

1 голос
/ 28 апреля 2011

Вы можете сделать что-то вроде этого:

#!/bin/bash
git fetch
count=$(git log --pretty=oneline | wc -l)
git merge origin/master
git reset --hard HEAD~$((count-1))

Я создал хранилище для этого скрипта и опробовал его. Следующее до и после слияния:

enter image description here

enter image description here

Теперь у меня не было удаленного репозитория, поэтому я подделал git fetch и удаленную ветку с локальным (с именем kalle), но вы поняли идею. Просто выполните полное слияние, а затем сделайте резервную копию указателя HEAD, пока не достигнете первого коммита от origin / master.

0 голосов
/ 21 апреля 2010

Используйте это для получения хешей из ветки:

git log --pretty=format:"%h" HEAD..origin/master

Затем используйте git cherry-pick -n <hash>, чтобы применить каждый из них.

Другой вариант, цитируемый @xenoterracide, - это использование githooks.

0 голосов
/ 21 апреля 2010

git remote update # fetch all remotes I like it better than just fetch

git log origin/master # can be any remote/branch

git cherry-pick origin/master # example remote/branch you can also specify a sha1

cherry-pick выберет верхний патч по умолчанию.

для третьей части, я думаю, вам придется написать скрипт, который сделает это за вас. Есть и другие способы получения хэшей и множество опций для лога. На самом деле может быть хук для cherry-pick или просто после коммита ... для запуска кода darcs. проверить git hooks.

фактически в этой заметке каждый патч, примененный в ребазе, может вызывать ловушку git commit, так что вы можете написать это, а затем выполнить git pull --rebase и использовать этот код при каждом применении ...

...