代码之家  ›  专栏  ›  技术社区  ›  Tim

将日志的有效负载记录到Tomcat

  •  18
  • Tim  · 技术社区  · 16 年前

    我通过编辑conf/server.xml并取消对org.apache.catalina.valves.accesslogvalve的条目的注释,成功地在Tomcat中启用了访问日志记录。我想能把邮局的有效载荷卸下来。似乎模式中的任何选项都不能做到这一点。有内置的方法吗?我用入口阀吗?

    4 回复  |  直到 8 年前
        1
  •  8
  •   Tim    16 年前

    由于没有关于获取Post有效负载的内置方法的建议,所以我继续编写了一个自定义过滤器来转储有效负载的内容。明确地:

    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse,
                         FilterChain chain) throws IOException, ServletException {
        HttpServletRequest request = (HttpServletRequest) servletRequest;
        LOG.debug("payload: " + requestWrapper.getRequestBody());
    

    和Web.xml:

    <filter>
        <filter-name>PayloadLoggingFilter</filter-name>
        <filter-class>com.host.PayloadLoggingFilter</filter-class>
    </filter>
    
    <filter-mapping>
        <filter-name>PayloadLoggingFilter</filter-name>
        <url-pattern>/resources/*</url-pattern>
    </filter-mapping>
    
        2
  •  4
  •   ZZ Coder    16 年前

    如果是表单(application/x-www-urlencoded),可以使用扩展访问日志阀,

    http://tomcat.apache.org/tomcat-6.0-doc/api/org/apache/catalina/valves/ExtendedAccessLogValve.html

    您必须像这样选择模式中的各个参数,

      x-P(param_name)
    
        3
  •  3
  •   Joel Peltonen    8 年前
    1. 在webapp web.xml中添加:

      <filter>
        <filter-name>PayloadLoggingFilter</filter-name>
        <filter-class>your.MyLogFilter</filter-class>
      </filter>
      <filter-mapping>
        <filter-name>PayloadLoggingFilter</filter-name>
        <url-pattern>/path/*</url-pattern>
      </filter-mapping>
      
    2. 创建筛选器:

      import java.io.BufferedReader;
      import java.io.ByteArrayInputStream;
      import java.io.ByteArrayOutputStream;
      import java.io.IOException;
      import java.io.InputStream;
      import java.io.InputStreamReader;
      import java.io.OutputStream;
      import java.io.OutputStreamWriter;
      import java.io.PrintWriter;
      import java.util.Enumeration;
      import java.util.HashMap;
      import java.util.Locale;
      import java.util.Map;
      
      import javax.servlet.Filter;
      import javax.servlet.FilterChain;
      import javax.servlet.FilterConfig;
      import javax.servlet.ServletException;
      import javax.servlet.ServletInputStream;
      import javax.servlet.ServletOutputStream;
      import javax.servlet.ServletRequest;
      import javax.servlet.ServletResponse;
      import javax.servlet.http.Cookie;
      import javax.servlet.http.HttpServletRequest;
      import javax.servlet.http.HttpServletRequestWrapper;
      import javax.servlet.http.HttpServletResponse;
      
      import org.apache.commons.io.output.TeeOutputStream;
      
      import com.liferay.portal.kernel.log.Log;
      import com.liferay.portal.kernel.log.LogFactoryUtil;
      import com.liferay.util.servlet.ServletInputStreamWrapper;
      
      public class MyLogFilter implements Filter {
      
          private static final Log logger = LogFactoryUtil.getLog(MyLogFilter.class);
      
          @Override
          public void init(FilterConfig filterConfig) throws ServletException {
          }
      
          @Override
          public void doFilter(ServletRequest request, ServletResponse response,
                  FilterChain chain) throws IOException, ServletException {
              try {
                  HttpServletRequest httpServletRequest = (HttpServletRequest) request;
                  HttpServletResponse httpServletResponse = (HttpServletResponse) response;
      
                  Map<String, String> requestMap = this.getTypesafeRequestMap(httpServletRequest);
                  BufferedRequestWrapper bufferedReqest = new BufferedRequestWrapper(httpServletRequest);
                  BufferedResponseWrapper bufferedResponse = new BufferedResponseWrapper(httpServletResponse);
      
                  chain.doFilter(bufferedReqest, bufferedResponse);
      
                  if(bufferedResponse.getContent()!=null){    //Response
                      final StringBuilder resMessage = new StringBuilder();
                      resMessage.append(" [RESPONSE:")
                              .append(bufferedResponse.getContent() )
                              .append("]");
                      logger.info(resMessage);
                  }
                  else{ //Request
                      final StringBuilder reqMessage = new StringBuilder(
                              "REST Request - ").append("[HTTP METHOD:")
                              .append(httpServletRequest.getMethod())
                              .append("] [PATH INFO:")
                              .append(httpServletRequest.getPathInfo())
                              .append("] [REQUEST PARAMETERS:").append(requestMap)
                              .append("] [REQUEST BODY:")
                              .append(bufferedReqest.getRequestBody())
                              .append("] [REMOTE ADDRESS:")
                              .append(httpServletRequest.getRemoteAddr()).append("]");
                      logger.info(reqMessage);
                  }
      
      
              } catch (Throwable a) {
                  logger.error(a);
              }
          }
      
          private Map<String, String> getTypesafeRequestMap(HttpServletRequest request) {
              Map<String, String> typesafeRequestMap = new HashMap<String, String>();
              Enumeration<?> requestParamNames = request.getParameterNames();
              while (requestParamNames.hasMoreElements()) {
                  String requestParamName = (String) requestParamNames.nextElement();
                  String requestParamValue = request.getParameter(requestParamName);
                  typesafeRequestMap.put(requestParamName, requestParamValue);
              }
              return typesafeRequestMap;
          }
      
          @Override
          public void destroy() {
          }
      
          private static final class BufferedRequestWrapper extends
                  HttpServletRequestWrapper {
      
              private ByteArrayInputStream bais = null;
              private ByteArrayOutputStream baos = null;
              private BufferedServletInputStream bsis = null;
              private byte[] buffer = null;
      
              public BufferedRequestWrapper(HttpServletRequest req)
                      throws IOException {
                  super(req);
                  // Read InputStream and store its content in a buffer.
                  InputStream is = req.getInputStream();
                  this.baos = new ByteArrayOutputStream();
                  byte buf[] = new byte[1024];
                  int letti;
                  while ((letti = is.read(buf)) > 0) {
                      this.baos.write(buf, 0, letti);
                  }
                  this.buffer = this.baos.toByteArray();
              }
      
              @Override
              public ServletInputStream getInputStream() {
                  this.bais = new ByteArrayInputStream(this.buffer);
                  this.bsis = new BufferedServletInputStream(this.bais);
      
                  return this.bsis;
              }
      
              @Override
              public BufferedReader getReader() throws IOException {
                  return new BufferedReader(new InputStreamReader(this.getInputStream()));
              }
      
              String getRequestBody() throws IOException {
                  BufferedReader reader = new BufferedReader(new InputStreamReader(
                          this.getInputStream()));
                  String line = null;
                  StringBuilder inputBuffer = new StringBuilder();
                  do {
                      line = reader.readLine();
                      if (null != line) {
                          inputBuffer.append(line.trim());
                      }
                  } while (line != null);
                  reader.close();
                  return inputBuffer.toString().trim();
              }
      
          }
      
          private static final class BufferedServletInputStream extends
                  ServletInputStream {
      
              private ByteArrayInputStream bais;
      
              public BufferedServletInputStream(ByteArrayInputStream bais) {
                  this.bais = bais;
              }
      
              @Override
              public int available() {
                  return this.bais.available();
              }
      
              @Override
              public int read() {
                  return this.bais.read();
              }
      
              @Override
              public int read(byte[] buf, int off, int len) {
                  return this.bais.read(buf, off, len);
              }
      
          }
      
          public class TeeServletOutputStream extends ServletOutputStream {
      
              private final TeeOutputStream targetStream;
      
              public TeeServletOutputStream(OutputStream one, OutputStream two) {
                  targetStream = new TeeOutputStream(one, two);
              }
      
              @Override
              public void write(int arg0) throws IOException {
                  this.targetStream.write(arg0);
              }
      
              public void flush() throws IOException {
                  super.flush();
                  this.targetStream.flush();
              }
      
              public void close() throws IOException {
                  super.close();
                  this.targetStream.close();
              }
          }
      
          public class BufferedResponseWrapper implements HttpServletResponse {
      
              HttpServletResponse original;
              TeeServletOutputStream teeStream;
              PrintWriter teeWriter;
              ByteArrayOutputStream bos;
      
              public BufferedResponseWrapper(HttpServletResponse response) {
                  original = response;
              }
      
              public String getContent() {
                  if(bos == null){
                      return null;
                  }
                  return bos.toString();
              }
      
              @Override
              public PrintWriter getWriter() throws IOException {
      
                  if (this.teeWriter == null) {
                      this.teeWriter = new PrintWriter(new OutputStreamWriter(
                              getOutputStream()));
                  }
                  return this.teeWriter;
              }
      
              @Override
              public ServletOutputStream getOutputStream() throws IOException {
      
                  if (teeStream == null) {
                      bos = new ByteArrayOutputStream();
                      teeStream = new TeeServletOutputStream(
                              original.getOutputStream(), bos);
                  }
                  return teeStream;
              }
      
              @Override
              public String getCharacterEncoding() {
                  return original.getCharacterEncoding();
              }
      
              @Override
              public String getContentType() {
                  return original.getContentType();
              }
      
              @Override
              public void setCharacterEncoding(String charset) {
                  original.setCharacterEncoding(charset);
              }
      
              @Override
              public void setContentLength(int len) {
                  original.setContentLength(len);
              }
      
              @Override
              public void setContentType(String type) {
                  original.setContentType(type);
              }
      
              @Override
              public void setBufferSize(int size) {
                  original.setBufferSize(size);
              }
      
              @Override
              public int getBufferSize() {
                  return original.getBufferSize();
              }
      
              @Override
              public void flushBuffer() throws IOException {
                  if (teeStream != null) {
                      teeStream.flush();
                  }
                  if (this.teeWriter != null) {
                      this.teeWriter.flush();
                  }
              }
      
              @Override
              public void resetBuffer() {
                  original.resetBuffer();
              }
      
              @Override
              public boolean isCommitted() {
                  return original.isCommitted();
              }
      
              @Override
              public void reset() {
                  original.reset();
              }
      
              @Override
              public void setLocale(Locale loc) {
                  original.setLocale(loc);
              }
      
              @Override
              public Locale getLocale() {
                  return original.getLocale();
              }
      
              @Override
              public void addCookie(Cookie cookie) {
                  original.addCookie(cookie);
              }
      
              @Override
              public boolean containsHeader(String name) {
                  return original.containsHeader(name);
              }
      
              @Override
              public String encodeURL(String url) {
                  return original.encodeURL(url);
              }
      
              @Override
              public String encodeRedirectURL(String url) {
                  return original.encodeRedirectURL(url);
              }
      
              @SuppressWarnings("deprecation")
              @Override
              public String encodeUrl(String url) {
                  return original.encodeUrl(url);
              }
      
              @SuppressWarnings("deprecation")
              @Override
              public String encodeRedirectUrl(String url) {
                  return original.encodeRedirectUrl(url);
              }
      
              @Override
              public void sendError(int sc, String msg) throws IOException {
                  original.sendError(sc, msg);
              }
      
              @Override
              public void sendError(int sc) throws IOException {
                  original.sendError(sc);
              }
      
              @Override
              public void sendRedirect(String location) throws IOException {
                  original.sendRedirect(location);
              }
      
              @Override
              public void setDateHeader(String name, long date) {
                  original.setDateHeader(name, date);
              }
      
              @Override
              public void addDateHeader(String name, long date) {
                  original.addDateHeader(name, date);
              }
      
              @Override
              public void setHeader(String name, String value) {
                  original.setHeader(name, value);
              }
      
              @Override
              public void addHeader(String name, String value) {
                  original.addHeader(name, value);
              }
      
              @Override
              public void setIntHeader(String name, int value) {
                  original.setIntHeader(name, value);
              }
      
              @Override
              public void addIntHeader(String name, int value) {
                  original.addIntHeader(name, value);
              }
      
              @Override
              public void setStatus(int sc) {
                  original.setStatus(sc);
              }
      
              @SuppressWarnings("deprecation")
              @Override
              public void setStatus(int sc, String sm) {
                  original.setStatus(sc, sm);
              }
      
          }
      
      }
      
        4
  •  1
  •   Janning Vygen    14 年前

    请参见此处的RequestDumperValve或RequestDumperFilter: http://tomcat.apache.org/tomcat-5.5-doc/config/valve.html#Request_Dumper_Valve 它做你想要的。