2013/06/18 修正
dev.haiku-os.org/wiki より、Package Management Infrastructure の私訳です。訳のおかしいところは、原文を参照ください。

パッケージ管理の基礎構造

このページは、Haiku のパッケージ管理の基礎構造に属するコンポーネントの概要と、それらがどのように動作し相互作用するかを説明します。

ソフトウェアのインストール場所

Haiku では、ソフトウェアをインストールする場所が、"/boot/system"、"/boot/common"、および "/boot/home/config" の 3 箇所あります。"/boot/system" は、基本システムがインストールされる場所です。それは変更不可であり、サードパーティソフトウェアに影響されるべきではありません。新しいシステムのリリース / アップデートをインストールすることによってのみ変更されるでしょう。"/boot/common" は、サードパーティソフトウェアがシステムワイド (すなわち全ユーザー用に) にインストールされる場所で、"/boot/home/config” は、個人ユーザー専用のソフトウェアがインストールされる場所です。これら 2 つの区別はまだあまり意味がないはずですが、Haiku がマルチユーザーをサポートするときには、意味を持つでしょう (明らかに、その結果各ユーザーは自分のホームディレクトリ、たとえば、"/boot/home/<user>" を必要とします)。

また、BeOS から継承したディレクトリ、"/boot/apps"、"/boot/preferences" もあります。パッケージ管理への移行に伴い、それらは、それぞれ、"/boot/common/apps" および "/boot/common/preferences" へのシンボリックリンクになるでしょう。あるいは、それらを完全に削除さえするかもしれません。

これら 3 か所のインストール場所のそれぞれに packagefs インスタンスがマウントされています。各インスタンスは、それらのサブディレクトリ "packages" 内のすべてのパッケージの内容の実際に展開された結合物を表示します。たとえば、"/boot/system/packages" 内のすべてのパッケージファイルの内容を実在するディレクトリに抽出した場合、それは "/boot/system" で packagefs によって表示されるものと正確に一致します。少数の例外を除いて、packagefs はいくつかの追加ディレクトリを提供します。

いわゆる shine-through (透過的な) ディレクトリが BFS ボリュームの下にあります。通常、ディレクトリにマウントされたファイルシステムは、そのディレクトリ内にあるものを完全に隠すでしょう。しかし、これらの shine-through ディレクトリは、特別に処理されます。packagefs はちょうどディレクトリが BFS ボリューム上にあるように表示します。これらのディレクトリのひとつが "packages" です。"packages" 以外では、任意のパッケージを追加、削除、または更新できないので、これは必要なことです。"/boot/common" と "/boot/home/config" には、"settings"、"cache"、および "non-packaged" のようないくつかの shine-through ディレクトリが追加で存在します。"non-packaged"は、ソフトウェアが "これまで通りの"、すなわちパッケージを展開する方法でインストール可能な場所です。

ソフトウェアのインストール

手動インストール

最下位レベルでは、単に "/boot/system"、"/boot/common"、または "/boot/home/config" のいずれかのサブディレクトリ "packages" に、それぞれのパッケージファイルをドロップすることでソフトウェアをインストールできます。packagefs はディレクトリを監視し、新たに追加されたパッケージに満足すれば、その内容をディレクトリ構造に即座に表示します。パッケージはアクティブ化されると言われます。パッケージを削除すると、逆の結果となります。

パッケージが通常依存関係を持っているという事実のために、物事はもう少し複雑になります。たとえば、不満足な依存関係 (たとえばインストールされていない特定のライブラリを必要とする) を持つパッケージを追加しているのに、それでもパッケージをアクティブにすることは良い考えではありません。パッケージの内容 (プログラム、ライブラリ…) は正しく動作しないかもしれません。たとえば、他のインストールされているソフトウェアを隠した場合、以前動いていたものを壊すかもしれません。

それを解決する方法は、パッケージが変更されたときに、packagefs は無分別に勝手に行動しないことです。代わりに、パッケージ管理デーモンが、それはほとんど常に寝ているバックグラウンドプロセスですが、新しい状況を分析し、すべての依存関係が満たされているかどうかチェックします。問題がなければ、デーモンは、要求により、パッケージをアクティブ / 非アクティブにするよう packagefs に伝えます。依存関係に問題がある場合は、それは設定で構成されている方法に従って、デーモンはすぐにユーザーにプロンプトで知らせ、問題解決のためにリモートリポジトリをチェックして、可能な選択肢をユーザーに提示するか、または可能であれば、ユーザーの手を煩わせることなく必要なすべてのアクションを実行します。最終的に、問題が (追加のパッケージをダウンロードすることなどで) 解決できれば、それぞれのパッケージが非アクティブ化 / アクティブ化されるでしょう。解決できない場合は、何も変更されません。

