incubator-sling-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From bdelacre...@apache.org
Subject svn commit: r1514287 - in /sling/trunk/contrib/extensions/healthcheck: api/src/main/java/org/apache/sling/hc/api/ api/src/main/java/org/apache/sling/hc/util/ api/src/test/java/org/apache/sling/hc/api/ api/src/test/java/org/apache/sling/hc/util/ healthc...
Date Thu, 15 Aug 2013 14:19:47 GMT
Author: bdelacretaz
Date: Thu Aug 15 14:19:46 2013
New Revision: 1514287

URL: http://svn.apache.org/r1514287
Log:
SLING-3020 - Result is now immutable

Added:
    sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/api/ResultLog.java
    sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/api/ResultLogTest.java
    sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/util/
    sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/util/FormattingResultLog.java
Removed:
    sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/api/ResultLogEntry.java
    sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/api/ResultMergeTest.java
Modified:
    sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/api/Result.java
    sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/util/SimpleConstraintChecker.java
    sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/api/ResultTest.java
    sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/util/SimpleConstraintCheckerTest.java
    sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/CompositeHealthCheck.java
    sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/DefaultLoginsHealthCheck.java
    sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/JmxAttributeHealthCheck.java
    sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/JmxScriptBinding.java
    sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/OsgiScriptBinding.java
    sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/ScriptableHealthCheck.java
    sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/SlingRequestStatusHealthCheck.java
    sling/trunk/contrib/extensions/healthcheck/healthchecks/src/test/java/org/apache/sling/hc/healthchecks/JmxScriptBindingTest.java
    sling/trunk/contrib/extensions/healthcheck/healthchecks/src/test/java/org/apache/sling/hc/healthchecks/OsgiScriptBindingTest.java
    sling/trunk/contrib/extensions/healthcheck/jmx/src/main/java/org/apache/sling/hc/jmx/impl/HealthCheckMBean.java
    sling/trunk/contrib/extensions/healthcheck/jmx/src/test/java/org/apache/sling/hc/jmx/HealthCheckMBeanTest.java
    sling/trunk/contrib/extensions/healthcheck/webconsole/src/main/java/org/apache/sling/hc/webconsole/impl/HealthCheckWebconsolePlugin.java

Modified: sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/api/Result.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/api/Result.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/api/Result.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/api/Result.java Thu Aug 15 14:19:46 2013
@@ -18,102 +18,48 @@
 package org.apache.sling.hc.api;
 
 import java.util.Iterator;
-import java.util.LinkedList;
-import java.util.List;
-
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
 
 /** The result of executing a {@link HealthCheck} */
-public class Result implements Iterable <ResultLogEntry >{
+public class Result implements Iterable <ResultLog.Entry> {
 
-    private final Logger logger;
-    private static final Logger CLASS_LOGGER = LoggerFactory.getLogger(Result.class);
-    
-    private final List<ResultLogEntry> logEntries = new LinkedList<ResultLogEntry>();
-    private Status status = Status.OK;
+    private final ResultLog resultLog;
     
     public enum Status {
+        DEBUG,              // used by ResultLog for debug messages, not an actual output status
+        INFO,               // used by ResultLog for info messages, not an actual output status
         OK,                 // no problem
         WARN,               // health check detected something wrong but not critical
         CRITICAL,           // health check detected a critical problem
         HEALTH_CHECK_ERROR  // health check did not execute properly
     }
     
-    /** Build a Result using the default logger */
-    public Result() {
-        this(null);
+    /** Build a single-value Result 
+     *  @param s if lower than OK, our status is set to OK */
+    public Result(Status s, String explanation) {
+        resultLog = new ResultLog().add(new ResultLog.Entry(s, explanation));
     }
 
-    /** Build a Result that logs to a specific logger */
-    public Result(Logger logger) {
-        this.logger = logger != null ? logger : CLASS_LOGGER;
-    }
-    
-    /** Merge a set of Result into this one. This Result's status
-     *  is set to the highest status of all supplied Result, and
-     *  their log entries are added to this. */
-    public void merge(Result ...results) {
-        for(Result r : results) {
-            setStatus(r.getStatus());
-            for(ResultLogEntry e : r) {
-                log(e);
-            }
-        }
-    }
-    
-    /** Add an entry to our log. Use the {@ResultLogEntry}.LT_* constants
-     *  for well-known entry types.
-     *  Adding an entry with a type where {@ResultLogEntry#isInformationalEntryType} returns
-     *  false causes our status to be set to WARN, unless it was already set higher.
+    /** Build a a Result based on a ResultLog, which can provide
+     *  more details than a single-value Result.
      */
-    public void log(String entryType, String message) {
-        log(new ResultLogEntry(entryType, message));
+    public Result(ResultLog log) {
+        resultLog = log;
     }
     
-    /** Add an entry to our log - in general it is more convenient to use the {@link #add(String, String)}
-     *  method - this is useful when merging Result for example.
-     */
-    public void log(ResultLogEntry e) {
-        if(logger.isDebugEnabled() && ResultLogEntry.LT_DEBUG.equals(e.getEntryType())) {
-            logger.debug(e.getMessage());
-        } else if(logger.isInfoEnabled() && ResultLogEntry.LT_INFO.equals(e.getEntryType())) {
-            logger.info(e.getMessage());
-        } else {
-            logger.warn(e.getMessage());
-        }
-        logEntries.add(e);
-        if(!ResultLogEntry.isInformationalEntryType(e.getEntryType()) && status.ordinal() < Status.WARN.ordinal()) {
-            logger.warn("Setting Result status to WARN due to log entry of type {}", e.getEntryType());
-            setStatus(Status.WARN);
-        }
-    }
-    
-    /** Set this Result's status. Attempts to set it lower than the current
-     *  status are ignored.
-     */
-    public void setStatus(Status s) {
-        if(s.ordinal() > status.ordinal()) {
-            status = s;
-        } else {
-            logger.debug("setStatus({}) ignored as current status {} is higher", s, status);
-        }
-    }
-    
-    public Iterator<ResultLogEntry> iterator() {
-        return logEntries.iterator();
-    }
-    
-    /** True if our status is OK - just to have a convenient way of 
+    /** True if our status is OK - provides a convenient way of 
      *  checking that.
      */
     public boolean isOk() {
-        return status.ordinal() == Status.OK.ordinal();
+        return getStatus().equals(Status.OK);
     }
     
     /** Return our Status */
     public Status getStatus() {
-        return status;
+        return resultLog.getAggregateStatus();
     }
     
+    /** Return an Iterator on the entries of our ResultLog */
+    public Iterator<ResultLog.Entry> iterator() {
+        return resultLog.iterator();
+    }
 }
\ No newline at end of file

Added: sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/api/ResultLog.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/api/ResultLog.java?rev=1514287&view=auto
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/api/ResultLog.java (added)
+++ sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/api/ResultLog.java Thu Aug 15 14:19:46 2013
@@ -0,0 +1,92 @@
+/*
+ * 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 SF 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.sling.hc.api;
+
+import java.util.Iterator;
+import java.util.LinkedList;
+import java.util.List;
+
+import org.apache.sling.hc.api.Result.Status;
+
+/** The log of a Result, allows for providing multiple lines
+ *  of information which are aggregated as a single Result. */
+public class ResultLog implements Iterable<ResultLog.Entry> {
+    
+    private List<Entry> entries = new LinkedList<Entry>();
+    private Status aggregateStatus;
+    
+    /** An entry in this log */
+    public static class Entry {
+        private final Status status;
+        private final String message;
+        
+        public Entry(Status s, String message) {
+            this.status = s;
+            this.message = message;
+        }
+
+        @Override
+        public String toString() {
+            return new StringBuilder(status.toString()).append(" ").append(message).toString();
+        }
+        
+        public Status getStatus() {
+            return status;
+        }
+        
+        public String getMessage() {
+            return message;
+        }
+    }
+    
+    /** Build a log. Initial aggregate status is 
+     *  set to WARN, as an empty log is not considered ok.
+     *  That's reset to OK before adding the first log entry,
+     *  and then the status aggregation rules take over.
+     */
+    public ResultLog() {
+        aggregateStatus = Result.Status.WARN;
+    }
+
+    /** Add an entry to this log. The aggregate status of 
+     *  this is set to the highest of the current aggregate status
+     *  and the new Entry's status */
+    public ResultLog add(Entry e) {
+        if(entries.isEmpty()) {
+            aggregateStatus = Result.Status.OK;
+        }
+        entries.add(e);
+        if(e.getStatus().ordinal() > aggregateStatus.ordinal()) {
+            aggregateStatus = e.getStatus();
+        }
+        return this;
+    }
+    
+    /** Return an Iterator on our entries */
+    public Iterator<ResultLog.Entry> iterator() {
+        return entries.iterator();
+    }
+    
+    /** Return our aggregate status, i.e. the highest status
+     *  of the entries added to this log. Starts at OK for an
+     *  empty ResultLog, so cannot be lower than that.
+     */
+    public Status getAggregateStatus() {
+        return aggregateStatus;
+    }
+}
\ No newline at end of file

Modified: sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/util/SimpleConstraintChecker.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/util/SimpleConstraintChecker.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/util/SimpleConstraintChecker.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/api/src/main/java/org/apache/sling/hc/util/SimpleConstraintChecker.java Thu Aug 15 14:19:46 2013
@@ -18,7 +18,7 @@
 package org.apache.sling.hc.util;
 
 import org.apache.sling.hc.api.Result;
-import org.apache.sling.hc.api.ResultLogEntry;
+import org.apache.sling.hc.api.ResultLog;
 import org.slf4j.helpers.MessageFormatter;
 
 /** Simple check of numeric values against expressions
@@ -30,13 +30,12 @@ public class SimpleConstraintChecker {
     public static final String CONTAINS = "contains";
     
     /** Check value against expression and report to result */
-    public void check(Object inputValue, String constraint, Result result) {
+    public void check(Object inputValue, String constraint, ResultLog resultLog) {
         
         final String stringValue = inputValue == null ? "" : inputValue.toString();
         
         if(constraint == null || constraint.trim().length() == 0) {
-            // No expression, result will be based on a.getValue() logging only
-            return;
+            throw new IllegalArgumentException("Empty constraint, cannot evaluate");
         }
         
         final String [] parts = constraint.split(" ");
@@ -64,19 +63,22 @@ public class SimpleConstraintChecker {
                 matches = constraint.equals(stringValue); 
             }
         } catch(NumberFormatException nfe) {
-            result.log(ResultLogEntry.LT_WARN, 
+            resultLog.add(new ResultLog.Entry(
+                    Result.Status.WARN, 
                     MessageFormatter.format(
-                    "Invalid numeric value [{}] while evaluating {}", inputValue, constraint).getMessage());
+                            "Invalid numeric value [{}] while evaluating {}", inputValue, constraint).getMessage()));
         }
         
         if(matches) {
-            result.log(ResultLogEntry.LT_DEBUG, 
+            resultLog.add(new ResultLog.Entry(
+                    Result.Status.DEBUG, 
                     MessageFormatter.format(
-                    "Value [{}] matches constraint [{}]", stringValue, constraint).getMessage());
+                            "Value [{}] matches constraint [{}]", stringValue, constraint).getMessage()));
         } else {
-            result.log(ResultLogEntry.LT_WARN, 
+            resultLog.add(new ResultLog.Entry(
+                    Result.Status.WARN, 
                     MessageFormatter.format(
-                    "Value [{}] does not match constraint [{}]", stringValue, constraint).getMessage());
+                            "Value [{}] does not match constraint [{}]", stringValue, constraint).getMessage()));
         }
     }
 }
