geronimo-scm mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From ammul...@apache.org
Subject svn commit: r224657 - in /geronimo/trunk: modules/assembly/src/plan/ modules/j2ee/src/java/org/apache/geronimo/j2ee/j2eeobjectnames/ modules/j2ee/src/java/org/apache/geronimo/j2ee/management/geronimo/ modules/j2ee/src/java/org/apache/geronimo/j2ee/mana...
Date Sun, 24 Jul 2005 20:52:48 GMT
Author: ammulder
Date: Sun Jul 24 13:52:35 2005
New Revision: 224657

URL: http://svn.apache.org/viewcvs?rev=224657&view=rev
Log:
Add logging to management API
Update system log portlet

Added:
    geronimo/trunk/modules/system/src/java/org/apache/geronimo/system/logging/SystemLog.java   (with props)
Removed:
    geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/util/LogHelper.java
Modified:
    geronimo/trunk/modules/assembly/src/plan/client-system-plan.xml
    geronimo/trunk/modules/assembly/src/plan/deployer-system-plan.xml
    geronimo/trunk/modules/assembly/src/plan/system-plan.xml
    geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/j2eeobjectnames/NameFactory.java
    geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/management/geronimo/JVM.java
    geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/management/impl/JVMImpl.java
    geronimo/trunk/modules/j2ee/src/test/org/apache/geronimo/j2ee/management/Abstract77Test.java
    geronimo/trunk/modules/system/src/java/org/apache/geronimo/system/logging/log4j/Log4jService.java
    geronimo/trunk/sandbox/console-core/src/java/org/apache/geronimo/console/util/KernelManagementHelper.java
    geronimo/trunk/sandbox/console-core/src/java/org/apache/geronimo/console/util/ManagementHelper.java
    geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/logmanager/LogManagerPortlet.java
    geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/logmanager/LogViewerPortlet.java
    geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/util/PortletManager.java
    geronimo/trunk/sandbox/console-standard/src/webapp/WEB-INF/view/logmanager/search.jsp

Modified: geronimo/trunk/modules/assembly/src/plan/client-system-plan.xml
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/assembly/src/plan/client-system-plan.xml?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/modules/assembly/src/plan/client-system-plan.xml (original)
+++ geronimo/trunk/modules/assembly/src/plan/client-system-plan.xml Sun Jul 24 13:52:35 2005
@@ -58,8 +58,8 @@
 
     <!-- Logging service -->
     <gbean name="Logger" class="org.apache.geronimo.system.logging.log4j.Log4jService">
-        <attribute name="configurationFile">var/log/client-log4j.properties</attribute>
-        <attribute name="refreshPeriod">60</attribute>
+        <attribute name="configFileName">var/log/client-log4j.properties</attribute>
+        <attribute name="refreshPeriodSeconds">60</attribute>
         <reference name="ServerInfo"><name>ServerInfo</name></reference>
     </gbean>
 

Modified: geronimo/trunk/modules/assembly/src/plan/deployer-system-plan.xml
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/assembly/src/plan/deployer-system-plan.xml?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/modules/assembly/src/plan/deployer-system-plan.xml (original)
+++ geronimo/trunk/modules/assembly/src/plan/deployer-system-plan.xml Sun Jul 24 13:52:35 2005
@@ -51,8 +51,8 @@
 
     <!-- Logging service -->
     <gbean name="Logger" class="org.apache.geronimo.system.logging.log4j.Log4jService">
-        <attribute name="configurationFile">var/log/deployer-log4j.properties</attribute>
-        <attribute name="refreshPeriod">60</attribute>
+        <attribute name="configFileName">var/log/deployer-log4j.properties</attribute>
+        <attribute name="refreshPeriodSeconds">60</attribute>
         <reference name="ServerInfo"><name>ServerInfo</name></reference>
     </gbean>
 </configuration>

Modified: geronimo/trunk/modules/assembly/src/plan/system-plan.xml
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/assembly/src/plan/system-plan.xml?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/modules/assembly/src/plan/system-plan.xml (original)
+++ geronimo/trunk/modules/assembly/src/plan/system-plan.xml Sun Jul 24 13:52:35 2005
@@ -65,8 +65,8 @@
 
     <!-- Logging service -->
     <gbean name="Logger" class="org.apache.geronimo.system.logging.log4j.Log4jService">
-        <attribute name="configurationFile">var/log/server-log4j.properties</attribute>
-        <attribute name="refreshPeriod">60</attribute>
+        <attribute name="configFileName">var/log/server-log4j.properties</attribute>
+        <attribute name="refreshPeriodSeconds">60</attribute>
         <reference name="ServerInfo"><name>ServerInfo</name></reference>
     </gbean>
 

Modified: geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/j2eeobjectnames/NameFactory.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/j2eeobjectnames/NameFactory.java?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/j2eeobjectnames/NameFactory.java (original)
+++ geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/j2eeobjectnames/NameFactory.java Sun Jul 24 13:52:35 2005
@@ -82,6 +82,8 @@
     public static final String CORBA_SERVICE = "CORBABean";
     public static final String JACC_MANAGER = "JACCManager";
 
+    public static final String SYSTEM_LOG = "SystemLog";
+
     public static String JAXR_CONNECTION_FACTORY = "JAXRConnectionFactory";
 
     public static final String CONFIG_BUILDER = "ConfigBuilder";

Modified: geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/management/geronimo/JVM.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/management/geronimo/JVM.java?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/management/geronimo/JVM.java (original)
+++ geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/management/geronimo/JVM.java Sun Jul 24 13:52:35 2005
@@ -21,7 +21,7 @@
 import java.util.Properties;
 
 /**
- *
+ * Geronimo extensions to the standard JSR-77 JVM type.
  *
  * @version $Rev$ $Date$
  */
@@ -31,6 +31,17 @@
     long getMaxMemory();
     int getAvailableProcessors();
 
+    /**
+     * Gets the date at which the kernel was most recently started in this JVM
+     */
     Date getKernelBootTime();
+    /**
+     * Gets the system properties for this JVM
+     */
     Properties getSystemProperties();
+
+    /**
+     * Gets the ObjectName of the system log for this JVM
+     */
+    String getSystemLog();
 }

