Criação de Log do Aplicativo no WebSphere Application Server Community Edition

Usando java.util.logging, Log4j e SLF4j

O WebSphere Application Server Community Edition oferece várias maneiras de configurar a criação de log do aplicativo, usando as APIs java.util.logging, Log4j e SLF4j. Embora as etapas para configurar estes serviços de criação de log sejam muito independentes de qualquer servidor de aplicativos, o WebSphere Application Server requer pequenas mudanças para a obtenção do comportamento de criação de log desejado. Este tutorial o orienta nestas pequenas mudanças relacionadas a aplicativos de amostra. O WebSphere® Application Server Community Edition está disponível para download gratuitamente, portanto, você pode começar em apenas alguns minutos.

Phani Madgula, Software Developer, IBM

author imagePhani está atualmente trabalhando para suporte ao WebSphere Application Server Community Edition nos Laboratórios de Software da Índia (ISL). Ele tem estado ativamente envolvido em muitos projetos relacionados à migração de aplicativos de outros servidores de aplicativos para o WebSphere Application Server Community Edition. Ele tem 5 anos de experiência na IBM. Trabalhou em diversas equipes de produtos, incluindo o WebSphere Application Server Community Edition, o WebSphere Business Integration Adapters e o DB2. Tem experiência em desenvolver aplicativos JEE, suporte a produto e administração de banco de dados. Ele é um profissional com certificação em Oracle9i.



14/Mai/2014

Introdução

A criação de log do aplicativo oferece maneiras de capturar vários eventos que ocorrem na execução de um aplicativo. Ela reúne informações sobre o que o aplicativo está fazendo quando ele executa várias tarefas. Esta informação é útil para depuração, resolução de problemas e até mesmo auditoria. O WebSphere® Application Server Community Edition (de agora em diante chamado de Community Edition) é fornecido com várias bibliotecas que ajudam os desenvolvedores de aplicativos a configurar serviços de criação de log. Estas bibliotecas são:

  • Log4j
  • SLF4j
  • java.util.logging

O pacote java.util.logging é uma API Java para criação de log que está disponível em todos os Java development kits padrão. Este tutorial explica com amostras como usar estas APIs em aplicativos implementados no Community Edition.

Configure java.util.logging por instância de JVM. Depois de configurado, ele fica disponível para todos os aplicativos em execução nesse servidor. Este tutorial explica como usar java.util.logging nos aplicativos em execução no Community Edition.

A API mais comumente usada para criação de log é Log4j da Apache Software Foundation. O Community Edition é fornecido com bibliotecas Log4j que são usadas pelos módulos do servidor no tempo de execução. Os aplicativos também podem usar estas bibliotecas; eles podem registrar mensagens no mesmo destino que o servidor registra no tempo de execução, ou podem configurar seus próprios destinos de criação de log e formatos conforme desejarem. Este tutorial demonstra diferentes formas de configurar a criação de log usando Log4j no Community Edition.

O Simple Logging Facade for Java (ou SLF4j) já é outra API de criação de log que os aplicativos podem usar com um serviço de criação de log. O SLF4j não inventa outra estrutura de criação de log, mas permite que os aplicativos usem uma API padrão e sejam conectados na implementação de criação de log real no tempo de implementação, por exemplo, NOP, Simple, log4j versão 1.2, criação de log de JDK 1.4, JCL e logback. O Community Edition também é fornecido com bibliotecas SLF4j. Este tutorial demonstra como usar SLF4j sobre log4j nos aplicativos destinados para execução no Community Edition.

O Community Edition v2.1 é um servidor de aplicativos leve baseado no Apache Geronimo v2.1. Community Edition também inclui muitas outras correções de defeitos e recebe suporte de nível mundial da IBM. Você pode fazer o download de imagens binárias do servidor gratuitamente. É um servidor totalmente certificado para Java EE 5.

Neste Tutorial

Este tutorial mostra como usar as APIs java.util.logging, Log4j e SLF4j em aplicativos destinados para execução no Community Edition. Ele contém as seguintes seções:

Em cada seção, descrevemos brevemente a API de criação de log correspondente e explicamos várias maneiras de configurar e usar a API para obter o comportamento de criação de log desejado. Usamos a amostra EMPDemo para demonstrar como usar as três APIs de criação de log. A API EMPDemo pode ser transferida por download a partir do site developerWorks .

Pré-requisitos

É necessário ter conhecimento em programação Java. Entender os conceitos de Java EE 5 e os conceitos de banco de dados ajudará com o contexto do tutorial. Se você tiver experiência em executar uma amostra HelloWorld no Community Edition e em escrever planos de implementação do Community Edition, então é o candidato perfeito para aproveitar este tutorial ao máximo.

Requisitos do Sistema

Para desenvolver, implementar e executar o aplicativo, o ambiente a seguir é necessário:

  • IBM Java SDK v1.5.0 SR8 ou acima
  • Community Edition v2.1.0.1 ou acima


Usamos o banco de dados Apache Derby fornecido com o Community Edition para implementar e executar o aplicativo EMPDemo convencional. A API EMPDemo conecta-se a EMPLOYEE_DB no banco de dados Derby integrado e recupera informações da tabela EMPLOYEE . Mostramos então as informações recuperadas para o usuário no navegador. Demonstramos o uso de APIs de criação de log para registrar mensagens quando o aplicativo executa várias operações do banco de dados.

Duração

2 horas


Configurando o Ambiente

Nesta seção, execute as seguintes tarefas:

  • Instale o Community Edition v2.1.0.1
  • Crie o banco de dados EMPLOYEE_DB no banco de dados Derby integrado.
  • Implemente a origem de dados EMPLOYEE_DS no banco de dados EMPLOYEE_DB.

Instale o Community Edition v2.1.0.1

O instalador do Community Edition está disponível para download a partir do developerWorks. Faça download do servidor para sua máquina e siga as instruções na documentação. Neste tutorial, fazemos referência ao diretório de instalação da Community Edition como <wasce_home>. O instalador do Community Edition fornece o IBM Java SDK1.5.0. Este JDK é usado pelo instalador e também no tempo de execução do servidor. Para obter informações adicionais sobre as plataformas recomendadas e compatíveis. consulte o site de site de suporte.

