Translation(s): Українська

Вступ

Однією із причин використання самозбірного пакунка є перспектива встановити його не лише на свою систему, а ще й додання його до [не] офіційного репозитарію Debian GNU/Linux. Щоб бути в курсі "офіційного" процесу, вивчайте нові версії Посібника нового розробника Debian.

Зазвичай пакунки Debian містять належний набір джерельних файлів, включно з файлом debian/rules, котрий автоматизовує процес створення двійкового пакунка. Тут ми демонструємо, як запакувати простий shell-сценарій або ж програму у вигляді двійкового файлу у невеличкий пакунок.

До речі, я припускаю, що ви уже вмієте користуватися утилітами 'tar', 'man', і звісно ж, розумієте, що таке '.tar.gz' файл та дистрибутив Debian GNU/Linux (і, як користуватися текстовим редактором ;-)), однак, я беру до уваги той факт, що ви могли ніколи не користуватися програмами 'ar' або 'dpkg'.

Ресурси тенет

quick-reference Довідник по Debian (The Debian Reference) надає чудовий, як короткий огляд, так і детальну інформацію по всій специфіці системи Debian.

Офіційним посібником по створенню власних пакунків Debian є maint-guide Посібник нового розробника Debian (Debian New Maintainers' Guide).

Давайте розпочнемо

Формат deb має властивість змінюватися між випусками, тому для маніпуляції .deb файлами завжди використовують утиліту dpkg-deb. Dpkg-deb запаковує, розпаковує та забезпечує інформацією про архіви Debian. deb файлами також можна маніпулювати за допомогою програм 'ar' і 'tar', якщо у цьому є є потреба. Використовуйте dpkg для встановлення та прибирання пакунків зі своєї системи. Спробуйте знайти декілька пакунків у теці '/var/cache/apt/archives/'. Скориставшись командою  'dpkg-deb -I назва_пакунка.deb'  , ви отримаєте коротку інформацію, з якої можна скласти загальне уявлення про пакунок.  'dpkg-deb -c  назва_пакунка.deb' виводить список файлів, котрі підлягають встановленню.

Вміст пакунка можна отримати за допомогою команди 'ar tv назва_пакунка.deb'. Для того, щоб добути файли з архіву, скористайтеся опцією  'x'. 

Структура пакунка

Давайте розглянемо якийсь приклад. Скажімо, пакунок parted_1.4.24-4_i386.deb містить три наступні файли:

$ ar tv parted_1.4.24-4_i386.deb
rw-r--r-- 0/0 4 Mar 28 13:46 2002 debian-binary
rw-r--r-- 0/0 1386 Mar 28 13:46 2002 control.tar.gz
rw-r--r-- 0/0 39772 Mar 28 13:46 2002 data.tar.gz

Тепер ми можемо розпакувати усі файли, зокрема, вміст tar архівів.

debian-binary

Вміст даного файлу наступний: "2.0\n". Цей рядок вказує на версію формату deb файлу. Усі інші рядки, що йдуть за "2.0\n" буде проі́ґноровано.

data.tar.gz

Файл data.tar.gz містить усі файли, котрі будуть встановлені, зі шляхами тек, котрі є їхнім призначенням.

drwxr-xr-x root/root 0     2002-03-28 13:44:57 ./
drwxr-xr-x root/root 0     2002-03-28 13:44:49 ./sbin/
-rwxr-xr-x root/root 31656 2002-03-28 13:44:49 ./sbin/parted
drwxr-xr-x root/root 0     2002-03-28 13:44:38 ./usr/
drwxr-xr-x root/root 0     2002-03-28 13:44:41 ./usr/share/
drwxr-xr-x root/root 0     2002-03-28 13:44:38 ./usr/share/man/
drwxr-xr-x root/root 0     2002-03-28 13:44:52 ./usr/share/man/man8/
-rw-r--r-- root/root 1608  2002-03-28 13:44:37 ./usr/share/man/man8/parted.8.gz
drwxr-xr-x root/root 0     2002-03-28 13:44:41 ./usr/share/doc/
drwxr-xr-x root/root 0     2002-03-28 13:44:52 ./usr/share/doc/parted/
-rw-r--r-- root/root 1880  2002-03-07 14:20:08 ./usr/share/doc/parted/README.Debian
-rw-r--r-- root/root 1347  2002-02-27 01:40:50 ./usr/share/doc/parted/copyright
-rw-r--r-- root/root 6444  2002-03-28 13:37:33 ./usr/share/doc/parted/changelog.Debian.gz
-rw-r--r-- root/root 15523 2002-03-28 02:36:43 ./usr/share/doc/parted/changelog.gz

Цей файл має бути останнім у deb архіві.

control.tar.gz

У нашому випадку даний файл має наступний вміст:

-rw-r--r-- 1 root root 1336 Mar 28 2002 control
-rw-r--r-- 1 root root 388  Mar 28 2002 md5sums
-rwxr-xr-x 1 root root 253  Mar 28 2002 postinst
-rwxr-xr-x 1 root root 194  Mar 28 2002 prerm
Файл 'md5sums' містить md5 суму кожного файлу, що входить до пакунку.

1d15dcfb6bb23751f76a2b7b844d3c57 sbin/parted
4eb9cc2e192f1b997cf13ff0b921af74 usr/share/man/man8/parted.8.gz
2f356768104a09092e26a6abb012c95e usr/share/doc/parted/README.Debian
a6259bd193f8f150c171c88df2158e3e usr/share/doc/parted/copyright
7f8078127a689d647586420184fc3953 usr/share/doc/parted/changelog.Debian.gz
98f217a3bf8a7407d66fd6ac8c5589b7 usr/share/doc/parted/changelog.gz

Не хвилюйтеся, файл 'md5sums' так само, як і 'postinst' та 'prerm' не є обов'язковим для вашого першого пакунка. Однак, пам'ятайте про їхнє існування, адже кожен офіційний пакунок Debian повинен їх містити.

'prerm' та 'postinst', здається, піклуються про видалення старої документації та додання посилань з doc до share/doc.

$ cat postinst
#!/bin/sh
set -e
# Automatically added by dh_installdocs
if [ "$1" = "configure" ]; then
 if [ -d /usr/doc -a ! -e /usr/doc/parted -a -d /usr/share/doc/parted ]; then
 ln -sf ../share/doc/parted /usr/doc/parted
 fi
fi
# End automatically added section

$ cat prerm
#!/bin/sh
set -e
# Automatically added by dh_installdocs
if [ \( "$1" = "upgrade" -o "$1" = "remove" \) -a -L /usr/doc/parted ]; then
 rm -f /usr/doc/parted
fi

# End automatically added section І на останок, найцікавіший файл:

$ cat control
Package: parted
Version: 1.4.24-4
Section: admin
Priority: optional
Architecture: i386
Depends: e2fsprogs (>= 1.27-2), libc6 (>= 2.2.4-4), libncurses5 (>= \
5.2.20020112a-1), libparted1.4 (>= 1.4.13+14pre1), libreadline4 (>= \
4.2a-4), libuuid1
Suggests: parted-doc
Conflicts: fsresize
Replaces: fsresize
Installed-Size: 76
Maintainer: Timshel Knoll <timshel@debian.org>
Description: The GNU Parted disk partition resizing program
 GNU Parted is a program that allows you to create, destroy,
 resize, move and copy hard disk partitions. This is useful
 for creating space for new operating systems, reorganizing
 disk usage, and copying data to new hard disks.
 .
 This package contains the Parted binary and manual page.
 .
 Parted currently supports DOS, Mac, Sun, BSD, GPT and PC98
 disklabels/partition tables, as well as a 'loop' (raw disk)
 type which allows use on RAID/LVM. Filesystems supported are
 ext2, ext3, FAT (FAT16 and FAT32) and linux-swap. Parted can
 also detect HFS (Mac OS), JFS, NTFS, ReiserFS, UFS and XFS
 filesystems, but cannot create/remove/resize/check these
 filesystems yet.
 .
 The nature of this software means that any bugs could cause
 massive data loss. While there are no known bugs at the moment,
 they could exist, so please back up all important files before
 running it, and do so at your own risk.

Детальнішу інформацію про файл 'control' можна отримати за допомогою команди 'man 5 deb-control'.

Він живий

control

Давайте почнемо з файлу 'control'. Номер версії повинен бути відділений від версії пакунка Debian за допомогою дефісу, наприклад, '1.1-1'. Якщо ваша програма, наприклад, використовує лише портативні скрипти оболонки, використовуйте 'all' у секції 'Architecture'. Для 'Depends' вам, можливо, доведеться дізнатися до якого пакету або програми належить належить ваш новий пакунок. Для з'ясування цієї інформації скористайтеся командою 'dpkg -S ', наприклад:

$ dkpg -S /bin/cat
coreutils: /bin/cat

Тепер для того, щоб дізнатися більше про пакунок 'coreutils', можна скористатися командою 'apt-cache showpkg coreutils', котра окрім іншої інформації видасть вам версію вже встановленого у системі пакунка.

В якості завваги скажу про існування ще одного способу довідатися про дану інформацію. Є веб-сторінка, на котрій ви можете здійснювати пошук пакунків: http://www.debian.org/distrib/packages. Прокрутіть сторінку до низу, там знаходиться форма пошуку.

Наостанок хотів би порекомендувати вам хорошу графічну програму, що зветься 'kpackage', котра надає зручний інтерфейс для перегляду списку панкунків та дозволяє шукати за назвою окремі файли у пакунках.

'Suggests', 'Conflicts', 'Replaces' і тому подібні у випадку відсутності потреби в їхній наявності, можуть бути пропущені.

Отже, ваш перший 'control' файл матиме наступний вміст:

Package: linuxstatus
Version: 1.1-1
Section: base
Priority: optional
Architecture: all
Depends: bash (>= 2.05a-11), textutils (>= 2.0-12), awk, procps (>= \
1:2.0.7-8), sed (>= 3.02-8), grep (>= 2.4.2-3), coreutils (>= 5.0-5)
Maintainer: Chr. Clemens Lee 
Description: Linux system information
 This script provides a broad overview of different
 system aspects.

Файл 'control' скопійовано до теки 'DEBIAN', котра знаходиться у середині іншої теки з назвою 'debian'.

$ mkdir -p debian/DEBIAN
$ find ./debian -type d | xargs chmod 755 # this is necessary on Debian Woody, don't ask me why
$ cp control debian/DEBIAN

dpkg-deb

Ну ось, майже все. Просто введіть:

$ dpkg-deb --build debian
dpkg-deb: building package `linuxstatus' in `debian.deb'.
$ mv debian.deb linuxstatus_1.1-1_all.deb

Ох, це було значно легше, ніж очікувалося. Тепер нам лишається просто встановити даний пакунок на нашій системі, і все буде готово.

# dpkg -i ./linuxstatus_1.1-1_all.deb

Введіть 'linuxstatus' або 'ls -l /usr/bin/linuxstatus' для того, щоб перевірити успішність процесу установки. Якщо вам перестане подобатися ваш пакунок, просто введіть команду 'dpkg -r linuxstatus', і знову перевірте, цього разу успішність видалення пакунка із системи. Якщо ви встановите нову версію, вам не доведеться видаляти стару, мабуть.

Якщо вас зацікавить схема нумерування версій та присвоєння назв для пакунків Debian, прочитайте відповідну секцію у http://www.debian.org.ua/doc/user-manuals#quick-reference Довіднику по Debian.

Перевірка

lintian

На щастя проект Debian забезпечив нас утиліткою 'lintian', котра перевіряє Debian`івські пакунки. Якщо її ще не встановлено на вашій системі, маєте гарний привід виправити це (apt-get install lintian).

Тепер ми випробуємо цей маленький інструмент на нашому пакунку.

$ lintian linuxstatus_1.1-1_all.deb
E: linuxstatus: binary-without-manpage linuxstatus
E: linuxstatus: no-copyright-file
W: linuxstatus: prerm-does-not-remove-usr-doc-link
W: linuxstatus: postinst-does-not-set-usr-doc-link

Ой, на ідеальну роботу це не схоже. Ми пропустили сторінки підручника man, файл copyright, а також скрипти 'prerm' та 'postinst'.

Мінімальна документація

дозвольте трішки забігти на перед, і припустити, що ви уже маєте чудові сторінки підручника man для свого скрипту в ./man/man1/linuxstatus.1.

Це стосується і файлу 'copyright'. Ви можете знайти достатньо прикладів у теці /usr/share/doc за допомогою цієї команди: find /usr/share/doc -name "copyright"

Ось наш власний приклад файлу 'copyright':

linuxstatus

Copyright: Chr. Clemens Lee <clemens@kclee.de>

2002-12-07

The home page of linuxstatus is at: 
http://www.kclee.de/clemens/unix/index.html#linuxstatus

The entire code base may be distributed under the terms of the GNU General
Public License (GPL), which appears immediately below. Alternatively, all
of the source code as any code derived from that code may instead be
distributed under the GNU Lesser General Public License (LGPL), at the
choice of the distributor. The complete text of the LGPL appears at the
bottom of this file.

See /usr/share/common-licenses/(GPL|LGPL) Для скриптів 'prerm' та 'postinst' ми один в один копіюємо приклади з пакунку 'parted' до файлів з таким же ім'я у теці нашого проекту. Ці файли повинні згодитися і для нас.

Тепер ми знову створюємо debian`івський пакунок. У файлі 'control' ми вперше збільшуємо номер версії з 1.1-1 до 1.2-1 (оскільки ми написали нову сторінку підручника man, то потрібно збільшити наш внутрішній номер випуску). Також нам потрібно скопіювати нові файли до відповідних тек:

$ mkdir -p ./debian/usr/share/man/man1
$ mkdir -p ./debian/usr/share/doc/linuxstatus
$ find ./debian -type d | xargs chmod 755
$ cp ./man/man1/linuxstatus.1 ./debian/usr/share/man/man1
$ cp ./copyright ./debian/usr/share/doc/linuxstatus
$ cp ./prerm ./postinst ./debian/DEBIAN
$ gzip --best ./debian/usr/share/man/man1/linuxstatus.1
$
$ dpkg-deb --build debian
dpkg-deb: building package `linuxstatus' in `debian.deb'.
$ mv debian.deb linuxstatus_1.2-1_all.deb

Утилітка lintian очікує їхнього максимально можливого стисення, тому нам необхідно скористатися gzip'оп.

===fakeroot=== Тепер давайте перевіримо, чи став наш пакунок кращим громадянином Debian:

$ lintian linuxstatus_1.2-1_all.deb
E: linuxstatus: control-file-has-bad-owner prerm clemens/clemens != root/root
E: linuxstatus: control-file-has-bad-owner postinst clemens/clemens != root/root
E: linuxstatus: bad-owner-for-doc-file usr/share/doc/linuxstatus/ clemens/clemens != root/root
E: linuxstatus: bad-owner-for-doc-file usr/share/doc/linuxstatus/copyright clemens/clemens != root/root
E: linuxstatus: debian-changelog-file-missing

Ой, нові скарги. Гаразд, ми всеодно не здамося. У принципі, більшість проблем є причиною тих же помилок. Усі наші файли запаковано для користувача і групи 'clemens', у той час, як більшість людей віддалиб перевагу їхньому встановленню, як 'root/root'. Але це легко виправити використовуючи ітуліту 'fakeroot'. Тож, давайте швиденько виправимо це, і одразу ж перевіримо результат (нехтуючи проблемою changelog):

$ fakeroot dpkg-deb --build debian
dpkg-deb: building package `linuxstatus' in `debian.deb'.
$ mv debian.deb linuxstatus_1.2-1_all.deb
$ lintian linuxstatus_1.2-1_all.deb
E: linuxstatus: debian-changelog-file-missing

Чудово! Однак, у нас є ще один файл, який нам потрібно додати до пакунка.

Додаткова документація

Дозвольте нагадати вам про те, що разом з файлом 'changelog' у теці 'doc/linuxstatus' також повинен бути присутній файлик 'changelog.Debian'. Обидва повинні бути стиснені gzip'ом із параметром --best.

Ось приклад файлу 'changelog':

linuxstatus (1.2-1)

 * Made Debian package lintian clean.

 -- Chr. Clemens Lee <clemens@kclee.de> 2002-12-13
та 'changelog.Debian':

linuxstatus Debian maintainer and upstream author are identical. Therefore see also normal changelog file for Debian changes. Файл політики Debian має більше деталей відносно формату файлу changelog.

А тепер, наш багатообіцяючий останній крок:

$ cp ./changelog ./changelog.Debian ./debian/usr/share/doc/linuxstatus
$ gzip --best ./debian/usr/share/doc/linuxstatus/changelog 
$ gzip --best ./debian/usr/share/doc/linuxstatus/changelog.Debian
$ fakeroot dpkg-deb --build ./debian
dpkg-deb: building package `linuxstatus' in `debian.deb'.
$ mv debian.deb linuxstatus_1.2-1_all.deb
$ lintian linuxstatus_1.2-1_all.deb

Ах, більше на нас не скаржаться :-). Як користувач root ви можете встановити цей пакунок поверх старого, знову за допомогою стандартної команди 'dpkg -i'.

