試験運用中なLinux備忘録・旧記事

はてなダイアリーで公開していた2007年5月-2015年3月の記事を保存しています。

Ubuntu 11.10におけるPython 3を用いたPyGIの使用について

  1. 既存のパッケージはPython 2専用?
  2. Python 3向けパッケージは存在するが...
  3. python3-gobject-cairoは?
    1. ソースパッケージの編集とビルド
    2. 無理に修正する必要はない?

既存のパッケージはPython 2専用?

GObject introspectionとPyGIの概要について」で扱っているPyGIはPyGObjectというパッケージの一部で、Debian/Ubuntuでは「python-gobject」というパッケージによって提供されている。
PyGObject自体は(Ubuntu 11.10に含まれているバージョンの)バージョン3.0.0の時点ではPython 3をサポートしているが、この「python-gobject」は、Ubuntu 11.10の時点ではバージョン2.6系とバージョン2.7系のPythonのみを対象としており、バージョン3系では使えない。

Python 3向けパッケージは存在するが...

Ubuntu 11.10の時点ではこれとは別に「python3-gobject」というパッケージが存在する。これはPython 3でPyGIを用いるための新しいパッケージで、「メールマガジン:PyGIを用いる上での基本的な部分について(概要のおさらい,インストール,名前空間,依存パッケージ,GTK+の簡単な例)」に書いた要領でPython 2と同じようにしてC言語のライブラリの機能を用いることができるようになる。
ところが、Ubuntu 11.10のこのパッケージを用いてGTK+ 3のGtkDrawingAreaというGUI部品にCairoで描画する処理を含んだコードを動かそうとすると正常に描画が行われず、端末には

TypeError: Couldn't find conversion for foreign struct 'cairo.Context'

と表示された。
bugs.launchpad.net/ubuntu/+source/software-center/+bug/829067
を見ると、PyGI用のCairoバインディングのパッケージ「python-gobject-cairo」を追加すれば解決するようだが、このパッケージ(バージョン2.6系と2.7系向け)はインストール済みで、ここでは「python-gobject-cairo」のPython 3向けバージョンが追加で必要ということになる。

python3-gobject-cairoは?

「python3-gobject」という名前のPython 3向けパッケージが存在するため、これに対応する「python3-gobject-cairo」というパッケージが存在するのではないかと探したのだが、見つからなかった。他の一部のディストリではこのような名前のパッケージが存在し、「python-gobject-cairo」パッケージと同様に_gi_cairo.soというファイルが含まれているようだが、Ubuntuにはないようだ。

ソースパッケージの編集とビルド
ソースパッケージ「pygobject」を

$ apt-get source pygobject

取得し、パッケージの構成を確認してみると、

(PyGObject自体はPython 3向けのパッケージが存在することを確認)
$ egrep "Package: .+gobject$" pygobject-3.0.0/debian/control
Package: python-gobject
Package: python3-gobject

(CairoサポートについてはPython 3向けのパッケージが存在しない)
$ egrep "Package: .+cairo$" pygobject-3.0.0/debian/control
Package: python-gobject-cairo

やはりdebian/controlには「python3-gobject-cairo」という記述は見られないものの、ビルドルールのdebian/rulesファイルに気になる記述を見つけた。
[引用]ファイル名: pygobject-3.0.0/debian/rules より

# FIXME: temporary rule until py3cairo gets packaged
build-3.2/configure-stamp: patch-stamp
	dh_testdir
	mkdir -p build-3.2
	cd build-3.2 && \
		PYTHON=/usr/bin/python3.2 CFLAGS="$(CFLAGS)" \
			$(CURDIR)/configure $(configure_flags) --disable-cairo CFLAGS="-g -O2 -I/usr/include/cairo"
	touch $@

この部分から、「py3cairoというパッケージがまだ利用できないために一時的にCairoサポートを無効にしてビルドするようにしている」と想像できる。一方で「py3cairo」のパッケージを調べてみると「python3-cairo-dev」というパッケージの存在が確認できたため、これをインストールした上で上の部分を
[一部]ファイル名: pygobject-3.0.0/debian/rules

build-3.2/configure-stamp: patch-stamp
	dh_testdir
	mkdir -p build-3.2
	cd build-3.2 && \
		PYTHON=/usr/bin/python3.2 CFLAGS="$(CFLAGS)" \
			$(CURDIR)/configure $(configure_flags) --enable-cairo CFLAGS="-g -O2 -I/usr/include/cairo"
	touch $@

とし、パッケージをビルドしてpython3-gobject_3.0.0_[アーキテクチャ].debをインストールすると、Cairoによる描画が正常に機能するようになった。追加されたファイルは/usr/lib/python3/dist-packages/gi/_gi_cairo.cpython-32mu.soで、「cpython-32mu」の部分は

$ python3.2 -c "import sysconfig; print (sysconfig.get_config_var ('SOABI'))"
cpython-32mu

のように取得される文字列となっている。

無理に修正する必要はない?
パッケージを修正することで動作自体は確認できたが、現時点では、Python 3が使いたいという事情がないのであれば、将来のバージョンで標準でPython 3向けのパッケージが用意されるまでは無理に修正作業はせずにPython 2を使用したほうがいいのかもしれない。もちろん、GtkDrawingAreaへのCairoの描画処理を含まないコードを動かすのなら修正の必要はない。

(2011/10/23)ソースパッケージ「pygobject」からPython 3向けの「python3-gobject-cairo」パッケージを追加で作成できるようにパッケージを修正するパッチを作成してUbuntuのpygobjectパッケージにバグ報告をしたが、Ubuntuの方は(Ubuntu向けパッケージのベースとなる)Debianpython-cairoのバージョンが1.8系で止まったままでpy3cairoすらDebianで利用できないという状況を先に解決したいようで、Debian側にpython-cairoのバージョンを更新するために働きかけている。Ubuntu側で「python3-gobject-cairo」パッケージが標準で(PPAを用いずに)利用できるようになるのは、送ったパッチに問題がなかったとしてもかなり後になるかもしれない。

使用したバージョン:

  • Python 3.2.2
  • PyGObject 3.0.0