SLING-3579 - Allow performance tests to report custom class name to the report logger

* applied patch from Andrei Dulvac

git-svn-id: https://svn.apache.org/repos/asf/sling/trunk@1608717 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/base/src/main/java/org/apache/sling/performance/AbstractRepositoryTest.java b/base/src/main/java/org/apache/sling/performance/AbstractRepositoryTest.java
index 4854bca..7a813ea 100644
--- a/base/src/main/java/org/apache/sling/performance/AbstractRepositoryTest.java
+++ b/base/src/main/java/org/apache/sling/performance/AbstractRepositoryTest.java
@@ -26,7 +26,7 @@
 
 
   
-public abstract class AbstractRepositoryTest {
+public abstract class AbstractRepositoryTest implements IdentifiableTestClass{
 
     protected String testInstanceName;
 
@@ -87,9 +87,8 @@
         }
         return testRoot;
     }
-    
-    public String toString(){
-    	return testInstanceName;
-    }
 
+    public String testClassName() {
+        return testInstanceName;
+    }
 }
diff --git a/base/src/main/java/org/apache/sling/performance/FrameworkPerformanceMethod.java b/base/src/main/java/org/apache/sling/performance/FrameworkPerformanceMethod.java
index be28c78..42ee110 100644
--- a/base/src/main/java/org/apache/sling/performance/FrameworkPerformanceMethod.java
+++ b/base/src/main/java/org/apache/sling/performance/FrameworkPerformanceMethod.java
@@ -39,6 +39,7 @@
 	private PerformanceSuiteState performanceSuiteState;
 	private PerformanceRunner.ReportLevel reportLevel = PerformanceRunner.ReportLevel.ClassLevel;
     private String testCaseName = "";
+    private String className;
 
 	public FrameworkPerformanceMethod(Method method, Object target,
 			PerformanceSuiteState performanceSuiteState, PerformanceRunner.ReportLevel reportLevel) {
@@ -48,7 +49,16 @@
 		this.reportLevel = reportLevel;
         if (target instanceof IdentifiableTestCase) {
             this.testCaseName = ((IdentifiableTestCase) target).testCaseName();
-	}
+	    }
+
+        // Name of the test class, as the report logger needs it
+        // This can be overwritten by tests by implementing IdentifiableTestClass
+        String longClassName = this.target.getClass().getName();
+        className = longClassName.substring(longClassName.lastIndexOf(".") + 1);
+        if (target instanceof IdentifiableTestClass) {
+            this.className = ((IdentifiableTestClass) target).testClassName();
+        }
+
     }
 
 	@Override
@@ -76,11 +86,9 @@
 		// in case we don't have to deal with a PerformanceSuite just skip this
 		// as JUnit will run the methods itself
 		if ((performanceSuiteState != null)
-				&& !performanceSuiteState.testSuiteName
-						.equals(ParameterizedTestList.TEST_CASE_ONLY)) {
+				&& !performanceSuiteState.testSuiteName.equals(ParameterizedTestList.TEST_CASE_ONLY)) {
 
-			recursiveCallSpecificMethod(this.target.getClass(), this.target,
-					Before.class);
+			recursiveCallSpecificMethod(this.target.getClass(), this.target, Before.class);
 		}
 
 		// Need to count the number of tests run from the PerformanceSuite
@@ -104,16 +112,12 @@
 
 		DescriptiveStatistics statistics = new DescriptiveStatistics();
 