root# dpkg -i ./linuxstatus_1.2-1_all.deb
(Reading database ... 97124 files and directories currently installed.)
Preparing to replace linuxstatus 1.1-1 (using linuxstatus_1.2-1_all.deb) ...
Unpacking replacement linuxstatus ...
Setting up linuxstatus (1.2-1) ...

Підсумок

Щоб не заплутатися, давайте почергово опишемо всі пророблені нами кроки для збирання нашого двійкового пакунку Debian.

Попередні файли:

* один або декілька shell сценаріїв * сторінки підручника man для кожного сценарію * файл 'control' * файл 'copyright' * файли 'changelog' та 'changelog.Debian'

* Встановлення тимчасових підтек 'debian':

* створіть теку 'debian/usr/bin' (або ж ту, де ви плануєте розмістити виконувані файли) * створіть 'debian/usr/share/man/man1' (або ж ту, де ви плануємо розмістити сторінки підручника man) * створіть теку 'debian/DEBIAN' * створіть теку 'debian/usr/share/doc/<ім'я_пакунку>' * переконайтеся у тім, що всі підтеки 'debian' мають права доступу 0755

Копіювання файлів до тимчасового дерева 'debian':

* скопіюйте executable файл до теки 'debian/usr/bin' (або ж туди, де ви палануєте розмістити свої виконувані файли) * скопіюйте сторінки man до теки 'debian/usr/share/man/man1' * скопіюйте файл 'control' до теки 'debian/DEBIAN' * скопіюйте файли 'copyright', 'changelog' та 'changelog.Debian' до 'debian/usr/share/doc/<ім'я_пакунку>'

Побудова та перевірка двійкового пакунку Debian:

* введіть 'dpkg-deb --build' використовуючи 'fakeroot' у теці 'debian' * перейменуйте вихідний файл 'debian.deb' на остаточне ім'я пакунку, включно з версією та інформацією про архітектуру * перевірте остаточний .deb пакунок на сумісність із політикою сумісності Debian використовуючи 'lintian'