Руководство разработчика по пакетированию приложений

Поддержка перемещения в неоднородной вычислительной среде

Исходная концепция пакетирования в System V предполагало наличие одной архитектуры на систему. В этом проектном решении концепция сервера не играла никакой роли. В настоящее время один сервер может осуществлять поддержку нескольких архитектур, то есть на сервере могут присутствовать несколько копий одного и того же программного обеспечения, разработанного для разных архитектур. Несмотря на то, что пакеты Solaris изолированы в рекомендованных рамках файловой системы (например, / и /usr) с размещением баз данных продукта на сервере и на каждом из клиентов, не все типы установок поддерживают это разделение. Некоторые разработки поддерживают совершенно другую структуру и предполагают наличие общей базы данных продуктов. Хотя направление клиента на другие версии представляется самым простым решением, в действительности установка пакетов System V в другие базовые каталоги может создать сложности для администратора.

При разработке пакета необходимо принять во внимание те методы, которые используют администраторы при внедрении новых версий ПО. Часто администраторы хотят устанавливать и тестировать новейшие версии наряду с уже установленной версией. Данная процедура включает в себя установку новой версии в базовый каталог, отличный от каталога, в котором расположена существующая версия, и направление нескольких некритических клиентов на новую версию в качестве теста. По мере нарастания уверенности в работе новой версии, администратор перенаправляет на нее все большее и большее число клиентов. В конечном итоге администратор оставляет старую версию только для чрезвычайных ситуаций, а позднее и полностью ее удаляет.

Все это подводит нас к тому, что пакеты, разработанные для современных неоднородных систем, должны поддерживать истинное перемещение в том смысле, что администратор может поместить их в любое допустимое место в файловой системе и при этом получить полную функциональность. Solaris 2.5 и совместимые выпуски предлагают ряд полезных средств, которые позволяют осуществлять чистую установку нескольких архитектур и версий на одну систему. Solaris 2.4 и совместимые версии также поддерживают истинное перемещение, однако решение этой задачи не совсем очевидно.

Традиционный подход

Перемещаемые пакеты

Двоичный интерфейс приложений System V предполагает, что первоначальным намерением при разработке перемещаемых пакетов было облегчить труд администратора по установке. В настоящее время потребности в перемещаемых пакетах идут гораздо дальше. Удобство уже не является единственной проблемой, поскольку вполне возможно, что в процессе установки активный программный продукт уже установлен в каталоге по умолчанию. Пакет, не спроектированный на решение данной ситуации, либо перезаписывает существующий продукт, либо установка не удается. С другой стороны пакет, разработанный для работы с многими архитектурами и версиями, может легко быть установлен и одновременно предлагает администратору широкий выбор возможностей, полностью совместимых с существующими традициями администрирования.

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

Пример. Традиционный перемещаемый пакет

В данном примере показано, как может выглядеть традиционный перемещаемый пакет. Пакет должен располагаться в каталоге /opt/SUNWstuf, а его файлы pkginfo и pkgmap могут выглядеть следующим образом:

Файл pkginfo

# pkginfo file
PKG=SUNWstuf
NAME=software stuff 
ARCH=sparc
VERSION=1.0.0,REV=1.0.5
CATEGORY=application
DESC=a set of utilities that do stuff
BASEDIR=/opt
VENDOR=Sun Microsystems, Inc.
HOTLINE=Please contact your local service provider
EMAIL=
MAXINST=1000
CLASSES=none
PSTAMP=hubert990707141632

Файл pkgmap

: 1 1758
1 d none SUNWstuf 0775 root bin
1 d none SUNWstuf/EZstuf 0775 root bin
1 f none SUNWstuf/EZstuf/dirdel 0555 bin bin 40 773 751310229
1 f none SUNWstuf/EZstuf/usrdel 0555 bin bin 40 773 751310229
1 f none SUNWstuf/EZstuf/filedel 0555 bin bin 40 773 751310229
1 d none SUNWstuf/HRDstuf 0775 root bin
1 f none SUNWstuf/HRDstuf/mksmart 0555 bin bin 40 773 751310229
1 f none SUNWstuf/HRDstuf/mktall 0555 bin bin 40 773 751310229
1 f none SUNWstuf/HRDstuf/mkcute 0555 bin bin 40 773 751310229
1 f none SUNWstuf/HRDstuf/mkeasy 0555 bin bin 40 773 751310229
1 i pkginfo 348 28411 760740163
1 i postinstall 323 26475 751309908
1 i postremove 402 33179 751309945
1 i preinstall 321 26254 751310019
1 i preremove 320 26114 751309865