Modified: geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/management/impl/JVMImpl.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/management/impl/JVMImpl.java?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/management/impl/JVMImpl.java (original)
+++ geronimo/trunk/modules/j2ee/src/java/org/apache/geronimo/j2ee/management/impl/JVMImpl.java Sun Jul 24 13:52:35 2005
@@ -21,12 +21,17 @@
 import java.net.UnknownHostException;
 import java.util.Date;
 import java.util.Properties;
+import java.util.Hashtable;
 
+import javax.management.ObjectName;
 import org.apache.geronimo.gbean.GBeanInfo;
 import org.apache.geronimo.gbean.GBeanInfoBuilder;
 import org.apache.geronimo.j2ee.j2eeobjectnames.NameFactory;
 import org.apache.geronimo.j2ee.management.geronimo.JVM;
 import org.apache.geronimo.kernel.Kernel;
+import org.apache.geronimo.kernel.jmx.JMXUtil;
+import org.apache.commons.logging.LogFactory;
+import org.apache.commons.logging.Log;
 
 /**
  *
@@ -34,6 +39,7 @@
  * @version $Rev$ $Date$
  */
 public class JVMImpl implements JVM {
+    private final static Log log = LogFactory.getLog(JVMImpl.class);
     public static final String JAVA_VERSION = System.getProperty("java.version");
     public static final String JAVA_VENDOR = System.getProperty("java.vendor");
     public static final String NODE;
@@ -51,10 +57,42 @@
 
     private final String objectName;
     private final Kernel kernel;
+    private final String baseName;
 
     public JVMImpl(String objectName, Kernel kernel) {
         this.objectName = objectName;
         this.kernel = kernel;
+        ObjectName myObjectName = JMXUtil.getObjectName(this.objectName);
+        verifyObjectName(myObjectName);
+
+        // build the base name used to query the server for related modules
+        Hashtable keyPropertyList = myObjectName.getKeyPropertyList();
+        String serverName = (String) keyPropertyList.get("J2EEServer");
+        baseName = myObjectName.getDomain() + ":J2EEServer=" + serverName + ",";
+    }
+
+    /**
+     * ObjectName must match this pattern:
+     * <p/>
+     * domain:j2eeType=JVM,name=MyName
+     */
+    private void verifyObjectName(ObjectName objectName) {
+        if (objectName.isPattern()) {
+            throw new InvalidObjectNameException("ObjectName can not be a pattern", objectName);
+        }
+        Hashtable keyPropertyList = objectName.getKeyPropertyList();
+        if (!"JVM".equals(keyPropertyList.get("j2eeType"))) {
+            throw new InvalidObjectNameException("JVM object name j2eeType property must be 'JVM'", objectName);
+        }
+        if (!keyPropertyList.containsKey("name")) {
+            throw new InvalidObjectNameException("JVM object must contain a name property", objectName);
+        }
+        if (!keyPropertyList.containsKey("J2EEServer")) {
+            throw new InvalidObjectNameException("JVM object must contain a J2EEServer property", objectName);
+        }
+        if (keyPropertyList.size() != 3) {
+            throw new InvalidObjectNameException("J2EEServer object name can only have J2EEServer, j2eeType, and name", objectName);
+        }
     }
 
     public String getObjectName() {
@@ -126,6 +164,15 @@
 
     public Properties getSystemProperties() {
         return System.getProperties();
+    }
+
+    public String getSystemLog() {
+        String[] logs = Util.getObjectNames(kernel, baseName, new String[]{NameFactory.SYSTEM_LOG});
+        if(logs.length != 1) {
+            log.error("Unable to resolve ObjectName for system log; got "+logs.length+" results!");
+            return null;
+        }
+        return logs[0];
     }
 
     public static final GBeanInfo GBEAN_INFO;

Modified: geronimo/trunk/modules/j2ee/src/test/org/apache/geronimo/j2ee/management/Abstract77Test.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/j2ee/src/test/org/apache/geronimo/j2ee/management/Abstract77Test.java?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/modules/j2ee/src/test/org/apache/geronimo/j2ee/management/Abstract77Test.java (original)
+++ geronimo/trunk/modules/j2ee/src/test/org/apache/geronimo/j2ee/management/Abstract77Test.java Sun Jul 24 13:52:35 2005
@@ -31,6 +31,10 @@
 import org.apache.geronimo.kernel.Kernel;
 import org.apache.geronimo.kernel.jmx.JMXUtil;
 import org.apache.geronimo.system.serverinfo.ServerInfo;
+import org.apache.log4j.Logger;
+import org.apache.log4j.Level;
+import org.apache.log4j.ConsoleAppender;
+import org.apache.log4j.PatternLayout;
 
 /**
  * @version $Rev$ $Date$
@@ -41,11 +45,13 @@
     protected static final String DOMAIN = "geronimo.test";
     protected static final ObjectName DOMAIN_NAME = JMXUtil.getObjectName(DOMAIN + ":j2eeType=J2EEDomain,name=" + DOMAIN);
     protected static final ObjectName SERVER_NAME = JMXUtil.getObjectName(DOMAIN + ":j2eeType=J2EEServer,name=Test");
-    protected static final ObjectName JVM_NAME = JMXUtil.getObjectName(DOMAIN + ":j2eeType=JVM,J2EEServer=Test");
+    protected static final ObjectName JVM_NAME = JMXUtil.getObjectName(DOMAIN + ":j2eeType=JVM,J2EEServer=Test,name=JVM");
 
     protected Kernel kernel;
 
     protected void setUp() throws Exception {
+        Logger.getRootLogger().setLevel(Level.WARN);
+        Logger.getRootLogger().addAppender(new ConsoleAppender(new PatternLayout("%p [%t] %m %n")));
         super.setUp();
         kernel = KernelFactory.newInstance().createKernel(DOMAIN);
         kernel.boot();

Added: geronimo/trunk/modules/system/src/java/org/apache/geronimo/system/logging/SystemLog.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/system/src/java/org/apache/geronimo/system/logging/SystemLog.java?rev=224657&view=auto
==============================================================================
--- geronimo/trunk/modules/system/src/java/org/apache/geronimo/system/logging/SystemLog.java (added)
+++ geronimo/trunk/modules/system/src/java/org/apache/geronimo/system/logging/SystemLog.java Sun Jul 24 13:52:35 2005
@@ -0,0 +1,114 @@
+/**
+ *
+ * Copyright 2003-2004 The Apache Software Foundation
+ *
+ *  Licensed 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.geronimo.system.logging;
+
+import java.io.Serializable;
+
+/**
+ * @version $Rev: 46019 $ $Date: 2004-09-14 05:56:06 -0400 (Tue, 14 Sep 2004) $
+ */
+public interface SystemLog {
+    /**
+     * The most search lines that will ever be returned, no matter what you
+     * ask for.  This is to conserve memory and transfer bandwidth.
+     */
+    public final static int MAX_SEARCH_RESULTS = 1000;
+    /**
+     * Gets the name of the file that configures the log system
+     */
+    String getConfigFileName();
+    /**
+     * Sets the name of the file that the log system should configure itself from.
+     */
+    void setConfigFileName(String fileName);
+    /**
+     * Gets the name of the log level used for the root logger.
+     */
+    String getRootLoggerLevel();
+    /**
+     * Sets the name of the log level used for the root logger.  Legal values
+     * are defined in GeronimoLogging.java (currently TRACE, DEBUG, INFO,
+     * WARN, ERROR, FATAL)
+     */
+    void setRootLoggerLevel(String level);
+    /**
+     * Indicates how often the log system should check to see if its
+     * configuration file has been updated.
+     */
+    int getRefreshPeriodSeconds();
+    /**
+     * Sets how often the log system should check to see if its
+     * configuration file has been updated.
+     */
+    void setRefreshPeriodSeconds(int seconds);
+    /**
+     * Gets the name of all log files used by this log system.  Typically there
+     * is only one, but specialized cases may use more.
+     */
+    String[] getLogFileNames();
+    /**
+     * Searches the log for records matching the specified parameters.  The
+     * maximum results returned will be the lesser of 1000 and the
+     * provided maxResults argument.
+     *
+     * @see #MAX_SEARCH_RESULTS
+     */
+    SearchResults getMatchingItems(String logFile, Integer firstLine, Integer lastLine, String minLevel,
+                                  String regex, int maxResults, boolean includeStackTraces);
+
+    public static class LogMessage implements Serializable {
+        private final int lineNumber;
+        private final String lineContent;
+
+        public LogMessage(int lineNumber, String lineContent) {
+            this.lineNumber = lineNumber;
+            this.lineContent = lineContent;
+        }
+
+        public int getLineNumber() {
+            return lineNumber;
+        }
+
+        public String getLineContent() {
+            return lineContent;
+        }
+    }
+
+    public static class SearchResults implements Serializable {
+        private final int lineCount;
+        private final LogMessage[] results;
+        private final boolean capped;
+
+        public SearchResults(int lineCount, LogMessage[] results, boolean capped) {
+            this.lineCount = lineCount;
+            this.results = results;
+            this.capped = capped;
+        }
+
+        public int getLineCount() {
+            return lineCount;
+        }
+
+        public LogMessage[] getResults() {
+            return results;
+        }
+
+        public boolean isCapped() {
+            return capped;
+        }
+    }
+}

Propchange: geronimo/trunk/modules/system/src/java/org/apache/geronimo/system/logging/SystemLog.java
------------------------------------------------------------------------------
    svn:eol-style = native

Modified: geronimo/trunk/modules/system/src/java/org/apache/geronimo/system/logging/log4j/Log4jService.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/system/src/java/org/apache/geronimo/system/logging/log4j/Log4jService.java?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/modules/system/src/java/org/apache/geronimo/system/logging/log4j/Log4jService.java (original)
+++ geronimo/trunk/modules/system/src/java/org/apache/geronimo/system/logging/log4j/Log4jService.java Sun Jul 24 13:52:35 2005
@@ -24,11 +24,23 @@
 import java.io.InputStreamReader;
 import java.io.OutputStream;
 import java.io.Reader;
+import java.io.RandomAccessFile;
 import java.net.MalformedURLException;
 import java.util.Timer;
 import java.util.TimerTask;
 import java.util.Set;
 import java.util.Iterator;
+import java.util.Enumeration;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.LinkedList;
+import java.util.regex.Pattern;
+import java.util.regex.Matcher;
+import java.util.regex.PatternSyntaxException;
+import java.nio.channels.FileChannel;
+import java.nio.MappedByteBuffer;
+import java.nio.CharBuffer;
+import java.nio.charset.Charset;
 
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogConfigurationException;
@@ -39,16 +51,38 @@
 import org.apache.geronimo.kernel.log.GeronimoLogFactory;
 import org.apache.geronimo.kernel.log.GeronimoLogging;
 import org.apache.geronimo.system.serverinfo.ServerInfo;
+import org.apache.geronimo.system.logging.SystemLog;
 import org.apache.log4j.Level;
 import org.apache.log4j.LogManager;
 import org.apache.log4j.Logger;
+import org.apache.log4j.FileAppender;
 
 /**
  * A Log4j logging service.
  *
  * @version $Rev$ $Date$
  */
-public class Log4jService implements GBeanLifecycle {
+public class Log4jService implements GBeanLifecycle, SystemLog {
+    // A substitution variable in the file path in the config file
+    private final static Pattern VARIABLE_PATTERN = Pattern.compile("\\$\\{.*?\\}");
+    // Next 6 are patterns that identify log messages in our default format
+    private final static Pattern DEFAULT_ANY_START = Pattern.compile("^\\d\\d\\:\\d\\d\\:\\d\\d\\,\\d\\d\\d (TRACE|DEBUG|INFO|WARN|ERROR|FATAL) .*");
+    private final static Pattern DEFAULT_FATAL_START = Pattern.compile("^\\d\\d\\:\\d\\d\\:\\d\\d\\,\\d\\d\\d FATAL .*");
+    private final static Pattern DEFAULT_ERROR_START = Pattern.compile("^\\d\\d\\:\\d\\d\\:\\d\\d\\,\\d\\d\\d (ERROR|FATAL) .*");
+    private final static Pattern DEFAULT_WARN_START = Pattern.compile("^\\d\\d\\:\\d\\d\\:\\d\\d\\,\\d\\d\\d (WARN|ERROR|FATAL) .*");
+    private final static Pattern DEFAULT_INFO_START = Pattern.compile("^\\d\\d\\:\\d\\d\\:\\d\\d\\,\\d\\d\\d (INFO|WARN|ERROR|FATAL) .*");
+    private final static Pattern DEFAULT_DEBUG_START = Pattern.compile("^\\d\\d\\:\\d\\d\\:\\d\\d\\,\\d\\d\\d (DEBUG|INFO|WARN|ERROR|FATAL) .*");
+    // Next 6 are patterns that identify log messages if the user changed the format -- but we assume the log level is in there somewhere
+    private final static Pattern UNKNOWN_ANY_START = Pattern.compile("(TRACE|DEBUG|INFO|WARN|ERROR|FATAL)");
+    private final static Pattern UNKNOWN_FATAL_START = Pattern.compile("FATAL");
+    private final static Pattern UNKNOWN_ERROR_START = Pattern.compile("(ERROR|FATAL)");
+    private final static Pattern UNKNOWN_WARN_START = Pattern.compile("(WARN|ERROR|FATAL)");
+    private final static Pattern UNKNOWN_INFO_START = Pattern.compile("(INFO|WARN|ERROR|FATAL)");
+    private final static Pattern UNKNOWN_DEBUG_START = Pattern.compile("(DEBUG|INFO|WARN|ERROR|FATAL)");
+    // Pattern that matches a single line  (used to calculate line numbers and check for follow-on stack traces)
+    private final static Pattern FULL_LINE_PATTERN = Pattern.compile("^.*", Pattern.MULTILINE);
+
+
     /**
      * The URL to the configuration file.
      */
@@ -178,7 +212,7 @@
      *
      * @return the refresh period (in seconds)
      */
-    public synchronized int getRefreshPeriod() {
+    public synchronized int getRefreshPeriodSeconds() {
         return refreshPeriod;
     }
 
@@ -188,7 +222,7 @@
      * @param period the refresh period (in seconds)
      * @throws IllegalArgumentException if refresh period is <= 0
      */
-    public synchronized void setRefreshPeriod(final int period) {
+    public synchronized void setRefreshPeriodSeconds(final int period) {
         if (period < 1) {
             throw new IllegalArgumentException("Refresh period must be > 0");
         }
@@ -204,7 +238,7 @@
      *
      * @return the logging configuration URL
      */
-    public synchronized String getConfigurationFile() {
+    public synchronized String getConfigFileName() {
         return configurationFile;
     }
 
@@ -213,8 +247,8 @@
      *
      * @param configurationFile the logging configuration file
      */
-    public synchronized void setConfigurationFile(final String configurationFile) {
-        if (this.configurationFile == null) {
+    public synchronized void setConfigFileName(final String configurationFile) {
+        if (configurationFile == null) {
             throw new IllegalArgumentException("configurationFile is null");
         }
 
@@ -296,6 +330,169 @@
         }
     }
 
+    public synchronized String[] getLogFileNames() {
+        List list = new ArrayList();
+        for (Enumeration e = Logger.getRootLogger().getAllAppenders(); e.hasMoreElements();) {
+            Object appender = e.nextElement();
+            if (appender instanceof FileAppender) {
+                list.add(((FileAppender) appender).getFile());
+            }
+        }
+        return (String[]) list.toArray(new String[list.size()]);
+    }
+
+    private static SearchResults searchFile(File file, String targetLevel, Pattern textSearch, Integer start, Integer stop, int max, boolean stacks) {
+        List list = new LinkedList();
+        boolean capped = false;
+        int lineCount = 0;
+        try {
+            RandomAccessFile raf = new RandomAccessFile(file, "r");
+            FileChannel fc = raf.getChannel();
+            MappedByteBuffer bb = fc.map(FileChannel.MapMode.READ_ONLY, 0, fc.size());
+            CharBuffer cb = Charset.forName("US-ASCII").decode(bb); //todo: does Log4J use a different charset on a foreign PC?
+            Matcher target = null;
+            Matcher any = null;
+            Matcher lines = FULL_LINE_PATTERN.matcher(cb);
+            Matcher text = textSearch == null ? null : textSearch.matcher("");
+            boolean hit = false;
+            max = Math.min(max, MAX_SEARCH_RESULTS);
+            while(lines.find()) {
+                ++lineCount;
+                if(target == null) {
+                    if(DEFAULT_ANY_START.matcher(cb.subSequence(lines.start(), lines.end())).find()) {
+                        target = getDefaultPatternForLevel(targetLevel).matcher("");
+                        any = DEFAULT_ANY_START.matcher("");
+                    } else {
+                        target = getUnknownPatternForLevel(targetLevel).matcher("");
+                        any = UNKNOWN_ANY_START.matcher("");
+                    }
+                }
+                if(start != null && start.intValue() > lineCount) {
+                    continue;
+                }
+                if(stop != null && stop.intValue() < lineCount) {
+                    continue;
+                }
+                CharSequence line = cb.subSequence(lines.start(), lines.end());
+                target.reset(line);
+                if(target.find()) {
+                    if(text != null) {
+                        text.reset(line);
+                        if(!text.find()) {
+                            hit = false;
+                            continue;
+                        }
+                    }
+                    list.add(new LogMessage(lineCount,line.toString()));
+                    if(list.size() > max) {
+                        list.remove(0);
+                        capped = true;
+                    }
+                    hit = true;
+                } else if(stacks && hit) {
+                    any.reset(line);
+                    if(!any.find()) {
+                        list.add(new LogMessage(lineCount,line.toString()));
+                        if(list.size() > max) {
+                            list.remove(0);
+                            capped = true;
+                        }
+                    } else {
+                        hit = false;
+                    }
+                }
+            }
+            fc.close();
+            raf.close();
+        } catch (Exception e) {}
+        return new SearchResults(lineCount, (LogMessage[]) list.toArray(new LogMessage[list.size()]), capped);
+    }
+
+    private static String substituteSystemProps(String source) {
+        StringBuffer buf = new StringBuffer();
+        int last = 0;
+        Matcher m = VARIABLE_PATTERN.matcher(source);
+        while(m.find()) {
+            buf.append(source.substring(last, m.start()));
+            String prop = source.substring(m.start()+2, m.end()-1);
+            buf.append(System.getProperty(prop));
+            last = m.end();
+        }
+        buf.append(source.substring(last));
+        return buf.toString();
+    }
+
+    private static Pattern getDefaultPatternForLevel(String targetLevel) {
+        if(targetLevel.equals("FATAL")) {
+            return DEFAULT_FATAL_START;
+        } else if(targetLevel.equals("ERROR")) {
+            return DEFAULT_ERROR_START;
+        } else if(targetLevel.equals("WARN")) {
+            return DEFAULT_WARN_START;
+        } else if(targetLevel.equals("INFO")) {
+            return DEFAULT_INFO_START;
+        } else if(targetLevel.equals("DEBUG")) {
+            return DEFAULT_DEBUG_START;
+        } else {
+            return DEFAULT_ANY_START;
+        }
+    }
+
+    private static Pattern getUnknownPatternForLevel(String targetLevel) {
+        if(targetLevel.equals("FATAL")) {
+            return UNKNOWN_FATAL_START;
+        } else if(targetLevel.equals("ERROR")) {
+            return UNKNOWN_ERROR_START;
+        } else if(targetLevel.equals("WARN")) {
+            return UNKNOWN_WARN_START;
+        } else if(targetLevel.equals("INFO")) {
+            return UNKNOWN_INFO_START;
+        } else if(targetLevel.equals("DEBUG")) {
+            return UNKNOWN_DEBUG_START;
+        } else {
+            return UNKNOWN_ANY_START;
+        }
+    }
+
+    public SearchResults getMatchingItems(String logFile, Integer firstLine, Integer lastLine, String minLevel, String text, int maxResults, boolean includeStackTraces) {
+        // Ensure the file argument is really a log file!
+        if(logFile == null) {
+            throw new IllegalArgumentException("Must specify a log file");
+        }
+        String[] files = getLogFileNames();
+        boolean found = false;
+        for (int i = 0; i < files.length; i++) {
+            if(files[i].equals(logFile)) {
+                found = true;
+                break;
+            }
+        }
+        if(!found) {
+            throw new IllegalArgumentException("Not a log file!");
+        }
+        // Check for valid log level
+        if(minLevel == null) {
+            minLevel = "TRACE";
+        } else if(!minLevel.equals("FATAL") && !minLevel.equals("ERROR") && !minLevel.equals("WARN") &&
+                !minLevel.equals("INFO") && !minLevel.equals("DEBUG") && !minLevel.equals("TRACE")) {
+            throw new IllegalArgumentException("Not a valid log level");
+        }
+        // Check that the text pattern is valid
+        Pattern textPattern = null;
+        try {
+            textPattern = text == null || text.equals("") ? null : Pattern.compile(text);
+        } catch (PatternSyntaxException e) {
+            throw new IllegalArgumentException("Bad regular expression '"+text+"'");
+        }
+        // Make sure we can find the log file
+        File log = new File(substituteSystemProps(logFile));
+        if(!log.exists()) {
+            throw new IllegalArgumentException("Log file "+log.getAbsolutePath()+" does not exist");
+        }
+        // Run the search
+        return searchFile(log, minLevel, textPattern, firstLine, lastLine, maxResults, includeStackTraces);
+    }
+
     /**
      * Force the logging system to reconfigure.
      */
@@ -454,10 +651,10 @@
     public static final GBeanInfo GBEAN_INFO;
 
     static {
-        GBeanInfoBuilder infoFactory = new GBeanInfoBuilder(Log4jService.class);
+        GBeanInfoBuilder infoFactory = new GBeanInfoBuilder(Log4jService.class, "SystemLog");
 
-        infoFactory.addAttribute("configurationFile", String.class, true);
-        infoFactory.addAttribute("refreshPeriod", int.class, true);
+        infoFactory.addAttribute("configFileName", String.class, true);
+        infoFactory.addAttribute("refreshPeriodSeconds", int.class, true);
         infoFactory.addAttribute("configuration", String.class, false);
         infoFactory.addAttribute("rootLoggerLevel", String.class, false);
 
@@ -467,8 +664,9 @@
         infoFactory.addOperation("setLoggerLevel", new Class[]{String.class, String.class});
         infoFactory.addOperation("getLoggerLevel", new Class[]{String.class});
         infoFactory.addOperation("getLoggerEffectiveLevel", new Class[]{String.class});
+        infoFactory.addInterface(SystemLog.class);
 
-        infoFactory.setConstructor(new String[]{"configurationFile", "refreshPeriod", "ServerInfo"});
+        infoFactory.setConstructor(new String[]{"configFileName", "refreshPeriodSeconds", "ServerInfo"});
 
         GBEAN_INFO = infoFactory.getBeanInfo();
     }

Modified: geronimo/trunk/sandbox/console-core/src/java/org/apache/geronimo/console/util/KernelManagementHelper.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/sandbox/console-core/src/java/org/apache/geronimo/console/util/KernelManagementHelper.java?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/sandbox/console-core/src/java/org/apache/geronimo/console/util/KernelManagementHelper.java (original)
+++ geronimo/trunk/sandbox/console-core/src/java/org/apache/geronimo/console/util/KernelManagementHelper.java Sun Jul 24 13:52:35 2005
@@ -46,6 +46,7 @@
 import org.apache.geronimo.j2ee.j2eeobjectnames.NameFactory;
 import org.apache.geronimo.kernel.Kernel;
 import org.apache.geronimo.kernel.proxy.ProxyManager;
+import org.apache.geronimo.system.logging.SystemLog;
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogFactory;
 
@@ -234,6 +235,18 @@
             Object[] temp = pm.createProxies(names);
             result = new JVM[temp.length];
             System.arraycopy(temp, 0, result, 0, temp.length);
+        } catch (Exception e) {
+            log.error(e);
+        }
+        return result;
+    }
+
+    public SystemLog getSystemLog(JVM jvm) {
+        SystemLog result = null;
+        try {
+            String name = jvm.getSystemLog();
+            Object temp = pm.createProxy(ObjectName.getInstance(name));
+            result = (SystemLog)temp;
         } catch (Exception e) {
             log.error(e);
         }

Modified: geronimo/trunk/sandbox/console-core/src/java/org/apache/geronimo/console/util/ManagementHelper.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/sandbox/console-core/src/java/org/apache/geronimo/console/util/ManagementHelper.java?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/sandbox/console-core/src/java/org/apache/geronimo/console/util/ManagementHelper.java (original)
+++ geronimo/trunk/sandbox/console-core/src/java/org/apache/geronimo/console/util/ManagementHelper.java Sun Jul 24 13:52:35 2005
@@ -37,6 +37,7 @@
 import org.apache.geronimo.j2ee.management.ResourceAdapter;
 import org.apache.geronimo.j2ee.management.geronimo.JVM;
 import org.apache.geronimo.j2ee.management.geronimo.J2EEApplication;
+import org.apache.geronimo.system.logging.SystemLog;
 
 /**
  * A helper interface to navigate between management objects.  This is not
@@ -64,7 +65,10 @@
     JDBCResource[] getJDBCResources(J2EEServer server);
     JMSResource[] getJMSResources(J2EEServer server);
     JVM[] getJavaVMs(J2EEServer server);
-    //todo: repository, logs, embedded database
+    //todo: repository, embedded database
+
+    // JVM properties
+    SystemLog getSystemLog(JVM jvm);
 
     // application properties
     J2EEModule[] getModules(J2EEApplication application);

Modified: geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/logmanager/LogManagerPortlet.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/logmanager/LogManagerPortlet.java?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/logmanager/LogManagerPortlet.java (original)
+++ geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/logmanager/LogManagerPortlet.java Sun Jul 24 13:52:35 2005
@@ -30,7 +30,8 @@
 import javax.portlet.RenderResponse;
 import javax.portlet.WindowState;
 
-import org.apache.geronimo.console.util.LogHelper;
+import org.apache.geronimo.console.util.PortletManager;
+import org.apache.geronimo.system.logging.SystemLog;
 
 public class LogManagerPortlet extends GenericPortlet {
 
@@ -48,26 +49,25 @@
         if (WindowState.MINIMIZED.equals(renderRequest.getWindowState())) {
             return;
         }
-        renderRequest.setAttribute("configFile", LogHelper.getConfigFile());
-        renderRequest.setAttribute("configuration", LogHelper
-                .getConfiguration());
-        renderRequest.setAttribute("logLevel", LogHelper.getLogLevel());
-        renderRequest.setAttribute("refreshPeriod", LogHelper
-                .getRefreshPeriod());
+        SystemLog log = PortletManager.getCurrentSystemLog(renderRequest);
+        renderRequest.setAttribute("configFile", log.getConfigFileName());
+//        renderRequest.setAttribute("configuration", LogHelper.getConfiguration());
+        renderRequest.setAttribute("logLevel", log.getRootLoggerLevel());
+        renderRequest.setAttribute("refreshPeriod", new Integer(log.getRefreshPeriodSeconds()));
 
         normalView.include(renderRequest, renderRespose);
     }
 
     public void init(PortletConfig portletConfig) throws PortletException {
         PortletContext pc = portletConfig.getPortletContext();
-        normalView = pc
-                .getRequestDispatcher("/WEB-INF/view/logmanager/view.jsp");
+        normalView = pc.getRequestDispatcher("/WEB-INF/view/logmanager/view.jsp");
         helpView = pc.getRequestDispatcher("/WEB-INF/view/logmanager/help.jsp");
         super.init(portletConfig);
     }
 
     public void processAction(ActionRequest actionRequest,
             ActionResponse actionResponse) throws PortletException, IOException {
+        SystemLog log = PortletManager.getCurrentSystemLog(actionRequest);
 
         String action = actionRequest.getParameter("action");
         String logLevel = actionRequest.getParameter("logLevel");
@@ -77,12 +77,10 @@
 
         if ("update".equals(action)) {
             if (refreshPeriod != null) {
-                LogHelper.setRefreshPeriod(Integer.parseInt(refreshPeriod));
+                log.setRefreshPeriodSeconds(Integer.parseInt(refreshPeriod));
             }
-            LogHelper.setConfigFile(configFile);
-            LogHelper.setLogLevel(logLevel);
-
+            log.setConfigFileName(configFile);
+            log.setRootLoggerLevel(logLevel);
         }
     }
-
 }

Modified: geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/logmanager/LogViewerPortlet.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/logmanager/LogViewerPortlet.java?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/logmanager/LogViewerPortlet.java (original)
+++ geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/logmanager/LogViewerPortlet.java Sun Jul 24 13:52:35 2005
@@ -18,6 +18,8 @@
 package org.apache.geronimo.console.logmanager;
 
 import java.io.IOException;
+import java.io.Serializable;
+import java.io.File;
 
 import javax.portlet.GenericPortlet;
 import javax.portlet.PortletConfig;
@@ -27,12 +29,13 @@
 import javax.portlet.RenderRequest;
 import javax.portlet.RenderResponse;
 import javax.portlet.WindowState;
+import javax.portlet.PortletSession;
 
-import org.apache.geronimo.console.util.LogHelper;
+import org.apache.geronimo.console.util.PortletManager;
+import org.apache.geronimo.system.logging.SystemLog;
 
 public class LogViewerPortlet extends GenericPortlet {
-
-    public static final int LOGS_PER_PAGE = 10;
+    private final static String CRITERIA_KEY = "org.apache.geronimo.console.log.CRITERIA";
 
     protected PortletRequestDispatcher searchView;
 
@@ -50,32 +53,60 @@
         }
         String action = renderRequest.getParameter("action");
 
+        SystemLog log = PortletManager.getCurrentSystemLog(renderRequest);
+        String[] logFiles = log.getLogFileNames();
+        LogFile[] files = new LogFile[logFiles.length];
+        for (int i = 0; i < files.length; i++) {
+            files[i] = new LogFile(logFiles[i]);
+        }
+        Criteria criteria;
         if ("refresh".equals(action)) {
-            LogHelper.refresh();
+            criteria = (Criteria) renderRequest.getPortletSession(true).getAttribute(CRITERIA_KEY, PortletSession.PORTLET_SCOPE);
+        } else {
+            String startPos = renderRequest.getParameter("startPos");
+            String endPos = renderRequest.getParameter("endPos");
+            String maxRows = renderRequest.getParameter("maxRows");
+            String logLevel = renderRequest.getParameter("logLevel");
+            String searchString = renderRequest.getParameter("searchString");
+            String stackTraces = renderRequest.getParameter("stackTraces");
+            String logFile = renderRequest.getParameter("logFile");
+            if(logFile == null || logFile.equals("")) {
+                logFile = logFiles[0];
+            }
+            if(logLevel == null || logLevel.equals("")) {
+                logLevel = "WARN";
+            }
+            if(maxRows == null || maxRows.equals("")) {
+                maxRows = "10";
+            }
+            criteria = new Criteria();
+            criteria.max = Integer.parseInt(maxRows);
+            criteria.start = startPos == null || startPos.equals("") ? null : new Integer(startPos);
+            criteria.stop = endPos == null || endPos.equals("") ? null : new Integer(endPos);
+            criteria.logFile = logFile;
+            criteria.stackTraces = stackTraces != null && !stackTraces.equals("");
+            criteria.level = logLevel;
+            criteria.text = searchString == null || searchString.equals("") ? null : searchString;
+            renderRequest.getPortletSession(true).setAttribute(CRITERIA_KEY, criteria, PortletSession.PORTLET_SCOPE);
         }
 
-        String startPos = renderRequest.getParameter("startPos");
-        String endPos = renderRequest.getParameter("endPos");
-        String logLevel = renderRequest.getParameter("logLevel");
-        String searchString = renderRequest.getParameter("searchString");
-
-        int lines = LogHelper.getLineCount();
-        int sPos = (startPos != null && startPos.length() > 0) ? Integer
-                .parseInt(startPos) : (lines - LOGS_PER_PAGE);
-        int ePos = (endPos != null && endPos.length() > 0) ? Integer
-                .parseInt(endPos) : lines;
-
-        try {
-            renderRequest.setAttribute("searchResults", LogHelper.searchLogs(
-                    sPos, ePos, logLevel, searchString));
-        } catch (IOException e) {
-            throw new PortletException(e.getMessage());
-        }
-        renderRequest.setAttribute("lineCount", new Integer(lines));
-        renderRequest.setAttribute("startPos", new Integer(sPos));
-        renderRequest.setAttribute("endPos", new Integer(ePos));
-        renderRequest.setAttribute("logLevel", logLevel);
-        renderRequest.setAttribute("searchString", searchString);
+        SystemLog.SearchResults results = log.getMatchingItems(criteria.logFile, criteria.start, criteria.stop,
+                        criteria.level, criteria.text, criteria.max, criteria.stackTraces);
+        renderRequest.setAttribute("searchResults", results.getResults());
+        renderRequest.setAttribute("lineCount", new Integer(results.getLineCount()));
+        renderRequest.setAttribute("startPos", criteria.start);
+        renderRequest.setAttribute("endPos", criteria.stop);
+        renderRequest.setAttribute("logLevel", criteria.level);
+        renderRequest.setAttribute("searchString", criteria.text);
+        renderRequest.setAttribute("maxRows", Integer.toString(criteria.max));
+        renderRequest.setAttribute("logFile", criteria.logFile);
+        renderRequest.setAttribute("logFiles", files);
+        if(criteria.stackTraces) {
+            renderRequest.setAttribute("stackTraces", Boolean.TRUE);
+        }
+        if(results.isCapped()) {
+            renderRequest.setAttribute("capped", Boolean.TRUE);
+        }
 
         searchView.include(renderRequest, renderRespose);
     }
@@ -89,4 +120,37 @@
         super.init(portletConfig);
     }
 
+    private static class Criteria implements Serializable {
+        int max;
+        Integer start;
+        Integer stop;
+        String text;
+        String level;
+        String logFile;
+        boolean stackTraces;
+    }
+
+    public static class LogFile {
+        private String fullName;
+        private String name;
+
+        public LogFile(String fullName) {
+            this.fullName = fullName;
+            //todo: what if portla JVM has different separator than server JVM?
+            int pos = fullName.lastIndexOf(File.separatorChar);
+            if(pos > -1) {
+                name = fullName.substring(pos+1);
+            } else {
+                name = fullName;
+            }
+        }
+
+        public String getFullName() {
+            return fullName;
+        }
+
+        public String getName() {
+            return name;
+        }
+    }
 }

Modified: geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/util/PortletManager.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/util/PortletManager.java?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/util/PortletManager.java (original)
+++ geronimo/trunk/sandbox/console-standard/src/java/org/apache/geronimo/console/util/PortletManager.java Sun Jul 24 13:52:35 2005
@@ -25,6 +25,7 @@
 import org.apache.geronimo.j2ee.management.J2EEDomain;
 import org.apache.geronimo.j2ee.management.J2EEServer;
 import org.apache.geronimo.j2ee.management.geronimo.JVM;
+import org.apache.geronimo.system.logging.SystemLog;
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogFactory;
 
@@ -33,21 +34,25 @@
  */
 public class PortletManager {
     private final static Log log = LogFactory.getLog(PortletManager.class);
+    // The following are currently static due to having only one server/JVM/etc. per Geronimo
     private final static String HELPER_KEY = "org.apache.geronimo.console.ManagementHelper";
     private final static String DOMAIN_KEY = "org.apache.geronimo.console.J2EEDomain";
     private final static String SERVER_KEY = "org.apache.geronimo.console.J2EEServer";
     private final static String JVM_KEY = "org.apache.geronimo.console.JVM";
+    private final static String SYSTEM_LOG_KEY = "org.apache.geronimo.console.SystemLog";
+    // The following may change based on the user's selections
+        // nothing yet
 
     private static ManagementHelper createHelper(PortletRequest request) {
         //todo: consider making this configurable; we could easily connect to a remote kernel if we wanted to
         Kernel kernel = null;
         try {
-            kernel = (Kernel) new InitialContext().lookup("java:comp/env/GeronimoKernel");
+            kernel = (Kernel) new InitialContext().lookup("java:comp/GeronimoKernel");
         } catch (NamingException e) {
 //            log.error("Unable to look up kernel in JNDI", e);
         }
         if(kernel == null) {
-            log.warn("Unable to find kernel in JNDI; using KernelRegistry instead");
+            log.debug("Unable to find kernel in JNDI; using KernelRegistry instead");
             kernel = KernelRegistry.getSingleKernel();
         }
         return new KernelManagementHelper(kernel);
@@ -90,5 +95,15 @@
             request.getPortletSession().setAttribute(JVM_KEY, jvm, PortletSession.APPLICATION_SCOPE);
         }
         return jvm;
+    }
+
+    public static SystemLog getCurrentSystemLog(PortletRequest request) {
+        SystemLog log = (SystemLog) request.getPortletSession(true).getAttribute(SYSTEM_LOG_KEY, PortletSession.APPLICATION_SCOPE);
+        if(log == null) {
+            ManagementHelper helper = getManagementHelper(request);
+            log = helper.getSystemLog(getCurrentJVM(request));
+            request.getPortletSession().setAttribute(SYSTEM_LOG_KEY, log, PortletSession.APPLICATION_SCOPE);
+        }
+        return log;
     }
 }

Modified: geronimo/trunk/sandbox/console-standard/src/webapp/WEB-INF/view/logmanager/search.jsp
URL: http://svn.apache.org/viewcvs/geronimo/trunk/sandbox/console-standard/src/webapp/WEB-INF/view/logmanager/search.jsp?rev=224657&r1=224656&r2=224657&view=diff
==============================================================================
--- geronimo/trunk/sandbox/console-standard/src/webapp/WEB-INF/view/logmanager/search.jsp (original)
+++ geronimo/trunk/sandbox/console-standard/src/webapp/WEB-INF/view/logmanager/search.jsp Sun Jul 24 13:52:35 2005
@@ -28,40 +28,20 @@
 function <portlet:namespace/>validateForm(){
     var startPos = document.<portlet:namespace/>searchForm.startPos.value;
     var endPos = document.<portlet:namespace/>searchForm.endPos.value;
-    if(startPos.length < 1){
-        alert("Please input a start position.");
-        document.<portlet:namespace/>searchForm.startPos.focus();
-        return false;
-    }
-    if(endPos.length < 1){
-        alert("Please input an end position.");
-        document.<portlet:namespace/>searchForm.endPos.focus();
-        return false;
-    }
+    var maxRows = document.<portlet:namespace/>searchForm.maxRows.value;
     if(!<portlet:namespace/>isNumeric(startPos)){
-        alert("Start Position must be a positive integer.");
+        alert("Start Position must be a number.");
         document.<portlet:namespace/>searchForm.startPos.focus();
         return false;
     }
-    if(parseInt(startPos) < 1){
-        alert("Start Position must be a non-zero positive integer.");
-        document.<portlet:namespace/>searchForm.startPos.focus();
-        return false;
-     }
-    if(!<portlet:namespace/>isNumeric(endPos) ||
-            parseInt(endPos) > ${lineCount}){
-        alert("End Position must be a positive integer less than or equal to ${lineCount}.");
+    if(!<portlet:namespace/>isNumeric(endPos)){
+        alert("End Position must be a number.");
         document.<portlet:namespace/>searchForm.endPos.focus();
         return false;
     }
-    if(parseInt(endPos) < 1){
-        alert("End Position must be a non-zero positive integer.");
-        document.<portlet:namespace/>searchForm.endPos.focus();
-        return false;
-     }
-    if(parseInt(startPos) > parseInt(endPos)){
-        alert("Start position must be less than or equal to end position.");
-        document.<portlet:namespace/>searchForm.startPos.focus();
+    if(!<portlet:namespace/>isNumeric(maxRows)){
+        alert("Maximum results must be a number.");
+        document.<portlet:namespace/>searchForm.maxRows.focus();
         return false;
     }
     return true;
@@ -80,39 +60,44 @@
     <form action="<portlet:renderURL/>" name="<portlet:namespace/>searchForm" onsubmit="return <portlet:namespace/>validateForm();">
     <b>Filter results:</b>
     <input type="hidden" value="search" name="action"/>
+    File <select name="logFile">
+        <c:forEach var="file" items="${logFiles}">
+            <option value="${file.fullName}" <c:if test="${logFile eq file.fullName}"> selected</c:if>>${file.name}</option>
+        </c:forEach>
+    </select>
     Lines <input type="text" name="startPos" value="${startPos}" size="3"/>
     to <input type="text" name="endPos" value="${endPos}" size="3"/>
-    Level 
+    Max Results <input type="text" name="maxRows" value="${maxRows}" size="3"/>
+    Level
     <select name="logLevel">
-        <option value=""<c:if test="${logLevel eq ''}"> selected</c:if>>ALL</option>
+        <option<c:if test="${logLevel eq 'TRACE' || logLevel eq ''}"> selected</c:if>>TRACE</option>
         <option<c:if test="${logLevel eq 'DEBUG'}"> selected</c:if>>DEBUG</option>
         <option<c:if test="${logLevel eq 'INFO'}"> selected</c:if>>INFO</option>
         <option<c:if test="${logLevel eq 'WARN'}"> selected</c:if>>WARN</option>
         <option<c:if test="${logLevel eq 'ERROR'}"> selected</c:if>>ERROR</option>
         <option<c:if test="${logLevel eq 'FATAL'}"> selected</c:if>>FATAL</option>
-        <option<c:if test="${logLevel eq 'TRACE'}"> selected</c:if>>TRACE</option>
     </select>
     Containing text <input type="text" name="searchString" value="${searchString}"/>
+    With Exceptions <input type="checkbox" name="stackTraces" <c:if test="${!empty stackTraces}">CHECKED </c:if>/>
     <input type="submit" value="Go"/>
     </form>
     </td>
-</tr>    
+</tr>
 <tr>
-    <td>     
-
+    <td>
 <c:choose>
 <c:when test="${searchResults != null && fn:length(searchResults) > 0}">
     <table>
         <tr>
             <td class="Smaller">
-            <b>${lineCount} total message(s) in log file. ${fn:length(searchResults)} matched your criteria.</b>
+            <b>${lineCount} total message(s) in log file. ${fn:length(searchResults)} matched your criteria<c:if test="${!empty capped}"> (number of results capped)</c:if>.</b>
             </td>
         </tr>    
             
     <c:forEach var="line" items="${searchResults}">
         <tr>
             <td class="Smaller">
-            ${line}
+            ${line.lineNumber}:&nbsp;${line.lineContent}
             </td>
         </tr>
     </c:forEach>
@@ -122,6 +107,6 @@
  No logs found with the specified criteria.
 </c:otherwise>
 </c:choose>  
-</td>     
+</td>
 </tr>
 </table>



Mime
View raw message