起動時に、常にすべての依存関係をチェックすることを避けるために、パッケージデーモンは、ファイル "packages/administrative/activated-packages" にパッケージアクティベーションの最新の整合性のある状態を書き込みます。packagefs がマウントされているとき、そのファイルを読み込んで、それに指定されたパッケージだけがアクティブになります。ファイルが存在しないか、それに指定されたパッケージが見つからないか、または読み込めない場合は、packagefs は "packages" ディレクトリ内のすべてのパッケージをアクティブ化した状態に戻ります。パッケージデーモンは、起動された時点で、状態をチェックします。

パッケージマネージャー経由のインストール

ソフトウェアの手動インストールはできますが、しかし、より快適な方法は、パッケージマネージャーを使用することです。パッケージマネージャーは、リモートソフトウェアリポジトリの設定可能なリストを持っています。それは、これらのリポジトリでどのソフトウェアが利用可能かということと、どのソフトウェアがローカルにインストールされているかを知っています。ユーザーが、インストール / アンインストールするソフトウェアパッケージを選択後、パッケージの依存関係が解決され、パッケージがダウンロードされ、それらのインストール場所に移動されます。

パッケージマネージャーは、トランザクションディレクトリ、つまり "packages/administrative" ディレクトリ内のサブディレクトリを準備します。そこには、新しいパッケージが含まれています。次に、パッケージマネージャーは、パッケージのアクティベーションの変更を実行するために、パッケージ管理デーモンに (​​パッケージキットを経由して) 連絡します。デーモンは、" packages" ディレクトリに新しいパッケージを移動し、以前の状態ディレクトリ (これもまた、"packages/administrative" ディレクトリ内のサブディレクトリであり、その名称に現在の日付と時刻をエンコードしたものです) に以前のパッケージを移動し、packagefs に個別のパッケージのアクティブ化 / 非アクティブ化を依頼します。以前の状態ディレクトリは、以前の状態の回復を可能にします。それは、システムのインストール場所には特に興味深いものです。セーフモード / リカバリーオプションとして、ブートローダは、最新の状態の代わりに、次に起動できる以前のインストール状態の選択をユーザーに提供しています。

アプリケーションバンドル