Criar o banco de dados EMPLOYEE_DB no banco de dados Derby integrado

  1. Inicie o servidor Community Edition e abra o console de administração da Web apontando a janela do navegador para http://localhost:8080/console
  2. Efetue login no console de administração fornecendo systemcomo o nome de usuário e manager como a senha.
  3. À esquerda do console de administração, no portlet Console Navigation , clique no link DB Manager para abrir os portles DB Viewer e Executar SQL à direita, conforme mostra a Figura 1:
    Figura 1. Comunicação de portlets DB Viewer e Run SQL
  4. No assistente Executar SQL , insira EMPLOYEE_DB nas ações Criar BD e clique no botão Criar , que criará um banco de dados EMPLOYEE_DB no banco de dados Derby integrado. Depois de criado, o portlet Database List lista o banco de dados EMPLOYEE_DB , conforme mostra a Figura 2.
    Figura 2. EMPLOYEE_DB no portlet DB Viewer
  5. Clique no link Application para o banco de dados EMPLOYEE_DB para mostrar uma lista de tabelas de aplicativos criadas no banco de dados. No momento, não existem tabelas de aplicativos no banco de dados. Na área de texto SQL Command/s , insira a instrução SQL na Listagem 1 para criar a tabela EMPLOYEE no banco de dados:
    Listagem 1. Instrução SQL para criar uma tabela
    create table EMPLOYEE (EMPNO int, ENAME varchar(50), JOB varchar(10),
    MGR varchar(10), SAL decimal(15,2), COMM decimal(15,2), DEPTNO int);
  6. De forma semelhante, insira algumas linhas de amostra no banco de dados usando as instruções SQL abaixo.
    Listagem 2. Instrução SQL para inserir linhas
    insert into EMPLOYEE values (1, 'PHANI', 'SSE', 'NIKHIL', 10000, 15, 100);
    insert into EMPLOYEE values (2, 'JOE', 'SSE', 'NIKHIL', 12000, 15, 100);
    insert into EMPLOYEE values (3, 'JOHN', 'SSE', 'BOB', 13000, 15, 200);
  7. Por último, a tabela deve ser semelhante à Figura 3:
    Figura 3. Tabela EMPLOYEE_DB

Implemente a origem de dados EMPLOYEE_DS no banco de dados EMPLOYEE_DB

  1. Clique em Database Pools nas ações Console Navigation no console de administração. Esta etapa abre o portlet Database Pools , que lista os conjuntos de bancos de dados implementados no servidor.
  2. Clique em Using the Geronimo database pool wizard para criar um novo conjunto de bancos de dados. Insira EMPLOYEE_DS no campo Name of the Database Pool e selecione Derby embedded na caixa de combinação Database Type conforme mostrado na Figura 4. Clique em Avançar.
    Figura 4. Criando o Conjunto de Bancos de Dados
  3. Na próxima tela, insira EMPLOYEE_DB no campo Database Name (Figura 5). Selecione a única entrada na caixa Driver JAR e clique em Deploy na parte inferior da página. Esta etapa implementa o conjunto de bancos de dados EMPLOYEE_DS. O portlet Database pools agora mostra o conjunto de bancos de dados recém-criado.
    Figura 5. Configurando o Conjunto de Bancos de Dados

Configurando java.util.logging no Community Edition

Nesta seção, descrevemos brevemente a API java.util.logging e explicamos como ela funciona no Community Edition. Não detalhamos os diversos recursos desta API. No entanto, listamos os objetos envolvidos e mostramos as diferentes formas de uso deste serviço de criação de log em um aplicativo.

Os aplicativos fazem chamadas de criação de log em objetos do Criador de Logs. Os objetos do Criador de Logs são organizados em forma de espaço de nomes hierárquico e os Criadores de Logs filhos podem herdar algumas propriedades de criação de log de seus pais na hierarquia. Os objetos do Criador de Logs alocam objetos LogRecord quando são feitas chamadas de criação de log. Eles passam os objetos LogRecord para os objetos do Criador de Logs para publicação em destinos. Os Criadores de Logs e os Manipuladores podem usar níveis de criação de log e, opcionalmente, filtros para avaliar se eles estão interessados no LogRecord. Se o LogRecord precisar ser publicado, um Manipulador poderá usar, opcionalmente, um Formatador para localizar e formatar a mensagem antes de enviá-la para o destino. A Figura 6 explica como todos estes objetos estão relacionados:

Figura 6. Relacionamentos do objeto java.util.logging

A API java.util.logging fornece os seguintes manipuladores:

  • StreamHandler: Um manipulador simples para gravar registros formatados em um OutputStream.
  • ConsoleHandler: Um manipulador simples para gravar registros formatados em System.err
  • FileHandler: Um manipulador que grava registros de log formatados em um único arquivo ou em um conjunto rotativo de arquivos de log.
  • SocketHandler: Um manipulador que grava registros de log formatados em portas TCP remotas.
  • MemoryHandler: Um manipulador que armazena em buffer registros de log na memória.

Além dos manipuladores acima, a API também fornece os seguintes formatadores:

  • SimpleFormatter : Grava breves resumos legíveis por humanos de registros de log.
  • XMLFormatter : Grava informações detalhadas estruturadas por XML

java.util.logging define os seguintes níveis de log:

  • SEVERE (mais alto)
  • WARNING
  • INFO
  • CONFIG
  • FINE
  • FINER
  • FINEST (mais baixo)

Nesta seção, mostramos os seguintes aspectos de java.util.logging, usando o aplicativo EMPDemo para ilustrar como o java.util.logging funciona:

  • Usando a Configuração de java.util.logging Padrão
  • Customizando java.util.logging Usando um gbean

Usando a Configuração de java.util.logging Padrão

Por padrão, java.util.logging usa o arquivo <JAVA_HOME>/jre/lib/logging.properties para configurar Criadores de Logs, Manipuladores e Formatadores. No entanto, é possível incluir programaticamente novos Manipuladores e Formatadores no tempo de execução. A configuração padrão fornecida é uma muito simples que configura apenas um ConsoleHandler com o SimpleFormatter. O nível de log configurado para ConsoleHandler é INFO; ou seja, as mensagens cujo nível de log é INFO ou acima são registradas pelo ConsoleHandler por padrão.

Podemos modificar o arquivo logging.properties para incluir novos Manipuladores ou Formatadores. EMPDemo contém o servlet com.ibm.sample.EMPDemo que se conecta ao banco de dados EMPLOYEE_DB e recupera as linhas da tabela EMPLOYEE. Ele também registra mensagens quando executa várias operações do banco de dados. A Listagem 3 mostra o código correspondente, com as instruções de criação de log marcadas em negrito:

Listagem 3. java.util.logging Padrão

Clique aqui para ver lista de códigos

Listagem 3. java.util.logging Padrão

Logger logger = Logger.getLogger(EMPDemo.class.getName());
logger.setLevel(Level.FINEST);
Connection con = null;
Statement stmt = null;
		
PrintWriter out = response.getWriter();
		
logger.info("Created the PrintWriter on the Response object");
		
try {
    Context initContext = new InitialContext();
    Context envContext = Context)initContext.lookup("java:comp/env");
    logger.info("Got Initial context: " +envContext);
    DataSource ds = (DataSource)envContext.lookup("jdbc/DataSource");
    logger.info("Got DataSource: " +ds.toString());
    con = ds.getConnection();
    logger.info("Got Connection: " +con.toString() +"\n");
    stmt = con.createStatement();	
    logger.info("Got Statement : " +stmt);
    ResultSet rs = stmt.executeQuery("SELECT * FROM EMPLOYEE");
    logger.info("Table EMP after SELECT:");
	
    out.println("Your EMP table contains the following entries:<BR>");

    out.println("<table>");
    out.println("<tr>");
    out.println("<th>Empno</th>");
    out.println("<th>Name</th>");
    out.println("<th>Job</th>");
    out.println("<th>Manager</th>");
    out.println("<th>Salary</th>");
    out.println("<th>Commission</th>");
    out.println("<th>Deptno</th>");
    out.println("</tr>");

        while (rs.next()) {
            String emp = rs.getString("EMPNO");
            String name  = rs.getString("ENAME");
            String job = rs.getString("JOB");
            String mgr = rs.getString("MGR");
            String sal = rs.getString("SAL");
            String comm = rs.getString("COMM");
            String dept = rs.getString("DEPTNO");

            out.println("<tr>");
            out.println("<td>"+emp+"</td>");
            out.println("<td>"+name+"</td>");
            out.println("<td>"+job+"</td>");
            out.println("<td>"+mgr+"</td>");
            out.println("<td>"+sal+"</td>");
            out.println("<td>"+comm+"</td>");
            out.println("<td>"+dept+"</td>");
            out.println("</tr>");
				
           logger.info(emp + "   " + name + "   " + job);logger.info("   " + mgr + "   " + dept);
        }
        out.println("</table>");
			
        rs.close();
        stmt.close();
        con.close();
			
   logger.severe("my severe message");logger.warning("my warning message");logger.info("my info message");logger.config("my config message");logger.fine("my fine message");logger.finer("my finer message");logger.finest("my finest message");

        }
        catch(java.lang.Exception e) {
			
            e.printStackTrace();
            logger.severe(e.getClass().getName());logger.severe(e.getMessage());
        }
}
>