Этот метод называется традиционным потому что каждый объект пакета устанавливается в базовый каталог, определенный параметром BASEDIR в файле pkginfo. Например, первый объект в файле pkgmap устанавливается как каталог /opt/SUNWstuf.

Абсолютные пакеты

Абсолютным является пакет, устанавливаемый в конкретную корневую (/) файловую систему. С точки зрения множественных версий и архитектур эти пакеты являются сложными в обращении. Как правило все пакеты должны быть перемещаемыми. Существуют, однако, довольно веские причины включать абсолютные элементы в перемещаемые пакеты.

Пример. Традиционный абсолютный пакет

Если бы пакет SUNWstuf являлся абсолютным, то определения параметра BASEDIR в файле pkginfo не потребовалось, а файл pkgmap выглядел бы так:

Файл pkgmap

: 1 1758
1 d none /opt ? ? ?
1 d none /opt/SUNWstuf 0775 root bin
1 d none /opt/SUNWstuf/EZstuf 0775 root bin
1 f none /opt/SUNWstuf/EZstuf/dirdel 0555 bin bin 40 773 751310229
1 f none /opt/SUNWstuf/EZstuf/usrdel 0555 bin bin 40 773 751310229
1 f none /opt/SUNWstuf/EZstuf/filedel 0555 bin bin 40 773 751310229
1 d none /opt/SUNWstuf/HRDstuf 0775 root bin
1 f none /opt/SUNWstuf/HRDstuf/mksmart 0555 bin bin 40 773 751310229
1 f none /opt/SUNWstuf/HRDstuf/mktall 0555 bin bin 40 773 751310229
1 f none /opt/SUNWstuf/HRDstuf/mkcute 0555 bin bin 40 773 751310229
1 f none /opt/SUNWstuf/HRDstuf/mkeasy 0555 bin bin 40 773 751310229
1 i pkginfo 348 28411 760740163
1 i postinstall 323 26475 751309908
1 i postremove 402 33179 751309945
1 i preinstall 321 26254 751310019
1 i preremove 320 26114 751309865

В данном примере если администратор в процессе установки указывает альтернативный базовый каталог, он будет проигнорирован командой pkgadd.. Данный пакет всегда будет устанавливаться в каталог /opt/SUNWstuf целевой системы.

Параметр -R команды pkgadd работает как и ожидалось. Например,


pkgadd -d . -R /export/opt/client3 SUNWstuf

устанавливает объекты в каталог /export/opt/client3/opt/SUNWstuf. Здесь пакет наиболее близко подходит к определению "перемещаемый".

Обратите внимание на использование знака вопроса (?) в каталоге /opt файла pkgmap. Он означает, что существующие атрибуты не должны изменяться. Он не означает "создать каталог с атрибутами по умолчанию", хотя при некоторых обстоятельствах это может случиться. Для любого каталога, относящегося к новому пакету, необходимо явно указывать все атрибуты.

Составные пакеты

Любой пакет, содержащий перемещаемые объекты, называется перемещаемым пакетом. Данное определение может ввести в заблуждение, поскольку в файле pkgmap перемещаемого пакета могут содержаться абсолютные пути. Использование корневой (/) записи в файле pkgmap может усилить перемещаемые аспекты пакета. Пакеты, содержащие одновременно перемещаемые и корневые записи, называются составными пакетами.

Пример. Традиционное решение

Предположим, что один объект в пакете SUNWstuf является сценарием запуска, выполняемым на уровне выполнения 2. Файл /etc/rc2.d/S70dostuf должен быть установлен как часть пакета, однако он не может быть помещен в базовый каталог. При условии, что единственным решением здесь будет перемещаемый пакет, файлы pkginfo и pkgmap могут иметь следующий вид:

