Как получить строку версии сборки приложения с помощью команды Git "description"?

Я хочу составить версию сборки приложения, которая будет автоматически получена из имени ветки Git, на которой я работаю (при сборке), и количества коммитов с тех пор, как ветвь разошлась. Я считаю, что это будет уникальным для любого коммита в моем Git-репозитории? Имена ветвей уникальны, а коммиты связаны друг с другом вдоль ветки? Если и когда я отмечу коммит, у меня также может быть префикс версии с этим тегом.

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

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

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

Ответ 1

То, что вы знаете о git, состоит в том, что ветки по существу просто фиксируют закладки. Тот факт, что вы были на ветке foo, когда вы сделали фиксацию 0deadbeef, не имеет значения для самой фиксации; ветвь не является частью ее тождества.

(Mercurial испекает название ветки в commit. По-разному это хуже, как объясняет Дастин Саллингс.)

Даже если предположить, что git describe будет использовать только текущую ветку - если у вас есть история mergy, может быть несколько путей, ведущих к тому же самому последнему тегированному фиксации, который будет использоваться git describe. Таким образом, даже не обязательно какая-либо одна ветка.

Еще одно замечание: вы можете возразить, что даже если "3-й фиксатор из тега X" является неоднозначным в общем случае, git describe может просто посмотреть на график и выяснить, является ли он неоднозначным, а если нет, оставьте хэш, Тем не менее, ничто не мешает кому-либо начинать ветку поверх этого тега позднее, поэтому ваша строка describe станет неоднозначной ретроспективно.

В нижней строке указано, что только однозначный идентификатор фиксации - это его хэш. Так что это должно быть там. То, что git describe делает, добавляет некоторую избыточность (и в случае номера фиксации, неоднозначную) информацию, которая делает описание более полезным для вида пространственного/реляционного понимания, с которым люди ориентируются, в рамках модели git.

Ответ 2

Вот что я использую:

echo "`git symbolic-ref HEAD 2> /dev/null | cut -b 12-`-`git log --pretty=format:\"%h\" -1`"

Он производит что-то вроде:

master-6de772e

Как отмечает Аристотель, на самом деле SHA-1 сам по себе является тем, что необходимо и достаточно для обеспечения однозначного тега сборки, а также полной информации об историческом контексте развития. Все остальное является избыточным, в том смысле, что любая информация, которую они предоставляют, может быть вычислена или получена из SHA-1. Тем не менее, людям может понравиться также дополнительная контекстная информация о фактической ветки, которая сразу же проявляется (или, по крайней мере, этот человек), и, следовательно, вложение имени ветки в метку. По этой причине (т.е. Немедленный анализ информации человеком) большинство моих проектов также используют более подробное описание идентификации сборки, которое включает дату и время фиксации, на которой была построена сборка, в дополнение к метке сборки 'приведенный выше.

Ответ 3

git describe --long всегда будет выводить номер версии следующим образом: v1.2-10-gdeadbee, что означает 10-й коммит с аннотированного тега 'v1.2', который указывает на коммит с укороченным SHA-1 'deadbee'. Так что все, что вам нужно сделать, это пометить начало ветки (точка ветвления ветки), например. <branch>-start.

Сокращенный хэш SHA-1 для коммита требуется для различения неоднозначных ситуаций, потому что "3-й коммит, т. К. Тег" x "" (например) не уникально различает коммит; может быть более одного коммита, который соответствует упомянутому описанию при наличии нелинейного, веткистого развития. Например, в ситуации, показанной на диаграмме ASCII-искусства ниже, оба коммита, отмеченные знаком *, соответствуют описанию "3-й коммит с тега" x "".

          /-.---*---.-\                   
         /             \                  
.---x---.---.---*---.---M---.    <--- branch

Обратите внимание, что в случае "слияния", как показано выше, вы не можете использовать имя ветки, чтобы различать эти два коммита с одинаковым описанием.

Поэтому вам нужно взять вывод git describe --long (здесь есть опция --long, чтобы избежать неоднозначностей при разборе, см. git description manpage), проанализировать его и добавить информацию о текущей ветке (из например, git symbolic-ref HEAD, не от вставки вывода git branch) самостоятельно.

Ответ 4

Официальные выпуски должны иметь тег с номером версии. В этом случае я предлагаю следующий подход:

  • Если текущий фиксатор имеет тег, используйте этот тег
  • Если тег недоступен, используйте имя ветки и ключ SHA1

Эта единственная команда должна работать:

git describe --exact-match 2> /dev/null || echo "`git symbolic-ref HEAD 2> /dev/null | cut -b 12-`-`git log --pretty=format:\"%h\" -1`"