2009-04-18 13 views
9

que tienen un oído con estructuras como:¿Cómo se configura el log4j múltiple para diferentes guerras en un solo EAR?

APP.ear 
- APP1.war 
    - WEB-INF/classes/log4j.properties 
- APP2.war 
    - WEB-INF/classes/log4j.properties 
- app1-ejb.jar 
- app2-ejb.jar 
- log4j.jar 
- spring.jar 
- commons-lang.jar (...and other jar) 

deseo que cada GUERRA tener su propio registro de aplicación. Pero parece que la configuración anterior no funciona. El registro para APP1 y APP2 va al registro de APP1. ¿Hay alguna forma de crear registros de aplicaciones separados?

Respuesta

7

Resulta que es imposible debido al cargador de clases. La jerarquía del cargador de clases es como: cargador de clases

Aplicación -> Ejb cargador de clases -> cargador de clases guerra

Para tener un registro sepearte para la guerra individual, uno puede poner log4j.jar dentro de la guerra y dejar que el log4j utiliza el cargador de clase de guerra. Pero como tanto app1-ejb.jar como app2-ebj.jar también necesitan usar log4j, log4j.jar solo puede colocarse en el nivel superior. Entonces el log4j está en el nivel del cargador de clases de la aplicación.

Puedo especificar una sola configuración de log4j para registrar paquetes diferentes en archivos diferentes. Pero para la biblioteca común como la primavera, el registro no se puede separar.

+0

"Pero como app1-ejb.jar y app2-ebj.jar también necesitan usar log4j, log4j.jar solo se puede colocar en el nivel superior." ¿No puedes simplemente incluir un log4j.jar en cada uno de los archivos WAR? – CodeClimber

0

También puede hacerlo cambiando dinámicamente la propiedad FILE en el archivo de propiedades utilizando el PropertyConfigurator en el código.

1

La razón por la que no funcionó porque el log4j está presente en la ubicación raíz, en cambio, cada guerra tiene un Log4j.jar en su directorio WEB-INF/lib y elimina el log4j.jar de la raíz.

Para obtener más información sobre este artículo, consulte mi blog en este http://techcrawler.wordpress.com/

0

Logback es una solución viable para hacer frente a este problema. Después de buscar alrededor de diferentes hacks para que esto funcione con log4j, hemos decidido cambiar a Logback. He utilizado la siguiente configuración con Logback jar dentro de la aplicación web.

archivo

Un Logback dentro de la aplicación web que incluyen un archivo externo:

<?xml version="1.0" encoding="UTF-8" ?> 
    <configuration scan="true" scanPeriod="10 seconds"> 
     <contextListener class="ch.qos.logback.classic.jul.LevelChangePropagator"> 
      <resetJUL>true</resetJUL> 
     </contextListener> 

     <contextName>${project.artifactId}</contextName> 

     <jmxConfigurator /> 

     <include file="${logback.configuration.filepath}" /> 
    </configuration> 

${logback.configuration.filepath} se sustituye durante el filtrado Maven por la ruta exacta, externo a la aplicación de web del archivo de configuración (algo así como /opt/servidor /conf/loback.included.conf).

Y luego, el contenido de la logback.included.conf (este archivo es parte de la projetct, entregado con build-helper:attach-artifact, por lo ${project.artifactId} también se sustituye durante el filtrado Maven):

<?xml version="1.0" encoding="UTF-8" ?> 
    <included> 
     <appender name="file" class="ch.qos.logback.core.FileAppender"> 
      <file>/var/log/server/${project.artifactId}.log</file> 
      <encoder> 
       <pattern>[@/%contextName] %date{ISO8601} [%-5level] %thread:[%logger] %msg%n</pattern> 
      </encoder> 
     </appender> 

     <root level="INFO"> 
      <appender-ref ref="file" /> 
     </root> 
    </included> 

única limitación, el contenido de los incluidos el archivo debe ser compatible con el del includer. Solo estoy escribiendo reglas de hecho.

Cuestiones relacionadas