Nokogiriへの移行
2011年1月10日
このサイトの大部分、このblikiを含め、XMLからHTMLへの変換プロセスを使って構築されています。私は記事やblikiエントリを独自のXML語彙で書き、これらのソースをあなたが読んでいるHTMLに変換します。2000年に始めた当初はXSLTで行っていました。XSLTのプログラミングはかなり得意になったのですが、使い続けるほどのマゾヒストではないという結論に至りました。バンガロールへのフライト中にRubyでbliki変換器を書くという短い実験の後、REXMLライブラリを使ってRubyに切り替えました。そして今、そのコアライブラリをNokogiriに変更する時が来ました。
Ruby変換器を始めた当時、RubyでXMLを解析するデフォルトの方法はREXMLライブラリでした。癖はありましたが、全体的には気に入っていました。APIは、当時のJavaライブラリよりも確実に使いやすかったです。しかし、時は流れました。REXMLはRubyライブラリなので、libxmlをベースにしたライブラリに比べて遅いです。より使いやすいAPIを提供する他のライブラリが登場しました。
最近、XML解析で人気があるのはNokogiriのようです。その結果、ここ数ヶ月、私はいくつかの変換タスクで試してみたところ、気に入るようになりました。すぐに新しい変換タスクの第一候補になりました。しかし、まだ大きな疑問が残っています。コア変換のためにREXMLを置き換えるべきでしょうか?
最近まで、私の生活はDSL本に支配されていたため、サイト生成コードの本格的な作業は考えていませんでした。それが終わると、まずサイトのデザインを一新し、ガイドページを導入することが優先されました。これには既存のRubyコードを大幅に修正する必要がなかったため、そのままにしていました。しかし、次のステップでは、そのコードの大幅なリファクタリングが必要になり、Nokogiriへの置き換えが私の思考の前面に出てきました。
実際、私はそれを最初に片付けることにしました。理由は2つあります。1つは、変換コードの多くがXMLを操作することに関わっており、そのためにNokogiriのAPIを使いたいからです。2つ目は、私の主な機能テストは、サイトを再構築し、その結果をリリースされたバージョンと比較することです。Nokogiriの速度の優位性(1分に対して10秒)は、それを行う際に重要になります。
変更を行う
XML処理を主に行うプログラムでXMLライブラリを置き換えることは、しばしば困難な作業と見なされます。コード全体にREXMLの呼び出しがあるため、これは非常にグローバルな変更です。私は唯一のプログラマーなので、チームで作業する場合よりもカジュアルにできますが、他の人と作業する場合とほぼ同じ習慣に従います。
基本的な計画は3つのステップに分かれています
- コードとREXMLの間に絶縁層を導入します。これにより、私の変換コードはすべてこの絶縁層を呼び出し、REXMLに呼び出しを渡します。この段階では、絶縁層のインターフェースはREXMLに近いものになります。
- 同じ呼び出しを代わりにNokogiriに渡す絶縁層の代替実装を作成します。これが完了したら、Nokogiriを使ってサイト全体を構築できます。
- インターフェースとアプリケーションコードを調整して、REXMLスタイルからNokogiriスタイルに変更します。最後に絶縁層を削除します。
このアプローチを使ってステップを小さく保ちます。Nokogiriへの切り替えを一度に行うのは大きすぎる変更なので、Nokogiriの実装が完了するまで、サイトがREXMLバージョンで正常に構築できるように、徐々に実装できます。他の人と作業している場合は、手術中に新しい機能を構築する必要があるため、これがより重要になります。このようにして、構築中に徐々に絶縁層に移行させることができます。
絶縁層をそのままにして、実質的にアンチ汚染層にするという議論もあります。Nokogiriとは異なるAPIを使用したい場合は、それが良い考えでしょう。この場合は、Nokogiri APIを積極的に使用したいため、そうしませんでした。もちろん、これはライブラリを変更する際にそれを再構築する必要があることを意味しますが、今のうちに不要なレイヤーを処理するコストを支払うよりも、そのコストを支払う方が良いです。