\ No newline at end of file

Added: sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/api/ResultLogTest.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/api/ResultLogTest.java?rev=1514287&view=auto
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/api/ResultLogTest.java (added)
+++ sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/api/ResultLogTest.java Thu Aug 15 14:19:46 2013
@@ -0,0 +1,107 @@
+/*
+ * 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 SF 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.sling.hc.api;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+
+import java.util.Iterator;
+
+import org.junit.Before;
+import org.junit.Test;
+
+public class ResultLogTest {
+
+    private ResultLog log;
+    
+    @Before
+    public void setup() {
+        log = new ResultLog();
+    }
+    
+    @Test
+    public void testEmptyLogIsNotOk() {
+        assertEquals(Result.Status.WARN, log.getAggregateStatus());
+        assertFalse(log.iterator().hasNext());
+    }
+    
+    @Test
+    public void testSetStatusGoingUp() {
+        log.add(new ResultLog.Entry(Result.Status.DEBUG, "argh"));
+        assertEquals(Result.Status.OK, log.getAggregateStatus());
+        log.add(new ResultLog.Entry(Result.Status.INFO, "argh"));
+        assertEquals(Result.Status.OK, log.getAggregateStatus());
+        log.add(new ResultLog.Entry(Result.Status.OK, "argh"));
+        assertEquals(Result.Status.OK, log.getAggregateStatus());
+        log.add(new ResultLog.Entry(Result.Status.WARN, "argh"));
+        assertEquals(Result.Status.WARN, log.getAggregateStatus());
+        log.add(new ResultLog.Entry(Result.Status.CRITICAL, "argh"));
+        assertEquals(Result.Status.CRITICAL, log.getAggregateStatus());
+        log.add(new ResultLog.Entry(Result.Status.HEALTH_CHECK_ERROR, "argh"));
+        assertEquals(Result.Status.HEALTH_CHECK_ERROR, log.getAggregateStatus());
+    }
+    
+    @Test
+    public void testSetStatusGoingDownHCE() {
+        log.add(new ResultLog.Entry(Result.Status.HEALTH_CHECK_ERROR, "argh"));
+        assertEquals(Result.Status.HEALTH_CHECK_ERROR, log.getAggregateStatus());
+        log.add(new ResultLog.Entry(Result.Status.CRITICAL, "argh"));
+        assertEquals(Result.Status.HEALTH_CHECK_ERROR, log.getAggregateStatus());
+    }
+    
+    @Test
+    public void testSetStatusGoingDownCRIT() {
+        log.add(new ResultLog.Entry(Result.Status.CRITICAL, "argh"));
+        assertEquals(Result.Status.CRITICAL, log.getAggregateStatus());
+        log.add(new ResultLog.Entry(Result.Status.WARN, "argh"));
+        assertEquals(Result.Status.CRITICAL, log.getAggregateStatus());
+    }
+    
+    @Test
+    public void testSetStatusGoingDownWARN() {
+        log.add(new ResultLog.Entry(Result.Status.WARN, "argh"));
+        assertEquals(Result.Status.WARN, log.getAggregateStatus());
+        log.add(new ResultLog.Entry(Result.Status.OK, "argh"));
+        assertEquals(Result.Status.WARN, log.getAggregateStatus());
+    }
+    
+    @Test
+    public void testSetStatusGoingDownOK() {
+        log.add(new ResultLog.Entry(Result.Status.OK, "argh"));
+        assertEquals(Result.Status.OK, log.getAggregateStatus());
+        log.add(new ResultLog.Entry(Result.Status.INFO, "argh"));
+        assertEquals(Result.Status.OK, log.getAggregateStatus());
+        log.add(new ResultLog.Entry(Result.Status.DEBUG, "argh"));
+        assertEquals(Result.Status.OK, log.getAggregateStatus());
+    }
+    
+    @Test
+    public void testLogEntries() {
+        log.add(new ResultLog.Entry(Result.Status.OK, "ok 1"));
+        log.add(new ResultLog.Entry(Result.Status.DEBUG, "debug 2"));
+        log.add(new ResultLog.Entry(Result.Status.WARN, "warn 3"));
+        log.add(new ResultLog.Entry(Result.Status.CRITICAL, "critical 4"));
+        
+        final Iterator<ResultLog.Entry> it = log.iterator();
+        assertEquals("OK ok 1", it.next().toString());
+        assertEquals("DEBUG debug 2", it.next().toString());
+        assertEquals("WARN warn 3", it.next().toString());
+        assertEquals("CRITICAL critical 4", it.next().toString());
+        assertFalse(it.hasNext());
+    }
+    }

Modified: sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/api/ResultTest.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/api/ResultTest.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/api/ResultTest.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/api/ResultTest.java Thu Aug 15 14:19:46 2013
@@ -18,119 +18,48 @@
 package org.apache.sling.hc.api;
 
 import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
 import static org.junit.Assert.assertTrue;
 
-import java.util.Iterator;
+import java.util.concurrent.atomic.AtomicInteger;
 
 import org.junit.Test;
-import org.mockito.Matchers;
-import org.mockito.Mockito;
-import org.slf4j.Logger;
 
 public class ResultTest {
     
-    @Test
-    public void testInitiallyOk() {
-        final Result result = new Result();
-        assertFalse(result.iterator().hasNext());
-        assertTrue(result.isOk());
-    }
-    
-    @Test
-    public void testDebugLogNoChange() {
-        final Result result = new Result();
-        result.log(ResultLogEntry.LT_DEBUG, "Some debug message");
-        assertTrue(result.iterator().hasNext());
-        assertTrue(result.isOk());
-    }
-    
-    @Test
-    public void testInfoLogNoChange() {
-        final Result result = new Result();
-        result.log(ResultLogEntry.LT_INFO, "Some info message");
-        assertTrue(result.iterator().hasNext());
-        assertTrue(result.isOk());
-    }
-    
-    @Test
-    public void testOthersTypesSetStatusWarn() {
-        final String [] entryTypes = new String [] {
-            ResultLogEntry.LT_WARN,
-            ResultLogEntry.LT_WARN_CONFIG,
-            ResultLogEntry.LT_WARN_SECURITY,
-            "SomeNewLogEntryType" + System.currentTimeMillis()
-        };
-        
-        for(String et : entryTypes) {
-            final Result result = new Result();
-            result.log(et, "Some message");
-            assertTrue(result.iterator().hasNext());
-            assertTrue(result.getStatus().equals(Result.Status.WARN));
-        }
-    }
+    private final AtomicInteger counter = new AtomicInteger();
     
-    @Test
-    public void testNoStatusChangeIfAlreadyCritical() {
-        final Result result = new Result();
-        result.setStatus(Result.Status.CRITICAL);
-        assertTrue(result.getStatus().equals(Result.Status.CRITICAL));
-        result.log(ResultLogEntry.LT_WARN, "Some message");
-        assertTrue(result.iterator().hasNext());
-        assertTrue(result.getStatus().equals(Result.Status.CRITICAL));
+    private void assertSingleResult(Result.Status toSet, Result.Status expected, boolean expectOk) {
+        final String msg = "test " + counter.incrementAndGet();
+        final Result r = new Result(toSet, msg);
+        assertEquals(expected, r.getStatus());
+        assertEquals(expectOk, r.isOk());
+        assertTrue(r.iterator().hasNext());
+        assertEquals(toSet.toString() + " " + msg, r.iterator().next().toString());
     }
     
     @Test
-    public void testSuppliedLogger() {
-        final Logger myLogger = Mockito.mock(Logger.class);
-        final Result r = new Result(myLogger);
-        r.log("foo", "Some message");
-        Mockito.verify(myLogger).warn(Matchers.anyString());
+    public void testSingleResult() {
+        assertSingleResult(Result.Status.DEBUG, Result.Status.OK, true);
+        assertSingleResult(Result.Status.INFO, Result.Status.OK, true);
+        assertSingleResult(Result.Status.OK, Result.Status.OK, true);
+        assertSingleResult(Result.Status.WARN, Result.Status.WARN, false);
+        assertSingleResult(Result.Status.CRITICAL, Result.Status.CRITICAL, false);
+        assertSingleResult(Result.Status.HEALTH_CHECK_ERROR, Result.Status.HEALTH_CHECK_ERROR, false);
     }
     
     @Test
-    public void testLogEntries() {
-        final Result r = new Result();
-        r.log("ONE", "M1");
-        r.log("two", "M2");
-        r.log("THREE", "M3");
+    public void testLog() {
+        final ResultLog log = new ResultLog();
+        log.add(new ResultLog.Entry(Result.Status.INFO, "argh"));
+        log.add(new ResultLog.Entry(Result.Status.WARN, "bad stuff"));
         
-        final Iterator<ResultLogEntry> it = r.iterator();
-        assertEquals("ONE", it.next().getEntryType());
-        assertEquals("two", it.next().getEntryType());
-        assertEquals("THREE", it.next().getEntryType());
-        assertFalse(it.hasNext());
-    }
-    
-    @Test
-    public void testSetStatus() {
-        final Result r = new Result();
-        assertEquals("Expecting initial OK status", Result.Status.OK, r.getStatus());
-        r.setStatus(Result.Status.CRITICAL);
-        assertEquals("Expecting CRITICAL status after setting it", Result.Status.CRITICAL, r.getStatus());
-        r.setStatus(Result.Status.WARN);
-        assertEquals("Still expecting CRITICAL status after setting it to WARN", Result.Status.CRITICAL, r.getStatus());
-    }
-    
-    @Test
-    public void testOkIsConsistent() {
-        {
-            final Result r = new Result();
-            assertTrue(r.isOk());
-            r.setStatus(Result.Status.OK);
-            assertTrue("Expecting isOk for OK Status", r.isOk());
-        }
+        final Result result = new Result(log);
+        assertEquals(Result.Status.WARN, result.getStatus());
         
-        final Result.Status [] ts = {
-            Result.Status.WARN,
-            Result.Status.CRITICAL,
-            Result.Status.HEALTH_CHECK_ERROR
-        };
-
-        for(Result.Status s : ts) {
-            final Result r = new Result();
-            r.setStatus(s);
-            assertFalse("Expecting isOk fales for " + s + " Status", r.isOk());
+        final StringBuilder sb = new StringBuilder();
+        for(ResultLog.Entry e : result) {
+            sb.append(e.toString()).append("#");
         }
+        assertEquals("INFO argh#WARN bad stuff#", sb.toString());
     }
 }

Modified: sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/util/SimpleConstraintCheckerTest.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/util/SimpleConstraintCheckerTest.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/util/SimpleConstraintCheckerTest.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/api/src/test/java/org/apache/sling/hc/util/SimpleConstraintCheckerTest.java Thu Aug 15 14:19:46 2013
@@ -21,146 +21,146 @@ import static org.junit.Assert.assertFal
 import static org.junit.Assert.assertTrue;
 
 import org.apache.sling.hc.api.Result;
-import org.apache.sling.hc.util.SimpleConstraintChecker;
+import org.apache.sling.hc.api.ResultLog;
 import org.junit.Before;
 import org.junit.Test;
 
 public class SimpleConstraintCheckerTest {
-    private Result result; 
+    private ResultLog resultLog; 
 
     private final SimpleConstraintChecker checker = new SimpleConstraintChecker();
 
     @Before
     public void setup() {
-        result = new Result();
+        resultLog = new ResultLog();
     }
     
     @Test
     public void testStringEquals() {
         final String s = "test_" + System.currentTimeMillis();
-        checker.check(s, s, result);
-        assertTrue(result.isOk());
+        checker.check(s, s, resultLog);
+        assertTrue(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testStringNotEquals() {
         final String s = "test_" + System.currentTimeMillis();
-        checker.check(s, "something else", result);
-        assertFalse(result.isOk());
+        checker.check(s, "something else", resultLog);
+        assertFalse(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testFiveEquals() {
         final String s = "5";
-        checker.check(s, s, result);
-        assertTrue(result.isOk());
+        checker.check(s, s, resultLog);
+        assertTrue(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testIntTwelveEquals() {
-        checker.check(12, "12", result);
-        assertTrue(result.isOk());
+        checker.check(12, "12", resultLog);
+        assertTrue(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testIntTwelveGreaterThan() {
-        checker.check(12, "> 11", result);
-        assertTrue(result.isOk());
+        checker.check(12, "> 11", resultLog);
+        assertTrue(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testFiveNotEquals() {
-        checker.check("5", "foo", result);
-        assertFalse(result.isOk());
+        checker.check("5", "foo", resultLog);
+        assertFalse(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testNullNotEquals() {
-        checker.check(null, "foo", result);
-        assertFalse(result.isOk());
+        checker.check(null, "foo", resultLog);
+        assertFalse(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testNullNotGreater() {
-        checker.check(null, "> 2", result);
-        assertFalse(result.isOk());
+        checker.check(null, "> 2", resultLog);
+        assertFalse(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testGreaterThanTrue() {
-        checker.check("5", "> 2", result);
-        assertTrue(result.isOk());
+        checker.check("5", "> 2", resultLog);
+        assertTrue(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testGreaterThanFalse() {
-        checker.check("5", "> 12", result);
-        assertFalse(result.isOk());
+        checker.check("5", "> 12", resultLog);
+        assertFalse(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testLessThanTrue() {
-        checker.check("5", "< 12", result);
-        assertTrue(result.isOk());
+        checker.check("5", "< 12", resultLog);
+        assertTrue(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testLessThanFalse() {
-        checker.check("5", "< 2", result);
-        assertFalse(result.isOk());
+        checker.check("5", "< 2", resultLog);
+        assertFalse(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testBetweenA() {
-        checker.check("5", "between 2 and 6", result);
-        assertTrue(result.isOk());
+        checker.check("5", "between 2 and 6", resultLog);
+        assertTrue(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testBetweenB() {
-        checker.check("5", "between 12 and 16", result);
-        assertFalse(result.isOk());
+        checker.check("5", "between 12 and 16", resultLog);
+        assertFalse(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testBetweenC() {
-        checker.check(5L, "between 12 and 16", result);
-        assertFalse(result.isOk());
+        checker.check(5L, "between 12 and 16", resultLog);
+        assertFalse(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testBetweenD() {
-        checker.check(5L, "between 4 and 16", result);
-        assertTrue(result.isOk());
+        checker.check(5L, "between 4 and 16", resultLog);
+        assertTrue(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testBetweenE() {
-        checker.check(5L, "betWEEN 4 aND 16", result);
-        assertTrue(result.isOk());
+        checker.check(5L, "betWEEN 4 aND 16", resultLog);
+        assertTrue(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testNotAnInteger() {
-        checker.check("foo", "between 12 and 16", result);
-        assertFalse(result.isOk());
+        checker.check("foo", "between 12 and 16", resultLog);
+        assertFalse(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testContainsA() {
-        checker.check("This is a NICE STRING ok?", "contains NICE STRING", result);
-        assertTrue(result.isOk());
+        checker.check("This is a NICE STRING ok?", "contains NICE STRING", resultLog);
+        assertTrue(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testContainsB() {
-        checker.check("This is a NICE TOUCH ok?", "contains NICE STRING", result);
-        assertFalse(result.isOk());
+        checker.check("This is a NICE TOUCH ok?", "contains NICE STRING", resultLog);
+        assertFalse(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
     
     @Test
     public void testContainsC() {
-        checker.check("This is a NICE TOUCH ok?", "contains NICE", result);
-        assertTrue(result.isOk());
+        checker.check("This is a NICE TOUCH ok?", "contains NICE", resultLog);
+        assertTrue(resultLog.getAggregateStatus().equals(Result.Status.OK));
     }
 }

Modified: sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/CompositeHealthCheck.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/CompositeHealthCheck.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/CompositeHealthCheck.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/CompositeHealthCheck.java Thu Aug 15 14:19:46 2013
@@ -30,7 +30,8 @@ import org.apache.sling.commons.osgi.Pro
 import org.apache.sling.hc.api.Constants;
 import org.apache.sling.hc.api.HealthCheck;
 import org.apache.sling.hc.api.Result;
-import org.apache.sling.hc.api.ResultLogEntry;
+import org.apache.sling.hc.api.ResultLog;
+import org.apache.sling.hc.healthchecks.util.FormattingResultLog;
 import org.apache.sling.hc.util.HealthCheckFilter;
 import org.osgi.framework.BundleContext;
 import org.osgi.service.component.ComponentContext;
@@ -73,40 +74,39 @@ public class CompositeHealthCheck implem
     
     @Override
     public Result execute() {
-        final Result result = new Result(log);
+        final FormattingResultLog resultLog = new FormattingResultLog();
         final List<HealthCheck> checks = new HealthCheckFilter(bundleContext).getTaggedHealthCheck(filterTags);
         if(checks.size() == 0) {
-            result.log(ResultLogEntry.LT_WARN, "HealthCheckFilter returns no HealthCheck for tags " + Arrays.asList(filterTags));
-            return result;
+            resultLog.warn("HealthCheckFilter returns no HealthCheck for tags {}", Arrays.asList(filterTags));
+            return new Result(resultLog);
         }
-            
-        result.log(ResultLogEntry.LT_DEBUG, 
-                "Executing " + checks.size() 
-                + " HealthCheck selected by the " + Arrays.asList(filterTags) + " tags");
+
+        int executed = 0;
+        resultLog.debug("Executing {} HealthCheck selected by the {} tags", checks.size(), Arrays.asList(filterTags));
         int failures = 0;
         for(HealthCheck hc : checks) {
             if(hc == this) {
-                result.log(ResultLogEntry.LT_WARN, 
-                        "Cowardly forfeiting execution of this HealthCheck in an infinite loop - do not include my tags in the filter tags!");
+                resultLog.info("Cowardly forfeiting execution of this HealthCheck in an infinite loop, ignoring it");
                 continue;
             }
-            result.log(ResultLogEntry.LT_DEBUG, "Executing " + hc); 
+            resultLog.debug("Executing {}", hc);
+            executed++;
             final Result sub = hc.execute();
             if(!sub.isOk()) {
                 failures++;
             }
-            result.merge(sub);
+            for(ResultLog.Entry e : sub) {
+                resultLog.add(e);
+            }
         }
         
         if(failures == 0) {
-            result.log(ResultLogEntry.LT_DEBUG, 
-                    checks.size() + " HealthCheck executed, all ok"); 
+            resultLog.debug("{} HealthCheck executed, all ok", executed);
         } else {
-            result.log(ResultLogEntry.LT_WARN, 
-                    checks.size() + " HealthCheck executed, " + failures + " failures"); 
+            resultLog.warn("{} HealthCheck executed, {} failures", executed, failures);
         }
         
-        return result;
+        return new Result(resultLog);
     }
 
     @Override

Modified: sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/DefaultLoginsHealthCheck.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/DefaultLoginsHealthCheck.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/DefaultLoginsHealthCheck.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/DefaultLoginsHealthCheck.java Thu Aug 15 14:19:46 2013
@@ -36,7 +36,7 @@ import org.apache.sling.commons.osgi.Pro
 import org.apache.sling.hc.api.Constants;
 import org.apache.sling.hc.api.HealthCheck;
 import org.apache.sling.hc.api.Result;
-import org.apache.sling.hc.api.ResultLogEntry;
+import org.apache.sling.hc.healthchecks.util.FormattingResultLog;
 import org.apache.sling.jcr.api.SlingRepository;
 import org.osgi.service.component.ComponentContext;
 import org.slf4j.Logger;
@@ -80,14 +80,14 @@ public class DefaultLoginsHealthCheck im
     
     @Override
     public Result execute() {
-        final Result result = new Result(log);
+        final FormattingResultLog resultLog = new FormattingResultLog();
         int checked=0;
         int failures=0;
         
         for(String login : logins) {
             final String [] parts = login.split(":");
             if(parts.length != 2) {
-                result.log(ResultLogEntry.LT_WARN, "Expected login in the form username:password, got " + login);
+                resultLog.warn("Expected login in the form username:password, got [{}]", login);
                 continue;
             }
             checked++;
@@ -99,12 +99,12 @@ public class DefaultLoginsHealthCheck im
                 s = repository.login(creds);
                 if(s != null) {
                     failures++;
-                    result.log(ResultLogEntry.LT_WARN_SECURITY, "Login as [" + username + "] succeeded, was expecting it to fail");
+                    resultLog.warn("Login as [{}] succeeded, was expecting it to fail", username);
                 } else {
-                    result.log(ResultLogEntry.LT_DEBUG, "Login as [" + username + "] didn't throw an Exception but returned null Session");
+                    resultLog.debug("Login as [{}] didn't throw an Exception but returned null Session", username);
                 }
             } catch(RepositoryException re) {
-                result.log(ResultLogEntry.LT_DEBUG, "Login as [" + username + "] failed, as expected");
+                resultLog.debug("Login as [{}] failed, as expected", username);
             } finally {
                 if(s != null) {
                     s.logout();
@@ -113,13 +113,13 @@ public class DefaultLoginsHealthCheck im
         }
         
         if(checked==0) {
-            result.log(ResultLogEntry.LT_WARN, "Did not check any logins, configured logins=" + logins);
+            resultLog.warn("Did not check any logins, configured logins={}", logins);
         } else if(failures != 0){
-            result.log(ResultLogEntry.LT_WARN_SECURITY, "Checked " + checked + " logins, " + failures + " tests failed");
+            resultLog.warn("Checked {} logins, {} failures", checked, failures);
         } else {
-            result.log(ResultLogEntry.LT_DEBUG, "Checked " + checked + " logins, all tests successful");
+            resultLog.debug("Checked {} logins, all successful", checked, failures);
         }
-        return result;
+        return new Result(resultLog);
     }
 
     @Override

Modified: sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/JmxAttributeHealthCheck.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/JmxAttributeHealthCheck.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/JmxAttributeHealthCheck.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/JmxAttributeHealthCheck.java Thu Aug 15 14:19:46 2013
@@ -32,12 +32,11 @@ import org.apache.sling.commons.osgi.Pro
 import org.apache.sling.hc.api.Constants;
 import org.apache.sling.hc.api.HealthCheck;
 import org.apache.sling.hc.api.Result;
-import org.apache.sling.hc.api.ResultLogEntry;
+import org.apache.sling.hc.healthchecks.util.FormattingResultLog;
 import org.apache.sling.hc.util.SimpleConstraintChecker;
 import org.osgi.service.component.ComponentContext;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
-import org.slf4j.helpers.MessageFormatter;
 
 /** {@link HealthCheck} that checks a single JMX attribute */
 @Component(
@@ -89,10 +88,8 @@ public class JmxAttributeHealthCheck imp
     
     @Override
     public Result execute() {
-        final Result result = new Result(log);
-        result.log(ResultLogEntry.LT_DEBUG, 
-                MessageFormatter.arrayFormat("Checking {} / {} with constraint {}", 
-                        new Object[] { mbeanName, attributeName, constraint }).getMessage());
+        final FormattingResultLog resultLog = new FormattingResultLog();
+        resultLog.debug("Checking {} / {} with constraint {}", mbeanName, attributeName, constraint);
         try {
             final MBeanServer jmxServer = ManagementFactory.getPlatformMBeanServer();
             final ObjectName objectName = new ObjectName(mbeanName);
@@ -100,15 +97,13 @@ public class JmxAttributeHealthCheck imp
                 log.error("MBean not found: {}", objectName);
             }
             final Object value = jmxServer.getAttribute(objectName, attributeName);
-            result.log(ResultLogEntry.LT_DEBUG,
-                    MessageFormatter.arrayFormat( 
-                    "{} {} returns {}", 
-                    new Object[] { mbeanName, attributeName, value }).getMessage());
-            new SimpleConstraintChecker().check(value, constraint, result);
+            resultLog.debug("{} {} returns {}", mbeanName, attributeName, value);
+            new SimpleConstraintChecker().check(value, constraint, resultLog);
         } catch(Exception e) {
-            log.warn(e.toString(), e);
+            log.warn("JMX attribute {}/{} check failed: {}", new Object []{ mbeanName, attributeName, e});
+            resultLog.healthCheckError("JMX attribute check failed: {}", e);
         }
-        return result;
+        return new Result(resultLog);
     }
 
     @Override