O servlet obtém o Criador de Logs e substitui o nível de log padrão (que é INFO no arquivo <JAVA_HOME>/jre/lib/logging.properties ) para FINEST. Ele inicia a criação de log das mensagens no nível INFO usando o método logger.info() em vários locais durante a execução. Para ilustrar a criação de log em diferentes níveis, ele também registra mensagens de amostra em todos os níveis depois de exibir as linhas da tabela EMPLOYEE. Por último, no bloco de captura, ele registra a exceção no nível SEVERE . Siga estas etapas para implementar e executar o aplicativo EMPDemo:

  1. Faça download do aplicativo EMPDemo. O arquivo WAR é EMPdemo-UtilLogging.war.
  2. Implemente o arquivo war usando este comando deploy:
    <wasce_home>/bin>deploy --user system --password manager deploy EMPdemo-UtilLogging.war
  3. Acesse o servlet EMPDemo em um navegador nesta URL: http://localhost:8080/EMPdemo-UtilLogging/EMPDemo.

É possível ver no console do servidor todas as mensagens INFO, WARNING e SEVERE registradas pelo aplicativo. O console não mostra as mensagens registradas com os outros níveis de log, mesmo que o nível de log seja substituído no servlet para ser FINEST. Isto ocorre porque, por padrão, o ConsoleHandler registra as mensagem com um nível de log INFO ou acima apenas conforme configurado no arquivo <JAVA_HOME>/jre/lib/logging.properties . A Listagem 4 mostra a saída:

Listagem 4. Mensagens registradas no console
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost INFO:
    Created the PrintWriter on the Response object
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost INFO:
    Got Initial context:
    org.apache.xbean.naming.context.ImmutableContext$NestedImmutableContext@16801680
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost INFO:
    Got DataSource: org.tranql.connector.jdbc.DataSource@55425542
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost INFO:
    Got Connection: org.tranql.connector.jdbc.ConnectionHandle@30363036
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost INFO:
    Got Statement : org.tranql.connector.jdbc.StatementHandle@43aa43aa
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost INFO: Table EMP after SELECT:
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost INFO: 1   PHANI   SSE
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost INFO:    NIKHIL   100
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost INFO: 2   JOE   SSE
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost INFO:    NIKHIL   100
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost INFO: 3   JOHN   SSE
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost INFO:    BOB   200
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost SEVERE: my severe message
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost WARNING: my warning message
Jan 2, 2009 10:49:14 AM com.ibm.sample.EMPDemo doPost INFO: my info message

É possível modificar o arquivo logging.properties para incluir um FileHandler para registrar a mensagem em um arquivo. Também é possível usar XMLFormatter em vez de SimpleFormatter. Por exemplo, configure o nível de log de ConsoleHandler como FINEST para observar se todas as mensagens de log registradas em todos os níveis no servlet são registradas no console. A linha a ser modificada é a seguinte.

java.util.logging.ConsoleHandler.level = FINEST.

Se houver um arquivo de configuração diferente do arquivo padrão <JAVA_HOME>/jre/lib/logging.properties , será possível fornecer o arquivo como um argumento de JVM durante a inicialização do servidor conforme a Listagem 5 (que é para Windows.)

Listagem 5. Iniciando um servidor Windows com um parâmetro de arquivo de propriedades
C:\>set -Djava.util.logging.config.file=<new_configuration.properties>
C:\>startup.bat

Customizando java.util.logging Usando um gbean

Às vezes, você pode fazer pequenas mudanças na configuração de criação de log programaticamente usando a API java.util.logging. Ou seja, incluir um novo manipulador dinamicamente e ajustar os níveis de criação de log etc. Portanto, java.util.logging é configurado por instância de JVM; a configuração programática é melhor efetuada em um módulo separado em vez de em quaisquer aplicativos. Dessa forma, é possível fazer facilmente qualquer mudança necessária para a configuração de criação de log neste módulo separado. O Community Edition fornece o mecanismo gbean para desenvolver e implementar serviços customizados. Esta seção explica o serviço gbean.

A Listagem 6 mostra UtilLogPropGBean.java, que implementa um serviço gbean, com a parte relevante marcada em negrito:

Listagem 6. UtilLogPropGBean.java
package com.ibm.sample;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.logging.LogManager;
import org.apache.geronimo.gbean.GBeanInfo;
import org.apache.geronimo.gbean.GBeanInfoBuilder;
import org.apache.geronimo.gbean.GBeanLifecycle;


public class UtilLogPropGBean implements GBeanLifecycle{

    private static final GBeanInfo GBEAN_INFO;
    private final String objectName;
		
    private String utilPropFile;

        static {
            GBeanInfoBuilder infoFactory =
                new GBeanInfoBuilder(UtilLogPropGBean.class.getName(),
                    UtilLogPropGBean.class);

            infoFactory.addAttribute("objectName", String.class, false);
            infoFactory.addAttribute("utilPropFile", String.class, true);

            infoFactory.setConstructor(
             new String[]{"objectName","utilPropFile"});
            GBEAN_INFO = infoFactory.getBeanInfo();
        }
		

        public UtilLogPropGBean(String objectName, String utilPropFile) {
            this.objectName = objectName;
            this.utilPropFile = utilPropFile;
        }

        public UtilLogPropGBean() {
            objectName = null;
            utilPropFile = null;
        }

        public void doFail() {
            System.out.println("UtilLogPropGBean has failed");
        }

        public void doStart(){
            LogManager logManager;
		    	
            try{
                System.out.println("[UtilLogPropGBean] GBean " + objectName + " Started");
                    InputStream in = new FileInputStream(utilPropFile);
                    logManager  = LogManager.getLogManager();
                    logManager.reset();
                    logManager.readConfiguration(in);
                    System.out.println("Properties file successfully read!!");

            }catch(IOException exp){
                exp.printStackTrace();
                logManager =  LogManager.getLogManager();
            }catch(Exception exp){
                exp.printStackTrace();
            }

            }
		
        public void doStop(){
            System.out.println("GBean " + objectName + " Stoped");
        }

