You are viewing a plain text version of this content. The canonical link for it is here.
Posted to log4j-dev@logging.apache.org by rg...@apache.org on 2011/05/25 09:41:12 UTC

svn commit: r1127414 - in /logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src: main/java/org/apache/logging/log4j/core/ main/java/org/apache/logging/log4j/core/appender/ main/java/org/apache/logging/log4j/core/helpers/ main/java/org/...

Author: rgoers
Date: Wed May 25 07:41:11 2011
New Revision: 1127414

URL: http://svn.apache.org/viewvc?rev=1127414&view=rev
Log:
Add HTMLLayout

Added:
    logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/helpers/Transform.java
    logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/layout/HTMLLayout.java
    logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/test/java/org/apache/logging/log4j/core/layout/HTMLLayoutTest.java
      - copied, changed from r1084027, logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/test/java/org/apache/logging/log4j/core/layout/PatternLayoutTest.java
Modified:
    logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/LoggerContext.java
    logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/appender/ListAppender.java
    logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/appender/OutputStreamManager.java

Modified: logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/LoggerContext.java
URL: http://svn.apache.org/viewvc/logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/LoggerContext.java?rev=1127414&r1=1127413&r2=1127414&view=diff
==============================================================================
--- logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/LoggerContext.java (original)
+++ logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/LoggerContext.java Wed May 25 07:41:11 2011
@@ -45,10 +45,16 @@ public class LoggerContext implements or
 
     private Object externalContext = null;
 
+    private static final long JVM_START_TIME = System.currentTimeMillis();
+
     public LoggerContext() {
         reconfigure();
     }
 
+    public static long getStartTime() {
+        return JVM_START_TIME;
+    }
+
     public void setExternalContext(Object context) {
         this.externalContext = context;
     }

Modified: logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/appender/ListAppender.java
URL: http://svn.apache.org/viewvc/logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/appender/ListAppender.java?rev=1127414&r1=1127413&r2=1127414&view=diff
==============================================================================
--- logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/appender/ListAppender.java (original)
+++ logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/appender/ListAppender.java Wed May 25 07:41:11 2011
@@ -33,19 +33,29 @@ import java.util.List;
  * This appender is primarily used for testing. Use in a real environment is discouraged as the
  * List could eventually grow to cause an OutOfMemoryError.
  */
-@Plugin(name="List",type="Core",elementType="appender",printObject=true)
+@Plugin(name = "List", type = "Core", elementType = "appender", printObject = true)
 public class ListAppender extends AppenderBase {
 
     private List<LogEvent> events = new ArrayList<LogEvent>();
 
     private List<String> messages = new ArrayList<String>();
 
+    private final boolean newLine;
+
     public ListAppender(String name) {
         super(name, null, null);
+        newLine = false;
     }
 
-    public ListAppender(String name, Filters filters, Layout layout) {
+    public ListAppender(String name, Filters filters, Layout layout, boolean newline) {
         super(name, filters, layout);
+        this.newLine = newline;
+        if (layout != null) {
+            byte[] bytes = layout.getHeader();
+            if (bytes != null) {
+                write(bytes);
+            }
+        }
     }
 
     public synchronized void append(LogEvent event) {
@@ -53,7 +63,41 @@ public class ListAppender extends Append
         if (layout == null) {
             events.add(event);
         } else {
-            messages.add(new String(layout.format(event)));
+            write(layout.format(event));
+        }
+    }
+
+    private void write(byte[] bytes) {
+        String str = new String(bytes);
+        if (newLine) {
+            int index = 0;
+            while (index < str.length()) {
+                int end = str.indexOf("\n", index);
+                if (index == end) {
+                    if (!messages.get(messages.size() - 1).equals("")) {
+                        messages.add("");
+                    }
+                } else if (end >= 0) {
+                    messages.add(str.substring(index, end));
+                } else {
+                    messages.add(str.substring(index));
+                    break;
+                }
+                index = end + 1;
+            }
+        } else {
+            messages.add(str);
+        }
+    }
+
+    public void stop() {
+        super.stop();
+        Layout layout = getLayout();
+        if (layout != null) {
+            byte[] bytes = layout.getFooter();
+            if (bytes != null) {
+                write(bytes);
+            }
         }
     }
 
@@ -72,6 +116,7 @@ public class ListAppender extends Append
 
     @PluginFactory
     public static ListAppender createAppender(@PluginAttr("name") String name,
+                                              @PluginAttr("entryPerNewLine") String newLine,
                                               @PluginElement("layout") Layout layout,
                                               @PluginElement("filters") Filters filters) {
 
@@ -80,6 +125,8 @@ public class ListAppender extends Append
             return null;
         }
 
-        return new ListAppender(name, filters, layout);
+        boolean nl = (newLine == null) ? false : Boolean.parseBoolean(newLine);
+
+        return new ListAppender(name, filters, layout, nl);
     }
 }

