Radiant-CMS の独自拡張機能を作る

EY-Officeのホームページ作成を Ruby on Rails製CMS Radiant を使う事にしました で予告した、Radiantから静的ページの作成し、公開サーバーへの転送する拡張機能に付いて書きます。

この拡張機能は上の画像のように Radiant のメニューに Deploy というタブが追加され、タブ上のリンクをクリックすると静的ページが作成され、そのページのリンクをクリックすると下の画像のように公開サーバーに scp でファイルコピーを行います。

Radiant 拡張機能の作成方法

Radiant 拡張機能の作成方法 Creating a Link Roll Extension というドキュメントを読むと判ります。おおまかには

  1. 開発用の Radiant環境を作る
  2. extension作成用のコードジェネレータを使い拡張機能のひな形を作る script/generate extension ExtensionName
  3. 設定ファイル ExtensionName_extension.rb を記述。ただし上のドキュメントは古いようで、少し記述方法が変わっています。設定ファイルのコメントを参考にして下さい。
  4. 拡張機能は通常のRuby on Railsアプリと同じ構造をしていますので、Railsプログラマーなら問題なく開発できると思います。

今回作った拡張機能 deploy_web_siteGitHub に置きましたが一部のコードを説明します。

  • 設定ファイル

拡張機能の説明、パス、メニュー (Deploy メニューは Pagesの次に置く)などが書かれています。

require 'radiant-deploy_web_site-extension/version'
class DeployWebSiteExtension < Radiant::Extension
  version RadiantDeployWebSiteExtension::VERSION
  description "deploy static contents to Web-site"
  url "http://www.ey-office.com/deploy_web_site"
  
  def activate
    tab 'Content' do
      add_item "Deploy", "/admin/deploy", :after => "Pages"
    end
  end
end
  • 静的ページの作成

このコードは thumblemonks/radiant-electrocstatic-extensionのコードを元にしました。下のように基本的には各ページのレンダー結果をファイルに書くだけの簡単な処理です。
ただし、radiant-electrocstatic-extensionそのままでは、CSS作成の部分で落ちてしまうので(最新のRadiantに対応してないのかも知れません) アドホックに手を入れました。

  def render_pages(static_path)
    logger("Rendering pages")
    Page.all.each do |p|
      logger(" #{p.id} #{p.title} : #{p.url}")
      if p.published? && p.part(:body).content
        if p.slug =~ /\.[^.]+$/i
          dir, filename = File.dirname(p.url), File.basename(p.url)
        else
          dir, filename = p.url, "index.html"
        end
        FileUtils.mkdir_p(File.join(static_path, dir))
        body = p.render
        body.gsub!(/(href=".*\.html)\/"/, "\\1\"")   # patch ^^;
        File.open(File.join(static_path, dir, filename), 'w') { |io| io.print(body) }
      else
        logger(" Not rendering #{p.id} - #{p.status.name} - #{p.url}")
      end
    end
    log
  end

TODO

現在このプラグインは毎回全てのページを生成して、公開サーバーに全てのHTMLを送っていますが、更新されたコンテンツのみ転送するようにしたいです。