HttpModule no IIS6, Eletronic Billing com Log4Net
Publicado; 12/01/2010 Arquivado em: Apache, HttpModule, IIS, ISAPI, Log4Net 3 Comments »Bom galera, estou a um bom tempo sem postar, né? Peço desculpas a todos que seguem o blog, mas entrei de férias no final de 2009 e me dei de presente um tempo de descanso, afinal ninguém é de ferro. Como esse é o primeiro post de 2010 desejo a todos um ótimo ano novo! O meu 2010 começou cheio de novidades e espero que o de vocês também.
Recebi uma proposta para mudar de emprego e resolvi aceitar, acredito que mudança de ares seja bom para minha carreira profissional, neste novo emprego estarei trabalhando diretamente com Flex + Java, legal né? Com uma dor do coração estou saindo da empresa que trabalho atualmente, gosto muito daqui e acredito que foi o lugar perfeito para ter o primeiro emprego. Aprendi muito e serei eternamente grato a todos que me ajudaram nesses quase 2 anos de experiência.
Sem mais lengalengas(alguém ainda fala isso?) farei um post rápido porém muito interessante. Recebi como tarefa recentemente o dever de desenvolver um sistema de Billing para os nossos serviços, afinal sem a capacidade de contabilizar os acessos feitos como poderíamos cobrar por algo? O metódo que escolhemos para billing foi atravez de log, isso parece simples, não? Mas, como sempre, o desenvolvimento e o ambiente que trabalhamos trouxeram algumas implicações e barreiras.
Nossos serviços estão disponibilizados através de um programa terceiro, com ducumentação vasta e uma ótima comunidade e isso sempre foi uma economia para a empresa. Precisávamos então de algo transparente para o usuário e para API.
Nossos serviços são disponibilizados no IIS 6, portanto o tutorial vai seguir esse mesmo requisito, porém no IIS 5 acredito que não deva haver nenhuma mudança.
Primeiramente crie uma Class Libery no Visual Studio, renomeie a primeira classe gerada VS para um nome que você goste. Precisamos então que a nossa classe implemente a interface IHttpModule, deixe que o VS gere os métodos necessários para validar nossa classe implementada. Seu projeto e sua classe devem estar da seguinte forma:
Bom, agora vamos desenvolver dois eventos e adiciona-los ao listener de Modulos do IIS, os dois eventos a serem desenvolvidos são BeginRequest e EndRequest, como o nome diz eles serão chamados antes e depois de cada requisição para assim termos acesso aos objetos de request e response. Diversos eventos podem ser mapeados e desenvolvidos, encontre o que se encaixa melhor em sua aplicação aqui.
using System;
using System.Collections.Generic;
using System.Text;
using System.Web;
using log4net.Config;
namespace MyModule
{
public class CustomModule : IHttpModule
{
//Instancia do Log4Net configurada genericamente, facilita para copiar e colar em outro projeto.
private static readonly log4net.ILog log = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
//Configuramos o Log4Net com o arquivo presente na raiz do projeto
public CustomModule()
{
XmlConfigurator.Configure(new System.IO.FileInfo(System.AppDomain.CurrentDomain.BaseDirectory + "\\bin\\log4net.config"));
}
public String ModuleName
{
get { return "ServicesModules"; }
}
public void Init(HttpApplication application)
{
//Aqui registramos os eventos desenvolvidos no listener
application.BeginRequest +=
(new EventHandler(this.Application_BeginRequest));
application.EndRequest +=
(new EventHandler(this.Application_EndRequest));
}
//Toda chamada feita é tratada pelo BeginRequest
private void Application_BeginRequest(Object source,
EventArgs e)
{
log.Info("Todas as chamadas antes de serem processadas passam por aqui.");
}
//Toda chamada a ser devolvida ao usuário passa primeiro pelo EndRequest
private void Application_EndRequest(Object source, EventArgs e)
{
try
{
HttpApplication application = (HttpApplication)source;
HttpContext context = application.Context;
string variavel = context.Request["variavel"];
if (!string.IsNullOrEmpty(token))
log.Info(string.Concat("Url de Chamada: ", context.Request.Url.AbsolutePath, " Variável a ser logada: ", variavel));
}
catch (Exception ex)
{
log.Error(ex.Message);
}
}
public void Dispose() { }
}
}
O código é simples e fácil de entender, com os diversos eventos que a API disponibiliza é possível fazer de tudo de maneira fácil e transparente para o usuário, legal não?!
Perceba que utilizamos o Log4Net, essa API da Apache surgiu a partir do Log4J para Java e é igualmente boa! Configurando ele corretamente é possível fazer de tudo com o log, desde de envio automático de email até gravar as linhas de log no banco com apenas algumas linhas de configuração.
Para este projeto utilizamos um Appender do Log4Net chamado de RollingFileAppender, com ele podemos fazer com que o Log4Net crie um arquivo de log para cada dia, dando um tamanho limite do arquivo e um estilo específico para o log.
Configuração do Log4Net:
<log4net>
<appender name="RollingLogFileAppender" type="log4net.Appender.RollingFileAppender">
<file value="logfile.txt" />
<appendToFile value="true" />
<rollingStyle value="Composite" />
<datePattern value="yyyyMMdd" />
<maxSizeRollBackups value="10" />
<maximumFileSize value="1024MB" />
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%date [%thread] %-5level - %message%newline" />
</layout>
</appender>
<root>
<level value="INFO" />
<appender-ref ref="RollingLogFileAppender" />
</root>
</log4net>
A Api que Microsoft dispõe para desenvolvimento Web é muito vasta e bem documentada, é possível tirar proveito de muitos recursos, basta você ter imaginação e vontade de procurar.
Agora com a .dll desenvolvida precisamos registrar ela na nossa aplicação .net, para que as requisições também sejam tratadas pelo nosso custom handler.
Abra o arquivo web.config do projeto Web e adicione a seguinte linha entre as tags <httpModules></httpModules>:
<add name="MyModule.CustomModule" type="MyModule.CustomModule, MyModule"/>
Reinicie o IIS e veja as chamadas ao seu projeto Web serem tratadas também pelo custom handler. As possiblidades de desenvolvimento são infinitas!
Acredite se quiser, fiquei cerca de 1 mês para conseguir desenvolver essa tarefa que contém apenas 10 linhas de programação, porém o resultado obtido foi excelente e se tornou algo transparente para o usuário e para API que utilizamos.
Bom galera, espero que gostem e que também venha ajudar alguém a não ficar 1 mês para desenvolver algo que aparentemente é tão simples.
Um abraço e lembrem, comentários e emails são bem vindos!


Diego,
estou tentando configurar o client do web service mas ta dando um erro
Exception in thread “main” javax.xml.ws.soap.SOAPFaultException: Could not send Message.
at org.apache.cxf.jaxws.JaxWsClientProxy.invoke(JaxWsClientProxy.java:145)
at com.mv.cxf.$Proxy32.calcularSoma(Unknown Source)
at com.mv.cxf.Client.main(Client.java:20)
Caused by: org.apache.cxf.interceptor.Fault: Could not send Message.
o que pode ser??? pode me ajudar??
fernandesleandro@yahoo.com.br
Olá amigo, tudo bom?
Tenha certeza que colocou as anotações nas interfaces e nas implementações dos seus serviços e que também declarou a area certa para o Spring fazer o reconhecimento das anotações. Qualquer dúvida entre em contato, desculpe pela demora para responder.
seu nerd! não entendi bulhufas!
ahuhsuausha beijos =*