Modified: logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/appender/OutputStreamManager.java
URL: http://svn.apache.org/viewvc/logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/appender/OutputStreamManager.java?rev=1127414&r1=1127413&r2=1127414&view=diff
==============================================================================
--- logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/appender/OutputStreamManager.java (original)
+++ logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/appender/OutputStreamManager.java Wed May 25 07:41:11 2011
@@ -48,8 +48,6 @@ public class OutputStreamManager {
 
     private int count;
 
-    private byte[] header = null;
-
     private byte[] footer = null;
 
     public StringBuilder buffer = new StringBuilder();
@@ -86,13 +84,17 @@ public class OutputStreamManager {
     }
 
     public synchronized void setHeader(byte[] header) {
-        if (header == null) {
-            this.header = header;
+        if (header != null) {
+            try {
+                this.os.write(header, 0, header.length);
+            } catch (IOException ioe) {
+                logger.error("Unable to write header", ioe);
+            }
         }
     }
 
     public synchronized void setFooter(byte[] footer) {
-        if (footer == null) {
+        if (footer != null) {
             this.footer = footer;
         }
     }

Added: logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/helpers/Transform.java
URL: http://svn.apache.org/viewvc/logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/helpers/Transform.java?rev=1127414&view=auto
==============================================================================
--- logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/helpers/Transform.java (added)
+++ logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/helpers/Transform.java Wed May 25 07:41:11 2011
@@ -0,0 +1,110 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache license, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the license for the specific language governing permissions and
+ * limitations under the license.
+ */
+package org.apache.logging.log4j.core.helpers;
+
+
+/**
+ * Utility class for transforming strings.
+ */
+public class Transform {
+
+    private static final String CDATA_START = "<![CDATA[";
+    private static final String CDATA_END = "]]>";
+    private static final String CDATA_PSEUDO_END = "]]&gt;";
+    private static final String CDATA_EMBEDED_END = CDATA_END + CDATA_PSEUDO_END + CDATA_START;
+    private static final int CDATA_END_LEN = CDATA_END.length();
+
+    /**
+     * This method takes a string which may contain HTML tags (ie,
+     * &lt;b&gt;, &lt;table&gt;, etc) and replaces any
+     * '<',  '>' , '&' or '"'
+     * characters with respective predefined entity references.
+     *
+     * @param input The text to be converted.
+     * @return The input string with the special characters replaced.
+     */
+    static public String escapeTags(final String input) {
+        //Check if the string is null, zero length or devoid of special characters
+        // if so, return what was sent in.
+
+        if (input == null
+            || input.length() == 0
+            || (input.indexOf('"') == -1 &&
+            input.indexOf('&') == -1 &&
+            input.indexOf('<') == -1 &&
+            input.indexOf('>') == -1)) {
+            return input;
+        }
+
+        //Use a StringBuffer in lieu of String concatenation -- it is
+        //much more efficient this way.
+
+        StringBuilder buf = new StringBuilder(input.length() + 6);
+        char ch = ' ';
+
+        int len = input.length();
+        for (int i = 0; i < len; i++) {
+            ch = input.charAt(i);
+            if (ch > '>') {
+                buf.append(ch);
+            } else if (ch == '<') {
+                buf.append("&lt;");
+            } else if (ch == '>') {
+                buf.append("&gt;");
+            } else if (ch == '&') {
+                buf.append("&amp;");
+            } else if (ch == '"') {
+                buf.append("&quot;");
+            } else {
+                buf.append(ch);
+            }
+        }
+        return buf.toString();
+    }
+
+    /**
+     * Ensures that embeded CDEnd strings (]]>) are handled properly
+     * within message, NDC and throwable tag text.
+     *
+     * @param buf StringBuffer holding the XML data to this point.  The
+     *            initial CDStart (<![CDATA[) and final CDEnd (]]>) of the CDATA
+     *            section are the responsibility of the calling method.
+     * @param str The String that is inserted into an existing CDATA Section within buf.
+     */
+    static public void appendEscapingCDATA(final StringBuilder buf,
+                                           final String str) {
+        if (str != null) {
+            int end = str.indexOf(CDATA_END);
+            if (end < 0) {
+                buf.append(str);
+            } else {
+                int start = 0;
+                while (end > -1) {
+                    buf.append(str.substring(start, end));
+                    buf.append(CDATA_EMBEDED_END);
+                    start = end + CDATA_END_LEN;
+                    if (start < str.length()) {
+                        end = str.indexOf(CDATA_END, start);
+                    } else {
+                        return;
+                    }
+                }
+                buf.append(str.substring(start));
+            }
+        }
+    }
+}

Added: logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/layout/HTMLLayout.java
URL: http://svn.apache.org/viewvc/logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/layout/HTMLLayout.java?rev=1127414&view=auto
==============================================================================
--- logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/layout/HTMLLayout.java (added)
+++ logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/main/java/org/apache/logging/log4j/core/layout/HTMLLayout.java Wed May 25 07:41:11 2011
@@ -0,0 +1,260 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache license, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the license for the specific language governing permissions and
+ * limitations under the license.
+ */
+package org.apache.logging.log4j.core.layout;
+
+import org.apache.logging.log4j.Level;
+import org.apache.logging.log4j.core.LogEvent;
+import org.apache.logging.log4j.core.LoggerContext;
+import org.apache.logging.log4j.core.config.plugins.Plugin;
+import org.apache.logging.log4j.core.config.plugins.PluginAttr;
+import org.apache.logging.log4j.core.config.plugins.PluginFactory;
+import org.apache.logging.log4j.core.helpers.Transform;
+
+import java.io.IOException;
+import java.io.InterruptedIOException;
+import java.io.LineNumberReader;
+import java.io.PrintWriter;
+import java.io.StringReader;
+import java.io.StringWriter;
+import java.nio.charset.Charset;
+import java.util.ArrayList;
+
+/**
+ * This layout outputs events in a HTML table.
+ * <p/>
+ * Appenders using this layout should have their encoding set to UTF-8 or UTF-16, otherwise events containing
+ * non ASCII characters could result in corrupted log files.
+ */
+@Plugin(name="HTMLLayout",type="Core",elementType="layout",printObject=true)
+public class HTMLLayout extends LayoutBase {
+
+    protected final int BUF_SIZE = 256;
+    protected final int MAX_CAPACITY = 1024;
+
+    static String TRACE_PREFIX = "<br>&nbsp;&nbsp;&nbsp;&nbsp;";
+
+    // output buffer appended to when format() is invoked
+    private StringBuilder sbuf = new StringBuilder(BUF_SIZE);
+
+    // Print no location info by default
+    protected final boolean locationInfo;
+
+    private static final String DEFAULT_TITLE = "Log4J Log Messages";
+
+    private static final String DEFAULT_CONTENT_TYPE = "text/html";
+
+    protected final String title;
+
+    protected final String contentType;
+
+    protected final Charset charset;
+
+    public HTMLLayout(boolean locationInfo, String title, String contentType, Charset charset) {
+        this.locationInfo = locationInfo;
+        this.title = title;
+        this.contentType = contentType;
+        this.charset = charset;
+    }
+
+    public byte[] format(LogEvent event) {
+
+        if (sbuf.capacity() > MAX_CAPACITY) {
+            sbuf = new StringBuilder(BUF_SIZE);
+        } else {
+            sbuf.setLength(0);
+        }
+
+        sbuf.append(LINE_SEP).append("<tr>").append(LINE_SEP);
+
+        sbuf.append("<td>");
+        sbuf.append(event.getMillis() - LoggerContext.getStartTime());
+        sbuf.append("</td>").append(LINE_SEP);
+
+        String escapedThread = Transform.escapeTags(event.getThreadName());
+        sbuf.append("<td title=\"" + escapedThread + " thread\">");
+        sbuf.append(escapedThread);
+        sbuf.append("</td>").append(LINE_SEP);
+
+        sbuf.append("<td title=\"Level\">");
+        if (event.getLevel().equals(Level.DEBUG)) {
+            sbuf.append("<font color=\"#339933\">");
+            sbuf.append(Transform.escapeTags(String.valueOf(event.getLevel())));
+            sbuf.append("</font>");
+        } else if (event.getLevel().isAtLeastAsSpecificAs(Level.WARN)) {
+            sbuf.append("<font color=\"#993300\"><strong>");
+            sbuf.append(Transform.escapeTags(String.valueOf(event.getLevel())));
+            sbuf.append("</strong></font>");
+        } else {
+            sbuf.append(Transform.escapeTags(String.valueOf(event.getLevel())));
+        }
+        sbuf.append("</td>").append(LINE_SEP);
+
+        String escapedLogger = Transform.escapeTags(event.getLoggerName());
+        if (escapedLogger.length() == 0) {
+            escapedLogger = "root";
+        }
+        sbuf.append("<td title=\"").append(escapedLogger).append(" category\">");
+        sbuf.append(escapedLogger);
+        sbuf.append("</td>").append(LINE_SEP);
+
+        if (locationInfo) {
+            StackTraceElement element = event.getSource();
+            sbuf.append("<td>");
+            sbuf.append(Transform.escapeTags(element.getFileName()));
+            sbuf.append(':');
+            sbuf.append(element.getLineNumber());
+            sbuf.append("</td>").append(LINE_SEP);
+        }
+
+        sbuf.append("<td title=\"Message\">");
+        sbuf.append(Transform.escapeTags(event.getMessage().getFormattedMessage()));
+        sbuf.append("</td>").append(LINE_SEP);
+        sbuf.append("</tr>").append(LINE_SEP);
+
+        if (event.getContextStack().size() > 0) {
+            sbuf.append(
+                "<tr><td bgcolor=\"#EEEEEE\" style=\"font-size : xx-small;\" colspan=\"6\" title=\"Nested Diagnostic Context\">");
+            sbuf.append("NDC: " + Transform.escapeTags(event.getContextStack().toString()));
+            sbuf.append("</td></tr>").append(LINE_SEP);
+        }
+
+
+        if (event.getContextMap().size() > 0) {
+            sbuf.append(
+                "<tr><td bgcolor=\"#EEEEEE\" style=\"font-size : xx-small;\" colspan=\"6\" title=\"Mapped Diagnostic Context\">");
+            sbuf.append("MDC: " + Transform.escapeTags(event.getContextMap().toString()));
+            sbuf.append("</td></tr>").append(LINE_SEP);
+        }
+
+        Throwable throwable = event.getThrown();
+        if (throwable != null) {
+            sbuf.append("<tr><td bgcolor=\"#993300\" style=\"color:White; font-size : xx-small;\" colspan=\"6\">");
+            appendThrowableAsHTML(throwable, sbuf);
+            sbuf.append("</td></tr>").append(LINE_SEP);
+        }
+
+        return sbuf.toString().getBytes(charset);
+    }
+
+    void appendThrowableAsHTML(Throwable throwable, StringBuilder sbuf) {
+        StringWriter sw = new StringWriter();
+        PrintWriter pw = new PrintWriter(sw);
+        try {
+            throwable.printStackTrace(pw);
+        } catch(RuntimeException ex) {
+        }
+        pw.flush();
+        LineNumberReader reader = new LineNumberReader(new StringReader(sw.toString()));
+        ArrayList<String> lines = new ArrayList<String>();
+        try {
+          String line = reader.readLine();
+          while(line != null) {
+            lines.add(line);
+            line = reader.readLine();
+          }
+        } catch(IOException ex) {
+            if (ex instanceof InterruptedIOException) {
+                Thread.currentThread().interrupt();
+            }
+            lines.add(ex.toString());
+        }
+        boolean first = true;
+        for (String line : lines) {
+            if (!first) {
+                sbuf.append(TRACE_PREFIX);
+            } else {
+                first = false;
+            }
+            sbuf.append(Transform.escapeTags(line));
+            sbuf.append(LINE_SEP);
+        }
+    }
+
+    /**
+     * Returns appropriate HTML headers.
+     */
+    @Override
+    public byte[] getHeader() {
+        StringBuilder sbuf = new StringBuilder();
+        sbuf.append(
+            "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">");
+        sbuf.append(LINE_SEP);
+        sbuf.append("<html>").append(LINE_SEP);
+        sbuf.append("<head>").append(LINE_SEP);
+        sbuf.append("<title>").append(title).append("</title>").append(LINE_SEP);
+        sbuf.append("<style type=\"text/css\">").append(LINE_SEP);
+        sbuf.append("<!--").append(LINE_SEP);
+        sbuf.append("body, table {font-family: arial,sans-serif; font-size: x-small;}").append(LINE_SEP);
+        sbuf.append("th {background: #336699; color: #FFFFFF; text-align: left;}").append(LINE_SEP);
+        sbuf.append("-->").append(LINE_SEP);
+        sbuf.append("</style>").append(LINE_SEP);
+        sbuf.append("</head>").append(LINE_SEP);
+        sbuf.append("<body bgcolor=\"#FFFFFF\" topmargin=\"6\" leftmargin=\"6\">").append(LINE_SEP);
+        sbuf.append("<hr size=\"1\" noshade>").append(LINE_SEP);
+        sbuf.append("Log session start time " + new java.util.Date() + "<br>").append(LINE_SEP);
+        sbuf.append("<br>").append(LINE_SEP);
+        sbuf.append(
+            "<table cellspacing=\"0\" cellpadding=\"4\" border=\"1\" bordercolor=\"#224466\" width=\"100%\">");
+        sbuf.append(LINE_SEP);
+        sbuf.append("<tr>").append(LINE_SEP);
+        sbuf.append("<th>Time</th>").append(LINE_SEP);
+        sbuf.append("<th>Thread</th>").append(LINE_SEP);
+        sbuf.append("<th>Level</th>").append(LINE_SEP);
+        sbuf.append("<th>Logger</th>").append(LINE_SEP);
+        if (locationInfo) {
+            sbuf.append("<th>File:Line</th>").append(LINE_SEP);
+        }
+        sbuf.append("<th>Message</th>").append(LINE_SEP);
+        sbuf.append("</tr>").append(LINE_SEP);
+        return sbuf.toString().getBytes(charset);
+    }
+
+    /**
+     * Returns the appropriate HTML footers.
+     */
+    @Override
+    public byte[] getFooter() {
+        StringBuilder sbuf = new StringBuilder();
+        sbuf.append("</table>").append(LINE_SEP);
+        sbuf.append("<br>").append(LINE_SEP);
+        sbuf.append("</body></html>");
+        return sbuf.toString().getBytes(charset);
+    }
+
+    @PluginFactory
+    public static HTMLLayout createLayout(@PluginAttr("locationInfo") String locationInfo,
+                                          @PluginAttr("title") String title,
+                                          @PluginAttr("contentType") String contentType,
+                                          @PluginAttr("charset") String charset) {
+        Charset c = Charset.isSupported("UTF-8") ? Charset.forName("UTF-8") : Charset.defaultCharset();
+        if (charset != null) {
+            if (Charset.isSupported(charset)) {
+                c = Charset.forName(charset);
+            } else {
+                logger.error("Charset " + charset + " is not supported for layout, using " + c.displayName());
+            }
+        }
+        boolean info = locationInfo == null ? false : Boolean.valueOf(locationInfo);
+        if (title == null) {
+            title = DEFAULT_TITLE;
+        }
+        if (contentType == null) {
+            contentType = DEFAULT_CONTENT_TYPE;
+        }
+        return new HTMLLayout(info, title, contentType, c);
+    }
+}

Copied: logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/test/java/org/apache/logging/log4j/core/layout/HTMLLayoutTest.java (from r1084027, logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/test/java/org/apache/logging/log4j/core/layout/PatternLayoutTest.java)
URL: http://svn.apache.org/viewvc/logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/test/java/org/apache/logging/log4j/core/layout/HTMLLayoutTest.java?p2=logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/test/java/org/apache/logging/log4j/core/layout/HTMLLayoutTest.java&p1=logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/test/java/org/apache/logging/log4j/core/layout/PatternLayoutTest.java&r1=1084027&r2=1127414&rev=1127414&view=diff
==============================================================================
--- logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/test/java/org/apache/logging/log4j/core/layout/PatternLayoutTest.java (original)
+++ logging/log4j/branches/BRANCH_2_0_EXPERIMENTAL/rgoers/log4j2-core/src/test/java/org/apache/logging/log4j/core/layout/HTMLLayoutTest.java Wed May 25 07:41:11 2011
@@ -19,13 +19,13 @@ package org.apache.logging.log4j.core.la
 import org.apache.logging.log4j.Level;
 import org.apache.logging.log4j.LogManager;
 import org.apache.logging.log4j.ThreadContext;
-import org.apache.logging.log4j.core.Appender;
-import org.apache.logging.log4j.core.Lifecycle;
+import org.apache.logging.log4j.core.BasicConfigurationFactory;
 import org.apache.logging.log4j.core.Logger;
 import org.apache.logging.log4j.core.LoggerContext;
-import org.apache.logging.log4j.core.BasicConfigurationFactory;
+import org.apache.logging.log4j.core.appender.ConsoleAppender;
 import org.apache.logging.log4j.core.appender.FileAppender;
 import org.apache.logging.log4j.core.appender.FileManager;
+import org.apache.logging.log4j.core.appender.ListAppender;
 import org.apache.logging.log4j.core.config.ConfigurationFactory;
 import org.apache.logging.log4j.core.util.Compare;
 import org.junit.AfterClass;
@@ -33,19 +33,17 @@ import org.junit.BeforeClass;
 import org.junit.Test;
 
 import java.io.FileOutputStream;
+import java.util.List;
 
 import static org.junit.Assert.assertTrue;
 
 /**
  *
  */
-public class PatternLayoutTest {
-    static String OUTPUT_FILE   = "target/output/PatternParser";
-    static String WITNESS_FILE  = "witness/PatternParser";
+public class HTMLLayoutTest {
     LoggerContext ctx = (LoggerContext) LogManager.getContext();
     Logger root = ctx.getLogger("");
 
-    static String msgPattern = "%m%n";
     static ConfigurationFactory cf = new BasicConfigurationFactory();
 
     @BeforeClass
@@ -60,24 +58,19 @@ public class PatternLayoutTest {
         ConfigurationFactory.removeConfigurationFactory(cf);
     }
 
+    private static final String body =
+        "<tr><td bgcolor=\"#993300\" style=\"color:White; font-size : xx-small;\" colspan=\"6\">java.lang.NullPointerException: test";
+
 
     /**
      * Test case for MDC conversion pattern.
      */
     @Test
-    public void mdcPattern() throws Exception {
-
-        String mdcMsgPattern1 = "%m : %X%n";
-        String mdcMsgPattern2 = "%m : %X{key1}%n";
-        String mdcMsgPattern3 = "%m : %X{key2}%n";
-        String mdcMsgPattern4 = "%m : %X{key3}%n";
-        String mdcMsgPattern5 = "%m : %X{key1},%X{key2},%X{key3}%n";
+    public void testLayout() throws Exception {
 
         // set up appender
-        PatternLayout layout = new PatternLayout(msgPattern);
-        //FileOutputStream fos = new FileOutputStream(OUTPUT_FILE + "_mdc");
-        FileManager manager = FileManager.getFileManager(OUTPUT_FILE + "_mdc", false, false, false);
-        FileAppender appender = new FileAppender("File", layout, null, manager, OUTPUT_FILE + "_mdc", true, false);
+        HTMLLayout layout = HTMLLayout.createLayout("true", null, null, null);
+        ListAppender appender = new ListAppender("List", null, layout, true);
         appender.start();
 
         // set appender on root and set level to debug
@@ -87,47 +80,25 @@ public class PatternLayoutTest {
         // output starting message
         root.debug("starting mdc pattern test");
 
-        layout.setConversionPattern(mdcMsgPattern1);
-        root.debug("empty mdc, no key specified in pattern");
-
-        layout.setConversionPattern(mdcMsgPattern2);
-        root.debug("empty mdc, key1 in pattern");
-
-        layout.setConversionPattern(mdcMsgPattern3);
-        root.debug("empty mdc, key2 in pattern");
-
-        layout.setConversionPattern(mdcMsgPattern4);
-        root.debug("empty mdc, key3 in pattern");
-
-        layout.setConversionPattern(mdcMsgPattern5);
-        root.debug("empty mdc, key1, key2, and key3 in pattern");
+        root.debug("empty mdc");
 
         ThreadContext.put("key1", "value1");
         ThreadContext.put("key2", "value2");
 
-        layout.setConversionPattern(mdcMsgPattern1);
-        root.debug("filled mdc, no key specified in pattern");
-
-        layout.setConversionPattern(mdcMsgPattern2);
-        root.debug("filled mdc, key1 in pattern");
-
-        layout.setConversionPattern(mdcMsgPattern3);
-        root.debug("filled mdc, key2 in pattern");
-
-        layout.setConversionPattern(mdcMsgPattern4);
-        root.debug("filled mdc, key3 in pattern");
-
-        layout.setConversionPattern(mdcMsgPattern5);
-        root.debug("filled mdc, key1, key2, and key3 in pattern");
+        root.debug("filled mdc");
 
         ThreadContext.remove("key1");
         ThreadContext.remove("key2");
 
-        layout.setConversionPattern(msgPattern);
-        root.debug("finished mdc pattern test");
-
-        assertTrue(Compare.compare(this.getClass(), OUTPUT_FILE + "_mdc", WITNESS_FILE + "_mdc"));
+        root.error("finished mdc pattern test", new NullPointerException("test"));
 
         appender.stop();
+
+        List<String> list = appender.getMessages();
+
+        assertTrue("Incorrect number of lines. Expected 93, actual " + list.size(), list.size() == 93);
+        assertTrue("Incorrect header", list.get(3).equals("<title>Log4J Log Messages</title>"));
+        assertTrue("Incorrect footer", list.get(92).equals("</body></html>"));
+        assertTrue("Incorrect body", list.get(61).equals(body));
     }
 }



---------------------------------------------------------------------
To unsubscribe, e-mail: log4j-dev-unsubscribe@logging.apache.org
For additional commands, e-mail: log4j-dev-help@logging.apache.org