読者です 読者をやめる 読者になる 読者になる

任意のデータ構造をMovableTypeのバックアップ形式に変換する

MovableType perl

 最近誕生日を迎え、いよいよアラサーの域に入り始めたtaiyoh@ttaiyoh)です。
 さて、早速本題ですが、とある案件のとある事情で、データをMovableTypeで読めるように変換する必要が出てきました。
 特定のMTで構築したブログで読めればいいのであれば、xmlrpcを使ってデータをこつこつアップロードすれば問題ありません。が、他のブログでもインポートできるようにしておく必要があるため、汎用性を高めるために、MovableTypeに割と古くからある、記事のインポート/エクスポート機能に対応したフォーマットに出力できるのが最適だろうという結論に至りました。
 もしかしたらMT::*をじっくり読めば、自分の欲しいものが見つかるかもしれませんが、ちょっとそこまで時間が割けないことと、MT::*に依存するのはあまりポータブルではないな、という判断から、この変換器は自分で作ることにしました。
 その成果が、こちらの"Text::MTFormatBuilder"です → taiyoh's Text-MTFormatBuilder at master - GitHub
 作るにあたって、何より、フォーマットに関する仕様がわからないと何もできないので、以下を参考にしました。
  → The Movable Type Import / Export Format
 仕様にしては若干緩い感がありますが、これが一番確実なドキュメントだと思うので、信じることにします><
 フォーマットの概念は割と単純で、"Entry"というエンティティの並びで、エントリのダンプを形成しています。その"Entry"の中身は、本体のほかに、コメント、ping送信先、とそれぞれ分類ができます。以下、Entryの構造を図におこしてみたものです。取り立てて変わってる部分はありません。
mt-entry-entity.png
 フォーマットの仕様には、エントリ内の「本体」「メタデータ」の区分はありません。Text::MTFormatBuilderの構成上、そのほうが都合がいいと(ほぼ勝手に)判断し、あえて分けています。
 さて、Text::MTFormatBuilderの役割は、このエントリのタイトルの通り、任意のデータ構造を、MTのバックアップ形式に変換することです。そのため、極力上記のエンティティの構造を意識するだけにしたかったので、以下のサンプルコードの通り、DSLのように簡単に記述できることを心がけました。

 Text::MTFormatBuilderをuseする際、import実行時の引数として'-Declare'を入れると、DSL用の関数がボコボコとエクスポートされます。あとは、blog_export関数の引数のコードブロック内で必要なエントリのリストをイテレートし、必要な項目を埋めていけば、blog_export関数の帰り値には、MTでインポート可能な形式のバックアップの文字列が出力されます。
 ちなみにこのモジュールは、依存はAny::Mooseのみ(正確にはそれに依存したモジュール含む)となっていますので、ある程度ポータビリティは高められていると思います。そして、例によって例のごとく、ドキュメントを書くところまで進めていませんが><、ひとまずテストは書いておりますし、実装もそこまで大きくはないので、解析は容易ではないかと思います…。
  なお、動作確認をした環境ですが、テストに使用した環境はPerlが5.12.2で、Mouseのバージョンが0.80です。インポート先のMTのバージョンは5.31でした。
 これを読んでくださった方の中で、もし似たような事例に遭遇したとき、このモジュールの存在をちょっと思い出してもらえたらな、と思います。

カヤックでは、楽をするために手間を惜しまない"怠惰"な技術者も募集しています!

(追記:2010-10-28 08:42:00)
 Text::MTFormatBuilderのバージョン0.02.3にて、DSL周りの仕様変更。 → diff
 それに伴い、エントリの表記も若干変更。