Файл pkginfo

# pkginfo file
PKG=SUNWstuf
NAME=software stuff 
ARCH=sparc
VERSION=1.0.0,REV=1.0.5
CATEGORY=application
DESC=a set of utilities that do stuff
BASEDIR=/
VENDOR=Sun Microsystems, Inc.
HOTLINE=Please contact your local service provider
EMAIL=
MAXINST=1000
CLASSES=none
PSTAMP=hubert990707141632

Файл pkgmap

: 1 1758
1 d none opt/SUNWstuf/EZstuf 0775 root bin
1 f none opt/SUNWstuf/EZstuf/dirdel 0555 bin bin 40 773 751310229
1 f none opt/SUNWstuf/EZstuf/usrdel 0555 bin bin 40 773 751310229
1 f none opt/SUNWstuf/EZstuf/filedel 0555 bin bin 40 773 751310229
1 d none opt/SUNWstuf/HRDstuf 0775 root bin
1 f none opt/SUNWstuf/HRDstuf/mksmart 0555 bin bin 40 773 751310229
1 f none opt/SUNWstuf/HRDstuf/mktall 0555 bin bin 40 773 751310229
1 f none opt/SUNWstuf/HRDstuf/mkcute 0555 bin bin 40 773 751310229
1 f none opt/SUNWstuf/HRDstuf/mkeasy 0555 bin bin 40 773 751310229
1 d none etc	? ? ?
1 d none etc/rc2.d ? ? ?
1 f none etc/rc2.d/S70dostuf 0744 root sys 450 223443
1 i pkginfo 348 28411 760740163
1 i postinstall 323 26475 751309908
1 i postremove 402 33179 751309945
1 i preinstall 321 26254 751310019
1 i preremove 320 26114 751309865

Нет большой разницы между этим подходом и подходом, применяемым в абсолютном пакете. В действительности абсолютный пакет был бы здесь предпочтительнее - если администратор указал альтернативный базовый каталог для этого пакета, то он не будет работать!

На самом деле только один файл в этом пакете должен быть связан с корнем - остальные файлы можно было бы переместить в любое место. В оставшейся части раздела будет показано, как решить эту проблему с помощью составного пакета.

За пределами традиции

Подход, описанный в данном разделе, не применим ко всем пакетам, но он приводит к увеличению производительности при установке в неоднородную среду. Приведенная здесь информация практически не относится к пакетам, поставляемым как часть ОС Solaris (собранные пакеты); однако на несобранных пакетах можно попрактиковаться в нетрадиционных способах создания пакетов.

Причиной стимулирования использования перемещаемых пакетов является поддержка следующего требования:

При добавлении или удалении пакета существующее желательное поведение установленных программных продуктов не должно измениться.

Несвязанные пакеты должны размещаться в каталоге /opt с тем, чтобы гарантировать отсутствие влияния нового пакета на существующие программные продукты.

Другой взгляд на составные пакеты

Существуют два правила, которым необходимо следовать при создании полнофункционального составного пакета:

Иными словами, поскольку "перемещаемый" означает, что объект может быть установлен в любом месте и по-прежнему работать, ни один стартовый сценарий, запускаемый с помощью init во время загрузки, не может считаться перемещаемым! И, хотя в поставляемом пакете вполне можно указать /etc/passwd в качестве относительного пути, есть только одно место, где он может быть размещен.

Представление абсолютных имен путей в виде перемещаемых

При создании составного пакета абсолютные пути должны работать так, чтобы не влиять на уже установленное программное обеспечение. Пакет, полностью размещаемый в каталоге /opt, обходит эту проблему, поскольку никакие существующие файлы ему не мешают. При включении файла из каталога /etc в пакет необходимо гарантировать, что абсолютные имена путей будут вести семя так же, как это ожидается от относительных имен путей. Рассмотрите следующие примеры.

Пример. Изменение файла

Описание

В таблицу добавляется запись или объект представляет собой новую таблицу, которая скорее всего будет изменена другими программами или пакетами.