        public static GBeanInfo getGBeanInfo() {
            return GBEAN_INFO;
        }

}

Ao implementar o gbean, o kernel GBean no Community Edition chama o método doStart() no gbean. Este método abre FileInputStream em utilPropFile, injetado no gbean especificado no plano de implementação do gbean como um atributo. Em seguida, o LogManager lê a configuração a partir do fluxo de entrada e configura java.util.logging.

A Listagem 7 mostra o plano de implementação do gbean.

Listagem 7. O plano de implementação do gbean
<module xmlns="http://geronimo.apache.org/xml/ns/deployment-1.2">

    <environment>
        <moduleId>
            <groupId>UtilLogPropGBean</groupId>
            <artifactId>UtilLogPropGBean-app</artifactId>
            <version>1.0</version>
            <type>car</type>
        </moduleId>

	<dependencies>
            <dependency>
                <groupId>GBeans</groupId>
                <artifactId>UtilLoggingCustom</artifactId>
                <version>1.0</version>
                <type>jar</type>
            </dependency>
       </dependencies>
    </environment>

    <gbean name="UtilLogPropGBean"
           class="com.ibm.sample.UtilLogPropGBean" xsi:type="dep:gbeanType"
           xmlns:dep="http://geronimo.apache.org/xml/ns/deployment-1.2"
           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
	
          <attribute name="utilPropFile">
            C:/temp/applevellogging/UtilLogging/UtilLogging.properties
          </attribute>
    </gbean>
</module>

Na Listagem 6, o arquivo de propriedades de configuração de java.util.logging, C:/temp/applevellogging/UtilLogging/UtilLogging.properties, é injetado como uma cadeia no atributo utilPropFile de UtilLogPropGBean.