-		// System.out.println("Warmup started - test :" +
-		// testMethodToInvoke.getName());
-
 		if (warmupinvocations != 0) {
 			// Run the number of invocation specified in the annotation
 			// for warming up the system
 			for (int invocationIndex = 0; invocationIndex < warmupinvocations; invocationIndex++) {
 
-				recursiveCallSpecificMethod(this.target.getClass(),
-						this.target, BeforeMethodInvocation.class);
+				recursiveCallSpecificMethod(this.target.getClass(), this.target, BeforeMethodInvocation.class);
 
 				// TODO: implement the method to run a before a specific test
 				// method
@@ -177,8 +181,8 @@
 		}
 
 		if (statistics.getN() > 0) {
-		    ReportLogger.writeReport(this.performanceSuiteState.testSuiteName, testCaseName, ((String )this.target.getClass().getMethod("toString", null).invoke(this.target, null)),
-                    getMethod().getName(), statistics, ReportLogger.ReportType.TXT, reportLevel);
+		    ReportLogger.writeReport(this.performanceSuiteState.testSuiteName, testCaseName, className, getMethod().getName(),
+                    statistics, ReportLogger.ReportType.TXT, reportLevel);
 		}
 
 		// In case of a PerformanceSuite we need to run the methods annotated
@@ -187,11 +191,9 @@
 		// with a PerformanceSuite
 		// just skip this as JUnit will run the methods itself
 		if ((performanceSuiteState != null)
-				&& !performanceSuiteState.testSuiteName
-						.equals(ParameterizedTestList.TEST_CASE_ONLY)) {
+				&& !performanceSuiteState.testSuiteName.equals(ParameterizedTestList.TEST_CASE_ONLY)) {
 
-			recursiveCallSpecificMethod(this.target.getClass(), this.target,
-					After.class);
+			recursiveCallSpecificMethod(this.target.getClass(), this.target, After.class);
 		}
 
 		// Check if this is the last test running from a PerformanceSuite
@@ -199,13 +201,9 @@
 		if ((performanceSuiteState != null)
 				&& (performanceSuiteState.getAfterSuiteMethod() != null)
 				&& (performanceSuiteState.getTargetObjectSuite() != null)
-				&& (performanceSuiteState.getNumberOfExecutedMethods() == performanceSuiteState
-						.getNumberOfMethodsInSuite())
-				&& !performanceSuiteState.testSuiteName
-						.equals(ParameterizedTestList.TEST_CASE_ONLY)) {
-			performanceSuiteState.getAfterSuiteMethod().invoke(
-					performanceSuiteState.getTargetObjectSuite());
-
+				&& (performanceSuiteState.getNumberOfExecutedMethods() == performanceSuiteState.getNumberOfMethodsInSuite())
+				&& !performanceSuiteState.testSuiteName.equals(ParameterizedTestList.TEST_CASE_ONLY)) {
+			performanceSuiteState.getAfterSuiteMethod().invoke(performanceSuiteState.getTargetObjectSuite());
 		}
 
 		return response;
@@ -240,8 +238,7 @@
 		// System.out.println("Start test: " + testMethodToInvoke.getName());
 		long start = System.nanoTime();
 		response = super.invokeExplosively(this.target, params);
-		long timeMilliseconds = TimeUnit.MILLISECONDS.convert(System.nanoTime()
-				- start, TimeUnit.NANOSECONDS);
+		long timeMilliseconds = TimeUnit.MILLISECONDS.convert(System.nanoTime() - start, TimeUnit.NANOSECONDS);
 		statistics.addValue(timeMilliseconds);
 
 		// System.out.println("End test: " + testMethodToInvoke.getName());
@@ -252,8 +249,7 @@
 		// recursiveCallSpecificMethod(this.target.getClass(), this.target,
 		// AfterSpecificTest.class);
 
-		recursiveCallSpecificMethod(this.target.getClass(), this.target,
-				AfterMethodInvocation.class);
+		recursiveCallSpecificMethod(this.target.getClass(), this.target, AfterMethodInvocation.class);
 
 		return response;
 	}
