(Java版) Apache Camel を使った HTTP 処理とファイル入出力 - Jettry, File コンポーネント、Gant の利用

id:fits:20080919 で作成したサンプルの Java版は以下の通り。動作は Groovy 版と基本的に同じ。Groovy 版との違いで注目すべき点は getOut().setBody() で String.class の指定が不要なところ。

SampleRoute.java
package sample;

import java.io.FileInputStream;
import java.nio.CharBuffer;
import java.nio.MappedByteBuffer;
import java.nio.channels.FileChannel;
import java.nio.charset.Charset;
import javax.servlet.http.HttpServletRequest;

import org.apache.camel.Exchange;
import org.apache.camel.Processor;
import org.apache.camel.impl.DefaultCamelContext;
import org.apache.camel.builder.RouteBuilder;
import org.apache.camel.component.file.FileExchange;

public class SampleRoute extends RouteBuilder {

    public void configure() {

        from("jetty:http://localhost/test").to("direct:response");

        from("direct:response").process(new Processor() {
            public void process(Exchange exchange) {

                HttpServletRequest req = (HttpServletRequest)exchange.getIn().getBody(javax.servlet.http.HttpServletRequest.class);

                String id = req.getParameter("id");

                exchange.getOut().setBody("<html><body><h1>id=" + id + "</h1></body></html>");
            }
        }).to("file:logs");

        from("file:logs").process(new Processor() {
            public void process(Exchange exchange) throws Exception {
                FileExchange fe = (FileExchange)exchange;

                //ファイルのパス出力
                System.out.print(fe.getFile().getPath() + " : ");

                FileInputStream fis = new FileInputStream(fe.getFile());

                try {
                    FileChannel fc = fis.getChannel();
                    MappedByteBuffer buffer = fc.map(FileChannel.MapMode.READ_ONLY, 0, fc.size());
                    CharBuffer chb = Charset.defaultCharset().decode(buffer);

                    //ファイルの内容を出力
                    System.out.println(chb.toString());
                }
                finally {
                    fis.close();
                }
            }
        });
    }

    public static void main(String[] args) throws Exception {

        DefaultCamelContext ctx = new DefaultCamelContext();

        ctx.addRoutes(new SampleRoute());

        ctx.start();

        System.out.println("start Camel");

        System.in.read();

        ctx.stop();
    }
}

実行には以下のような Gant ファイルを使用した。
実行するには Camel と Jetty のホームディレクトリを環境変数 CAMEL_HOME と JETTY_HOME にそれぞれ設定しておく必要がある。

build.gant
includeTargets << gant.targets.Clean

Ant.property(environment: "env")
camelHome = Ant.antProject.properties."env.CAMEL_HOME"
jettyHome = Ant.antProject.properties."env.JETTY_HOME"

destDir = "dest"

cleanDirectory << destDir

target("default": "") {
    compile()
}

target(init: "") {
    path(id: "project.classpath") {
        pathelement(path: destDir)

        fileset(dir: camelHome) {
            include(name: "**/*.jar")
        }

        fileset(dir: jettyHome) {
            include(name: "**/*.jar")
        }
    }
}

target(compile: "") {
    depends(init)

    Ant.mkdir(dir: destDir)

    Ant.javac(srcdir: "src", destdir: destDir) {
        classpath(refid: "project.classpath")
    }
}

target(run: "") {
    depends(compile)

    Ant.java(classname: "sample.SampleRoute", fork: true) {
        classpath(refid: "project.classpath")
    }
}

実行はカレントディレクトリで gant コマンドを実行し、起動後の動作確認は Groovy 版と同様に Web ブラウザでアクセスすればよい。

>gant

Gant に関する備考

Gant では以下のようにして環境変数の値を利用できる。("${プレフィックス名.環境変数名}" という記述は使えない模様)

Ant.property(environment: プレフィックス名)
envValue = Ant.antProject.properties."プレフィックス名.環境変数名"
//以下でも可
envValue = Ant.antProject.properties["プレフィックス名.環境変数名"]
//Ant は ant でも可
envValue = ant.antProject.properties."プレフィックス名.環境変数名"

また、以下のように記述すると、clean ターゲットが追加され、その実行時(>gant clean)に dest ディレクトリを削除するように簡単に指定できる。(cleanDirectory で clean ターゲット実行時に削除するディレクトリを指定)

includeTargets << gant.targets.Clean
・・・
destDir = "dest"

cleanDirectory << destDir