Powered by SmartDoc

mod_chxj

29 Mar 2005
Atsushi Konno

目次

Overview

mod_chxjはオープンソースの携帯向けコンテンツ変換Apache2.0用モジュールであり、CHTML(DoCoMo i-Mode用CHTML3.0)で記述された文書を、アクセスに来た端末のUser-Agentヘッダを見て、それぞれの端末にあった形式に変換します。HTML文書に限らず、画像(jpg、gif、png)、絵文字についても、定義ファイルに従ってそれぞれのキャリアにあった絵文字に変換します。

時代遅れの感はありますが・・・。

インストール

準備

mod_chxjをインストールする前に、下記のものを用意する必要があります。

  1. Apache2.0のヘッダーファイル群
  2. Apache2.0用のapxs
  3. apr(Apache Portable Runtime)ライブラリとそのヘッダファイル郡
  4. automake、autoconf、libtool1.3.X
  5. ImageMagick(MagickWand)
  6. Linux

mod_chxjの入手

mod_chxjはこちらからダウンロードすることができます。

インストール

以下にmod_chxjインストール手順を示します。

  1. Configureスクリプトを生成します

    Configure スクリプトの生成
    $ ./buildconf.sh
    

    (1)

  2. Configure

    以下は、/usr/include/apache2.0に、Apache2.0のヘッダーファイルが存在する場合です。

    Configure
    $ ./configure --with-apache-header=/usr/include/apache2.0
    

    (2)(3)

  3. mod_chxj.soを生成します
    make
    $ make
    
  4. apacheにインストールします
    install
    $ make install
    
  5. データの設置etcディレクトリは以下のdevice_data.xmlとemoji.xmlをApacheからアクセスできるところに配置します。

    以下、/etc/apache2/chxjディレクトリにchxj用設定ファイルを用意する場合

    データの設置
    $ mkdir -p /etc/apache2/chxj
    $ cp etc/device_data.xml /etc/apache2/chxj
    $ cp etc/emoji.xml /etc/apache2/chxj
    
  1. "$"はプロンプトをあらわします。
  2. --with-apache-headerは必須です。
  3. FreeBSD等の場合は--with-iconvも必須です。

Configuration

以下はmod_chxjが/usr/lib/apache2/modulesディレクトリ配下に設置されたものとしています

htmlファイルが変換対象の場合

例として、Locationが"/chxj"以下のものは全て変換する場合を説明します。

  1. httpd.confに以下を追加します。
    httpd.conf
    #====================================================================================
    # モジュールをApache2.0にロード
    #====================================================================================
    LoadModule chxj_module /usr/lib/apache2/modules/mod_chxj.so
    
    #====================================================================================
    # デバイスデータファイルの設定
    #====================================================================================
    ChxjLoadDeviceData  /etc/apache2/chxj/device_data.xml
    
    #====================================================================================
    # 絵文字データファイルの設定
    #====================================================================================
    ChxjLoadEmojiData   /etc/apache2/chxj/emoji.xml
    
    #====================================================================================
    # 変換エンジン動作指示命令(下記のSetOutputFilter、SetInputFilterも必須です)
    # ChxjConvRule ==> ディレクティブ
    # "^/chxj.+$"  ==> Perl互換のURIパターン
    # EngineOn     ==> 変換エンジンを動作させる指示
    # NONE         ==> サーバ側の文字コード。(NONEを指定した場合は文字コード変換しない)
    #====================================================================================
    ChxjConvertRule "^/chxj.+$" "EngineOn" "NONE"
    
    #====================================================================================
    # 変換させる対象の設定
    #====================================================================================
    <Location /chxj>
      SetOutputFilter chxj_output_filter
      SetInputFilter  chxj_input_filter
    </Location>
    
  2. apacheの再起動。

