XML形式のlog4j設定(log4j.xml)をGrailsで使用する
Grailsではロギングの設定がConfig.groovyで設定できますが、なんらかの理由でXML形式の設定(log4j.xml)で行ないたいことがあるかもしれません。しかし、その場合log4j.xmlをどこに置くか、という問題があり得ます。
この問題を説明します。まずGrailsでlog4jのXML設定を使用するには、springの設定ファイルresouces.groovyで、以下のようにlog4jConfigurerを設定します。
GRAILS_PROJ/grails-app/conf/spring/resources.groovy
beans = {
log4jConfigurer(org.springframework.beans.factory.config.MethodInvokingFactoryBean){
targetClass = "org.springframework.util.Log4jConfigurer"
targetMethod = "initLogging"
// arguments = "grails-app/conf/log4j.xml" // ★1
arguments = "classpath:log4j.xml" // ★2
}
}
問題は、★1のようにカレントディレクトリ相対で指定すると、warにしてtomcatなどにデプロイした状態では、tomcatが走行しているときのカレントディレクトリ($CATARINA_BASE)からの相対になり、読み取ることができないということです。だからといって、絶対指定も一般にはできないでしょう。
この解決策ですが、まずlog4j.xmlはgrails-app/conf配下に置いた上で、(★2)のようにxmlがclasspath配下にあると指定します。run-appの際には、grails-app/confはクラスパスに入っていますのでこれで動作します。
ただし、warにしたときには、conf配下は特にはクラスパスにはいっているわけではないので(Config.groovyなどはコンパイルされてclasses配下に移動している)、warの作成時にgrails-app/conf/log4j.xmlを適切なclasspathの通っているところ、たとえば以下ではWAR中の$WEB-INF/classes/配下にコピーするように、BuildConfigに以下の設定を追加します。
GRAILS_PROJ/grails-app/conf/BuildConfig.groovyに追加。
grails.war.resources = { stagingDir, args ->
println "$stagingDir, $args"
copy(file: "grails-app/conf/log4j.xml",
todir: "${stagingDir}/WEB-INF/classes/")
}
なおログファイルをそもそもどこに置くか、という設定はlog4j.xmlに記入しておく必要があります。XML設定の場合、grailsのConfig.groovyで設定するように、developmentのときとprod/testのときに場所を切り替えたりということはたぶんできないので、適当に絶対パスで指定することになるでしょう。
ちなみに、Wiki - Log4j XML Pluginというプラグインもあり、XMLでの設定に対応する、markupbuilderっぽい記法で設定することができるようです。これを使えば、もっとうまくいくのかもしれませんが試してません。