Реализация

Определите объект как файловый типа e и относящийся к классу build, awk или sed. Сценарий, выполняющий эту задачу, должен удалять себя так же эффективно, как добавляет.

Пример

Необходимо добавить запись в /etc/vfstab для обеспечения поддержки нового твердотельного жесткого диска.

Запись в файле pkgmap может быть такой:


1 e sed /etc/vfstab ? ? ?

Сценарий request спрашивает оператора, должен ли каталог /etc/vfstab быть изменен пакетом. Если оператор отвечает “no” (нет), то сценарий запроса выведет на печать инструкции о том, как выполнить это задание вручную, и выполнит


echo "CLASSES=none" >> $1

Если оператор отвечает “yes” (да), тогда сценарий выполнит


echo "CLASSES=none sed" >> $1

активируя сценарий действия над классом, который произведет необходимые изменения. Класс sed означает, что файл пакета /etc/vfstab представляет собой программу sed, содержащую операции по установке и удалению одноименного файла в целевой системе.

Пример. Создание нового файла

Описание

Объект представляет собой совершенно новый файл, который вряд ли будет изменяться в будущем, или он заменяет файл, принадлежащий другому пакету.

Реализация

Определите объект пакета как тип файла f и установите его с помощью сценария действия над классом, способного отменить изменения.

Пример

В каталоге /etc необходим совершенно новый файл для предоставления необходимой информации для поддержки твердотельного жесткого диска с именем /etc/shdisk.conf. Запись в файле pkgmap может выглядеть следующим образом:


 
.
.
.
1 f newetc /etc/shdisk.conf
.
.
.

Сценарий действия над классом i.newetc отвечает за установку этого и любых других файлов, которые должны быть размещены в каталоге /etc. Он проверяет наличие в этом каталоге другого файла. Если файла нет, сценарий просто скопирует новый файл на место. Если же там уже существует файл, сценарий произведет его резервное копирование перед установкой нового файла. Сценарий r.newetc удаляет эти файлы и, если требуется, восстанавливает оригиналы файлов. Ниже представлен ключевой фрагмент установочного сценария.

# i.newetc
while read src dst; do
	  if [ -f $dst ]; then
	    dstfile=`basename $dst`
	    cp $dst $PKGSAV/$dstfile
	  fi
	  cp $src $dst
done
 
if [ "${1}" = "ENDOFCLASS" ]; then
	  cd $PKGSAV
	  tar cf SAVE.newetc .
	  $INST_DATADIR/$PKG/install/squish SAVE.newetc
fi

Обратите внимание, что сценарий использует переменную среды PKGSAV для сохранения резервной копии заменяемого файла. Когда аргумент ENDOFCLASS передается в сценарий, команда pkgadd сообщает сценарию, что это последние записи в данном классе, после чего сценарий производит архивирование и сжатие файлов, сохраненных с помощью частной программы сжатия, хранящейся в установочном каталоге пакета.

Использование переменной среды PKGSAV во время обновления пакета представляется ненадежным; однако, если пакет не обновляется (посредством внесения изменений, например), то архивный файл остается в безопасности. Следующий сценарий удаления содержит программный код, который решает другую проблему - старые версии команды pkgrmне передают сценариям правильный путь к переменной среды PKGSAV.

Сценарий удаления может выглядеть так:

# r.newetc
 
# make sure we have the correct PKGSAV
if [ -d $PKG_INSTALL_ROOT$PKGSAV ]; then
	  PKGSAV="$PKG_INSTALL_ROOT$PKGSAV"
fi
 
# find the unsquish program
UNSQUISH_CMD=`dirname $0`/unsquish
 
while read file; do
	  rm $file
done
 
if [ "${1}" = ENDOFCLASS ]; then
	  if [ -f $PKGSAV/SAVE.newetc.sq ]; then
	     $UNSQUISH_CMD $PKGSAV/SAVE.newetc
	  fi
 
	  if [ -f $PKGSAV/SAVE.newetc ]; then
	     targetdir=dirname $file	# get the right directory
	     cd $targetdir
		    tar xf $PKGSAV/SAVE.newetc
		    rm $PKGSAV/SAVE.newetc
	  fi
