/* * Copyright (c) 2013, the Dart project authors. * * Licensed under the Eclipse Public License v1.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.eclipse.org/legal/epl-v10.html * * 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 com.google.dart.tools.tests.buildbot; import com.google.dart.tools.tests.buildbot.runner.AbstractTestRunner; import junit.framework.Test; import junit.framework.TestCase; import junit.framework.TestFailure; import junit.framework.TestResult; import org.eclipse.core.resources.IResource; import org.eclipse.core.resources.ResourcesPlugin; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.ILogListener; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.core.runtime.IStatus; import org.eclipse.core.runtime.NullProgressMonitor; import org.eclipse.core.runtime.Platform; import org.eclipse.core.runtime.Status; import org.eclipse.core.runtime.jobs.Job; import java.text.DecimalFormat; import java.text.NumberFormat; import java.util.Collections; import java.util.Enumeration; import java.util.List; /** * Run the given TestSuite, and optionally exit Eclipse when finished. */ class BuildbotTestsJob extends Job { private class JobTestRunner extends AbstractTestRunner implements ILogListener { private IProgressMonitor monitor; public JobTestRunner(IProgressMonitor monitor, Test test) { super(test); this.monitor = monitor; Platform.addLogListener(this); } @Override public void logging(IStatus status, String plugin) { if (status.getSeverity() == IStatus.ERROR) { markCurrentTestLoggedError(); } } @Override protected boolean filterTest(TestCase test) { final List<String> proscribed = Collections.emptyList(); String testId = getTestId(test); if (proscribed.contains(testId)) { return true; } return super.filterTest(test); } @Override protected void testFailed(TestCase test, TestResult result) { System.out.println("fail"); } @Override protected void testPassed(TestCase test) { System.out.println("pass"); } @Override protected void testsFinished(List<TestCase> allTests, List<TestResult> failures, List<TestTime> slowTests, long totalTime) { Platform.removeLogListener(this); // shame the slow tests printHeader("slow tests"); if (slowTests.size() > 0) { Collections.sort(slowTests); for (TestTime testTime : slowTests) { System.out.println(testTime.toString()); } } else { System.out.println("No slow tests!"); } // print any test failures w/ details printHeader("test summary"); if (failures.size() > 0) { for (TestResult result : failures) { printFailures(result.failures()); printFailures(result.errors()); } } System.out.println(formatInt(allTests.size()) + " tests were run; " + formatInt(failures.size()) + " failures [" + formatDouble(totalTime / 1000.0) + " secs]."); monitor.done(); } @Override protected void testsStarted(List<TestCase> tests) { monitor.beginTask(getName(), tests.size()); } @Override protected void testStarted(TestCase test) { System.out.print(getTestId(test) + ": "); monitor.worked(1); } } private static String formatDouble(double d) { NumberFormat nf = new DecimalFormat(); nf.setMaximumFractionDigits(2); nf.setMinimumFractionDigits(2); return nf.format(d); } private static String formatInt(int i) { return NumberFormat.getIntegerInstance().format(i); } private boolean exitWhenFinished; private Test mainTest; public BuildbotTestsJob(boolean exitWhenFinished) { this(exitWhenFinished, TestAll.suite()); } public BuildbotTestsJob(boolean exitWhenFinished, Test mainTest) { super("Running tests..."); this.exitWhenFinished = exitWhenFinished; this.mainTest = mainTest; } @Override protected IStatus run(final IProgressMonitor monitor) { // First, refresh the workspace. Otherwise out-of-sync resources will cause problems. try { ResourcesPlugin.getWorkspace().getRoot().refreshLocal( IResource.DEPTH_INFINITE, new NullProgressMonitor()); } catch (CoreException e) { BuildbotPlugin.getPlugin().log(e); } // Now, run the tests. JobTestRunner testRunner = new JobTestRunner(monitor, mainTest); boolean testsPassed = testRunner.runTests(); if (exitWhenFinished) { int exitCode = testsPassed ? 0 : 1; // We do a hard exit. System.exit(exitCode); } return Status.OK_STATUS; } private void printFailure(TestFailure failure) { TestCase test = (TestCase) failure.failedTest(); System.out.println(AbstractTestRunner.getTestId(test)); printStackTrace(failure.trace().split("\n")); System.out.println(); } private void printFailures(Enumeration<TestFailure> failures) { while (failures.hasMoreElements()) { printFailure(failures.nextElement()); } } private void printHeader(String title) { System.out.println("\n--- " + title + " ---"); } private void printStackTrace(String[] lines) { for (String line : lines) { if (line.startsWith("\tat sun.reflect.NativeMethod") || line.startsWith("\tat java.lang.reflect.Method") || line.startsWith("\tat junit.framework.TestCase.runTest") || line.startsWith("\tat junit.framework.TestCase.runBare")) { return; } System.out.println(line); } } }