「Haskell」の版間の差分

提供: ArchWiki
ナビゲーションに移動 検索に移動
(Pkg/AUR テンプレートの更新)
(同期)
25行目: 25行目:
 
}}
 
}}
   
=== リンクの問題 ===
+
== リンクの問題 ==
   
GHC はデフォルトで静的リンクを使用します、動的リンクをするときには {{ic|-dynamic}} フラグを使用します。バージョン [https://git.archlinux.org/svntogit/community.git/commit/trunk?h=packages/ghc&id=7a948cdfb808afd3ce6f93047ae0dc1778e79f9f 8.0.2-1] から、Arch の {{Pkg|ghc}} パッケージには GHC プラットフォームライブラリの静的バージョンが含まれていません。デフォルトのコパイラフラグ機能させるには {{Pkg|ghc-static}} パッケージが必要です。
+
バージョン [https://git.archlinux.org/svntogit/community.git/commit/trunk?h=packages/ghc&id=7a948cdfb808afd3ce6f93047ae0dc1778e79f9f 8.0.2-1] から、Arch の {{Pkg|ghc}} パッケージには GHC プラットフォームライブラリの静的バージョンが含まれていません。''community'' リポジトリの [https://www.archlinux.jp/packages/?q=haskell haskell-*] パッケージも同じです。GHC はデフォルトで静的リ使用します、動的リンクを使うときには {{ic|-dynamic}} フラグを使用します。Cabal の場合、以下のようになります:
  +
  +
$ cabal configure --disable-library-vanilla --enable-shared --enable-executable-dynamic
  +
  +
* {{ic|--disable-library-vanilla}} は静的ライブラリの作成を止めます (プロジェクトにライブラリが含まれる場合)。
  +
* {{ic|--enable-shared}} は共有ライブラリの作成を有効にします (プロジェクトにライブラリが含まれる場合)。
  +
* {{ic|--enable-executable-dynamic}} は実行ファイルで動的リンクを使用します (プロジェクトに実行ファイルが含まれる場合)。
  +
  +
{{ic|~/.cabal/config}} に上記のフラグを設定することで、デフォルトで全てのプロジェクトで動的リンクを使うことができます:
  +
  +
{{hc|~/.cabal/config|
  +
library-vanilla: False
  +
shared: True
  +
executable-dynamic: True
  +
}}
   
 
[[pacman]] でパッケージ化されている Haskell モジュールの多くは動的リンクを使っており、[[AUR]] のパッケージも同様です。GHC はコンパイラのバージョン間で [[w:ja:Application Binary Interface|ABI]] 互換性を維持していないため、パッケージシステムから外れたローカルの開発環境では静的リンクを使うことが推奨されます。
 
[[pacman]] でパッケージ化されている Haskell モジュールの多くは動的リンクを使っており、[[AUR]] のパッケージも同様です。GHC はコンパイラのバージョン間で [[w:ja:Application Binary Interface|ABI]] 互換性を維持していないため、パッケージシステムから外れたローカルの開発環境では静的リンクを使うことが推奨されます。
   
  +
{{Note|この記事では、静的リンクとは完全に静的な ELF バイナリの生成を意味しません。単体の ELF バイナリに静的リンクされるのは Haskell のコードだけで、''glibc'' など他のシステムライブラリは動的リンクされる可能性があります。}}
また、Cabal でデフォルトの静的リンクを使おうとしたときにも問題があります。Cabal で動的リンクを使うには、{{ic|~/.cabal/config}} を編集して {{ic|executable-dynamic: True}} 行を追加してください。
 
  +
  +
=== 静的リンク ===
  +
  +
静的リンクを使うには、最低でも {{Pkg|ghc-static}} パッケージで静的ブートライブラリをインストールする必要があります。ブートライブラリや {{ic|haskell-*}} パッケージでインストールされないライブラリに依存するプロジェクトをビルドできるようになります。
  +
  +
残念ながら、プロジェクトが {{ic|haskell-*}} パッケージのどれかに依存する場合、Cabal は依存関係を解決するときに静的ライブラリが存在しないことを考慮しません。したがって、既存の {{ic|haskell-*}} パッケージを使用しようとすると [https://bugs.archlinux.org/task/54563#comment158808 リンカのエラー] によって静的ライブラリが存在しないことがわかります。{{ic|ghc-static}} と違って、問題を解決するための {{ic|haskell-*-static}} パッケージは存在しません。
  +
  +
問題を回避するために、{{AUR|ghc-pristine}} をインストールして既存の GHC 環境をラッピングして {{ic|/usr/share/ghc-pristine}} に別の GHC 環境を作成することができます。パッケージデータベースにはブートライブラリのみが含まれます。静的リンクでソフトウェアをビルドするときは、ラッピングされたコマンド {{ic|/usr/share/ghc-pristine/bin/ghc}} を実行します。Cabal の場合、以下のようになります:
  +
  +
$ cabal configure --with-compiler=/usr/share/ghc-pristine
  +
  +
{{ic|~/.cabal/config}} を編集することで設定を永続化できます。{{ic|ghc-static}} は依然として必要なので注意してください。
  +
  +
{{ic|ghc-pristine}} の代わりに以下の方法もあります:
  +
  +
* {{ic|cabal install --force-reinstalls}} を手動で実行して対応する {{ic|haskell-*}} パッケージを遮蔽する。既存の {{ic|haskell-*}} パッケージと重なる依存パッケージを全て指定する必要があるため面倒です。
  +
* 完全に分離された GHC 環境を使用する: [https://www.haskell.org/ghc/ GHC] と [https://www.haskell.org/cabal/download.html cabal-install] の公式 Linux バイナリをダウンロードしてどこかに展開する。{{ic|ghc-pristine}} と同じことになりますが、{{ic|ghc-pristine}} の方が必要なディスク容量が小さくてすみます。
  +
  +
=== Cabal で静的にリンクしたパッケージをビルド (共有ライブラリを使用しない) ===
  +
  +
このセクションでは公式の {{Pkg|cabal-install}} パッケージの代わりに [https://hackage.haskell.org/package/cabal-install Hackage] から {{ic|cabal-install}} をインストールする方法を説明します。動的リンクが必要な公式の {{Pkg|cabal-install}} と異なり、Hackage の {{ic|cabal-install}} は [https://downloads.haskell.org/~ghc/latest/docs/html/users_guide/shared_libs.html 共有ライブラリ] を使用せずに Haskell パッケージをビルドします。
  +
  +
原則的に {{ic|cabal-install}} では Haskell のコードをリンクする時に静的・動的どちらの方法も選択できます。Arch では基本的な Haskell ライブラリ ({{ic|haskell-*}} パッケージ) が共有オブジェクト ({{ic|.so}} ファイル) として用意されており Cabal でグローバルにライブラリが登録されるため、静的リンクで同じライブラリを使用すると問題が起こります。リンクの [https://bugs.archlinux.org/task/54563#comment158826 エラー] を避けるために、同じ環境に静的・動的な Haskell パッケージを混在させてはいけません。どちらかのパッケージがグローバルに登録されている場合 ({{ic|ghc-pkg list}} コマンドで確認できます)、Cabal は必要なパッケージを取得しません (必要なパッケージのリンクの種別は関係ありません)。
  +
  +
そのため、インストールする Haskell 関連のパッケージはコンパイルの {{Pkg|ghc}} と静的ブートライブラリの {{Pkg|ghc-static}} だけに限ります ({{Pkg|stack}}, {{Pkg|cabal-helper}}, {{Pkg|cabal-install}}, 公式リポジトリに存在する {{ic|haskell-*}} 動的ライブラリ [https://www.archlinux.jp/packages/?q=haskell-] はインストールしません)。
  +
  +
Haskell パッケージのビルドツールとして [https://www.haskellstack.org/ Stack] を使うこともできます。Stack はデフォルトで静的リンクを使います。Cabal で静的リンクを使ってビルドしたい場合、以下の手順に従うことで Hackage から {{ic|cabal-install}} をインストールできます。ここで [https://haskellstack.org/ Stack] ツールは必要な依存パッケージを取得して {{ic|cabal-install}} をビルドするのに使用します。
  +
  +
まず {{AUR|stack-static}} をインストールしてください。Cabal のコンパイルをブートストラップするのに使用します。依存パッケージとして {{ic|haskell-*}} 動的ライブラリを含む公式 Arch リポジトリのパッケージを使うことはしません。
  +
  +
それから Stack のパッケージインデックスをダウンロードします。Stack は {{ic|cabal-install}} のコンパイルをブートストラップするためだけに使いますが、インストール済みの {{Pkg|ghc}} コンパイルも使用します:
  +
$ stack setup --system-ghc
  +
  +
そして {{ic|cabal-install}} をインストール:
  +
$ stack install --system-ghc cabal-install
  +
  +
新しくインストールされる {{ic|cabal-install}} は共有ライブラリを使わずにコンパイルされ、パッケージをビルドするときにデフォルトで共有ライブラリを使用しません。また、{{ic|cabal-install}} はインストールされた {{Pkg|ghc}} コンパイラを使用します。
   
 
=== Haskell Platform ===
 
=== Haskell Platform ===
41行目: 92行目:
 
[[Arch User Repository|AUR]] のパッケージが存在 ({{AUR|haskell-platform}}{{Broken package link|{{aur-mirror|haskell-platform}}}}) しますが、[[公式リポジトリ]]から[https://bbs.archlinux.org/viewtopic.php?pid=1151382#p1151382 以下のパッケージ]を[[インストール]]することに置き換えられます:
 
[[Arch User Repository|AUR]] のパッケージが存在 ({{AUR|haskell-platform}}{{Broken package link|{{aur-mirror|haskell-platform}}}}) しますが、[[公式リポジトリ]]から[https://bbs.archlinux.org/viewtopic.php?pid=1151382#p1151382 以下のパッケージ]を[[インストール]]することに置き換えられます:
   
* ghc ({{Pkg|ghc}} と {{Pkg|ghc-static}}) — 動的 [https://ghc.haskell.org/trac/ghc/wiki/Commentary/Libraries ブートライブラリ] が付属するコンパイラ静的ブートライブラリ
+
* ghc ({{Pkg|ghc}}) — 動的 [https://ghc.haskell.org/trac/ghc/wiki/Commentary/Libraries ブートライブラリ] ({{Pkg|ghc-libs}}) が付属するコンパイラ静的ブートライブラリ ({{Pkg|ghc-static}}) は別個にインストールが必要です。
* cabal-install ({{Pkg|cabal-install}}) — ''Cabal'' と ''Hackage''コマンラインインタフェイス
+
* cabal-install ({{Pkg|cabal-install}}) — Hackage の依存解決とパッケージの取得に焦点が置かれたビルル。
  +
* stack ({{Pkg|stack}}) — Stackage の厳選されたスナップショットとパッケージの取得に焦点が置かれたビルドツール。
 
* haddock ({{Pkg|haskell-haddock-api}}{{Broken package link|{{aur-mirror|haskell-haddock-api}}}} と {{Pkg|haskell-haddock-library}}) — ドキュメントを生成するためのツール
 
* haddock ({{Pkg|haskell-haddock-api}}{{Broken package link|{{aur-mirror|haskell-haddock-api}}}} と {{Pkg|haskell-haddock-library}}) — ドキュメントを生成するためのツール
* happy ({{Pkg|happy}}) — パーサジェネレータ
 
 
* alex ({{Pkg|alex}}) — 字句解析器ジェネレータ
 
* alex ({{Pkg|alex}}) — 字句解析器ジェネレータ
  +
* happy ({{Pkg|happy}}) — パーサジェネレータ
   
 
また、[https://docs.haskellstack.org/en/stable/install_and_upgrade/#arch-linux] に従って {{Pkg|stack}} を使って Haskell 環境を管理する方法もあります。
 
また、[https://docs.haskellstack.org/en/stable/install_and_upgrade/#arch-linux] に従って {{Pkg|stack}} を使って Haskell 環境を管理する方法もあります。
51行目: 103行目:
 
== Haskell パッケージの管理 ==
 
== Haskell パッケージの管理 ==
   
Haskell ライブラリや実行可能ファイルの多くはパッケージにまとめられています。どれも [http://hackage.haskell.org Hackage] から利用することが可能です。パッケージをインストール・管理する方法は複数存在します。あまり一般的でない方法もこのセクションで説明を行います。
+
Haskell ライブラリや実行可能ファイルの多くはパッケージにまとめられています。どれも [http://hackage.haskell.org Hackage] から利用することが可能です。また、厳選されたパッケージが [https://www.stackage.org Stackage] に存在します。パッケージをインストール・管理する方法は複数存在します:
   
  +
* 以下のどちらか (共存不可):
推奨されるワークフローは以下の通りです:
 
  +
** [[公式リポジトリ]]
* [[公式リポジトリ]]または [[ArchHaskell|ArchHaskell リポジトリ]]は Hakell パッケージの第一のソース (ここでの ''or'' は排他)
 
  +
** [[ArchHaskell|ArchHaskell リポジトリ]]
* [[#cabal-install|cabal-install]] (あるいは sandbox を使用) は Haskell 開発用
 
  +
* [[#cabal-install|cabal-install]]
* [[Arch User Repository]] は他で得られないパッケージのために使用
 
  +
* [[#stack|stack]]
  +
* [[Arch User Repository]]
   
 
[https://github.com/magthe/cblrepo cblrepo] は Linux ディストリビューションの Haskell パッケージを管理するために使用するツールです。これのラッパーである、{{AUR|cabal2pkgbuild-git}}{{Broken package link|{{aur-mirror|cabal2pkgbuild-git}}}} は Hackage パッケージから PKGBUILD を作成することができます。新しい Haskell パッケージを作成することについては [[Haskell パッケージガイドライン]]に詳しく記載があります。
 
[https://github.com/magthe/cblrepo cblrepo] は Linux ディストリビューションの Haskell パッケージを管理するために使用するツールです。これのラッパーである、{{AUR|cabal2pkgbuild-git}}{{Broken package link|{{aur-mirror|cabal2pkgbuild-git}}}} は Hackage パッケージから PKGBUILD を作成することができます。新しい Haskell パッケージを作成することについては [[Haskell パッケージガイドライン]]に詳しく記載があります。
69行目: 123行目:
 
! '''悪い点'''
 
! '''悪い点'''
 
|-
 
|-
| [[公式リポジトリ]] || ArchLinux 開発者が運営、パッケージのバージョンの整合性に問題なし、コンパイル済み || 利用できるパッケージの数が限られる
+
| [[公式リポジトリ]] || ArchLinux 開発者が運営、パッケージのバージョンの整合性に問題なし、コンパイル済み || 利用できるパッケージの数が限られる、動的ライブラリのみ
 
|-
 
|-
 
| [[#ArchHaskell リポジトリ|ArchHaskell リポジトリ]] || ArchHaskell グループが運営、パッケージのバージョンの整合性に問題なし、コンパイル済み || 使用するのに手動で設定が必要
 
| [[#ArchHaskell リポジトリ|ArchHaskell リポジトリ]] || ArchHaskell グループが運営、パッケージのバージョンの整合性に問題なし、コンパイル済み || 使用するのに手動で設定が必要
 
|-
 
|-
| [[#cabal-install|cabal-install]] || 全てのパッケージが利用可能 || インストール先がホームフォルダ、{{Pkg|cabal-install}} [https://ivanmiljenovic.wordpress.com/2010/03/15/repeat-after-me-cabal-is-not-a-package-manager はパッケージマネージャではない]、パッケージのバージョンの整合性に問題がある可能性 (別名 [http://www.haskell.org/haskellwiki/Cabal/Survival#What_is_the_difficulty_caused_by_Cabal-install.3F cabal hell])
+
| [[#cabal-install|cabal-install]] || 全てのパッケージが利用可能、root 権限が不要 || インストール先がホームフォルダ、{{Pkg|cabal-install}} [https://ivanmiljenovic.wordpress.com/2010/03/15/repeat-after-me-cabal-is-not-a-package-manager はパッケージマネージャではない]、パッケージのバージョンの整合性に問題がある可能性 (別名 [http://www.haskell.org/haskellwiki/Cabal/Survival#What_is_the_difficulty_caused_by_Cabal-install.3F cabal hell])
  +
|-
  +
| [[#stack|stack]] || (Stackage にある) 全てのパッケージが利用可能、root 権限が不要 || インストール先がホームフォルダで、バージョンがスナップショットに固定、特定のパッケージを削除するのは難しい
 
|-
 
|-
 
| [[Arch User Repository]] || 始めるのが簡単 || パッケージのメンテナンスがなくなる可能性、パッケージのバージョンの整合性に問題がある可能性
 
| [[Arch User Repository]] || 始めるのが簡単 || パッケージのメンテナンスがなくなる可能性、パッケージのバージョンの整合性に問題がある可能性
85行目: 141行目:
 
=== cabal-install ===
 
=== cabal-install ===
   
  +
[[公式リポジトリ]]から {{Pkg|cabal-install}} をインストールしてください。
{{warning|非推奨の方法です。{{Pkg|cabal-install}} [https://ivanmiljenovic.wordpress.com/2010/03/15/repeat-after-me-cabal-is-not-a-package-manager はパッケージマネージャではない]ことを肝に銘じて下さい。}}
 
   
  +
{{Note|{{ic|cabal-install}} パッケージには "cabal" コマンドラインユーティリティが含まれています。一方、{{ic|Cabal}} は "Cabal" ライブラリを提供するパッケージであり、cabal-install と stack の両方が使用します。}}
{{Note|Haskell 開発での唯一の例外は {{Pkg|cabal-install}} が推奨されるツールだということです。バージョン 1.18 から、cabal には ''sandbox'' システムが装備され異なるバージョンのライブラリをプロジェクトごとに分離することができます。cabal sandbox のイントロダクションは [http://coldwa.st/e/blog/2013-08-20-Cabal-sandbox.html ここ] にあります。}}
 
   
 
==== 準備 ====
 
==== 準備 ====
[[公式リポジトリ]]から {{Pkg|cabal-install}} をインストールしてください。
 
   
 
パスを指定しないでインストールした実行可能ファイルを実行するには、cabal のバイナリフォルダ {{ic|~/.cabal/bin}} を {{ic|$PATH}} 変数に追加する必要があります。シェルの設定ファイルに以下の行を記述することで追加できます ({{Pkg|bash}} の場合 {{ic|~/.bashrc}}、{{Pkg|zsh}} の場合 {{ic|~/.zshrc}}):
 
パスを指定しないでインストールした実行可能ファイルを実行するには、cabal のバイナリフォルダ {{ic|~/.cabal/bin}} を {{ic|$PATH}} 変数に追加する必要があります。シェルの設定ファイルに以下の行を記述することで追加できます ({{Pkg|bash}} の場合 {{ic|~/.bashrc}}、{{Pkg|zsh}} の場合 {{ic|~/.zshrc}}):
96行目: 151行目:
 
cabal sandbox の中で実行したい場合:
 
cabal sandbox の中で実行したい場合:
 
PATH=$PATH:.cabal-sandbox/bin
 
PATH=$PATH:.cabal-sandbox/bin
cabal サンドボックスの中で実行するには以下も追加する必要があります:{{bc|PATH=$PATH:.cabal-sandbox/bin}}
 
   
 
==== パッケージのインストール ====
 
==== パッケージのインストール ====
 
{{bc|
 
{{bc|
$ cabal update
+
1=$ cabal update
  +
$ cabal install <pkg>}}
 
  +
$ # Dynamic linking
  +
$ cabal install --disable-library-vanilla --enable-shared --enable-executable-dynamic ''<pkg>''
  +
  +
$ # Static linking (requires ghc-static and ghc-pristine)
  +
$ cabal install --with-compiler=/usr/share/ghc-pristine/bin/ghc ''<pkg>''
  +
}}
   
 
{{ic|-j}} を追加することで並列コンパイルができます。また、{{ic|--global}} フラグを使うことでシステム全体にパッケージをインストールすることもできますが、これは非推奨です。ユーザーごとのインストールでは、全てのファイルは {{ic|~/.cabal}} に配置されライブラリは {{ic|~/.ghc}} に登録されるので、フォルダを削除することで簡単にクリーンアップすることができます。システム全体にインストールすると、ファイルがファイルシステムに散らばってしまい管理するのが難しくなります。
 
{{ic|-j}} を追加することで並列コンパイルができます。また、{{ic|--global}} フラグを使うことでシステム全体にパッケージをインストールすることもできますが、これは非推奨です。ユーザーごとのインストールでは、全てのファイルは {{ic|~/.cabal}} に配置されライブラリは {{ic|~/.ghc}} に登録されるので、フォルダを削除することで簡単にクリーンアップすることができます。システム全体にインストールすると、ファイルがファイルシステムに散らばってしまい管理するのが難しくなります。
  +
  +
==== サンドボックス ====
  +
  +
Cabal のサンドボックスは矛盾のないローカルパッケージデータベースと環境を提供します (Python における virtual-env あるいは Ruby における rvm に似ています)。カレントディレクトリにサンドボックスを作成するには:
  +
  +
$ cabal sandbox init
  +
  +
削除するには:
  +
  +
$ cabal sandbox delete
  +
  +
カレントディレクトリにサンドボックスが存在する場合、デフォルトで cabal はその環境を使用します。[[#パッケージのインストール]]と同じ手順でインストールができます。別のサンドボックスを使いたい場合、{{ic|cabal exec "$SHELL"}} を実行してサンドボックスのシェルを起動します。そこからディレクトリを移動しても cabal は指定されたサンドボックスを使用します。また、cabal に {{ic|1=--sandbox-config-file=''/somewhere''/cabal.sandbox.config}} フラグを渡して使うことも可能です。
  +
  +
cabal のサンドボックスの中で実行ファイルを実行するには、{{bc|PATH&#61;$PATH:$PWD/.cabal-sandbox/bin}} を設定するか、{{ic|cabal exec "$SHELL"}} でローカルシェルを起動する必要があります。
   
 
==== パッケージの削除 ====
 
==== パッケージの削除 ====
 
パッケージの削除を簡単に行う方法はありません。Cabal には削除機能がありません。
 
パッケージの削除を簡単に行う方法はありません。Cabal には削除機能がありません。
  +
  +
サンドボックスにインストールした場合、他のサンドボックスへの影響を及ぼさずに削除することができます。
   
 
zsh の自動補完を使うことで haskell パッケージを探し出しやすくなります。
 
zsh の自動補完を使うことで haskell パッケージを探し出しやすくなります。
   
Haskell のパッケーシステム全体を修正・再インストールしたい場合、{{ic|~/.cabal}} と {{ic|~/.ghc}} を削除してスクラッチからインストールしなおしてください。
+
Haskell のパッケーシステム全体を修正・再インストールしたい場合、{{ic|~/.cabal}} と {{ic|~/.ghc}} を削除してスクラッチからインストールしなおしてください。GHC をアップグレードした場合に必要になります
  +
  +
=== stack ===
  +
  +
[https://haskellstack.org Stack] は依存関係の解決よりも自動的に精選された、矛盾のないパッケージに焦点を置いたビルドツールです。Stackage スナップショットの中で共存させる限り、バージョンの衝突に気をつかうことなくパッケージを簡単にインストールすることができます。Stack は {{Pkg|stack}} または {{AUR|stack-static}} パッケージでインストールできます。後者は静的リンクライブラリを提供し、様々な {{ic|haskell-*}} 依存パッケージを必要としません。詳しくは [https://docs.haskellstack.org/en/stable/install_and_upgrade/#arch-linux § Install/upgrade # Arch Linux] を参照。
   
 
== 参照 ==
 
== 参照 ==

2017年10月19日 (木) 00:59時点における版

Haskell は汎用の純関数型プログラミング言語です。

インストール

Haskell は Linux でネイティブに実行することができるマシンコードを生成します。(コンパイル済みの) バイナリのソフトウェアを実行するのに特別なものは必要ありません。公式リポジトリArchHaskell で提供されているソフトウェアと同じです。一方、AUR のパッケージやソースコードは、ソフトウェアをビルドするのにコンパイラを必要とします。

コンパイラをインストールするだけで Haskell のソースコードがビルドできるようになります。Haskell での開発を始めるためのツールのコンプリートセットである Haskell-Platform もあります。

コンパイラ

Haskell のソースコードをネイティブコードにビルドするには、コンパイラをインストールする必要があります。複数の 実装 が存在しますが、一番よく使われている (事実上のリファレンス実装となっている) のは GHC (Glasgow Haskell Compiler) です。公式リポジトリの ghc でインストールができます。

次のファイルを用意して:

Main.hs
main = putStrLn "Hello, World"

以下を実行して試すことができます:

$ ghc -dynamic Main.hs
$ ./Main 
Hello, World

リンクの問題

バージョン 8.0.2-1 から、Arch の ghc パッケージには GHC プラットフォームライブラリの静的バージョンが含まれていません。community リポジトリの haskell-* パッケージも同じです。GHC はデフォルトで静的リンクを使用します、動的リンクを使うときには -dynamic フラグを使用します。Cabal の場合、以下のようになります:

$ cabal configure --disable-library-vanilla --enable-shared --enable-executable-dynamic
  • --disable-library-vanilla は静的ライブラリの作成を止めます (プロジェクトにライブラリが含まれる場合)。
  • --enable-shared は共有ライブラリの作成を有効にします (プロジェクトにライブラリが含まれる場合)。
  • --enable-executable-dynamic は実行ファイルで動的リンクを使用します (プロジェクトに実行ファイルが含まれる場合)。

~/.cabal/config に上記のフラグを設定することで、デフォルトで全てのプロジェクトで動的リンクを使うことができます:

~/.cabal/config
library-vanilla: False
shared: True
executable-dynamic: True

pacman でパッケージ化されている Haskell モジュールの多くは動的リンクを使っており、AUR のパッケージも同様です。GHC はコンパイラのバージョン間で ABI 互換性を維持していないため、パッケージシステムから外れたローカルの開発環境では静的リンクを使うことが推奨されます。

ノート: この記事では、静的リンクとは完全に静的な ELF バイナリの生成を意味しません。単体の ELF バイナリに静的リンクされるのは Haskell のコードだけで、glibc など他のシステムライブラリは動的リンクされる可能性があります。

静的リンク

静的リンクを使うには、最低でも ghc-static パッケージで静的ブートライブラリをインストールする必要があります。ブートライブラリや haskell-* パッケージでインストールされないライブラリに依存するプロジェクトをビルドできるようになります。

残念ながら、プロジェクトが haskell-* パッケージのどれかに依存する場合、Cabal は依存関係を解決するときに静的ライブラリが存在しないことを考慮しません。したがって、既存の haskell-* パッケージを使用しようとすると リンカのエラー によって静的ライブラリが存在しないことがわかります。ghc-static と違って、問題を解決するための haskell-*-static パッケージは存在しません。

問題を回避するために、ghc-pristineAUR をインストールして既存の GHC 環境をラッピングして /usr/share/ghc-pristine に別の GHC 環境を作成することができます。パッケージデータベースにはブートライブラリのみが含まれます。静的リンクでソフトウェアをビルドするときは、ラッピングされたコマンド /usr/share/ghc-pristine/bin/ghc を実行します。Cabal の場合、以下のようになります:

$ cabal configure --with-compiler=/usr/share/ghc-pristine

~/.cabal/config を編集することで設定を永続化できます。ghc-static は依然として必要なので注意してください。

ghc-pristine の代わりに以下の方法もあります:

  • cabal install --force-reinstalls を手動で実行して対応する haskell-* パッケージを遮蔽する。既存の haskell-* パッケージと重なる依存パッケージを全て指定する必要があるため面倒です。
  • 完全に分離された GHC 環境を使用する: GHCcabal-install の公式 Linux バイナリをダウンロードしてどこかに展開する。ghc-pristine と同じことになりますが、ghc-pristine の方が必要なディスク容量が小さくてすみます。

Cabal で静的にリンクしたパッケージをビルド (共有ライブラリを使用しない)

このセクションでは公式の cabal-install パッケージの代わりに Hackage から cabal-install をインストールする方法を説明します。動的リンクが必要な公式の cabal-install と異なり、Hackage の cabal-install共有ライブラリ を使用せずに Haskell パッケージをビルドします。

原則的に cabal-install では Haskell のコードをリンクする時に静的・動的どちらの方法も選択できます。Arch では基本的な Haskell ライブラリ (haskell-* パッケージ) が共有オブジェクト (.so ファイル) として用意されており Cabal でグローバルにライブラリが登録されるため、静的リンクで同じライブラリを使用すると問題が起こります。リンクの エラー を避けるために、同じ環境に静的・動的な Haskell パッケージを混在させてはいけません。どちらかのパッケージがグローバルに登録されている場合 (ghc-pkg list コマンドで確認できます)、Cabal は必要なパッケージを取得しません (必要なパッケージのリンクの種別は関係ありません)。

そのため、インストールする Haskell 関連のパッケージはコンパイルの ghc と静的ブートライブラリの ghc-static だけに限ります (stack, cabal-helper, cabal-install, 公式リポジトリに存在する haskell-* 動的ライブラリ [1] はインストールしません)。

Haskell パッケージのビルドツールとして Stack を使うこともできます。Stack はデフォルトで静的リンクを使います。Cabal で静的リンクを使ってビルドしたい場合、以下の手順に従うことで Hackage から cabal-install をインストールできます。ここで Stack ツールは必要な依存パッケージを取得して cabal-install をビルドするのに使用します。

まず stack-staticAUR をインストールしてください。Cabal のコンパイルをブートストラップするのに使用します。依存パッケージとして haskell-* 動的ライブラリを含む公式 Arch リポジトリのパッケージを使うことはしません。

それから Stack のパッケージインデックスをダウンロードします。Stack は cabal-install のコンパイルをブートストラップするためだけに使いますが、インストール済みの ghc コンパイルも使用します:

$ stack setup --system-ghc

そして cabal-install をインストール:

$ stack install --system-ghc cabal-install

新しくインストールされる cabal-install は共有ライブラリを使わずにコンパイルされ、パッケージをビルドするときにデフォルトで共有ライブラリを使用しません。また、cabal-install はインストールされた ghc コンパイラを使用します。

Haskell Platform

Haskell での開発を簡単に始められる、haskell-platform バンドルは次のように説明されます:

Haskell のプログラミングを始める一番簡単な方法です。立ち上げて動作させるのに必要な全てが入っています。次のように考えて下さい "Haskell: batteries included" (電池付属)。

AUR のパッケージが存在 (haskell-platformAUR[リンク切れ: アーカイブ: aur-mirror]) しますが、公式リポジトリから以下のパッケージインストールすることに置き換えられます:

  • ghc (ghc) — 動的 ブートライブラリ (ghc-libs) が付属するコンパイラ。静的ブートライブラリ (ghc-static) は別個にインストールが必要です。
  • cabal-install (cabal-install) — Hackage の依存解決とパッケージの取得に焦点が置かれたビルドツール。
  • stack (stack) — Stackage の厳選されたスナップショットとパッケージの取得に焦点が置かれたビルドツール。
  • haddock (haskell-haddock-api[リンク切れ: アーカイブ: aur-mirror]haskell-haddock-library) — ドキュメントを生成するためのツール
  • alex (alex) — 字句解析器ジェネレータ
  • happy (happy) — パーサジェネレータ

また、[2] に従って stack を使って Haskell 環境を管理する方法もあります。

Haskell パッケージの管理

Haskell ライブラリや実行可能ファイルの多くはパッケージにまとめられています。どれも Hackage から利用することが可能です。また、厳選されたパッケージが Stackage に存在します。パッケージをインストール・管理する方法は複数存在します:

cblrepo は Linux ディストリビューションの Haskell パッケージを管理するために使用するツールです。これのラッパーである、cabal2pkgbuild-gitAUR[リンク切れ: アーカイブ: aur-mirror] は Hackage パッケージから PKGBUILD を作成することができます。新しい Haskell パッケージを作成することについては Haskell パッケージガイドラインに詳しく記載があります。

方法ごとのプラス面とマイナス面

以下の表はそれぞれのパッケージ管理方法のメリットとデメリットのまとめです。

方法 良い点 悪い点
公式リポジトリ ArchLinux 開発者が運営、パッケージのバージョンの整合性に問題なし、コンパイル済み 利用できるパッケージの数が限られる、動的ライブラリのみ
ArchHaskell リポジトリ ArchHaskell グループが運営、パッケージのバージョンの整合性に問題なし、コンパイル済み 使用するのに手動で設定が必要
cabal-install 全てのパッケージが利用可能、root 権限が不要 インストール先がホームフォルダ、cabal-install はパッケージマネージャではない、パッケージのバージョンの整合性に問題がある可能性 (別名 cabal hell)
stack (Stackage にある) 全てのパッケージが利用可能、root 権限が不要 インストール先がホームフォルダで、バージョンがスナップショットに固定、特定のパッケージを削除するのは難しい
Arch User Repository 始めるのが簡単 パッケージのメンテナンスがなくなる可能性、パッケージのバージョンの整合性に問題がある可能性

ArchHaskell リポジトリ

詳細は ArchHaskell を見て下さい。

cabal-install

公式リポジトリから cabal-install をインストールしてください。

ノート: cabal-install パッケージには "cabal" コマンドラインユーティリティが含まれています。一方、Cabal は "Cabal" ライブラリを提供するパッケージであり、cabal-install と stack の両方が使用します。

準備

パスを指定しないでインストールした実行可能ファイルを実行するには、cabal のバイナリフォルダ ~/.cabal/bin$PATH 変数に追加する必要があります。シェルの設定ファイルに以下の行を記述することで追加できます (bash の場合 ~/.bashrczsh の場合 ~/.zshrc):

PATH=$PATH:~/.cabal/bin

cabal sandbox の中で実行したい場合:

PATH=$PATH:.cabal-sandbox/bin

パッケージのインストール

$ cabal update

$ # Dynamic linking
$ cabal install --disable-library-vanilla --enable-shared --enable-executable-dynamic <pkg>

$ # Static linking (requires ghc-static and ghc-pristine)
$ cabal install --with-compiler=/usr/share/ghc-pristine/bin/ghc <pkg>

-j を追加することで並列コンパイルができます。また、--global フラグを使うことでシステム全体にパッケージをインストールすることもできますが、これは非推奨です。ユーザーごとのインストールでは、全てのファイルは ~/.cabal に配置されライブラリは ~/.ghc に登録されるので、フォルダを削除することで簡単にクリーンアップすることができます。システム全体にインストールすると、ファイルがファイルシステムに散らばってしまい管理するのが難しくなります。

サンドボックス

Cabal のサンドボックスは矛盾のないローカルパッケージデータベースと環境を提供します (Python における virtual-env あるいは Ruby における rvm に似ています)。カレントディレクトリにサンドボックスを作成するには:

$ cabal sandbox init

削除するには:

$ cabal sandbox delete

カレントディレクトリにサンドボックスが存在する場合、デフォルトで cabal はその環境を使用します。#パッケージのインストールと同じ手順でインストールができます。別のサンドボックスを使いたい場合、cabal exec "$SHELL" を実行してサンドボックスのシェルを起動します。そこからディレクトリを移動しても cabal は指定されたサンドボックスを使用します。また、cabal に --sandbox-config-file=/somewhere/cabal.sandbox.config フラグを渡して使うことも可能です。

cabal のサンドボックスの中で実行ファイルを実行するには、

PATH=$PATH:$PWD/.cabal-sandbox/bin

を設定するか、cabal exec "$SHELL" でローカルシェルを起動する必要があります。

パッケージの削除

パッケージの削除を簡単に行う方法はありません。Cabal には削除機能がありません。

サンドボックスにインストールした場合、他のサンドボックスへの影響を及ぼさずに削除することができます。

zsh の自動補完を使うことで haskell パッケージを探し出しやすくなります。

Haskell のパッケーシステム全体を修正・再インストールしたい場合、~/.cabal~/.ghc を削除してスクラッチからインストールしなおしてください。GHC をアップグレードした場合に必要になります。

stack

Stack は依存関係の解決よりも自動的に精選された、矛盾のないパッケージに焦点を置いたビルドツールです。Stackage スナップショットの中で共存させる限り、バージョンの衝突に気をつかうことなくパッケージを簡単にインストールすることができます。Stack は stack または stack-staticAUR パッケージでインストールできます。後者は静的リンクライブラリを提供し、様々な haskell-* 依存パッケージを必要としません。詳しくは § Install/upgrade # Arch Linux を参照。

参照