В чем разница между аннотированным и аннотированным тегом?
Если я хочу пометить текущий коммит. Я знаю, что обе следующие командные строки работают:
git tag <tagname>
а также
git tag -a <tagname> -m '<message>'
В чем разница между этими командами?
4 ответа
TL;DR
Разница между командами заключается в том, что одна предоставляет вам сообщение тега, а другая - нет. У аннотированного тега есть сообщение, которое можно отобразить с помощью git-show(1), а тег без аннотаций - это просто именованный указатель на коммит.
Подробнее о легких тегах
Согласно документации: "Чтобы создать легкий тег, не указывайте ни один из параметров -a, -s или -m, просто укажите имя тега". Есть также несколько вариантов написания сообщения для аннотированных тегов:
- Когда вы используете
git tag <tagname>
, Git создаст тег в текущей ревизии, но не будет запрашивать аннотацию. Он будет помечен без сообщения (это облегченный тег). - Когда вы используете
git tag -a <tagname>
, Git предложит вам аннотацию, если вы не использовали флаг -m для предоставления сообщения. - Когда вы используете
git tag -a -m <msg> <tagname>
, Git пометит коммит и аннотирует его предоставленным сообщением. - Когда вы используете
git tag -m <msg> <tagname>
, Git будет вести себя так, как будто вы передали флаг -a для аннотации и используете предоставленное сообщение.
По сути, это просто означает, хотите ли вы, чтобы у тега была аннотация и некоторая другая информация, связанная с ним, или нет.
Нажмите аннотированные метки, сохраняйте вес локальным
man git-tag
говорит:
Аннотированные теги предназначены для выпуска, в то время как легкие теги предназначены для меток частных или временных объектов.
И некоторые виды поведения делают различие между ними таким образом, что эта рекомендация полезна, например:
аннотированные теги могут содержать сообщение, создателя и дату, отличную от фиксации, на которую они указывают. Таким образом, вы можете использовать их для описания релиза, не делая релиз релиза.
Облегченные теги не имеют такой дополнительной информации и не нуждаются в ней, поскольку вы будете использовать ее только для разработки.
- git push --follow-tags будет толкать только аннотированные теги
git describe
без параметров командной строки видит только аннотированные теги
Внутренние различия
как легкие, так и аннотированные теги являются файлом под
.git/refs/tags
который содержит SHA-1для легких тегов SHA-1 указывает непосредственно на коммит:
git tag light cat .git/refs/tags/light
печатает так же, как SHA-1 ГОЛОВКИ.
Поэтому неудивительно, что они не могут содержать никаких других метаданных.
аннотированные теги указывают на объект тега в базе данных объекта.
git tag -as -m msg annot cat .git/refs/tags/annot
содержит SHA аннотированного тегового объекта:
c1d7720e99f9dd1d1c8aee625fd6ce09b3a81fef
и тогда мы можем получить его содержание с:
git cat-file -p c1d7720e99f9dd1d1c8aee625fd6ce09b3a81fef
образец вывода:
object 4284c41353e51a07e4ed4192ad2e9eaada9c059f type commit tag annot tagger Ciro Santilli <your@mail.com> 1411478848 +0200 msg -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.4.11 (GNU/Linux) <YOUR PGP SIGNATURE> -----END PGP SIGNAT
И вот как он содержит дополнительные метаданные. Как мы видим из вывода, поля метаданных:
- объект, на который он указывает
- тип объекта, на который он указывает. Да, объекты тегов могут указывать на любой другой тип объекта, например, BLOB-объекты, а не только на коммиты.
- название тега
- личность тега и метка времени
- сообщение. Обратите внимание, как подпись PGP только что добавлена к сообщению
Более подробный анализ формата представлен по адресу: Что такое формат объекта тега git и как рассчитать его SHA?
Бонусы
Определите, является ли тег аннотированным:
git cat-file -t tag
Выходы
commit
для легкого веса,tag
для аннотированных.Список только легких тегов: Как я могу перечислить все легкие теги?
Большая разница прекрасно объясняется здесь.
По сути, легкие теги являются просто указателями на конкретные коммиты. Дальнейшая информация не сохраняется; с другой стороны, аннотированные теги являются обычными объектами, которые имеют автора и дату, и на них можно ссылаться, поскольку они имеют свой собственный ключ SHA.
Если вы знаете, кто пометил, что и когда для вас актуально, используйте аннотированные теги. Если вы просто хотите пометить конкретную точку в своем развитии, независимо от того, кто и когда это сделал, тогда легкие теги достаточно хороши.
Обычно вы бы использовали аннотированные теги, но это действительно зависит от мастера Git проекта.
Еще одно отличие заключается в случае сбоя, поскольку тег уже есть, как .
С Git 2.42 (3 квартал 2023 г.): " « ( мужчина ) научился выходить из"$GIT_DIR/TAG_EDITMSG"
файл в случае сбоя команды, чтобы пользователь мог восстановить то, что он набрал.
Этот файл сообщения тега git не будет существовать для облегченного тега.
См. , коммит 669c11d , (16 мая 2023 г.) Кристоффера Хаугсбакка (
LemmingAvalanche
) .
(Объединено Джунио К. Хамано --
gitster
-- в коммите 6d2a88c, 13 июня 2023 г.)
коммит 08c12ec: сохранить файл сообщений на случай сбоя ref-транзакции
Подпись: Кристоффер Хаугсбакк
Ссылочная транзакция может завершиться неудачно после того, как пользователь записал свое сообщение тега.
В частности, если существует тегfoo/bar
иgit tag -a foo
( человек ) говорит, что команда завершится неудачно только тогда, когда она попытается записатьrefs/tags/foo
, то есть после того, как файл был отключен.Подержите файл сообщения еще немного, чтобы он не был отсоединен до того, как произойдет фатальная ошибка.
И:
коммит 719515f
doc
: тег: документПредложено: Джунио К. Хамано
Подпись: Кристоффер Хаугсбакк
Документ, о котором мы сообщали пользователю при неудачном вызове команды после ("
tag
: удалитьTAG_EDITMSG
только при успешном теге", 6 декабря 2008 г., Git v1.6.1-rc2 -- merge).Представьте эту документацию, поскольку мы собираемся добавить тесты на время жизни этого файла в случае сбоя и успеха команды.
Используйте документацию для
COMMIT_EDITMSG
отgit-commit.txt
в качестве шаблона, поскольку эти два файла имеют одну и ту же цель. описано здесь1† 1: из фиксации 3927bbeфиксации 3927bbe :
“ This matches the behavior of COMMIT_EDITMSG, which stays around in case of error.
теперь включает в свою справочную страницу :
ФАЙЛЫ
$GIT_DIR/TAG_EDITMSG
Этот файл содержит сообщение текущего аннотированного тега. Если произойдет выход из-за ошибки до создания аннотированного тега, то сообщение тега, предоставленное пользователем в сеансе редактирования, будет доступно в этом файле, но может быть перезаписано при следующем вызове
git tag
.