また、Haiku は、一般的にアプリケーションバンドルと呼ばれる概念をサポートします。アプリケーションバンドルには、どこにもインストールする必要のない、完全に自己完結型のパッケージです。実装の詳細は、まだに決定されていません。基本的な考え方は、そのようなパッケージの内容を持つ専用の packagefs をマウントするか、すでにマウントされている 3 つの packagefs インスタンスのうちのひとつ (おそらく "/boot/home/config”) にパッケージの内容を表示する特別な場所を持たせることです。Tracker (あるいは libbe) の少しの統合によって、そのようなパッケージがダブルクリックされたとき、マウントされたディレクトリを開かせ、またアプリケーションを起動させます。

インストール場所の順序と一貫性

ソフトウェア用に 3 つの個別のインストール場所を持つことは、その一貫性と相互作用に関するいくつかの考慮を必要とします。インストール場所には明確に定義された順序があります。それは、"boot/home/config/"、"/boot/common"、"/boot/system" の順です。これは、すでに BeOS のコマンド、ライブラリ、およびアドオンが検索される順番でした (環境変数 PATH、LIBRARY_PATH、そして ADDON_PATH によると、"/boot/common " が唯一の計画であったが、今のところは存在しません)。それはたとえば、ユーザーが "/boot/home/config” にプログラムの新しい / 別のバージョンをインストールすることや、"/boot/common" 内のバージョンを上書きすることを認めています。

この順序は、パッケージの依存関係が管理される順番でもある必要があります。それにより、"boot/home/config/" にあるライブラリが "/boot/common" 内のライブラリを上書きすることと、"/boot/common" にインストールされているプログラムが、オーバーライドされたライブラリを使用することを可能にするでしょう。インストール場所にあるパッケージは、順序が前の場所にインストールされたパッケージだけで解決できる依存関係を持ってはいけません。たとえば、"/boot/common" にインストールされたプログラムは "/boot/home/config" だけにインストールされているライブラリに依存してはなりません。マルチユーザーになると、プログラムは一人のユーザーのために動き、ライブラリをインストールしていない別のユーザーのためには動かないことを意味するでしょう。同様に、"/boot/system" は、完全に自己完結型の基本システムです。すべての依存関係が、その中で解決される必要があります。セーフモード起動は、マウントされている "/boot/system" packagefs のみで実行できるべきです。結果として、これらの制約は、ソフトウェアのインストール / アンインストール時に順守される必要があります。

3 つのインストール場所を持つことに伴う別の課題は、いくつかのパッケージがそれらのファイル (たとえばデータファイル)、または依存関係に対して絶対パスでコンパイルされていることです。パッケージの別バージョンを作ることで前者は解決できますが、それは、後者では動かず、どのみち退屈なことでしょう。解決方法は、固定された位置、"/boot/system/package-links" に動的に生成されたシンボリックリンクです。それは、インストールされた各パッケージおよびその依存関係がそれぞれのインストール場所を参照するものです。

インストールされた各パッケージに対して、package (package 名 + バージョン) のような名前のサブディレクトリが自動的に生成されます。そのサブディレクトリには、パッケージ自体のインストール場所を参照するシンボリックリンク ".self" を含んでいるだけでなく、パッケージのそれぞれの依存関係に関して、それらのインストール場所を指すシンボリックリンクを含んでいます。たとえば、"/boot/common" にインストールされている OpenSSH パッケージと、"/boot/system" にインストールされている OpenSSL について、ディレクトリは、次のようになります。

/boot/system/package-links/openssh-5.8p2-1/
	.self		-> ../../common
	haiku		-> ../..
	lib:libssl	-> ../..

別の、互換性のあるバージョンの OpenSSL を "/boot/home/config" にインストールすると、自動的にそれぞれの依存関係のシンボリックリンクを変更するでしょう。いったん完全にマルチユーザーをサポートすると、シンボリックリンクのターゲットはまた、それらをチェックするプロセスのユーザー ID に依存するので、ユーザー専用にインストールされたソフトウェアが正しく処理されます。

シンボリックリンクは、パスが示す位置にインストールされたパッケージの場所に依存しますが、パッケージリンク自体の絶対パスは不変のままです。したがって、パッケージのビルド時にコンパイルでき、パッケージがインストールされている場所に関係なく動作します。

パッケージのリンクが解決するもうひとつの問題は、別の場所にインストールされている同じパッケージの互換性のないバージョンです。たとえば、プログラムとそれが依存する別のプログラムが "/boot/common" にインストールされている場合、後者の非互換のバージョンを "/boot/home/config" にインストールしても、前者を壊しません。それは、依存関係リンクは互換性のあるバージョンを指し続けるからです。ランタイムローダーからの少しの協力で、ライブラリに対しても同様に動作するでしょう。しかしながら、ライブラリの場合、実際にはそれほど問題にはなりません。それは、ライブラリは通常、すでに不一致を防ぐ命名スキームと一致する共有オブジェクトの名前を持っているからです。

ソフトウェアリポジトリ

ソフトウェアリポジトリは、パッケージのコレクションです。それは通常インターネットを経由してアクセス可能です。Haiku のパッケージ管理ソリューションは、パッケージをそこからダウンロードおよびインストールできるソフトウェアリポジトリをいくらでも参照できます。リポジトリの構造は非常に単純です。単にそれは共通のプロトコル (HTTP または FTP) 経由でダウンロード可能な一組のファイルです。HPKR 形式のリポジトリインデックスファイルが 1 つあります。それは、リポジトリで利用可能なすべてのパッケージをそれらの説明および依存情報とともにリストアップします。それはダウンロードされてキャッシュされ、ユーザーインターフェースに情報を表示させ、依存関係ソルバーにローカルで計算を行わせます。他のファイルは、個々のパッケージファイルです。

標準リポジトリ

Haiku 用に 2 つの標準リポジトリがあります。

異なるビルドとリリース用に、これらの 2 つのリポジトリの別のインスタンスがあります。

リポジトリは Haiku の git リポジトリ内のファイルを介して維持されています。各アーキテクチャと各リポジトリ用に、Haiku の git リポジトリはそのリポジトリに対するパッケージをリストアップしたファイルが含まれています。HaikuPorts リポジトリに関しては、パッケージは、それぞれのバージョンでリストアップされます。Haiku リポジトリに関しては、バージョンは暗黙のうちに含まれています。

開発者が HaikuPorts パッケージを更新または追加するときは、常に新しいパッケージファイルは、vmrepo.haiku-os.org アカウントにアップロードされる必要があり、リポジトリのパッケージリストファイルには、それに応じて調節しなければなりません。ヘルパースクリプトは、その両方のステップを実行するために提供されています。その後、変更がコミットされ、vmrepo.haiku-os.org にプッシュする必要があります。サーバー上のプッシュフックが、変化を分析し、開発者のアカウントから、リポジトリのディレクトリに新しいパッケージファイルを移動し、新しいリポジトリのスナップショットを構築します。パッケージファイルが見つからないか壊れている場合、開発者に問題について通知するメッセージとともにプッシュは拒否されます。

公式リリースのリポジトリの作成および更新は、サーバー上で明示的にトリガーする必要があります。いずれの場合にも Haiku リポジトリはビルドサービスによって構築されています。

パッケージキット

パッケージキットには、すべてのパッケージ管理関連タスク用の API が用意されています。それには次のものを含みます。

ローカライズ

パッケージファイルとリポジトリのインデックスファイルは、テキスト文字列を含んでいます-たとえば、パッケージの短い説明および詳細説明 –それらは、ユーザーに示されます。したがって、これらの文字列の翻訳が利用可能でなければなりません。翻訳をパッケージとリポジトリのインデックスファイルに含めるのは実用的ではないので、翻訳は別のファイルで提供されなければなりません。どのようにするかまだ正確に決定されていません。