001: /*
002: * Copyright 2001-2007 Geert Bevin <gbevin[remove] at uwyn dot com>
003: * Distributed under the terms of either:
004: * - the common development and distribution license (CDDL), v1.0; or
005: * - the GNU Lesser General Public License, v2.1 or later
006: * $Id: ParametrizedTestSuite.java 3634 2007-01-08 21:42:24Z gbevin $
007: */
008: package com.uwyn.rife;
009:
010: import com.uwyn.rife.tools.ExceptionUtils;
011: import java.lang.reflect.Constructor;
012: import java.lang.reflect.InvocationTargetException;
013: import java.lang.reflect.Method;
014: import java.lang.reflect.Modifier;
015: import java.util.ArrayList;
016: import java.util.Vector;
017: import junit.framework.Test;
018: import junit.framework.TestCase;
019: import junit.framework.TestSuite;
020:
021: public class ParametrizedTestSuite extends TestSuite {
022: public ParametrizedTestSuite(String name) {
023: super (name);
024: }
025:
026: public ParametrizedTestSuite(final Class theClass,
027: Class[] argsTypes, ArrayList<Object[]> argsList) {
028: super (theClass.getName());
029:
030: initParametrization(theClass, argsTypes, argsList);
031: }
032:
033: protected void initParametrization(final Class theClass,
034: Class[] argsTypes, ArrayList<Object[]> argsList) {
035: Constructor constructor = null;
036: try {
037: constructor = getParametrizedConstructor(theClass,
038: argsTypes);
039: } catch (NoSuchMethodException e) {
040: addTest(parametrizationWarning("Class "
041: + theClass.getName()
042: + " has no public constructor that fits."));
043: return;
044: }
045:
046: if (!Modifier.isPublic(theClass.getModifiers())) {
047: addTest(parametrizationWarning("Class "
048: + theClass.getName() + " is not public."));
049: return;
050: }
051:
052: Class super Class = theClass;
053: Vector<String> names = new Vector<String>();
054: while (Test.class.isAssignableFrom(super Class)) {
055: Method[] methods = super Class.getDeclaredMethods();
056: for (int i = 0; i < methods.length; i++) {
057: addParametrizedTestMethod(methods[i], names,
058: constructor, argsList);
059: }
060: super Class = super Class.getSuperclass();
061: }
062: if (countTestCases() == 0) {
063: addTest(parametrizationWarning("No tests found in "
064: + theClass.getName()));
065: }
066: }
067:
068: protected Constructor getParametrizedConstructor(Class theClass,
069: Class[] argsTypes) throws NoSuchMethodException {
070: return theClass.getConstructor(argsTypes);
071: }
072:
073: protected Test parametrizationWarning(final String message) {
074: return new TestCase("warning") {
075: protected void runTest() {
076: fail(message);
077: }
078: };
079: }
080:
081: protected void addParametrizedTestMethod(Method m,
082: Vector<String> names, Constructor constructor,
083: ArrayList<Object[]> argsList) {
084: String name = m.getName();
085: if (names.contains(name)) {
086: return;
087: }
088:
089: if (isPublicTestMethod(m)) {
090: names.addElement(name);
091:
092: Object test = null;
093:
094: for (Object[] args : argsList) {
095: args[args.length - 1] = name;
096: try {
097: test = constructor.newInstance(args);
098: if (test instanceof Test) {
099: addTest((Test) test);
100: } else {
101: addTest(parametrizationWarning("Cannot instantiate test case: "
102: + name
103: + " (is no instance of Test but of "
104: + test.getClass().getName() + ")"));
105: }
106: } catch (InstantiationException e) {
107: addTest(parametrizationWarning("Cannot instantiate test case: "
108: + name
109: + " ("
110: + ExceptionUtils.getExceptionStackTrace(e)
111: + ")"));
112: } catch (InvocationTargetException e) {
113: addTest(parametrizationWarning("Exception in constructor: "
114: + name
115: + " ("
116: + ExceptionUtils.getExceptionStackTrace(e
117: .getTargetException()) + ")"));
118: } catch (IllegalAccessException e) {
119: addTest(parametrizationWarning("Cannot access test case: "
120: + name
121: + " ("
122: + ExceptionUtils.getExceptionStackTrace(e)
123: + ")"));
124: }
125: }
126:
127: } else {
128: // almost a test method
129: if (isTestMethod(m)) {
130: addTest(parametrizationWarning("Test method isn't public: "
131: + m.getName()));
132: }
133: }
134: }
135:
136: protected boolean isPublicTestMethod(Method m) {
137: return isTestMethod(m) && Modifier.isPublic(m.getModifiers());
138: }
139:
140: protected boolean isTestMethod(Method m) {
141: String name = m.getName();
142: Class[] parameters = m.getParameterTypes();
143: Class returnType = m.getReturnType();
144: return parameters.length == 0 && name.startsWith("test")
145: && returnType.equals(Void.TYPE);
146: }
147: }
|