@@ -309,14 +305,12 @@
 			throws InvalidAttributesException, IllegalAccessException,
 			InstantiationException {
 
-		Method[] methodsToReturn = getSpecificMethods(testClass,
-				methodAnnotation);
+		Method[] methodsToReturn = getSpecificMethods(testClass, methodAnnotation);
 		Method methodToReturn = null;
 		if (methodsToReturn.length == 1) {
 			methodToReturn = methodsToReturn[0];
 		} else if (methodsToReturn.length > 1) {
-			throw new InvalidAttributesException(
-					"Only 1 non parameterized before method accepted");
+			throw new InvalidAttributesException("Only 1 non parameterized before method accepted");
 		}
 
 		return methodToReturn;
diff --git a/base/src/main/java/org/apache/sling/performance/IdentifiableTestClass.java b/base/src/main/java/org/apache/sling/performance/IdentifiableTestClass.java
new file mode 100644
index 0000000..b7c78d0
--- /dev/null
+++ b/base/src/main/java/org/apache/sling/performance/IdentifiableTestClass.java
@@ -0,0 +1,10 @@
+package org.apache.sling.performance;
+
+/**
+ * Interface to be implemented by a class with PerformanceTests.
+ * <p></p>The provided method @{link #testCaseName()} exposes the possibility to give a name to each instance of the
+ * implementing class</p>
+ */
+public interface IdentifiableTestClass {
+    public String testClassName();
+}
diff --git a/base/src/main/java/org/apache/sling/performance/PerformanceRunner.java b/base/src/main/java/org/apache/sling/performance/PerformanceRunner.java
index a2ff109..ecd1bbc 100644
--- a/base/src/main/java/org/apache/sling/performance/PerformanceRunner.java
+++ b/base/src/main/java/org/apache/sling/performance/PerformanceRunner.java
@@ -196,17 +196,14 @@
 
 		if (!suiteAlreadyRegistered) {
 			if (beforeSuiteMethods.size() == 1) {
-				newSuite.setBeforeSuiteMethod(beforeSuiteMethods.get(0)
-						.getMethod());
+				newSuite.setBeforeSuiteMethod(beforeSuiteMethods.get(0).getMethod());
 			}
 			if (afterSuiteMethods.size() == 1) {
-				newSuite.setAfterSuiteMethod(afterSuiteMethods.get(0)
-						.getMethod());
+				newSuite.setAfterSuiteMethod(afterSuiteMethods.get(0).getMethod());
 			}
 
 			current = newSuite;
-			newSuite.setTargetObjectSuite(getTestClass().getJavaClass()
-					.newInstance());
+			newSuite.setTargetObjectSuite(getTestClass().getJavaClass().newInstance());
 
 		}
 
@@ -218,14 +215,11 @@
 			for (Object testObject : testObjects) {
 
 				// retrieve the test methods from the test classes
-				Method[] testMethods = getSpecificMethods(
-						testObject.getClass(), PerformanceTest.class);
-
+				Method[] testMethods = getSpecificMethods(testObject.getClass(), PerformanceTest.class);
 
 				for (Method method : testMethods) {
-					FrameworkPerformanceMethod performaceTestMethod = new
-							FrameworkPerformanceMethod(
-							method, testObject, current, reportLevel);
+					FrameworkPerformanceMethod performaceTestMethod =
+                            new FrameworkPerformanceMethod(method, testObject, current, reportLevel);
 					tests.add(performaceTestMethod);
 				}
 
@@ -240,8 +234,7 @@
 
 		// Retrieve the performance tests in the case we don't have a
 		// performance test suite
-		for (FrameworkMethod method : getTestClass().getAnnotatedMethods(
-				PerformanceTest.class)) {
+		for (FrameworkMethod method : getTestClass().getAnnotatedMethods(PerformanceTest.class)) {
 			Object targetObject = getTestClass().getJavaClass().newInstance();
 			FrameworkPerformanceMethod performanceTestMethod = new FrameworkPerformanceMethod(
 					method.getMethod(), targetObject, current, reportLevel);
diff --git a/base/src/main/java/org/apache/sling/performance/ReportLogger.java b/base/src/main/java/org/apache/sling/performance/ReportLogger.java
index 6e3161e..ac4ed49 100644
--- a/base/src/main/java/org/apache/sling/performance/ReportLogger.java
+++ b/base/src/main/java/org/apache/sling/performance/ReportLogger.java
@@ -37,10 +37,10 @@
     public static void writeReport(String testSuiteName, String testCaseName, String className, String methodName,
             DescriptiveStatistics statistics, ReportType reportType, PerformanceRunner.ReportLevel reportLevel) throws Exception {
 		switch (reportType) {
-		case TXT:
+            case TXT:
                 writeReportTxt(testSuiteName, testCaseName, className, methodName, statistics, reportLevel);
-			break;
-		default:
+                break;
+            default:
                 throw new Exception("The specified reporting format is not yet supported");
 		}
 	}
@@ -53,21 +53,16 @@
      * @param className
      * @param methodName
 	 * @param statistics
-     * @param reportlevel
+     * @param reportLevel
      * @throws Exception
 	 */
     public static void writeReportTxt(String testSuiteName, String testCaseName, String className, String methodName,
-            DescriptiveStatistics statistics, PerformanceRunner.ReportLevel reportlevel) throws Exception {
-
-        // Short class form
-        String shortClassName = className.substring(className.lastIndexOf(".") + 1);
+            DescriptiveStatistics statistics, PerformanceRunner.ReportLevel reportLevel) throws Exception {
 
         File reportDir = new File("target/" + REPORTS_DIR);
-		if (!reportDir.exists()) {
-            if (!reportDir.mkdir()) {
+		if (!reportDir.exists() && !reportDir.mkdir()) {
                 throw new IOException("Unable to create " + REPORTS_DIR + " directory");
 		}
-        }
 
 		// need this in the case a user wants to set the suite name from the
 		// command line
@@ -79,13 +74,13 @@
 			}
 		}
 
-        String resultFileName = shortClassName;
-		if (reportlevel.equals(PerformanceRunner.ReportLevel.ClassLevel)){
-			writeReportClassLevel(resultFileName, testSuiteName, statistics);
-			}else if (reportlevel.equals(PerformanceRunner.ReportLevel.MethodLevel)){
-            resultFileName = shortClassName + "." + methodName;
+		if (reportLevel.equals(PerformanceRunner.ReportLevel.ClassLevel)) {
+            String resultFileName = className;
+            writeReportClassLevel(resultFileName, testSuiteName, statistics);
+        } else if (reportLevel.equals(PerformanceRunner.ReportLevel.MethodLevel)) {
+            String resultFileName = className + "." + methodName;
             writeReportMethodLevel(resultFileName, testSuiteName, testCaseName, className, methodName, statistics);
-			}
+        }
 	}
 	
 	/**
@@ -104,22 +99,20 @@
 	    		new FileWriterWithEncoding(report, "UTF-8", true));
 	    try {
 	    	if (needsPrefix) {
-	    		writer.format(
-	    				"# %-34.34s     min     10%%     50%%     90%%     max%n",
-	    				resultFileName);
+	    		writer.format("# %-50.50s     min     10%%     50%%     90%%     max%n", resultFileName);
 	    	}
 	    	
 	    	writer.format(
-	    			"%-36.36s  %6.0f  %6.0f  %6.0f  %6.0f  %6.0f%n",
+	    			"%-52.52s  %6.0f  %6.0f  %6.0f  %6.0f  %6.0f%n",
 	    			testSuiteName,
 	    			statistics.getMin(),
 	    			statistics.getPercentile(10.0),
 	    			statistics.getPercentile(50.0),
 	    			statistics.getPercentile(90.0),
 	    			statistics.getMax());
-	    	} finally {
-	    		writer.close();
-	   		}
+        } finally {
+            writer.close();
+        }
 	}
     
     /**