Nesta seção, implementaremos nosso gbean no Community Edition. Quando este gbean for implementado, todos os aplicativos que usam a API java.util.logging usarão esta configuração. Siga estas etapas para implementar o gbean:

  1. Faça download do arquivo zip e descompacte arquivo ZIP do gbean (UtilLogPropGBean.jar), do plano de implementação (UtilLogPropGBean.xml) e do arquivo de propriedades de configuração de java.util.logging de amostra (UtilLogging.properties.
  1. Este arquivo jar contém UtilLogPropGBean.java. O arquivo UtilLogging.properties define um ConsoleHandler e um FileHandler. O FileHandler registra as mensagens no arquivo C:/temp/applevellogging/UtilLogging/java.log . Os níveis de log de FileHandler e de ConsoleHandler são FINER e CONFIG respectivamente. O nível de log para com.ibm.sample.EMPDemo será configurado como SEVERE na parte inferior do arquivo. Naturalmente este valor é substituído no servlet EMPDemo. É possível modificar estes valores incluindo o local do arquivo de log, de acordo com suas necessidades.
  1. Faça upload do UtilLogPropGBean.jar para o repositório do servidor Community Edition com a configuração de moduleid como GBeans/UtilLoggingCustom/1.0/jar. Este link explica como fazer upload das bibliotecas Java para o repositório.
  1. Abra um prompt de comandos e vá para o diretório <wasce_home>/bin. Implemente o GBean usando o comando deploy .
    <wasce_home>/bin>deploy –user system –password manager deploy UtilLogPropGBean.xml
  1. O gbean lê o arquivo UtilLogging.properties e configura o sistema java.util.logging. Acesse o servlet EMPDemo apontando seu navegador para esta URL http://localhost:8080/EMPdemo-UtilLogging/EMPDemo(implementada na seção anterior).

A Listagem 8 mostra as mensagens do console do servidor:

Listagem 8. Mensagens do console do servidor
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost INFO:
 Created the PrintWriter on the Response object
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost INFO:
 Got Initial context:
 org.apache.xbean.naming.context.ImmutableContext$NestedImmutableContext@16801680
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost INFO:
 Got DataSource: org.tranql.connector.jdbc.DataSource@a000a00
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost INFO:
 Got Connection: org.tranql.connector.jdbc.ConnectionHandle@1b3a1b3a
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost INFO:
 Got Statement : org.tranql.connector.jdbc.StatementHandle@3b6e3b6e

Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost INFO: Table EMP after SELECT:
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost INFO: 1   PHANI   SSE
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost INFO:    NIKHIL   100
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost INFO: 2   JOE   SSE
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost INFO:    NIKHIL   100
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost INFO: 3   JOHN   SSE
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost INFO:    BOB   200
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost SEVERE: my severe message
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost WARNING: my warning message
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost INFO: my info message
Jan 2, 2009 11:11:46 AM com.ibm.sample.EMPDemo doPost CONFIG: my config message

O nível de log do ConsoleHandler foi configurado como CONFIG no arquivo UtilLogging.properties . Portanto, são vistas todas as mensagens registradas no nível de log CONFIG ou acima (CONFIG, INFO, WARNING e SEVERE).

Além da saída na Listagem 5, o arquivo de log, o Community Edition também cria C:/temp/applevellogging/UtilLogging/java.log. Como o XMLFormatter foi configurado para FileHandler, este arquivo tem as mensagens registradas em formato XML. Além disso, o nível de log foi configurado como FINER para FileHandler. Portanto, no arquivo, são vistas todas as mensagens registradas em FINER ou acima, exceto para FINEST.


Nuances do Community Edition e obtendo o máximo de proveito do Log4j

Log4j é uma biblioteca de software livre para serviços de criação de log da Apache Software Foundation. Log4j é amplamente usado na comunidade de software livre, incluindo alguns grandes nomes como Apache Geronimo, JBoss, etc. A arquitetura de Log4j gira em torno de três conceitos principais: Criadores de Logs, Anexadores e Layouts.

Primeiro, os aplicativos chamam os objetos do Criador de Logs para iniciar a criação de log de uma mensagem. Quando uma mensagem é fornecida para registro, os criadores de log geram objetos LogEvent para quebrar a mensagem especificada. Os criadores de log então passam os objetos LogEvents para seus Anexadores associados. Os Anexadores enviam as informações contidas pelos LogEvents para os destinos de saída especificados. Por exemplo, um ConsoleAppender grava as informações em System.out, e um FileApppender grava-as em um arquivo de log. Antes de enviar as informações para o destino, os Anexadores podem usar Layouts para criar uma representação de texto das informações em um formato desejado. Por exemplo, os Anexadores podem usar XMLLayout que formata as mensagens de log como cadeias XML.

Aos LoggingEvents é designado um nível que indica sua prioridade. Os níveis padrão são (do mais alto para o mais baixo):

  • OFF
  • FATAL
  • ERROR,
  • WARN
  • INFO
  • DEBUG
  • ALL

Aos Criadores de Log e Anexadores é designado um nível. Se um LogEvent tiver o nível de como WARN e o nível de log do Anexador for ERROR, o Anexador não gravará o LogEvent. Desta maneira, é possível controlar a quantidade de saída de log.

Todos os Criadores de Logs no Log4j têm um nome. Log4j organiza instâncias do Criador de Logs em uma estrutura em árvore, hierárquica, de acordo com os nomes, como no espaço de nomes do pacote na linguagem Java. A documentação do Log4j informa

"Um Criador de Log é considerado um anterior de outro Criador de Log, se seu nome seguido por um ponto for um prefixo do nome do Criador de Log descendente. Um Criador de Logs será considerado um pai de um Criador de Logs filho se não houver anteriores entre entre ele mesmo e o Criador de Logs descendente".

Por exemplo, um Criador de Log denominado com.ibm é considerado o filho do Criador de Log com . Os com.ibm.wasce é o filho do Criador de Logs com.ibm e o neto do Criador de Logs com . Se a um Criador de Logs não for designado um nível explicitamente, ele usará o nível de seu anterior mais próximo ao qual foi designado um nível. Os Criadores de Logs herdam Anexadores de seus anteriores, embora eles também possam ser configurados para usar apenas Anexadores que estejam diretamente designados a eles.

Configure todos os Criadores de Logs, Anexadores e Layouts no arquivo log4j.properties ou log4j.xml . As bibliotecas Log4j primeiro procuram o arquivo log4j.xml e, em seguida, o arquivo log4j.properties no caminho de classe para configurar o serviço de criação de log.

A partir da discussão acima, você pode achar que Log4j é semelhante a java.util.logging. É evidente que eles são iguais conceitualmente, mas Log4j pode fazer mais do que java.util. Os Manipuladores em java.util.logging executam as mesmas tarefas que os Anexadores no Log4j. Os Formatadores em java.util.logging executam a mesma tarefa que Layouts no Log4j. No entanto, java.util.logging possui apenas quatro Manipuladores, enquanto Log4j possui vários Anexadores. Além disso, Log4j oferece um importante conjunto de Layouts enquanto java.util.logging oferece apenas SimpleFormatter e XMLFormatter. Alguns dos Anexadores disponíveis no Log4j são:

  • FileAppender: Anexa eventos de log a um arquivo.
  • RollingFileAppender: Estende FileAppender para fazer backup dos arquivos de log quando eles atingem um determinado tamanho.
  • ConsoleAppender: Anexa eventos de log em System.out ou System.err usando um layout especificado pelo usuário. O destino padrão é System.out
  • SocketAppender: Envia objetos LoggingEvent para um servidor de log remoto, geralmente um SocketNode.
  • JMSAppender: Um Anexador simples que publica eventos em um Tópico JMS. Os eventos são serializados e transmitidos como o tipo de mensagem JMS, ObjectMessage.
  • NTEventLogAppender: Anexa ao sistema de log de eventos do NT.

Log4j inclui XMLLayout, SimpleLayout, TTCCLayout, HTMLLayout. Para obter descrições de vários Anexadores e Layouts, consulte a documentação do Log4j .

Nesta seção, mostramos como usar o Log4j em aplicativos implementados no Community Edition. Por padrão, o Community Edition usa os seguintes arquivos de configuração de log4j:

  • <wasce_home>/var/log/server-log4j.properties: Este arquivo configura Anexadores e Layouts para os componentes do servidor, bem como, aplicativos implementados no servidor. Este arquivo configura um ConsoleAppender e um RollingFileAppender. O ConsoleAppender é registrado no System.out e RollingFileAppender é registrado no arquivo <wasce_home>/var/log/server.log . A criação de log padrão é WARN. Também substitui níveis de log para vários Criadores de Logs no arquivo de propriedades.
  • <wasce_home>/var/log/deployer-log4j.properties: Este arquivo configura o serviço de criação de log para o implementador. O componente do implementador é invocado quando algum aplicativo é implementado usando o implementador da linha de comando.
  • <wasce_home>/var/log/client-log4.properties: Este arquivo configura o serviço de criação de log para um aplicativo cliente Java EE.

Nesta seção, configuraremos Log4j das seguintes maneiras

  1. Usando a configuração de Log4j do servidor padrão
  2. Configurando o Log4j no nível do aplicativo

Usando a configuração de Log4j do servidor padrão

Conforme descrito anteriormente, os componentes do servidor, bem como aplicativos implementados no Community Edition, usam a configuração em <wasce_home>/var/log/server-log4j.properties. Usaremos a amostra EMPDemo modificada que possui Log4j para criação de log. Também é usada a configuração padrão disponível no Community Edition. A amostra contém o mesmo servlet EMPDemo modificado para criação de log usando a API Log4j. A Listagem 9 mostra o EMPDemo modificado, com as instruções de criação de log marcadas em negrito. O servlet obtém o Criador de Logs e configura o nível de log como ALL.

Listagem 9. EMPDemo modificado usando a API Log4j

Clique aqui para ver lista de códigos

Listagem 9. EMPDemo modificado usando a API Log4j

Logger logger = Logger.getLogger(EMPDemo.class.getName());logger.setLevel(Level.ALL);
Connection con = null;
Statement stmt = null;
		
PrintWriter out = response.getWriter();
		
logger.info("Created the PrintWriter on the Response object");
		
try {
    Context initContext = new InitialContext();
    Context envContext  = (Context)initContext.lookup("java:comp/env");
    logger.info("Got environment context: " +envContext);
    DataSource ds = (DataSource)envContext.lookup("jdbc/DataSource");
    logger.info("Got DataSource: " +ds.toString());
    con = ds.getConnection();
    logger.info("Got Connection: " +con.toString() +"\n");

    stmt = con.createStatement();	
    logger.info("Created the statement: " +stmt);
    ResultSet rs = stmt.executeQuery("SELECT * FROM EMPLOYEE");
    logger.info("Gto the result set: " +rs);
    logger.info("Table EMP after SELECT:");
	
out.println("Your EMP table contains the following entries:<BR>");
		
out.println("<table>");
out.println("<tr>");
out.println("<th>Empno</th>");
out.println("<th>Name</th>");
out.println("<th>Job</th>");
out.println("<th>Manager</th>");
out.println("<th>Salary</th>");
    out.println("<th>Commission</th>");
    out.println("<th>Deptno</th>");
    out.println("</tr>");

    while (rs.next()) {
        String emp = rs.getString("EMPNO");
        String name  = rs.getString("ENAME");
        String job = rs.getString("JOB");
        String mgr = rs.getString("MGR");
        String sal = rs.getString("SAL");
        String comm = rs.getString("COMM");
        String dept = rs.getString("DEPTNO");

        out.println("<tr>");
        out.println("<td>"+emp+"</td>");
        out.println("<td>"+name+"</td>");
        out.println("<td>"+job+"</td>");
        out.println("<td>"+mgr+"</td>");
        out.println("<td>"+sal+"</td>");
        out.println("<td>"+comm+"</td>");
        out.println("<td>"+dept+"</td>");
        out.println("</tr>");
				
        logger.info(emp + "   " + name + "   " + job);logger.info("   " + mgr + "   " + dept);

    out.println("</table>");
			
    rs.close();
    stmt.close();
    con.close();
	
    logger.debug("Debug");logger.info("Info");logger.warn("Warn");logger.error("Error");logger.fatal("Fatal");

}
catch(java.lang.Exception e) {
			
    e.printStackTrace();
    logger.fatal(e.getClass().getName());logger.fatal(e.getMessage());

}

Siga estas etapas para implementar e executar o aplicativo:

  1. A partir da amostra faça download, descompacte o arquivo ZIP da amostra EMPDemo em um diretório. O nome do arquivo war é EMPdemo-Log4jLogging1.war.
  2. Implemente o aplicativo.
    <wasce_home>/bin>deploy --user system --password manager deploy Log4jLogging1.war.
  3. Acesse o servlet EMPDemo apontando seu navegador para http://localhost:8080/EMPdemo-log4j1/EMPDemo. O servlet mostra as linhas da tabela de funcionários na janela do navegador.

Observe a janela do console para notar se apenas as mensagens de log mostradas na Listagem 10 foram registradas. Isto ocorre porque o nível de log do ConsoleAppender é WARN por padrão (no server-log4j.properties). Portanto, as mensagens de log cujo nível de log é WARN ou acima são registradas no console.

Listagem 10. Método Mensagens de log no console
14:13:31,687 WARN  [EMPDemo] Warn
14:13:31,687 ERROR [EMPDemo] Error
14:13:31,687 FATAL [EMPDemo] Fatal

Abra a área de janela <wasce_home>/var/log/server.log para observar se todas as mensagens de log foram registradas. Isto ocorre porque o nível de log do FileAppender é TRACE por padrão. Portanto, ele registrou todas as mensagens. A Listagem 11 mostra as mensagens registradas:

Listagem 11. Arquivo server.log
14:13:31,687 INFO  [EMPDemo]
 Created the PrintWriter on the Response object
14:13:31,687 INFO  [EMPDemo]
 Got environment context:
 org.apache.xbean.naming.context.ImmutableContext$NestedImmutableContext@5b9e5b9e
14:13:31,687 INFO  [EMPDemo]
 Got DataSource: org.tranql.connector.jdbc.DataSource@8660866
14:13:31,687 INFO  [EMPDemo]
 Got Connection: org.tranql.connector.jdbc.ConnectionHandle@a1e0a1e
14:13:31,687 INFO  [EMPDemo]
 Created the statement: org.tranql.connector.jdbc.StatementHandle@c980c98
14:13:31,687 INFO  [EMPDemo]
 Got the result set: org.tranql.connector.jdbc.ResultSetHandle@11221122

14:13:31,687 INFO  [EMPDemo] Table EMP after SELECT:
14:13:31,687 INFO  [EMPDemo] 1   PHANI   SSE
14:13:31,687 INFO  [EMPDemo]    NIKHIL   100
14:13:31,687 INFO  [EMPDemo] 2   JOE   SSE
14:13:31,687 INFO  [EMPDemo]    NIKHIL   100
14:13:31,687 INFO  [EMPDemo] 3   JOHN   SSE
14:13:31,687 INFO  [EMPDemo]    BOB   200
14:13:31,687 DEBUG [EMPDemo] Debug
14:13:31,687 INFO  [EMPDemo] Info
14:13:31,687 WARN  [EMPDemo] Warn
14:13:31,687 ERROR [EMPDemo] Error
14:13:31,687 FATAL [EMPDemo] Fatal

Configurando o Log4j no nível do aplicativo

Às vezes, você pode configurar o Log4j no nível do aplicativo, ignorando a configuração no nível do servidor. Isto pode ser feito compactando as bibliotecas Log4j e a configuração de log4j.properties com o próprio aplicativo e implementando o aplicativo. No entanto, há um obstáculo aqui -- o Community Edition usa uma política de carregador de classe de “pai primeiro”. Isto significa que, se as classes estiverem disponíveis no carregador de classe pai, elas serão carregadas a partir do carregador de classe pai. Como o Log4j é usado pelos componentes do servidor e carregado por um carregador de classe (que está em uma posição mais alta na hierarquia do carregador de classe), o Log4j configurado no nível do servidor será sempre usado, mesmo que as bibliotecas Log4j e o arquivo log4.properties sejam compactados com o aplicativo.

Para resolver este problema, é necessário ocultar o Log4j do carregador de classe pai e fazer com que ele seja sempre carregado a partir do carregador de classe do aplicativo. Para ocultar o Loh4j, especifique <hidden-classes> para as classes de Log4j no plano de implementação de aplicativo do Community Edition. Para obter informações sobre outras diversas políticas do carregador de classe disponíveis no Community Edition, consulte esta nota técnica.
Esta seção ilustra como configurar o Log4j no nível do aplicativo. Usamos a mesma amostra que na seção anterior. No entanto, modificamos o plano de implementação do aplicativo do Community Edition (geronimo-web.xml) para ocultar as classes de Log4j. A Listagem 12 mostra o plano de implementação modificado do Geronimo, com a parte relevante do plano marcada em negrito.

Listagem 12. Plano de implementação modificado de geronimo-web.xml
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<web:web-app xmlns:dep="http://geronimo.apache.org/xml/ns/deployment-1.2"
    xmlns:conn="http://geronimo.apache.org/xml/ns/j2ee/connector-1.2"
    xmlns:name="http://geronimo.apache.org/xml/ns/naming-1.2"
    xmlns:ejb="http://openejb.apache.org/xml/ns/openejb-jar-2.2"
    xmlns:pkgen="http://openejb.apache.org/xml/ns/pkgen-2.1"
    xmlns:app="http://geronimo.apache.org/xml/ns/j2ee/application-2.0"
    xmlns:sec="http://geronimo.apache.org/xml/ns/security-2.0"
    xmlns:web="http://geronimo.apache.org/xml/ns/j2ee/web-2.0.1"
    xmlns:pers="http://java.sun.com/xml/ns/persistence"
    xmlns:client="http://geronimo.apache.org/xml/ns/j2ee/application-client-2.0">
    <dep:environment>
        <dep:moduleId>
            <dep:groupId>com.ibm.wasce.samples</dep:groupId>
            <dep:artifactId>EMPdemo-log4j-2</dep:artifactId>
            <dep:version>2.1.0.0</dep:version>
            <dep:type>war</dep:type>
        </dep:moduleId>
        <dependencies>
            <dependency>
                <groupId>console.dbpool</groupId>
                <artifactId>EMPLOYEE_DS</artifactId>
            </dependency>
        </dependencies>
        <hidden-classes>
  	<filter>org.apache.log4j</filter>
       </hidden-classes>
    </dep:environment>
    <web:context-root>/EMPdemo-log4j2</web:context-root>
    <name:resource-ref>
        <name:ref-name>jdbc/DataSource</name:ref-name>
        <name:resource-link>EMPLOYEE_DS</name:resource-link>
    </name:resource-ref>
</web:web-app>

Também copiamos o arquivo log4j.properties para o diretório WEB-INF/classes e copiamos log4j-1.2.14.jar para o diretório WEB-INF/lib do aplicativo EMPDemo. A Listagem 13 mostra o arquivo log4j.properties :

Listagem 13. O arquivo log4j.properties
log4j.logger.com.ibm.sample=debug,applog

log4j.appender.applog=org.apache.log4j.DailyRollingFileAppender
log4j.appender.applog.File=C:/temp/applevellogging/Log4J/applog1.log
log4j.appender.applog.layout=org.apache.log4j.PatternLayout

log4j.appender.applog.layout.ConversionPattern=%d{ABSOLUTE} %-5p [%c{1}] %m%n

Este arquivo de propriedades define um Criador de Logs para o servlet, e configura o Nível de Log como DEBUG. Mas o servlet substitui este valor para torná-lo ALL. Também define um DailyRollingFileAppender que registra mensagens no arquivo C:/temp/applevellogging/Log4J/applog1.log . O Layout usado pelo Anexador é o layout padrão do Community Edition usado no arquivo server-log4j.properties . Siga estas etapas para implementar o aplicativo.

  1. A partir da amostra faça download, descompacte o arquivo ZIP do aplicativo da Web modificado. O nome do arquivo WAR é EMPdemo-Log4jLogging2.war.
  2. Implemente o aplicativo.
    <wasce_home>/bin>deploy --user system --password manager deploy EMPdemo-Log4jLogging2.war
  3. Acesse o servlet EMPDemo apontando um navegador para http://localhost:8080/EMPdemo-log4j2/EMPDemo. O servlet mostra as linhas da tabela de funcionários no navegador.

Observe que nenhuma mensagem foi registrada no console do servidor ou no arquivo server.log, porque substituímos a arquivo do Log4j no nível do servidor e o configuramos no nível do aplicativo. Além disso, o aplicativo cria o arquivo C:/temp/applevellogging/Log4J/applog1.log e registra as mensagens neste arquivo. A Listagem 14 mostra as mensagens registradas no arquivo:

Listagem 14. Mensagens no arquivo applog1.log
15:18:36,078 INFO  [EMPDemo]
 Created the PrintWriter on the Response object
15:18:36,093 INFO  [EMPDemo]
 Got environment context:
 org.apache.xbean.naming.context.ImmutableContext$NestedImmutableContext@d760d76
15:18:36,093 INFO  [EMPDemo]
 Got DataSource: org.tranql.connector.jdbc.DataSource@32a232a2
15:18:36,109 INFO  [EMPDemo]
 Got Connection: org.tranql.connector.jdbc.ConnectionHandle@61e461e4
15:18:36,109 INFO  [EMPDemo]
 Created the statement: org.tranql.connector.jdbc.StatementHandle@67206720
15:18:36,109 INFO  [EMPDemo]
 Got the result set: org.tranql.connector.jdbc.ResultSetHandle@6f9a6f9a

15:18:36,109 INFO  [EMPDemo] Table EMP after SELECT:
15:18:36,109 INFO  [EMPDemo] 1   PHANI   SSE
15:18:36,109 INFO  [EMPDemo]    NIKHIL   100
15:18:36,109 INFO  [EMPDemo] 2   JOE   SSE
15:18:36,109 INFO  [EMPDemo]    NIKHIL   100
15:18:36,109 INFO  [EMPDemo] 3   JOHN   SSE
15:18:36,109 INFO  [EMPDemo]    BOB   200
15:18:36,109 DEBUG [EMPDemo] Debug
15:18:36,109 INFO  [EMPDemo] Info
15:18:36,109 WARN  [EMPDemo] Warn
15:18:36,109 ERROR [EMPDemo] Error
15:18:36,109 FATAL [EMPDemo] Fatal

Usando o SLF4J no Community Edition

O Simple Logging Facade for Java (SLF4J) serve como uma fachada simples para várias APIs de criação de log, que permite a conexão na implementação desejada no tempo de implementação. O SLF4j não inventa outra estrutura de criação de log, mas permite que o aplicativo use uma API padrão e seja conectado na implementação de criação de log real no tempo de implementação.

O SLF4j suporta vários sistemas de criação de log, tais como, NOP, Simple, Log4j versão 1.2, java.util.logging, JCL e logback. A distribuição SLF4j é fornecida com vários arquivos JAR:

  • slf4j-nop.jar
  • slf4j-simple.jar
  • slf4j-log4j12.jar
  • slf4j-log4j13.jar
  • slf4j-jdk14.jar
  • slf4j-jcl.jar.

Cada um destes arquivos jar é conectado fisicamente no tempo de compilação para usar apenas uma implementação. Todas as ligações fornecidas com o SLF4j dependem do slf4j-api.jar, que deve estar presente no caminho da classe para que a ligação funcione corretamente. Ele também fornece um caminho de migração para aplicativos que usam implementações de criação de log concretas usando módulos de ponte. O Community Edition é fornecido com estas bibliotecas que podem ser usadas em aplicativos:

  • slf4j-api-1.4.3.jar
  • slf4j-log4j12-1.4.3.jar
  • jcl104-over-slf4j-1.4.3.jar

Nesta seção, mostramos o uso do SLF4j das seguintes maneiras.

  1. Configurar o SLF4j para usar a configuração de Log4j do servidor
  2. Configurar o SLF4j usando Log4j no nível do aplicativo

Configurar o SLF4j para usar a configuração de Log4j do servidor

Nesta seção, usamos a API do SLF4j no servlet EMPDemo em vez da API Log4j. No entanto, ele usa a implementação de Log4j configurada no nível do servidor para implementação concreta. A Listagem 15 mostra o código do servlet:

Listagem 15. Esquema Servlet EMPDemo usando a API do SLF4j

Clique aqui para ver lista de códigos

Listagem 15. Esquema Servlet EMPDemo usando a API do SLF4j

Logger logger =  LoggerFactory.getLogger(EMPDemo.class.getName());
Connection con = null;
Statement stmt = null;
		
PrintWriter out = response.getWriter();
		
logger.info("Created the PrintWriter on the Response object");
		
try {
    Context initContext = new InitialContext();
    Context envContext  = (Context)initContext.lookup("java:comp/env");
    logger.info("Got environment context: "+envContext);
    DataSource ds = (DataSource)envContext.lookup("jdbc/DataSource");
    logger.info("Got DataSource: "+ds.toString());
    con = ds.getConnection();
    logger.info("Got Connection: "+con.toString() +"\n");
    stmt = con.createStatement();	
    logger.info("Created the statement: " +stmt);
    ResultSet rs = stmt.executeQuery("SELECT * FROM EMPLOYEE");
    logger.info("Gto the result set: " +rs);logger.info("Table EMP after SELECT:");
	
out.println("Your EMP table contains the following entries:<BR>");
		
out.println("<table>");
out.println("<tr>");
out.println("<th>Empno</th>");
out.println("<th>Name</th>");
out.println("<th>Job</th>");
out.println("<th>Manager</th>");
out.println("<th>Salary</th>");
    out.println("<th>Commission</th>");
    out.println("<th>Deptno</th>");
    out.println("</tr>");

    while (rs.next()) {
        String emp = rs.getString("EMPNO");
        String name  = rs.getString("ENAME");
        String job = rs.getString("JOB");
        String mgr = rs.getString("MGR");
        String sal = rs.getString("SAL");
        String comm = rs.getString("COMM");
        String dept = rs.getString("DEPTNO");

        out.println("<tr>");
        out.println("<td>"+emp+"</td>");
        out.println("<td>"+name+"</td>");
        out.println("<td>"+job+"</td>");
        out.println("<td>"+mgr+"</td>");
        out.println("<td>"+sal+"</td>");
        out.println("<td>"+comm+"</td>");
        out.println("<td>"+dept+"</td>");
        out.println("</tr>");
				
        logger.info(emp + "   " + name + "   " +job);logger.info("   " + mgr + "   " + dept);
    }
    out.println("</table>");
			
    rs.close();
    stmt.close();
    con.close();
			
        	
    logger.trace("Trace");logger.debug("Debug");logger.info("Info");logger.warn("Warn");logger.error("Error");

}
catch(java.lang.Exception e) {
			
        e.printStackTrace();
        logger.error(e.getClass().getName());logger.error(e.getMessage());

}

A Listagem 16 mostra as dependências declaradas para o SLF4j no plano de implementação do aplicativo do Community Edition (geronimo-web.xml).

Listagem 16. Função O arquivo geronimo-web.xml com dependências para SLF4j
<dependencies>
        …………
        …………

<dependency>
    <groupId>org.slf4j</groupId>
    <artifactId>slf4j-log4j12</artifactId>
    <version>1.4.3</version>
    <type>jar</type>
</dependency>
<dependency>
    <groupId>org.slf4j</groupId>
    <artifactId>slf4j-api</artifactId>
    <version>1.4.3</version>
    <type>jar</type>
    </dependency>
</dependencies>

Siga estas etapas para implementar e executar o aplicativo:

  1. A partir da amostra faça download, descompacte o arquivo ZIP do aplicativo. O arquivo war é Log4j-SLF4j-WEB.war.
  2. Implemente o aplicativo.
    <wasce_home>/bin>deploy --user system –-password manager deploy Log4j-SLF4j-WEB.war
  3. Acesse o servlet EMPDemo em http://localhost:8080/Log4j-SLF4j-WEB/EMPDemo.

A Listagem 17 mostra as mensagens de log que são exibidas no console do servidor:

Listagem 17. Mensagens do console do servidor
10:25:18,593 WARN  [EMPDemo] Warn
10:25:18,593 ERROR [EMPDemo] Error

Estas mensagens são exibidas porque o nível de log do ConsoleAppender está configurado como WARN no arquivo server-log4j.properties . Portanto, apenas as mensagens de log com o nível de log WARN ou acima são registradas no console. No entanto, é possível ver se todas as mensagens de log estão registradas no arquivo server.log .

Configurar o SLF4j usando Log4j no nível do aplicativo

Nesta seção, configuramos o SLF4j para usar a Log4j configurada no nível do aplicativo para o servlet EMPDemo. O código do servlet na Listagem 13 não é alterado. No entanto, o aplicativo é fornecido com um arquivo log4j.properties que substitui a configuração de Log4j no nível do servidor. O servlet EMPDemo usa a API do SLF4j para registrar as mensagens. A Listagem 18 mostra o arquivo log4j.properties :

Listagem 18. O arquivo log4j.properties
log4j.logger.com.ibm.sample=debug,applog

log4j.appender.applog=org.apache.log4j.DailyRollingFileAppender
log4j.appender.applog.File=C:/temp/applevellogging/SLF4j/java.log
log4j.appender.applog.layout=org.apache.log4j.PatternLayout

log4j.appender.applog.layout.ConversionPattern=%d{ABSOLUTE} %-5p [%c{1}] %m%n

Este arquivo log4j.properties configura o serviço de Log4j para usar DailyRollingFileAppender para registrar mensagens no arquivo C:/temp/applevellogging/SLF4j/java.log . Ele usa o formato do Community Edition usado para registrar mensagens.

A Listagem 19 mostra a parte relevante do plano de plano de implementação do Community Edition (geronimo-web.xml) para o aplicativo:

Listagem 19. Plano de implementação do aplicativo do Community Edition
<dep:environment>
	…………………
	…………………

        <dependencies>
	…………………
	…………………
            <dependency>
                <groupId>org.slf4j</groupId>
                <artifactId>slf4j-log4j12</artifactId>
                <version>1.4.3</version>
                <type>jar</type>
            </dependency>
            <dependency>
                <groupId>org.slf4j</groupId>
                <artifactId>slf4j-api</artifactId>
                <version>1.4.3</version>
                <type>jar</type>
            </dependency>
            <dependency>
                <groupId>log4j</groupId>
                <artifactId>log4j</artifactId>
                <version>1.2.14</version>
                <type>jar</type>
            </dependency>
        </dependencies>
        <hidden-classes>
  	<filter>org.apache.log4j</filter>
       </hidden-classes>
    </dep:environment>

O plano de implementação declara uma dependência das bibliotecas Log4j e SLF4j e oculta o pacote Log4j do carregador de classe pai. Siga estas etapas para implementar o aplicativo.

  1. Faça download do aplicativo e salve-o em um diretório. O nome do arquivo WAR é Log4j-SLF4j-AppLevel-WEB.war.
  2. Implemente o aplicativo.
    <wasce_home>/bin>deploy –user system –password manager deploy Log4j-SLF4j-AppLevel-WEB.war.
  3. Acesse o servlet EMPDemo em http://localhost:8080/Log4j-SLF4j-WEB/EMPDemo.

É possível ver se não existem mensagens registradas no console do servidor ou no arquivo server.log . No entanto, o aplicativo cria o arquivo C:/temp/applevellogging/SLF4j/java.log e registra a mensagem conforme configurada.


Conclusão

Mostramos como usar java.util.logging, Log4j e SLF4j no Community Edition de várias formas. Você aprendeu como usar gbeans para configurar serviços no escopo do servidor. Também aprendeu como as questões do carregador de classe podem se tornar um problema quando são necessárias configurações específicas do aplicativo para serviços de criação de log. Por último, seus aplicativos podem beneficiar-se do uso do SLF4j como uma API padrão para criação de log, para permitir a conexão na implementação de criação de log desejada no tempo de implementação.


Recursos


Download

DescriçãoNomeTamanhoMétodo de download
Sample codewasce_logging.zip358KBHTTP

Informações sobre métodos de download

Comentários

developerWorks: Conecte-se

Los campos obligatorios están marcados con un asterisco (*).


Precisa de um ID IBM?
Esqueceu seu ID IBM?


Esqueceu sua senha?
Alterar sua senha

Ao clicar em Enviar, você concorda com os termos e condições do developerWorks.

 


A primeira vez que você entrar no developerWorks, um perfil é criado para você. Informações no seu perfil (seu nome, país / região, e nome da empresa) é apresentado ao público e vai acompanhar qualquer conteúdo que você postar, a menos que você opte por esconder o nome da empresa. Você pode atualizar sua conta IBM a qualquer momento.

Todas as informações enviadas são seguras.

Elija su nombre para mostrar



Ao se conectar ao developerWorks pela primeira vez, é criado um perfil para você e é necessário selecionar um nome de exibição. O nome de exibição acompanhará o conteúdo que você postar no developerWorks.

Escolha um nome de exibição de 3 - 31 caracteres. Seu nome de exibição deve ser exclusivo na comunidade do developerWorks e não deve ser o seu endereço de email por motivo de privacidade.

Los campos obligatorios están marcados con un asterisco (*).

(Escolha um nome de exibição de 3 - 31 caracteres.)

Ao clicar em Enviar, você concorda com os termos e condições do developerWorks.

 


Todas as informações enviadas são seguras.


static.content.url=http://www.ibm.com/developerworks/js/artrating/
SITE_ID=80
Zone=Software livre
ArticleID=392621
ArticleTitle=Criação de Log do Aplicativo no WebSphere Application Server Community Edition
publish-date=05142014