php等の出力結果が変換対象の場合

  1. httpd.confに以下を追加します
    httpd.conf
    #====================================================================================
    # モジュールをApache2.0にロード
    #====================================================================================
    LoadModule chxj_module /usr/lib/apache2/modules/mod_chxj.so
    
    #====================================================================================
    # デバイスデータの設定
    #====================================================================================
    ChxjLoadDeviceData  /etc/apache2/chxj/device_data.xml
    
    #====================================================================================
    # 絵文字データの設定
    #====================================================================================
    ChxjLoadEmojiData   /etc/apache2/chxj/emoji.xml
    
    #====================================================================================
    # 変換エンジン動作指示命令(下記のSetOutputFilter、SetInputFilterも必須です)
    # ChxjConvRule ==> ディレクティブ
    # "^/chxj.+$"  ==> Perl互換のURIパターン
    # EngineOn     ==> 変換エンジンを動作させる指示。動作させたく無い場合は"EngineOff"
    # EUC-JP       ==> サーバ側の文字コード。(NONEを指定した場合は文字コード変換しない)
    #                  EUC-JPからCP932に文字コード変換します。
    #====================================================================================
    ChxjConvertRule "^/chxj.+$" "EngineOn" "EUC-JP"
    
    <Location /chxj>
      SetOutputFilter chxj_output_filter
      SetInputFilter  chxj_input_filter
    </Location>
    
  2. apacheの再起動。

mod_jk2を使用したtomcatの出力結果が変換対象の場合

  1. httpd.confに以下を追加します

    httpd.conf
    #====================================================================================
    # モジュールをApache2.0にロード
    #====================================================================================
    LoadModule chxj_module /usr/lib/apache2/modules/mod_chxj.so
    
    #====================================================================================
    # デバイスデータの設定
    #====================================================================================
    ChxjLoadDeviceData  /etc/apache2/chxj/device_data.xml
    
    #====================================================================================
    # 絵文字データの設定
    #====================================================================================
    ChxjLoadEmojiData   /etc/apache2/chxj/emoji.xml
    
    #====================================================================================
    # 変換エンジン動作指示命令(下記のSetOutputFilter、SetInputFilterも必須です)
    # ChxjConvRule ==> ディレクティブ
    # "^/chxj.+$"  ==> Perl互換のURIパターン
    # EngineOn     ==> 変換エンジンを動作させる指示。動作させたく無い場合は"EngineOff"
    # EUC-JP       ==> サーバ側の文字コード。(NONEを指定した場合は文字コード変換しない)
    #                  EUC-JPからCP932に文字コード変換します。
    #====================================================================================
    ChxjConvertRule "^/chxj.+$" "EngineOn" "EUC-JP"
    
    <Location /chxj>
       SetOutputFilter chxj_output_filter
    </Location>
    

    (4)

  2. chxjfilter-0.0.1.jarを生成します
    1. build.propertiesを環境に合わせて編集します
      build.propertiesの編集
      $ cd java
      $ vi build.properties
      
    2. chxjfilter-0.0.1.jarを生成します
      コンパイル
      $ ant dist
      
    3. 生成されたchxjfilter-0.0.1.jarにクラスパスをとおします
  3. web.xmlの編集し、以下を追加します。
    web.xml
    <filter>
       <filter-name>chxjfilter</filter-name>
       <filter-class>com.qsdn.filter.CHXJFilter</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>chxjfilter</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>
    
  4. apache等の再起動
  1. 注意:input_filterは設定しないでください!!!