fi

Данный сценарий использует частный не установленный алгоритм (unsquish), который расположен в установочном каталоге базы данных пакета. Это происходит автоматически с помощью команды pkgadd во время установки. Все сценарии, не опознанные явно командой pkgadd как сценарии "только для установки", остаются в этом каталоге для использования командой pkgrm. Нельзя рассчитывать на местоположение каталога, но можно положиться на то, что каталог является неструктурированным и содержит все надлежащие информационные файлы и установочные сценарии, необходимые для пакета. Данный сценарий находит каталог благодаря тому, что сценарий действия над классом наверняка будет исполняться из каталога, содержащего программу unsquish.

Обратите также внимание на то, что в данном сценарии просто не предполагается, что целевым каталогом является каталог /etc. В действительности это может быть каталог /export/root/client2/etc . Правильный каталог может быть составлен одним из двух способов.

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

Пример. Составной пакет

Ниже приведен пример файлов pkginfo и pkgmap для составного пакета.

Файл pkginfo

PKG=SUNWstuf
NAME=software stuff 
ARCH=sparc
VERSION=1.0.0,REV=1.0.5
CATEGORY=application
DESC=a set of utilities that do stuff
BASEDIR=/opt
VENDOR=Sun Microsystems, Inc.
HOTLINE=Please contact your local service provider
EMAIL=
MAXINST=1000
CLASSES=none daemon
PSTAMP=hubert990707141632

Файл pkgmap

: 1 1758
1 d none SUNWstuf/EZstuf 0775 root bin
1 f none SUNWstuf/EZstuf/dirdel 0555 bin bin 40 773 751310229
1 f none SUNWstuf/EZstuf/usrdel 0555 bin bin 40 773 751310229
1 f none SUNWstuf/EZstuf/filedel 0555 bin bin 40 773 751310229
1 d none SUNWstuf/HRDstuf 0775 root bin
1 f none SUNWstuf/HRDstuf/mksmart 0555 bin bin 40 773 751310229
1 f none SUNWstuf/HRDstuf/mktall 0555 bin bin 40 773 751310229
1 f none SUNWstuf/HRDstuf/mkcute 0555 bin bin 40 773 751310229
1 f none SUNWstuf/HRDstuf/mkeasy 0555 bin bin 40 773 751310229
1 d none /etc	? ? ?
1 d none /etc/rc2.d ? ? ?
1 e daemon /etc/rc2.d/S70dostuf 0744 root sys 450 223443
1 i i.daemon 509 39560 752978103
1 i pkginfo 348 28411 760740163
1 i postinstall 323 26475 751309908
1 i postremove 402 33179 751309945
1 i preinstall 321 26254 751310019
1 i preremove 320 26114 751309865
1 i r.daemon 320 24573 742152591

Хотя S70dostufпринадлежит к классу daemon, каталоги, которые ведут к нему (и которые уже находятся на месте во время установки), принадлежат к классу none. Даже если каталоги являются уникальными для этого пакета, все равно следует оставить их в классе none. Причина этого кроется в том, что каталоги необходимо создавать в первую, а удалять в последнюю очередь, что всегда истинно для класса none. Команда pkgadd создает каталоги; они не копируются из пакета и не передаются в сценарий действия над классом для создания. Вместо этого они создаются командой pkgadd перед тем, как она вызывает установочный сценарий действия над классом, а команда pkgrm удаляет каталоги после завершения удаления сценария действия над классом.

Это означает, что если каталог в особом классе содержит объекты в классе none, то при попытке команды pkgrm удалить этот каталог произойдет сбой, поскольку каталог не будет вовремя освобожден. Если объект класса none необходимо вставить в каталог какого-либо особого класса, этот каталог еще не будет существовать в это время для принятия такого объекта. Команда pkgadd создаст каталог динамически в ходе установки объекта и, возможно, не сможет синхронизировать атрибуты этого каталога на момент появления его определения в файле pkgmap.


Примечание –

При назначении каталога классу всегда помните о порядке создания и удаления.