Как восстановить код (файл) из репозитория Git, который был удален с - PullRequest
0 голосов
/ 21 мая 2019

Я реализовал инструмент с графическим интерфейсом, который показывает, что все коммиты определенного объекта (назовем его "foo") были изменены. Затем я могу выбрать два коммита и сравнить две версии.

Для этого мне нужно восстановить код (файл) из коммитов, очевидно. Я использую

show {commitHash}:/pathto/foo --find-renames

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

Это работает нормально, пока код (файл) все еще существует. Если его больше не существует, я получаю сообщение об ошибке «Не удалось получить ревизию для {commitHash}! Подробности: fatal: option --find-rename должна предшествовать аргументам без опций», что, кстати, не совсем полезно, но в любом случае. ..

Так что мой вопрос в том, что использовать вместо show, или какие параметры использовать в случае, если show действительно может сделать это другим способом.

Ответы [ 2 ]

0 голосов
/ 22 мая 2019

[учитывая] все коммиты, определенный объект был изменен с помощью [...] Я могу затем выбрать два коммита и сравнить две версии.

Итак, вы выбираете два коммита и хотите следовать любым переименованиям от более старого к более новому при дифференцировании?

Когда вы создаете этот список, самый простой способ отследить имена будет

git log --raw --follow --oneline -- path/to/file

, который покажет вам пути и идентификаторы BLOB-объектов. Вот недавняя история для git-legacy-stash.sh, например:

7b556aa4b8 legacy stash: fix "rudimentary backport of -q"
:100755 100755 8a8c4a9270 f60e9b3e87 M  git-legacy-stash.sh
90a462725e stash: optionally use the scripted version again
:100755 100755 789ce2f41d 8a8c4a9270 R097       git-stash.sh    git-legacy-stash.sh
8d8e9c2a94 stash: add back the original, scripted `git stash`
:000000 100755 0000000000 789ce2f41d A  git-stash.sh
40af146834 stash: convert `stash--helper.c` into `stash.c`
:100755 000000 695f1feba3 0000000000 D  git-stash.sh
64fe9c26a4 stash: convert save to builtin
:100755 100755 51d7a06601 695f1feba3 M  git-stash.sh
d553f538b8 stash: convert push to builtin
:100755 100755 a9b3064ff0 51d7a06601 M  git-stash.sh
d4788af875 stash: convert create to builtin
:100755 100755 ff5556ccb0 a9b3064ff0 M  git-stash.sh
41e0dd55c4 stash: convert store to builtin
:100755 100755 d0318f859e ff5556ccb0 M  git-stash.sh

с указанием номеров старого и нового режимов и идентификаторов BLOB-объектов, характера изменений и любого старого и нового имени.

Затем вы можете использовать идентификатор комита и путь в каждом коммите, например

git diff 41e0dd5:git-stash.sh 7b556aa:git-legacy-stash.sh

или если по какой-то причине вам не нужны преобразования текста и фильтры, вы можете просто использовать идентификаторы BLOB-объектов напрямую.

0 голосов
/ 22 мая 2019

Вы можете запустить git cat-file blob COMMIT:RELATIVE-PATH. Это должно работать для любой ревизии COMMIT, которая указывает на фиксацию, при условии, что вы указали действительное относительное имя файла в этой ревизии .

Если файл не существует в этой ревизии, вы получите что-то вроде следующего:

fatal: Not a valid object name HEAD:not-here

Обратите внимание, что здесь нет возможности рассматривать переименования; это спецификация ревизии (см. gitrevisions(7)), которая разрешается непосредственно в имя BLOB-объекта.

Если вы хотите следить за переименованием файла, вам придется выполнять гораздо больше работы со сценариями. Вы можете найти имя файла, в который был переименован файл, выполнив что-то вроде следующего:

git log -M --follow --diff-filter=R --format=tformat:%H -- RELATIVE-PATH | \
    head -n1 | \
    xargs git diff-tree -M --diff-filter=R --raw -z

Это покажет все файлы, которые были переименованы в этом коммите; проанализируйте имя, которое вы хотите, и продолжайте с новым git log вызовом, ревизией и путем к файлу в случае, если файл был переименован снова.

В целом, эта последняя часть может быть более производительной, если использовать обертку для обходчика версий libgit2.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...