画像自動変換機能を使用する場合

  1. httpd.confに以下を追加します。下記は、URIが/imgで始まる全ての画像に対して動作するようmod_chxjに指示しています。

    httpd.conf
    <Location /img>
    ChxjImageEngine On
    ChxjImageCacheDir /tmp
    ChxjImageCopyright "A.Konno"
    </Location>
    

    上記の説明を以下に示します。

    1. ChxjImageEngine

      mod_chxjの画像変換ハンドラを起動するよう指示しています。DefaultはOff





    2. ChxjImageCacheDir

      mod_chxj画像変換ハンドラが使用する変換後の画像をおいておくディレクトリを指定します。デフォルトは/tmp。

      ChxjImageCacheDir
            ChxjImageCacheDir /tmp
            
      

      mod_chxjに画像変換キャッシュとして/tmpを使用するよう指示します。



    3. ChxjImageCopyright

      mod_chxjの画像変換ハンドラに、転送禁止設定を行うよう指示します。パラメータとして任意の文字列をとります。ChxjImageCopyrightディレクティブで指定された文字列は、それぞれのイメージのコメント部に埋め込まれます。

      ChxjImageCopyright
            ChxjImageCopyright "A.Konno"
            
      

      mod_chxjに転送禁止設定を行うよう指示しています。変換後イメージのコメント部分には、キャリア毎に以下の文字列を埋め込みます。

      AU の場合

      AU
             kddi_copyright=on,A.Konno
             
      

      DoCoMoの場合

      DoCoMo
      copy="NO",A.Konno
      

      Vodafoneの場合は、レスポンスヘッダに

      Vodafone/J-PHONE
               x-jphone-copyright:no-transfer
             
      

      を埋め込みます。(5)

  1. Vodafoneの場合は、リクエストURLの最後が.pnzか、.jpzで終わるようにダミーを付けなければなりません。

文字コードを変換したい場合(EXPERIMENTAL)

  1. httpd.confに以下を追加します。下記は、URIが/chxjで始まる全てのコンテンツに対して動作するようmod_chxjに指示しています。サーバ側はEUC-JPであった場合の例です。mod_chxjによってSJISに変換するように指示しています。

    httpd.conf
    ChxjConvRule "^/chxj.+$" "EngineOn" "EUC-JP"
    

    上記の説明を以下に示します。

    1. ChxjConvertRule

      サーバサイドの文字コードを指定します。ここに、EUC-JPと指定してあった場合は、EUC-JPからCP932に変換後、クライアントに出力されます。省略した場合はNONE

      1. 変換エンジン動作指示命令(下記のSetOutputFilter、SetInputFilterも必須です)

        ChxjConvertRule ==>ディレクティブ

        "^/chxj.+$" ==> Perl互換のURIパターン

        EngineOn ==>変換エンジンを動作させる指示。動作させたく無い場合は"EngineOff"

        EUC-JP ==>サーバ側の文字コード。(NONEを指定した場合は文字コード変換しない)



        EUC-JPからCP932に文字コード変換します。(libiconvに依存します)





ディレクティブ

  1. ChxjLoadDeviceData

    デバイス定義ファイルを指定します。
    ex)
        ChxjLoadDeviceData /etc/apache2/device.xml
      
    
  2. ChxjLoadEmojiData

    絵文字変換定義ファイルを指定します。
    ex)
        ChxjLoadEmojiData   /etc/apache2/chxj/emoji.xml
      
    
  3. ChxjImageEngine

    画像変換エンジンを有効にします。パラメータとしてOnとOffを指定できます。DefaultはOffです。
    ex)
        ChxjImageEngine On
      
    
  4. ChxjImageCacheDir

    イメージの一時ファイル保存場所を指定します。
    ex)
        ChxjImageCacheDir   /tmp
      
    
  5. ChxjImageCopyright

    イメージに著作権情報を付与します。
    ex)
        ChxjImageCacheDir   "chosakuken jyoho"
      
    
  6. ChxjConvertRule

    HTML変換エンジンの適用ルールを記述します。本ディレクティブを使用し、変換エンジンのOn|Offを指定します。DefaultはOFFです。また、ルールは記述された順番に評価し、マッチするものがあれば、その時点で対象ルールを適用します。パラメータは3つ必要です。下記にパラメータを記します。
    パラメータ
    第1パラメータ URIを評価するPerl互換の正規表現を指定します
    第2パラメータ HTML変換エンジンのOn|Offを指定します。Onの場合は"EngineOn"。Offの場合は"EngineOff"を指定します。
    第3パラメータ 文字コードを指定します。ここで指定した文字コードから"CP932"に変換します。指定できる文字コードはiconv -lコマンドによって確認することができます。変換しなくて良い場合はNONEを指定してください。
    第4パラメータ 省略した場合は、携帯ページからの変換を意味します。PC用ページからの変換を行う場合は"PC"を第四パラメータに指定します。
    ex)
        ChxjConvertRule "^/chxj.+$/" EngineOn EUC-JP
      
    

