1 package org.apache.maven.surefire.junit;
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 import java.lang.reflect.InvocationTargetException;
23 import java.lang.reflect.Method;
24 import java.lang.reflect.Modifier;
25 import java.util.ArrayList;
26 import java.util.List;
27 import org.apache.maven.surefire.report.LegacyPojoStackTraceWriter;
28 import org.apache.maven.surefire.report.RunListener;
29 import org.apache.maven.surefire.report.SimpleReportEntry;
30 import org.apache.maven.surefire.report.StackTraceWriter;
31 import org.apache.maven.surefire.testset.TestSetFailedException;
32
33 import static org.apache.maven.surefire.report.SimpleReportEntry.withException;
34
35
36
37
38
39 public class PojoTestSet
40 implements SurefireTestSet
41 {
42 private static final String TEST_METHOD_PREFIX = "test";
43
44 private static final Object[] EMPTY_OBJECT_ARRAY = new Object[0];
45
46 private final Object testObject;
47
48 private final Class<?> testClass;
49
50 private List<Method> testMethods;
51
52 private Method setUpMethod;
53
54 private Method tearDownMethod;
55
56 public PojoTestSet( final Class<?> testClass )
57 throws TestSetFailedException
58 {
59 if ( testClass == null )
60 {
61 throw new IllegalArgumentException( "testClass is null" );
62 }
63
64 this.testClass = testClass;
65
66 try
67 {
68 testObject = testClass.newInstance();
69 }
70 catch ( InstantiationException e )
71 {
72 throw new TestSetFailedException( "Unable to instantiate POJO '" + testClass + "'", e );
73 }
74 catch ( IllegalAccessException e )
75 {
76 throw new TestSetFailedException( "Unable to instantiate POJO '" + testClass + "'", e );
77 }
78 }
79
80 @Override
81 public void execute( RunListener reportManager, ClassLoader loader )
82 throws TestSetFailedException
83 {
84 if ( reportManager == null )
85 {
86 throw new NullPointerException( "reportManager is null" );
87 }
88
89 executeTestMethods( reportManager );
90 }
91
92 private void executeTestMethods( RunListener reportManager )
93 {
94 if ( reportManager == null )
95 {
96 throw new NullPointerException( "reportManager is null" );
97 }
98
99 if ( testMethods == null )
100 {
101 discoverTestMethods();
102 }
103
104 boolean abort = false;
105
106 for ( int i = 0; i < testMethods.size() && !abort; ++i )
107 {
108 abort = executeTestMethod( testMethods.get( i ), EMPTY_OBJECT_ARRAY, reportManager );
109 }
110 }
111
112 private boolean executeTestMethod( Method method, Object[] args, RunListener reportManager )
113 {
114 if ( method == null || args == null || reportManager == null )
115 {
116 throw new NullPointerException();
117 }
118
119 final String testClassName = getTestClass().getName();
120 final String methodName = method.getName();
121 final String userFriendlyMethodName = methodName + '(' + ( args.length == 0 ? "" : "Reporter" ) + ')';
122 final String testName = getTestName( userFriendlyMethodName );
123
124 reportManager.testStarting( new SimpleReportEntry( testClassName, testName ) );
125
126 try
127 {
128 setUpFixture();
129 }
130 catch ( Throwable e )
131 {
132 StackTraceWriter stackTraceWriter = new LegacyPojoStackTraceWriter( testClassName, methodName, e );
133 reportManager.testFailed( withException( testClassName, testName, stackTraceWriter ) );
134
135
136
137
138
139
140 return true;
141 }
142
143
144 try
145 {
146 method.invoke( testObject, args );
147 reportManager.testSucceeded( new SimpleReportEntry( testClassName, testName ) );
148 }
149 catch ( InvocationTargetException e )
150 {
151 Throwable t = e.getTargetException();
152 StackTraceWriter stackTraceWriter = new LegacyPojoStackTraceWriter( testClassName, methodName, t );
153 reportManager.testFailed( withException( testClassName, testName, stackTraceWriter ) );
154
155
156 }
157 catch ( Throwable t )
158 {
159 StackTraceWriter stackTraceWriter = new LegacyPojoStackTraceWriter( testClassName, methodName, t );
160 reportManager.testFailed( withException( testClassName, testName, stackTraceWriter ) );
161
162
163 }
164
165 try
166 {
167 tearDownFixture();
168 }
169 catch ( Throwable t )
170 {
171 StackTraceWriter stackTraceWriter = new LegacyPojoStackTraceWriter( testClassName, methodName, t );
172
173 reportManager.testFailed( withException( testClassName, testName, stackTraceWriter ) );
174
175
176
177
178
179
180 return true;
181 }
182
183
184
185
186
187
188 return false;
189 }
190
191 private String getTestName( String testMethodName )
192 {
193 if ( testMethodName == null )
194 {
195 throw new NullPointerException( "testMethodName is null" );
196 }
197
198 return getTestClass().getName() + "." + testMethodName;
199 }
200
201 private void setUpFixture()
202 throws Throwable
203 {
204 if ( setUpMethod != null )
205 {
206 setUpMethod.invoke( testObject );
207 }
208 }
209
210 private void tearDownFixture()
211 throws Throwable
212 {
213 if ( tearDownMethod != null )
214 {
215 tearDownMethod.invoke( testObject );
216 }
217 }
218
219 private void discoverTestMethods()
220 {
221 if ( testMethods == null )
222 {
223 testMethods = new ArrayList<Method>();
224
225 Method[] methods = getTestClass().getMethods();
226
227 for ( Method m : methods )
228 {
229 if ( isValidTestMethod( m ) )
230 {
231 String simpleName = m.getName();
232
233
234 if ( simpleName.length() > 4 )
235 {
236 String firstFour = simpleName.substring( 0, 4 );
237
238
239 if ( firstFour.equals( TEST_METHOD_PREFIX ) )
240 {
241 testMethods.add( m );
242 }
243 }
244 }
245 else if ( m.getName().equals( "setUp" ) && m.getParameterTypes().length == 0 )
246 {
247 setUpMethod = m;
248 }
249 else if ( m.getName().equals( "tearDown" ) && m.getParameterTypes().length == 0 )
250 {
251 tearDownMethod = m;
252 }
253 }
254 }
255 }
256
257 private static boolean isValidTestMethod( Method m )
258 {
259 boolean isInstanceMethod = !Modifier.isStatic( m.getModifiers() );
260
261 boolean returnsVoid = m.getReturnType().equals( void.class );
262
263 boolean hasNoParams = m.getParameterTypes().length == 0;
264
265 return isInstanceMethod && returnsVoid && hasNoParams;
266 }
267
268 @Override
269 public String getName()
270 {
271 return getTestClass().getName();
272 }
273
274 private Class<?> getTestClass()
275 {
276 return testClass;
277 }
278 }