Git
Всё о GIT, со слов ldv
- Руководство по git.alt (в процессе)
Здесь на самом деле не про git per se, а про git применительно к ALT Linux и git.alt; в качестве введения в git см., например, Everyday GIT.
Некое подобие QuickStart по git@ALT для присматривающихся участников team -- здесь.
- Введение в git + ссылки
- Руководство по git.alt
- Ведение пакетов при помощи gear
- Справочник по git.alt
- Справочник по gear
GEAR
В апреле 2007 года идея хранить исходный код пакетов в git-репозитории была реализована с помощью утилиты, которая 27-го апреля получила имя gear. Напомню вкратце:
Основной смысл хранения исходного кода пакетов в git-репозитории заключается в более эффективной и удобной совместной разработке, а также минимизации трафика и места на диске для хранения архива репозитория за длительный срок. Идея gear заключается в том, чтобы с помощью одного файла с простыми правилами (для обработки которых достаточно git+sed) можно было собирать пакеты из произвольно устроенного git-репозитория, по аналогии с hasher, который был задуман как средство собирать пакеты из произвольных srpm-пакетов.
За время, прошедшее с конца апреля, многие из вас успели освоиться с gear, появилась базовая документация, семейство вспомогательных утилит и опыт эксплуатации. Поэтому весьма вероятно, что те из вас, кому только предстоит осваивать gear, пройдут этот путь гораздо легче и быстрее чем я. :) Например, одна только утилита gear-srpmimport позволяет на начальном этапе вообще не интересоваться синтаксисом файла .gear-rules.
На всякий случай рекомендую установить/обновить пакет gear, а также освежить в своей памяти содержимое файлов /usr/share/doc/gear-1.4.0/QUICKSTART.ru.html и /usr/share/doc/git-1.5.5.3/tutorial.html
Структура репозитория
Как уже было сказано, gear не накладывает ограничений на внутреннюю организацию git-репозитория (не считая файла с правилами). Тем не менее, у меня есть несколько соображений о том, как более эффективно и удобно организовывать git-репозитории, предназначенные для хранения пакетов:
- Одна сущность - один репозиторий.
- Не стоит помещать в один репозиторий несколько разных пакетов, за исключением случаев, когда у этих пакетов есть общий пакет-предок. Соблюдение этого правила облегчает совместную работу над пакетом, поскольку не перегруженный репозиторий легче клонировать и в целом инструментарий git больше подходит для работы с такими репозиториями.
- Отрицательная сторона: несколько сложнее делать «push» и «pull» в случае, когда репозиториев, которые надо обработать, много. Впрочем, push/pull в цикле выручает.
- Несжатый исходный код.
- Сжатый разными архиваторами исходный код (как правило это tarball'ы) лучше хранить в git-репозитории в несжатом виде. Изменение файлов, которые помещены в репозиторий в сжатом виде, менее удобно отслеживать штатными средствами (git-diff). Поскольку git хранит объекты в сжатом виде, двойное сжатие редко приводит к экономии дискового пространства. Наконец, алгоритм, применяемый для минимизации трафика при обновлении репозитория по протоколу git, заметно более эффективен на несжатых данных.
- Отрицательная сторона: поскольку некоторые виды сжатия одних и тех же данных могут приводить к разным результатам, может уменьшиться степень первозданности (нативности) исходного кода.
- Распакованный исходный код.
- Исходный код, запакованный tar/cpio/..., лучше хранить в git-репозитории в распакованном виде, по тем же причинам (заметно удобнее отслеживать изменения, существенно меньше трафик при обновлении).
- Отрицательная сторона: поскольку git из информации о владельце, правах доступа и дате модификации файлов хранит только исполняемость файлов, любой архив, созданный из репозитория, будет по этим параметрам отличаться от первозданного. Помимо потери нативности, изменение прав доступа и даты модификации может теоретически повлиять на результат сборки пакета. Впрочем, такие пакеты, если они будут обнаружены, всё равно надо править.
- Аккуратный changelog.
- В changelog релизного commit'а стоит включать соответствующий текст из changelog'а пакета, как это делают утилиты gear-commit (обёртка к git-commit, специально предназначенная для этих целей) и gear-srpmimport. В результате можно будет получить представление об изменениях в пакете, не заглядывая в spec-файл самого пакета.
Транспорты git
Как известно, git может использовать разные виды транспорта для своего внутреннего протокола передачи данных, подробнее см. секцию GIT URLS в git-pull(1) или git-push(1). Из них rsync лучше всех подходит для первичного клонирования репозиториев большого размера по нестабильным каналам связи, только два, ssh:// и git://, наиболее удобны для обновления уже существующих репозиториев, а из этих двух только ssh подходит для организации полноценного разграничения доступа. По этой причине предложенное ранее размещение git-репозиториев на rsync.altlinux.org::people/*/ было заменено на полноценный git over ssh.
Инструкция по эксплуатации git.altlinux.org
Для преодоления барьеров вида «админ закрыл наружу всё и оставил только прокси» ssh на git.altlinux.org доступен также и на порту 443. Инструкция по использованию transconnect для хождения к ssh через прокси находится тут.
По всем вопросам, связанным с этой частью инструкции, пишите на join@.
Проверка связи, она же памятка:
$ ssh git.alt help help git-receive-pack <directory> git-upload-pack <directory> charset <path to git repository> [<charset>] clone <path to git repository> [<path to directory>] find-package <pattern> init-db <path to directory> ls [<path to directory>] mv-db <path to source directory> <path to destination directory> quota rm-db <path to git repository> build <path to git repository> <tag name> <binary package repository name> [<project name>]
(вывод может меняться время от времени)
При входе на git.alt с вашей учётной записью USER текущим каталогом для вас будет git.alt:/people/USER/.
Перечень своих каталогов:
$ ssh git.alt ls total 16 drwxr-s--- 4 4096 Feb 13 2007 etc drwxr-sr-x 13 4096 May 28 13:52 packages drwxr-s--x 2 4096 Feb 13 2007 private drwxr-sr-x 2 4096 Feb 13 2007 public
Перечень своих репозиториев:
$ ssh git.alt ls packages total 0
Команда ls на git.alt работает относительно текущего каталога, но ей можно передавать в качестве аргумента и полные пути. Например: Посчитать, сколько у меня git-репозиториев на данный момент:
$ ssh git.alt ls /people/ldv/packages/ |grep -c ^d 317
Создать новый git-репозиторий (команда init-db, будучи вызваной с аргументом 'foo', создаёт репозиторий 'packages/foo.git'. При передаче аргумента, содержащего '/', такого дополнения не происходит), полюбоваться на него снаружи, удалить и снова посмотреть:
$ ssh git.alt init-db foobar $ rsync git.altlinux.org::people/USER/packages/ Welcome to ALT Linux Team public GIT archive! drwxr-sr-x 4096 2006/09/12 01:23:45 . drwxr-sr-x 4096 2006/09/12 01:23:45 foobar.git $ ssh git.alt rm-db foobar $ rsync git.altlinux.org::people/USER/packages/ Welcome to ALT Linux Team public GIT archive! drwxr-sr-x 4096 2006/09/12 01:23:45 .
Клонировать в свой каталог packages на git.alt внутренний репозиторий:
$ ssh git.alt clone /people/ldv/packages/vitmp.git remote: Generating pack... remote: Done counting 12 objects. Deltifying 12 objects. 100% (remote: 12/12) done Total 12, written 12 (delta 2), reused 12 (delta 2)
Клонировать в свой каталог packages на git.alt внешний репозиторий:
$ ssh git.alt clone rsync://git.altlinux.org/people/ldv/packages/vitmp.git Welcome to ALT Linux Team public rsync archive! receiving file list ... done ./ pack/ pack/pack-a54ac6c3e16e68ac9cf1b45218ae536a21da52ee.idx pack/pack-a54ac6c3e16e68ac9cf1b45218ae536a21da52ee.pack sent 175 bytes received 4944 bytes 98765.43 bytes/sec total size is 4629 speedup is 0.90
Клонировать к себе на компьютер свой репозиторий с git.altlinux.org:
$ git-clone git.alt:packages/vitmp.git remote: Generating pack... remote: Done counting 12 objects. remote: Deltifying 12 objects. remote: 100% (12/12) done remote: Total 12, written 12 (delta 2), reused 12 (delta 2)
Клонировать к себе на компьютер чужой репозиторий с git.altlinux.org:
$ git-clone git.alt:/people/ldv/packages/vitmp.git
Залить на git.alt свой ранее созданный git-репозиторий:
cd ~/package $ git push --all git.alt:packages/package.git
Представим, что некий foo сделал какие-либо изменения для нашего пакета bar в бранче bar-bugfree и выложил их на git.alt. Узнаем, как называется его этот бранч:
$ git ls-remote git.alt:/people/foo/packages/bar.git
Далее зафетчим этот бранч к нам с одноименным названием:
$ git-fetch git.alt:/people/foo/packages/bar.git bar-bugfree:bar-bugfree
Дальше работаем с ним как хотим ;)
Удалить бранч на git.alt (задав пустое имя локального бранча):
$ git push ... :branch
Копирование файлов из одного бранча в другой:
$ git-archive --format=tar --prefix=directory-branchXXX branchXXX:directory | tar xf -
и устаревший способ:
$ git-tar-tree branchXXX:directory directory-branchXXX | tar xf -
Инструкции по эксплуатации etc/packages.git
С помощью специального репозитория etc/packages.git можно настроить рассылку email-уведомлений об изменениях в git-репозиториях.
Рассылка уведомлений может быть двух типов:
- По инициативе подписчиков, которые выбирают, какие уведомления им нужны.
- По инициативе владельцев репозиториев, которые решают, куда рассылать уведомления.
Для каждого из этих типов в etc/packages.git заведено по файлу специального формата.
Файл для подписки на уведомления первого типа называется email-subscription и состоит из строк вида
USER PACKAGE REFTYPE REFNAME
где
- USER: имя владельца репозитория (USER в git_USER);
- PACKAGE: имя репозитория (PACKAGE в /people/USER/packages/PACKAGE.git);
- REFTYPE: вид изменяемой ссылки (head, release, remote или tag);
- REFNAME: имя изменяемой ссылки (basename от refs/*/*).
Каждое из этих 4-ех полей может быть либо полным именем, либо символом «*». Для пакетов также разрешён синтаксис "имя-*", с вайлдкардом в конце имени.
Файл для рассылки уведомлений второго типа называется email-distribution и состоит из строк вида
PACKAGE REFTYPE REFNAME MAILTO
где
- PACKAGE: имя репозитория (PACKAGE в /people/USER/packages/PACKAGE.git);
- REFTYPE: вид изменяемой ссылки (head, release, remote или tag);
- REFNAME: имя изменяемой ссылки (basename от refs/*/*);
- MAILTO: разделённый запятыми список получателей (USER1,USER2).
Каждое из первых 3-ех полей может быть либо полным именем, либо символом «*». Для пакетов также разрешён синтаксис "имя-*", с вайлдкардом в конце имени. Способ указать в MAILTO вместо идентификаторов разработчиков произвольные адреса пока не придуман.
Для того чтобы начать экспериментировать с email-файлами, нужно сделать
$ git-clone git.alt:etc/packages.git
Изменения этих файлов отслеживаются hooks/update'ом только если они сделаны в refs/heads/master.
На мой взгляд, практический интерес представляет первый тип уведомлений. Пока писем не очень много, я записал «* * * *» в свой email-subscription.
Ответы на часто забываемые вопросы
packages, private и public
> А notifier не разошлет ли сообщения об загрузке новых пакетов подписавшимся на рассылки обновления всех пакетов? Вы можете подписать кого-то на обновления своего репозитория в packages, public или private (с помощью etc/packages/email-distribution, etc/public/email-distribution и etc/private/email-distribution, соответственно), но подписаться можно только на обновления чужих packages и public (с помощью etc/packages/email-subscription и etc/public/email-subscription соответственно). Подписаться на чужой private нельзя.
ldv@ в devel@
«Как найти майнтейнера?»
1. http://alt3.linux.kiev.ua/srpm/Sisyphus/spt/git (с датами и ссылками) 2. http://git.altlinux.org/people-packages-list 3. см. ниже:
> Слить сорцы из git'а, сделать патч и отправить автору (да, в мире существуют > другие git-репозитории, помимо git.a.o). Совершенно обычный use-case для того > типа пользователя, кого сейчас в инфраструктуре совершенно игнорируют: casual > mantainers, которых почти всё устраивает, но иногда хочется написать патчик и > отправить обратно. В принципе, даже той информации, которая есть в бинарном пакете сейчас, уже достаточно для casual mantainers: 1. В установленном бинарном пакете есть %{SOURCERPM} (виден по rpmquery -i), из которого однозначно вычисляется имя исходного пакета. 2. Далее, в установленном бинарном пакете есть %{CHANGELOGNAME} (виден по rpmquery --lastchange). 3. По именам мантейнера (MAINT) и исходного пакета (PKG) можно с очень высокой вероятностью предположить, что если пакет был собран из git-репозитория, то этот репозиторий называется http://git.altlinux.org/people/MAINT/packages/?p=PKG.git
Как вести пакет в git
damir@
Посмотрите на http://git.altlinux.org/people/damir/packages/?p=liblazy.git;a=summary Там правда апстрим git-овый, но это сути не меняет. .gear-rules там состоит из одной строчки - вот такой: tar.bz2: @name@-@version@:. @name@ и @version@ берутся из спека. @name@ - это liblazy. а @version@ - это 0.1 На ветке upstream присутствует тег liblazy-0.1. Поэтому апстримный тарбол будет браться из этого тега. При переезде на новую версию надо будет всего лишь: 1. Поставить нужный тег на апстримной ветке (например liblazy-0.2). 2. Смержить этот тег в master с -s ours 3. Заменить в спеке версию с 0.1 на 0.2. 4. Выполнить gear-update-tag -ac 5. Дописать changelog
Как втащить пакет из Сизифа, если его нет на git.alt/people
Пакет, который давно не собирался или заброшен, или его майнтейнер не пользуется git.alt, можно найти в архиве Сизифа. Архив Сизифа содержит последние версии когда-либо собиравшихся в Сизиф пакетов (с историей) и доступен по ssh git.alt в каталоге /archive. Для удобства хранилища собраны в двухуровневое дерево (по первой букве), без различия майнтейнеров.
Таким образом на сегодня git-clone git.alt:/archive/m/mkimage отдаст хранилище, соответствующее текущему пакету mkimage в Сизифе, кто бы его ни собрал на этот раз.
Ссылки
- Everyday Git With 20 Commands Or So
- Использование gear
- Как переделать commit, в котором сразу же нашёлся ляп
- Как мержить бранчи, поддерживая пакет с N пересекающимися патчами
- Как установить git в Compact 3.0
- Линкдамп по документации git
- tutorial по 1.5+, в частности
- Intro to Distributed Version Control (Illustrated)
- Distributed Version Control Systems: A Not-So-Quick Guide Through
- Обзор git для сообщества OpenSolaris
- Учебник "введение в git" (для версии 1.5.1 или более поздняя версия
- 20 повседневных команд git
- Главы из руководства пользователя git
- GitWiki
- Zack Rusin: Git cheat sheet (A4)
- Kernel Hackers' Guide to git
- A tour of git: the basics
- Git Guide - SourceMage Wiki
- Git Magic
- git-fu
- Version Control Blog
- GitHub: Git Guides
- Git Howtos
- GitCasts