対応するCHTMLタグ

変換可能なCHTMLタグは以下のとおりです。

対応タグ一覧
タグ 属性 CHTML HDML XHTML JHTML 備考
<HTML> 属性を指定した場合は無視します
<META> http-equiv × CHTML1.0、HDMLでは無視します
content × CHTML1.0、HDMLでは無視します
<HEAD> 属性を指定した場合は無視します
<TITLE> 属性を指定した場合は無視します
<BASE> × HDMLでは無視します
<BODY> bgcolor × HDML、CHTML1.0、CHTML2.0では無視します
text × HDML、CHTML1.0、CHTML2.0では無視します
link × HDML、CHTML1.0、CHTML2.0では無視します
<A> href
accesskey
<BR>
<FONT> color × HDML,CHTML1.0では無視します
<FORM> action
method × HDMLでは無視します
<INPUT> name
type text,password,hidden,radio,checkbox,submitに対応
value
istyle
<SELECT< name
size × HDMLでは無視します
<OPTION> value (7)
checked
<DIV> align
<HR>
<CENTER>
<IMG> src
<CHXJ:IF> lang lang="chtml" lang="xhtml" lang="hdml" lang="jhtml"が指定できます
  1. 必ず閉じてください。そのうち対応します。

独自拡張タグ

  1. <CHXJ:IF>

    <CHXJ:IF>タグと</CHXJ:IF>タグではさまれたタグやテキストは、変換せずにそのまま(8)出力します。必須の属性としてlangがあります。lang属性を指定することによって、例えば、「HDML機の場合のみ出力させる」といったことを可能にします。



    ex)

    HTML文書中にHDML機の場合のみ有効にしたいタグ、または文書がある場合
           <CHXJ:IF lang="HDML" >
             <NODISPLAY>
    <ACTION TYPE=ACCEPT TASK=GOSUB \
        DEST='device:data/dnld?url=abc&name=abc.jpg&size=100&disposition=devjaww&title=test'> \
             </NODISPLAY>
           </CHXJ:IF>
           
    



    ex)

    i-Modeのみ出力したい文書がある場合
           <CHXJ:IF lang="chtml" >
             シークレットコードがどーのこーの。
           </CHXJ:IF>
           
    



    また、lang属性は、複数指定することも可能です。

    HDML機,J-PHONE機は以下を出力します
           <CHXJ:IF lang="chtml" lang="jhtml">
           あなたの携帯は、HDML機かJ-HTML機です。
           </CHXJ:IF>
           
    



  1. 変換しませんので注意が必要です

文字コード

文字コードは、絵文字の入出力がある関係上、Shift_JISのみとしています。

絵文字について

