LINUX.ORG.RU

git glue

 ,


0

3

Продолжаю разбираться с Git.

Возникла такая задача [просили именно о задачах]

Есть куча каталогов с разными версиями одного и того же проекта.

Существует ли скрипт для автоматизации «склеивания» этих каталогов в одно git-дерево, с возможностью отложенной простановки описаний к таким diff-ам?

Допустим, чтобы скрипт показал коэффициент «красивости» потенциального слияния. Остальное (например, переименования файлов, которые скрипт не сможет различить) я бы указал вручную.



Последнее исправление: i_am_not_ai (всего исправлений: 2)

Логика у скрипта будет простая:

  1. Удалить все файлы из текущего репозитория кроме директории .git.

  2. Скопировать файлы из директории с очередной версией.

  3. Закоммитить файлы с номером версии в качестве описания коммита.

  4. Повторять шаги, пока есть версии.

В результате получится линейная история коммитов от самой старой версии к самой новой.

Отложенную простановку описаний легко будет сделать с помощью интерактивного ребейза.

чтобы скрипт показал коэффициент «красивости» потенциального слияния

Никакого слияния в терминах git не будет. Просто коммит. Git сам увидит изменения в файлах. Коэффициент красивости — вообще непонятно что такое.

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

Какие файлы скрипт различить не сможет?

static_lab ★★★★★
()
Ответ на: комментарий от static_lab

Какие файлы скрипт различить не сможет?

Он не сможет понять, что сделано git mv file1 file2 с последующей модификацией этого файла в рамках одного commit.

i_am_not_ai
() автор топика
Последнее исправление: i_am_not_ai (всего исправлений: 1)
Ответ на: комментарий от i_am_not_ai

Там всё зависит от количества изменений в файле, а не от использования git mv. Если файл меняется существенно, то вам и git mv не поможет, чтобы файл остался в истории как moved, а не парой deleted-added.

static_lab ★★★★★
()
Ответ на: комментарий от static_lab

Там всё зависит от количества изменений в файле

Вот под процентом удачно построенных diff (без deleted-added) я и понимал «хорошесть».

Впрочем, мне это не так и нужно. Задача в целом будет выполнена.

Спасибо.

i_am_not_ai
() автор топика
Последнее исправление: i_am_not_ai (всего исправлений: 1)

Существует ли скрипт для автоматизации «склеивания» этих каталогов в одно git-дерево

Скрипта нет, это твоя личная задача, поэтому ты лично его пишешь.

с возможностью отложенной простановки описаний к таким diff-ам?

Да, всегда можно сделать git rebase -i и изменить описания коммитов.

Допустим, чтобы скрипт показал коэффициент «красивости» потенциального слияния.

Что это ещё за красивость и что в действиях скрипта от неё будет зависеть?

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

Git’у не нужно явно указывать переименования и копирования.

В общем можешь начать с того что написал @static_lab, а потом можешь делать git rebase -i сколько угодно раз для доведения репозитория до адекватного состояния - разбивать коммиты на более мелкие и добавлять к ним описания.

slovazap ★★★★★
()
Ответ на: комментарий от i_am_not_ai

Вот под процентом удачно построенных diff (без deleted-added) я и понимал «хорошесть».

А как бы предполагалось этим пользоваться? Кстати надо понимать, что git хранит не изменения, а сами файлы целиком.

static_lab ★★★★★
()
Ответ на: комментарий от static_lab

А как бы предполагалось этим пользоваться?

Вручную разбить diff на два. Или явно сделать вначале переименование файла. Т.е., максимально реконструировать историю событий.

i_am_not_ai
() автор топика
Ответ на: комментарий от i_am_not_ai

Тогда можете в скрипте сравнивать выдачу

git diff --staged --name-status
git diff --staged --name-status --find-renames=10%

например, дополнить | wc -l

И если есть различие, то останавливаться и предлагать разрулить такое изменение вручную.

По умолчанию --find-renames=50%.

static_lab ★★★★★
()
Ответ на: комментарий от i_am_not_ai

Т.е., максимально реконструировать историю событий.

Надо ли? Учитывая, что т.к. раньше система контроля версий не использовалась, и всё равно будет невозможно понять полную историю. Например, это изменение ­— это новая функциональность, или костыль, который нужен потому что сторонняя библиотека без него падает?

История часто нужна для этого - понять почему вносилось определенное изменение, а эта информация всё равно уже утеряна.

emorozov
()
Ответ на: комментарий от static_lab

Не надо ничего удалять. В корневой директории, в которой лежат версии, создаём директорию repo, переходим в нее и делаем git init -bare. Далее поднимаемся обратно в корневую директорию и обходим директории с версиями. В каждой директории делаем git commit -a -m"ver xx".

DrBrown
()
Ответ на: комментарий от static_lab

Да, память меня подвела и я не правильно расписал действия. Тем не менее, есть рабочий способ без манипуляций с директориями.

Сначала в директории trash делаем три версии «проекта».

#!/usr/bin/sh
cd ~
mkdir trash trash/v1 trash/v2 trash/v3
echo "Hello wrot!" > trash/v1/1.txt
cp trash/v1/* trash/v2
echo "Hello Word!" > trash/v2/1.txt
echo "Hello LOR!" > trash/v2/2.txt
cp trash/v2/* trash/v3
rm trash/v3/1.txt

Далее делаем каталог repo для репозитория и собираем историю.

#!/usr/bin/sh
cd ~
# Подготавливаем репозиторий
mkdir trash/repo trash/repo/.git
cd trash/v1
git init --separate-git-dir ../repo/.git
cp .git ../v2
cp .git ../v3
# Собираем историю
git add *
git commit -m"v1"
cd ../v2
git add *
git commit -a -m"v2"
cd ../v3
git add *
git commit -a -m"v3"
# Необязательно:
# Переходим в репу и восстанавливаем рабочую директорию
cd ../repo
git restore *

@emorozov, это делает нормальное дерево версий.

DrBrown
()
Ответ на: комментарий от DrBrown

Еще вариант

#!/usr/bin/sh

cd ~
# Подготавливаем репозиторий
mkdir trash/repo
cd trash/repo
git init
export GIT_DIR=$PWD/.git
# Собираем историю
cd ../v1
git add *
git commit -a -m"v1"
cd ../v2
git add *
git commit -a -m"v2"
cd ../v3
git add *
git commit -a -m"v3"
# Необязательно:
# Переходим в репу и восстанавливаем рабочую директорию
cd ../repo
git restore *
DrBrown
()
Ответ на: комментарий от static_lab

Кстати надо понимать, что git хранит не изменения, а сами файлы целиком.

Я придерживаюсь следующей методики для бэкапов гита.

Делаю clone+tgz репозитория после финальных правок, а между ними храню диффы git diff commit1 commit2 в виде небольших файликов-патчей.

i_am_not_ai
() автор топика