Modified: sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/JmxScriptBinding.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/JmxScriptBinding.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/JmxScriptBinding.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/JmxScriptBinding.java Thu Aug 15 14:19:46 2013
@@ -27,9 +27,7 @@ import javax.management.MalformedObjectN
 import javax.management.ObjectName;
 import javax.management.ReflectionException;
 
-import org.apache.sling.hc.api.Result;
-import org.apache.sling.hc.api.ResultLogEntry;
-import org.slf4j.helpers.MessageFormatter;
+import org.apache.sling.hc.healthchecks.util.FormattingResultLog;
 
 /** The JmxBinding is meant to be bound as "jmx" global variables
  *  in scripted rules, to allow for writing scripted expressions
@@ -37,10 +35,10 @@ import org.slf4j.helpers.MessageFormatte
  */
 public class JmxScriptBinding {
     private MBeanServer jmxServer = ManagementFactory.getPlatformMBeanServer();
-    private final Result result;
+    private final FormattingResultLog resultLog;
     
-    public JmxScriptBinding(Result result) {
-        this.result = result;
+    public JmxScriptBinding(FormattingResultLog resultLog) {
+        this.resultLog = resultLog;
     }
     
     public Object attribute(String objectNameString, String attributeName) 
@@ -48,15 +46,12 @@ public class JmxScriptBinding {
         final ObjectName name = new ObjectName(objectNameString);
         if(jmxServer.queryNames(name, null).size() == 0) {
             final String msg = "JMX object name not found: [" + objectNameString + "]";
-            result.log(ResultLogEntry.LT_WARN, msg);
+            resultLog.warn(msg);
             throw new IllegalStateException(msg);
         }
-        result.log(ResultLogEntry.LT_DEBUG, MessageFormatter.format("Got JMX Object [{}]", name).getMessage());
+        resultLog.debug("Got JMX Object [{}]", name);
         final Object value = jmxServer.getAttribute(name, attributeName);
-        result.log(ResultLogEntry.LT_DEBUG, 
-                MessageFormatter.arrayFormat(
-                        "JMX Object [{}] Attribute [{}] = [{}]", 
-                        new Object[] { name, attributeName, value }).getMessage());
+        resultLog.debug("JMX Object [{}] Attribute [{}] = [{}]", name, attributeName, value);
         return value;
     }
 }
\ No newline at end of file

Modified: sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/OsgiScriptBinding.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/OsgiScriptBinding.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/OsgiScriptBinding.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/OsgiScriptBinding.java Thu Aug 15 14:19:46 2013
@@ -17,23 +17,21 @@
  */
 package org.apache.sling.hc.healthchecks.impl;
 
-import org.apache.sling.hc.api.Result;
-import org.apache.sling.hc.api.ResultLogEntry;
+import org.apache.sling.hc.healthchecks.util.FormattingResultLog;
 import org.osgi.framework.Bundle;
 import org.osgi.framework.BundleContext;
 import org.osgi.framework.Constants;
-import org.slf4j.helpers.MessageFormatter;
 
 /** The OsgiBinding is meant to be bound as an "osgi" global variable
  *  in scripted rules, to allow for checking some OSGi states in
  *  a simple way
  */
 public class OsgiScriptBinding {
-    private final Result result;
+    private final FormattingResultLog resultLog;
     private final BundleContext bundleContext;
     
-    public OsgiScriptBinding(BundleContext ctx, Result result) {
-        this.result = result;
+    public OsgiScriptBinding(BundleContext ctx, FormattingResultLog resultLog) {
+        this.resultLog = resultLog;
         this.bundleContext = ctx;
     }
     
@@ -44,7 +42,7 @@ public class OsgiScriptBinding {
                 count++;
             }
         }
-        result.log(ResultLogEntry.LT_DEBUG, MessageFormatter.format("inactiveBundlesCount={}", count).getMessage());
+        resultLog.debug("inactiveBundlesCount={}", count);
         return count;
     }
     
@@ -52,10 +50,7 @@ public class OsgiScriptBinding {
         boolean active = true;
         if(!isFragment(b) && Bundle.ACTIVE != b.getState()) {
             active = false;
-            result.log(ResultLogEntry.LT_INFO, 
-                    MessageFormatter.arrayFormat(
-                            "Bundle {} is not active, state={} ({})", 
-                            new Object[] { b.getSymbolicName(), b.getState(), b.getState()}).getMessage());
+            resultLog.info("Bundle {} is not active, state={} ({})", b.getSymbolicName(), b.getState(), b.getState());
         }
         return active;
     }
@@ -63,8 +58,7 @@ public class OsgiScriptBinding {
     private boolean isFragment(Bundle b) {
         final String header = (String) b.getHeaders().get( Constants.FRAGMENT_HOST );
         if(header!= null && header.trim().length() > 0) {
-            result.log(ResultLogEntry.LT_DEBUG, 
-                    MessageFormatter.format("{} is a fragment bundle, state won't be checked", b).getMessage());
+            resultLog.debug("{} is a fragment bundle, state won't be checked", b);
             return true;
         } else {
             return false;

Modified: sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/ScriptableHealthCheck.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/ScriptableHealthCheck.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/ScriptableHealthCheck.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/ScriptableHealthCheck.java Thu Aug 15 14:19:46 2013
@@ -32,12 +32,11 @@ import org.apache.sling.commons.osgi.Pro
 import org.apache.sling.hc.api.Constants;
 import org.apache.sling.hc.api.HealthCheck;
 import org.apache.sling.hc.api.Result;
-import org.apache.sling.hc.api.ResultLogEntry;
+import org.apache.sling.hc.healthchecks.util.FormattingResultLog;
 import org.osgi.framework.BundleContext;
 import org.osgi.service.component.ComponentContext;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
-import org.slf4j.helpers.MessageFormatter;
 
 /** {@link HealthCheck} that checks a scriptable expression */
 @Component(
@@ -89,39 +88,30 @@ public class ScriptableHealthCheck imple
     
     @Override
     public Result execute() {
-        final Result result = new Result(log);
-        result.log(ResultLogEntry.LT_DEBUG, 
-                MessageFormatter.format(
-                        "Checking expression [{}], language extension=[{}]", 
-                        expression, languageExtension).getMessage());
+        final FormattingResultLog resultLog = new FormattingResultLog();
+        resultLog.debug("Checking expression [{}], language extension=[{}]",  expression, languageExtension);
         try {
             final ScriptEngine engine = scriptEngineManager.getEngineByExtension(languageExtension);
             if(engine == null) {
-                result.log(ResultLogEntry.LT_WARN, 
-                        MessageFormatter.format(
-                                "No ScriptEngine available for extension {}", 
-                                languageExtension).getMessage());
+                resultLog.healthCheckError("No ScriptEngine available for extension {}", languageExtension);
             } else {
                 // TODO pluggable Bindings? Reuse the Sling bindings providers?
                 final Bindings b = engine.createBindings();
-                b.put("jmx", new JmxScriptBinding(result));
-                b.put("osgi", new OsgiScriptBinding(bundleContext, result));
+                b.put("jmx", new JmxScriptBinding(resultLog));
+                b.put("osgi", new OsgiScriptBinding(bundleContext, resultLog));
                 final Object value = engine.eval(expression, b);
                 if(value!=null && "true".equals(value.toString())) {
-                    result.log(ResultLogEntry.LT_DEBUG, 
-                            MessageFormatter.format(
-                                    "Expression [{}] evaluates to true as expected", expression).getMessage());
+                    resultLog.debug("Expression [{}] evaluates to true as expected", expression);
                 } else {
-                    result.log(ResultLogEntry.LT_WARN, 
-                            MessageFormatter.format(
-                                    "Expression [{}] does not evaluate to true, value={}", 
-                                    expression, value).getMessage());
+                    resultLog.warn("Expression [{}] does not evaluate to true as expected, value=[{}]", expression, value); 
                 }
             }
         } catch(Exception e) {
-            result.log(ResultLogEntry.LT_WARN, e.toString()); 
+            resultLog.healthCheckError(
+                    "Exception while evaluating expression [{}] with language extension [{}]: {}", 
+                    expression, languageExtension, e); 
         }
-        return result;
+        return new Result(resultLog);
     }
 
     @Override

Modified: sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/SlingRequestStatusHealthCheck.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/SlingRequestStatusHealthCheck.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/SlingRequestStatusHealthCheck.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/impl/SlingRequestStatusHealthCheck.java Thu Aug 15 14:19:46 2013
@@ -35,11 +35,10 @@ import org.apache.sling.engine.SlingRequ
 import org.apache.sling.hc.api.Constants;
 import org.apache.sling.hc.api.HealthCheck;
 import org.apache.sling.hc.api.Result;
-import org.apache.sling.hc.api.ResultLogEntry;
+import org.apache.sling.hc.healthchecks.util.FormattingResultLog;
 import org.osgi.service.component.ComponentContext;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
-import org.slf4j.helpers.MessageFormatter;
 
 /** {@link HealthCheck} that checks the HTTP status of Sling requests */
 @Component(
@@ -101,15 +100,17 @@ public class SlingRequestStatusHealthChe
     
     @Override
     public Result execute() {
-        final Result result = new Result(log);
+        final FormattingResultLog resultLog = new FormattingResultLog();
         
         ResourceResolver resolver = null;
         int checked = 0;
         int failed = 0;
+        String lastPath = null;
         
         try {
             resolver = resolverFactory.getAdministrativeResourceResolver(null);
             for(String p : paths) {
+                lastPath = p;
                 final PathSpec ps = new PathSpec(p);
                 final HttpServletRequest request = new InternalRequest(ps.path);
                 final InternalResponse response = new InternalResponse();
@@ -117,18 +118,14 @@ public class SlingRequestStatusHealthChe
                 final int status = response.getStatus();
                 if(status != ps.status) {
                     failed++;
-                    result.log(ResultLogEntry.LT_WARN,
-                            MessageFormatter.arrayFormat(
-                            "[{}] returns status {}, expected {}", new Object[] { ps.path, status, ps.status }).getMessage());
+                    resultLog.warn("[{}] returns status {}, expected {}", new Object[] { ps.path, status, ps.status });
                 } else {
-                    result.log(ResultLogEntry.LT_DEBUG,
-                            MessageFormatter.format(
-                            "[{}] returns status {} as expected", ps.path, status).getMessage());
+                    resultLog.debug("[{}] returns status {} as expected", ps.path, status);
                 }
                 checked++;
             }
         } catch(Exception e) {
-            result.log(ResultLogEntry.LT_WARN, "Exception while executing request: " + e.toString());
+            resultLog.warn("Exception while executing request [{}]: {}", lastPath, e);
         } finally {
             if(resolver != null) {
                 resolver.close();
@@ -136,14 +133,12 @@ public class SlingRequestStatusHealthChe
         }
         
         if(checked == 0) {
-            result.log(ResultLogEntry.LT_WARN, "No paths checked, empty paths list?");
+            resultLog.warn("No paths checked, empty paths list?");
         } else {
-            result.log(ResultLogEntry.LT_DEBUG, 
-                    MessageFormatter.format(
-                            "{} paths checked, {} failures", checked, failed).getMessage());
+            resultLog.debug("{} paths checked, {} failures", checked, failed);
         }
         
-        return result;
+        return new Result(resultLog);
     }
 
     @Override

Added: sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/util/FormattingResultLog.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/util/FormattingResultLog.java?rev=1514287&view=auto
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/util/FormattingResultLog.java (added)
+++ sling/trunk/contrib/extensions/healthcheck/healthchecks/src/main/java/org/apache/sling/hc/healthchecks/util/FormattingResultLog.java Thu Aug 15 14:19:46 2013
@@ -0,0 +1,49 @@
+/*
+ * 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 SF 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.sling.hc.healthchecks.util;
+import org.apache.sling.hc.api.Result;
+import org.apache.sling.hc.api.ResultLog;
+import org.slf4j.helpers.MessageFormatter;
+
+/** Utility that provides a logging-like facade on a ResultLog */
+public class FormattingResultLog extends ResultLog {
+    
+    private ResultLog.Entry createEntry(Result.Status status, String format, Object ... args) {
+        return new ResultLog.Entry(status, MessageFormatter.arrayFormat(format, args).getMessage());
+    }
+    
+    public void debug(String format, Object ... args) {
+        add(createEntry(Result.Status.DEBUG, format, args));
+    }
+    
+    public void info(String format, Object ... args) {
+        add(createEntry(Result.Status.INFO, format, args));
+    }
+    
+    public void warn(String format, Object ... args) {
+        add(createEntry(Result.Status.WARN, format, args));
+    }
+    
+    public void critical(String format, Object ... args) {
+        add(createEntry(Result.Status.CRITICAL, format, args));
+    }
+
+    public void healthCheckError(String format, Object ... args) {
+        add(createEntry(Result.Status.HEALTH_CHECK_ERROR, format, args));
+    }
+}
\ No newline at end of file

Modified: sling/trunk/contrib/extensions/healthcheck/healthchecks/src/test/java/org/apache/sling/hc/healthchecks/JmxScriptBindingTest.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/healthchecks/src/test/java/org/apache/sling/hc/healthchecks/JmxScriptBindingTest.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/healthchecks/src/test/java/org/apache/sling/hc/healthchecks/JmxScriptBindingTest.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/healthchecks/src/test/java/org/apache/sling/hc/healthchecks/JmxScriptBindingTest.java Thu Aug 15 14:19:46 2013
@@ -20,20 +20,16 @@ package org.apache.sling.hc.healthchecks
 import static org.junit.Assert.assertNotNull;
 import static org.junit.Assert.assertTrue;
 
-import org.apache.sling.hc.api.Result;
 import org.apache.sling.hc.healthchecks.impl.JmxScriptBinding;
+import org.apache.sling.hc.healthchecks.util.FormattingResultLog;
 import org.junit.Test;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
 
 public class JmxScriptBindingTest {
     
-    private final Logger logger = LoggerFactory.getLogger(getClass());
-    
     @Test
     public void testJmxAttribute() throws Exception {
-        final Result r = new Result(logger);
-        final JmxScriptBinding b = new JmxScriptBinding(r);
+        final FormattingResultLog resultLog = new FormattingResultLog();
+        final JmxScriptBinding b = new JmxScriptBinding(resultLog);
         final Object value= b.attribute("java.lang:type=ClassLoading", "LoadedClassCount");
         assertNotNull("Expecting non-null attribute value", value);
         assertTrue("Expecting non-empty value", value.toString().length() > 0);

Modified: sling/trunk/contrib/extensions/healthcheck/healthchecks/src/test/java/org/apache/sling/hc/healthchecks/OsgiScriptBindingTest.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/healthchecks/src/test/java/org/apache/sling/hc/healthchecks/OsgiScriptBindingTest.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/healthchecks/src/test/java/org/apache/sling/hc/healthchecks/OsgiScriptBindingTest.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/healthchecks/src/test/java/org/apache/sling/hc/healthchecks/OsgiScriptBindingTest.java Thu Aug 15 14:19:46 2013
@@ -22,20 +22,16 @@ import static org.junit.Assert.assertEqu
 import java.util.Dictionary;
 import java.util.Hashtable;
 
-import org.apache.sling.hc.api.Result;
 import org.apache.sling.hc.healthchecks.impl.OsgiScriptBinding;
+import org.apache.sling.hc.healthchecks.util.FormattingResultLog;
 import org.junit.Test;
 import org.mockito.Mockito;
 import org.osgi.framework.Bundle;
 import org.osgi.framework.BundleContext;
 import org.osgi.framework.Constants;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
 
 public class OsgiScriptBindingTest {
     
-    private final Logger logger = LoggerFactory.getLogger(getClass());
-    
     private Bundle mockBundle(boolean isFragment, boolean isActive) {
         final Bundle b = Mockito.mock(Bundle.class);
         Mockito.when(b.getState()).thenReturn(isActive ? Bundle.ACTIVE : Bundle.RESOLVED);
@@ -60,8 +56,8 @@ public class OsgiScriptBindingTest {
         };
         Mockito.when(ctx.getBundles()).thenReturn(bundles);
         
-        final Result r = new Result(logger);
-        final OsgiScriptBinding b = new OsgiScriptBinding(ctx, r);
+        final FormattingResultLog resultLog = new FormattingResultLog();
+        final OsgiScriptBinding b = new OsgiScriptBinding(ctx, resultLog);
         assertEquals(1, b.inactiveBundlesCount());
     }
 }
\ No newline at end of file

Modified: sling/trunk/contrib/extensions/healthcheck/jmx/src/main/java/org/apache/sling/hc/jmx/impl/HealthCheckMBean.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/jmx/src/main/java/org/apache/sling/hc/jmx/impl/HealthCheckMBean.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/jmx/src/main/java/org/apache/sling/hc/jmx/impl/HealthCheckMBean.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/jmx/src/main/java/org/apache/sling/hc/jmx/impl/HealthCheckMBean.java Thu Aug 15 14:19:46 2013
@@ -44,7 +44,7 @@ import javax.management.openmbean.Tabula
 import org.apache.sling.hc.api.Constants;
 import org.apache.sling.hc.api.HealthCheck;
 import org.apache.sling.hc.api.Result;
-import org.apache.sling.hc.api.ResultLogEntry;
+import org.apache.sling.hc.api.ResultLog;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -141,10 +141,10 @@ public class HealthCheckMBean implements
     private TabularData logData(Result er) {
         final TabularDataSupport result = new TabularDataSupport(LOG_TABLE_TYPE);
         int i=1;
-        for(ResultLogEntry e : er) {
+        for(ResultLog.Entry e : er) {
             final Map<String, Object> data = new HashMap<String, Object>();
             data.put(INDEX_COLUMN, i++);
-            data.put(LEVEL_COLUMN, e.getEntryType());
+            data.put(LEVEL_COLUMN, e.getStatus().toString());
             data.put(MESSAGE_COLUMN, e.getMessage());
             try {
                 result.put(new CompositeDataSupport(LOG_ROW_TYPE, data));

Modified: sling/trunk/contrib/extensions/healthcheck/jmx/src/test/java/org/apache/sling/hc/jmx/HealthCheckMBeanTest.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/jmx/src/test/java/org/apache/sling/hc/jmx/HealthCheckMBeanTest.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/jmx/src/test/java/org/apache/sling/hc/jmx/HealthCheckMBeanTest.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/jmx/src/test/java/org/apache/sling/hc/jmx/HealthCheckMBeanTest.java Thu Aug 15 14:19:46 2013
@@ -29,7 +29,7 @@ import javax.management.ObjectName;
 
 import org.apache.sling.hc.api.HealthCheck;
 import org.apache.sling.hc.api.Result;
-import org.apache.sling.hc.api.ResultLogEntry;
+import org.apache.sling.hc.api.ResultLog;
 import org.apache.sling.hc.jmx.impl.HealthCheckMBean;
 import org.apache.sling.hc.util.SimpleConstraintChecker;
 import org.junit.Test;
@@ -49,13 +49,11 @@ public class HealthCheckMBeanTest {
 
         @Override
         public Result execute() {
-            final Result result = new Result();
             if(resultOk) {
-                result.log(ResultLogEntry.LT_DEBUG, "Nothing to report, result ok");
+                return new Result(Result.Status.OK, "Nothing to report, result ok");
             } else {
-                result.log(ResultLogEntry.LT_WARN, "Result is not ok!");
+                return new Result(Result.Status.WARN, "Result is not ok!");
             }
-            return result;
         }
 
         @Override
@@ -71,9 +69,9 @@ public class HealthCheckMBeanTest {
             fail("MBean not found: " + objectName);
         }
         final Object value = jmxServer.getAttribute(objectName, attributeName);
-        final Result result = new Result();
-        new SimpleConstraintChecker().check(value, constraint, result);
-        assertEquals("Expecting result " + expected, expected, result.isOk());
+        final ResultLog resultLog = new ResultLog();
+        new SimpleConstraintChecker().check(value, constraint, resultLog);
+        assertEquals("Expecting result " + expected, expected, resultLog.getAggregateStatus().equals(Result.Status.OK));
         
     }
     

Modified: sling/trunk/contrib/extensions/healthcheck/webconsole/src/main/java/org/apache/sling/hc/webconsole/impl/HealthCheckWebconsolePlugin.java
URL: http://svn.apache.org/viewvc/sling/trunk/contrib/extensions/healthcheck/webconsole/src/main/java/org/apache/sling/hc/webconsole/impl/HealthCheckWebconsolePlugin.java?rev=1514287&r1=1514286&r2=1514287&view=diff
==============================================================================
--- sling/trunk/contrib/extensions/healthcheck/webconsole/src/main/java/org/apache/sling/hc/webconsole/impl/HealthCheckWebconsolePlugin.java (original)
+++ sling/trunk/contrib/extensions/healthcheck/webconsole/src/main/java/org/apache/sling/hc/webconsole/impl/HealthCheckWebconsolePlugin.java Thu Aug 15 14:19:46 2013
@@ -37,7 +37,7 @@ import org.apache.sling.api.request.Resp
 import org.apache.sling.hc.api.Constants;
 import org.apache.sling.hc.api.HealthCheck;
 import org.apache.sling.hc.api.Result;
-import org.apache.sling.hc.api.ResultLogEntry;
+import org.apache.sling.hc.api.ResultLog;
 import org.apache.sling.hc.util.HealthCheckFilter;
 import org.osgi.framework.BundleContext;
 import org.osgi.service.component.ComponentContext;
@@ -145,13 +145,13 @@ public class HealthCheckWebconsolePlugin
         
         c.tr();
         c.tdContent();
-        for(ResultLogEntry e : result) {
-            if(!debug && e.getEntryType().equals(ResultLogEntry.LT_DEBUG)) {
+        for(ResultLog.Entry e : result) {
+            if(!debug && e.getStatus().equals(Result.Status.DEBUG)) {
                 continue;
             }
             final StringBuilder sb = new StringBuilder();
-            sb.append("<div class='log").append(e.getEntryType()).append("'>");
-            sb.append(e.getEntryType())
+            sb.append("<div class='log").append(e.getStatus()).append("'>");
+            sb.append(e.getStatus())
                 .append(" ")
                 .append(ResponseUtil.escapeXml(e.getMessage()))
                 .append("</div>");



Mime
View raw message