i-Mode用の絵文字を書いておけば、アクセスしたキャリアによって、mod_chxjが対応の絵文字に自動変換します。ソースに2byteのバイナリコードを直接書いても、10進参照文字列(9)(&#XXX;の形)で書いても、どちらでも変換対象になります。10進参照文字列で書いた場合は、mod_chxjにより、自動で2バイトコードに変換します。

  1. 16進参照文字列には対応していません

絵文字変換定義

絵文字の変換に関する動作を変えたい場合(例えば「ハートがあったら、AUの場合はスペードに」とか、「変換定義がおかしい」といった場合)は、emoji.xmlファイルを直接編集することによって定義を変更することが可能です。emoji.xmlはXMLファイルとなっていますので、vi等で簡単に定義を変更することができます(10)



以下に、emoji.xmlファイルの一部を記します。

emoji.xml
<?xml encoding="Shift_JIS" >

<emoji>
  <set>
    <no>1</no>
    <imode>
      <hex1>f8</hex1>
      <hex2>9f</hex2>
      <string>&#63647;</string>
      <description></description>
    </imode>
    <ezweb>
      <A>44</A>
      <B>44</B>
      <C>44</C>
      <D>44</D>
    </ezweb>
    <jphone>
      <string>$Gj</string>
    </jphone>
  </set>

絵文字の定義は、<emoji>タグから</emoji>タグまでの間にあります。その中の要素を説明します。1つの絵文字につき、1つのセット(<set>タグから</set>タグまで)とし、キャリア毎の絵文字を定義しています。

  1. <imode>要素

    まず、元となるi-Mode用の絵文字は、<imode>タグにはさまれた間に定義されています。<imode>要素は、2バイトコード要素(<hex1><hex2>)と、10進参照文字列要素(<string>)を保持していて、この2つの要素を変換元の値として使用します。アクセスしてきた端末が、i-Mode機であった場合で、かつCHTML中に10進参照文字列が絵文字として書かれている場合には、<hex1><hex2>要素に定義されている値に置換します。



  2. <ezweb>要素

    アクセスしてきた端末が、AU機であった場合、<ezweb>要素に定義されている値に変換します。<ezweb>要素は、<A>〜<D>要素を持っていて、それぞれAUの絵文字タイプA〜Dに対応していますので、もし、Dタイプの絵文字端末であったなら、<D>要素に定義されている値に変換します。ここで定義されている値は、HDML機の場合は、<IMG ICON="XX">の"XX"の部分に当てはめられて、置換されます。XHTML機の場合は、<IMG LOCALSRC="XX">の"XX"の部分に当てはめられて、置換されます。



  3. <jphone>要素

    アクセスしてきた端末が、Vodafone/J-Phone端末であった場合、<jphone>要素に定義されている値に変換します。<jphone>要素は、<string>要素を保持していて、ここで定義されている値を直接使用します。



emoji.xmlに定義されていない絵文字で、変換したい絵文字がある場合には、このファイルに新たな定義を足せば、変換するようになります。

  1. 厳密にはXMLになっていないので、日本語の記述はSJISでお願いします。

デバイス定義 device_data.xml

mod_chxjの動作を決定付ける重要な定義です。変換対象の端末は全て、device_data.xmlファイルに定義される必要があります。定義されていない端末は、mod_chxjとしては、認識することができません。認識できない場合には、CHTMLをそのまま出力します。

イメージ画像変換機能

mod_chxjには、JPEG、GIF、PNG、BMPファイルを置いておくだけで、デバイス定義に従って、それぞれのキャリア対応のフォーマットに変換する機能があります。画像のサイズ(縦X横)も、端末の画面サイズに合わせて変換します。画像のサイズ(バイト数)については、デバイス定義中のキャッシュサイズを見て、その値よりも小さくなるように努力しますが、元の画像が大きすぎる場合や、複雑な画像の場合には、キャッシュサイズよりも小さくできずに表示できない場合があります。

それぞれのタグで指定する場合には、ファイル名の拡張子(.jpgや.gif等)をはずした形で指定します。

本機能には3つのモードが存在します。そのモードを以下に記します。

サムネイルモード

端末側画面サイズの約3分の1程度のサイズ(縦X横)に画像を縮小表示します。

サムネイルモード 使用例
  <IMG SRC="/img/logo?Mode=Thumbnail">
  

壁紙モード

端末側画面のサイズにマッチするサイズに拡大・縮小します。横長の画像の場合には、縦幅を合わせた後に左右をトリミングします。

壁紙モード 使用例
  <IMG SRC="/img/logo?Mode=WP">
  

EzGetモード

壁紙ダウンロードを行いたい場合に使用します。EzGETモードは、壁紙モードで出力される画像サイズと同一サイズの画像が使用されます。

EzGetモード 使用例
  <A HREF="/img/logo?Mode=EzGet">
  

その他の機能

モードの他に、画像サイズ(縦X横)を直接指定することも可能です。wパラメータ、hパラメータを使用して指定します。

  1. wパラメータ

    横幅を指定します。
  2. hパラメータ

    縦幅を指定します。
    w/hパラメータ 使用例
      <IMG SRC="/img/logo?w=100&h=200">
      
    
  3. User-Agentパラメータ(uaパラメータ)

    User-Agentを指定します。指定した場合は、リクエストヘッダ中のUser-Agentを本パラメータの値で上書きします。このパラメータに"IGN"を指定した場合は、User-Agentを無視します。Thumbnailモード、壁紙モードと併用時は、640x480を元に画像サイズを算出します。

上記全てのモード、パラメータはGETリクエストとしてのみ使用できます。

QRコード出力機能

QRコード出力ハンドラの登録

QRコード出力機能を使用するには、QRコードハンドラを登録します。httpd.confに以下の記述を追加します。

httpd.conf
  AddHandler chxj-qrcode .qrc

なお、ハンドラを登録しないでも、出力フィルターを経由させることで、QRコードを出力させることも可能です。(※QRコードの動的出力を参照)

QRコードソースファイルの設置

ハンドラを登録したら、その登録した拡張子を持つファイルを用意します。

例:a.qrc
  <?xml version=1.0 ?>
  
  <qrcode>
    <version>13</version>
    <level>H</level>
    <mode>8bit</mode>
    <size>1</size>
    <data>テストデータです</data>
  </qrcode>

.qrcファイルは、qrcode要素、version要素、level要素、mode要素、size要素、data要素から成り立ちます。

  1. versionタグversionタグは出力するQRコードの生成に利用するバージョンを指定します。使用できるバージョンは、1〜40までの40種類です。
  2. levelタグlevelタグは出力するQRコードの生成に利用する誤り検出レベルを指定します。 使用できるレベルは、L、Q、M、Hの4つです。
  3. modeタグmodeタグは出力するQRコードの生成に利用するモードを指定します。使用できるモードは、NUM(数字モード)ALPHA(英数字モード)8BIT(8ビットバイトモード)KANJI(漢字モード)です。
  4. sizeタグsizeタグは1モジュールを何ピクセルであらわすかを指定します。0を指定した場合は、4を指定した場合と同じ動作をします。 使用できるサイズは、0〜20までです。
  5. dataタグdataタグは、QRコードに出力するデータを指定します。改行した場合は、改行文字もQRコード内に符号化されます。

QRコードの動的出力機能

プログラム等を使用し、動的にQRコードを出力したい場合は、上記の.qrcファイルの内容をそのままOutputFilterに通してあげればOKです。

phpでQRコードを動的に出力する例
    <php
      $version = $_POST["version"];
      $level   = $_POST["level"];
      $mode    = $_POST["mode"];
      $size    = $_POST["size"];
      $data    = $_POST["data"];

      echo "<qrcode>\n";
      echo "<version>".$version."</version>\n";
      echo "<level>".$level."</level>\n";
      echo "<mode>".$mode."</mode>\n";
      echo "<size>".$size."</size>\n";
      echo "<data>".$data."</data>\n";
      echo "</qrcode>\n";
    >
  

そして、上記のコードを、OutputFilterを通るところに設置すれば完了です。なお、OutputFilterを通る場合は、画像変換エンジンも動作してしまうため、使用するクライアントのUser-Agentを定義するか、もしくは、ua=IGNを指定して、リクエストしなければなりません。(もちろん、画像変換エンジンをそのまま使用する場合は何もしないでいいです。)