PKGBUILD это обычный текстовый скрипт, который описывает пакет для makepkg: откуда взять исходники, как их собрать и куда положить готовые файлы. Свой PKGBUILD для маленького приложения пишется за десять минут: заполняешь переменные, добавляешь функции build() и package(), запускаешь makepkg и получаешь архив .pkg.tar.zst, который ставится через pacman. Ниже полный разбор структуры на реальном примере.
PKGBUILD это скрипт-описание для makepkg. Внутри него переменные и функции на bash-подобном синтаксисе. makepkg читает файл, скачивает исходники, собирает программу и упаковывает результат в архив с расширением .pkg.tar.zst. Дальше с архивом работает pacman: проверяет зависимости, раскладывает файлы по системе и записывает пакет в свою базу.
Каждый пакет в официальных репозиториях Arch и в AUR собран именно из PKGBUILD. Разница в том, кто запускает makepkg: для официальных пакетов это делают сопровождающие, для AUR ты сам. Умение читать и писать PKGBUILD открывает дорогу к сборке чего угодно: от маленького скрипта до собственного ядра.
Для публикации в AUR к PKGBUILD добавляется файл .SRCINFO. Его генерирует команда makepkg –printsrcinfo, и в нём дублируются все метаданные пакета в машиночитаемом виде. AUR-клиенты вроде yay и paru читают именно .SRCINFO, чтобы показать тебе описание, версию и зависимости до сборки. Сам PKGBUILD при этом остаётся главным файлом: .SRCINFO без него бесполезен, а он без .SRCINFO собирается нормально.
Минимальный PKGBUILD состоит из двух частей: переменные с описанием пакета и функции со сборкой.
Обязательные переменные:
Частые необязательные переменные:
Функций две:
Внутри makepkg используются три каталога: $srcdir с исходниками, $pkgdir с будущим содержимым пакета и $startdir с самим PKGBUILD. Понимание этих трёх путей решает половину проблем при написании своих пакетов.
Ещё одна полезная переменная pkgdesc: короткое описание пакета в одну строку. Его видно в выводе pacman -Ss и в списках AUR. Хорошее описание отвечает на вопрос, что делает программа, без маркетинга. Например, для morse подойдёт «Конвертер текста в азбуку Морзе».
Вот простой пример: скрипт на Python, который переводит текст в азбуку Морзе. Один файл, никакой компиляции. Пакет называется morse.
pkgname=morse
pkgver=1.0
pkgrel=1
pkgdesc="Конвертер текста в азбуку Морзе"
arch=('any')
url="https://example.com/morse"
license=('MIT')
depends=('python')
source=("$pkgname-$pkgver.py::https://example.com/morse-$pkgver.py")
sha256sums=('a1b2c3d4e5f67890a1b2c3d4e5f67890')
package() {
install -Dm755 "$srcdir/$pkgname-$pkgver.py" "$pkgdir/usr/bin/$pkgname"
}
Сам скрипт выглядит так:
#!/usr/bin/env python3
import sys
MORSE = {'а': '.-', 'б': '-...', 'в': '.--', 'г': '--.', 'д': '-..'}
def encode(text):
return ' '.join(MORSE.get(ch.lower(), ch) for ch in text)
if __name__ == '__main__':
print(encode(sys.argv[1] if len(sys.argv) > 1 else 'привет'))
Для примера словарь сокращён до пяти букв, в реальном скрипте он полный. Важно, что в PKGBUILD сам код не хранится: makepkg скачивает его по адресу из source. Если хочешь собрать пакет из локального файла, положи скрипт рядом с PKGBUILD и укажи в source просто имя файла.
Разбор по строкам. Запись вида имя::адрес в source переименовывает скачанный файл: вместо длинного имени из URL в $srcdir появится morse-1.0.py. Контрольную сумму подставляй реальную: её выдаёт makepkg при первой попытке сборки или команда sha256sum.
В package() команда install -Dm755 копирует скрипт в $pkgdir/usr/bin/morse и делает его исполняемым. Флаг -D создаёт недостающие каталоги, -m755 ставит права на запуск. Всё, что попало в $pkgdir, окажется в архиве пакета, а после установки в системе.
Положи PKGBUILD в отдельный каталог и запусти сборку:
makepkg -si
Флаг -s сам подтянет зависимости из depends и makedepends через pacman, флаг -i установит собранный пакет сразу после сборки. Хочешь только собрать без установки, убери -i.
makepkg запрещено запускать от root: он сам сбросит права или откажется работать. Сборка идёт от обычного пользователя, а установка через -i попросит пароль через sudo. Каталог сборки создаётся рядом с PKGBUILD, в нём же появляется готовый архив.
Перед установкой полезно прогнать namcap, анализатор пакетов:
namcap PKGBUILD
namcap morse-1.0-1-any.pkg.tar.zst
Первая команда проверяет сам PKGBUILD, вторая готовый архив. namcap подскажет лишние зависимости, забытые файлы и другие мелочи. Не каждый его совет обязателен, но ошибки уровня «файл не в /usr» он ловит надёжно.
Готовый архив можно установить и вручную:
sudo pacman -U morse-1.0-1-any.pkg.tar.zst
Так ставятся любые собранные пакеты. Подробнее про установку из AUR и связанные с ней проверки читай в статье «Установка пакетов из AUR».
В Arch принято ставить всё в /usr, а не в /usr/local. Для проектов на C с configure это делается флагом:
./configure --prefix=/usr
make
Без –prefix configure по умолчанию соберёт в /usr/local, и файлы разъедутся по системе. Подробный разбор сборки из исходников есть в статье «Сборка из исходников: configure и make».
В package() для configure-проектов стандартный шаблон такой:
package() {
cd "$srcdir/$pkgname-$pkgver"
make DESTDIR="$pkgdir" install
}
Переменная DESTDIR подставляет $pkgdir перед путями установки: make install пишет файлы не в корень системы, а в каталог пакета. Без DESTDIR make install полез бы в настоящий /usr, а это при сборке пакета недопустимо.
Для простых скриптов и бинарников хватает install, как в примере с morse. Главное правило: в $pkgdir файлы лежат по тем же путям, что и в системе после установки.
Кроме бинарников в /usr/bin, пакеты часто кладут файлы в /usr/share: иконки, переводы, документацию. Для них в package() добавляют строки install с нужными каталогами. Например, man-страницу ставят так:
install -Dm644 "$srcdir/morse.1" "$pkgdir/usr/share/man/man1/morse.1"
Правило то же: путь внутри $pkgdir повторяет путь в системе. Если сомневаешься, куда класть файл, посмотри, как это делают похожие пакеты в официальных репозиториях.
Собранные пакеты можно складывать в локальный репозиторий и ставить на нескольких машинах без повторной сборки. Для этого нужны каталог с архивами и база, которую создаёт repo-add. Пошаговая инструкция есть в статье «Свой репозиторий: repo-add». После создания базы подключи её в /etc/pacman.conf строкой Server = file:///путь/к/каталогу, и пакеты из неё станут доступны через pacman -S.
Когда выходит новая версия программы, правь pkgver и пересчитывай sha256sums. Контрольные суммы меняются почти всегда, потому что меняется содержимое архива. Старый PKGBUILD с новым архивом соберётся с ошибкой проверки суммы, и это нормально: так makepkg защищает тебя от подмены исходников.
pkgrel поднимай, когда меняется сам PKGBUILD, а не программа: добавил зависимость, поправил пути установки, обновил описание. Версия пакета в системе складывается из pkgver и pkgrel, например 1.0-1. Если pkgrel не поднять, pacman посчитает новый пакет тем же самым и откажется переустанавливать.
Для пакетов из git-репозиториев версию часто берут из даты коммита или счётчика. Тогда pkgver обновляется автоматически при каждой сборке, а pkgrel остаётся единицей. Такой подход удобен, но требует аккуратных sha256sums: для git-исходников их обычно заменяют на SKIP.
Нет. Для скриптов на Python, bash и других интерпретируемых языках build() можно опустить. makepkg спокойно соберёт пакет с одной package().
Проверь, что скачался именно тот файл, который ты ожидал. Частая причина: исходник меняется при каждом скачивании, например снимок git-репозитория. Тогда сумму обновляют вручную или фиксируют конкретный коммит в source.
Можно, но не нужно. makepkg сам скачает исходники, проверит суммы, соберёт и упакует. Ручная сборка с ручной упаковкой только добавит ошибок.
Makefile описывает сборку одной программы. PKGBUILD описывает весь пакет: исходники, зависимости, лицензию, пути установки. Внутри PKGBUILD может вызываться make, но это разные уровни: первый про пакет, второй про компиляцию.
Потому что сборка от root опасна: скрипты из build() и package() выполняются с полными правами, а исходники могут быть вредоносными. Запускай makepkg от обычного пользователя, а установку делай через sudo.
PKGBUILD это скрипт-описание для makepkg: переменные описывают пакет, функции build() и package() собирают и раскладывают файлы. Минимальный пакет для скрипта на Python умещается в десять строк, а для configure-проектов добавляются –prefix=/usr и DESTDIR. Сборка запускается одной командой makepkg -si, namcap ловит ошибки, а установка в /usr сводится к простому правилу: в $pkgdir файлы лежат по системным путям. Дальше пакет ставится через pacman -U или попадает в свой репозиторий. Начни с маленького скрипта, собери его, и через пару пакетов PKGBUILD перестанет казаться магией.
Задай вопрос в чате — отвечаем быстро, по делу и без воды.
Комментарии