View Javadoc

1   /*
2    *  soapUI, copyright (C) 2004-2010 eviware.com 
3    *
4    *  soapUI is free software; you can redistribute it and/or modify it under the 
5    *  terms of version 2.1 of the GNU Lesser General Public License as published by 
6    *  the Free Software Foundation.
7    *
8    *  soapUI is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without 
9    *  even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 
10   *  See the GNU Lesser General Public License for more details at gnu.org.
11   */
12  
13  package com.eviware.soapui.impl.wsdl.testcase;
14  
15  import java.util.Collections;
16  import java.util.LinkedList;
17  import java.util.List;
18  
19  import org.apache.commons.httpclient.HttpState;
20  
21  import com.eviware.soapui.SoapUI;
22  import com.eviware.soapui.impl.wsdl.support.AbstractTestRunner;
23  import com.eviware.soapui.impl.wsdl.teststeps.WsdlTestStep;
24  import com.eviware.soapui.model.iface.SubmitContext;
25  import com.eviware.soapui.model.testsuite.TestCaseRunner;
26  import com.eviware.soapui.model.testsuite.TestRunListener;
27  import com.eviware.soapui.model.testsuite.TestStep;
28  import com.eviware.soapui.model.testsuite.TestStepResult;
29  import com.eviware.soapui.model.testsuite.TestStepResult.TestStepStatus;
30  import com.eviware.soapui.support.types.StringToObjectMap;
31  
32  /***
33   * WSDL TestCase Runner - runs all steps in a testcase and collects performance
34   * data
35   * 
36   * @author Ole.Matzura
37   */
38  
39  public class WsdlTestCaseRunner extends AbstractTestRunner<WsdlTestCase, WsdlTestRunContext> implements TestCaseRunner
40  {
41  	private TestRunListener[] listeners =new TestRunListener[0]; 
42  	private List<TestStepResult> testStepResults = Collections.synchronizedList( new LinkedList<TestStepResult>() );
43  	private int gotoStepIndex;
44  	private int resultCount;
45  	private int initCount;
46  
47  	public WsdlTestCaseRunner( WsdlTestCase testCase, StringToObjectMap properties )
48  	{
49  		super( testCase, properties );
50  	}
51  
52  	public WsdlTestRunContext createContext( StringToObjectMap properties )
53  	{
54  		return new WsdlTestRunContext( this, properties );
55  	}
56  
57  	public void onCancel( String reason )
58  	{
59  		TestStep currentStep = getRunContext().getCurrentStep();
60  		if( currentStep != null )
61  			currentStep.cancel();
62  	}
63  
64  	public void onFail( String reason )
65  	{
66  		TestStep currentStep = getRunContext().getCurrentStep();
67  		if( currentStep != null )
68  			currentStep.cancel();
69  	}
70  
71  	public void internalRun( WsdlTestRunContext runContext ) throws Exception
72  	{
73  		WsdlTestCase testCase = getTestRunnable();
74  		gotoStepIndex = -1;
75  		testStepResults.clear();
76  
77  		// create state for testcase if specified
78  		if( testCase.getKeepSession() )
79  		{
80  			runContext.setProperty( SubmitContext.HTTP_STATE_PROPERTY, new HttpState() );
81  		}
82  
83  		listeners = testCase.getTestRunListeners();
84  		testCase.runSetupScript( runContext, this );
85  		if( !isRunning() )
86  			return;
87  
88  		if( testCase.getTimeout() > 0 )
89  		{
90  			startTimeoutTimer( testCase.getTimeout() );
91  		}
92  
93  		notifyBeforeRun();
94  		if( !isRunning() )
95  			return;
96  
97  		initCount = 0;
98  
99  		setStartTime();
100 		for( ; initCount < testCase.getTestStepCount() && isRunning(); initCount++ )
101 		{
102 			WsdlTestStep testStep = testCase.getTestStepAt( initCount );
103 			if( testStep.isDisabled() )
104 				continue;
105 
106 			try
107 			{
108 				testStep.prepare( this, runContext );
109 			}
110 			catch( Exception e )
111 			{
112 				setStatus( Status.FAILED );
113 				SoapUI.logError( e );
114 				throw new Exception( "Failed to prepare testStep [" + testStep.getName() + "]; " + e.toString() );
115 			}
116 		}
117 
118 		int currentStepIndex = 0;
119 
120 		for( ; isRunning() && currentStepIndex < testCase.getTestStepCount(); currentStepIndex++ )
121 		{
122 			TestStep currentStep = runContext.getCurrentStep();
123 			if( !currentStep.isDisabled() )
124 			{
125 				TestStepResult stepResult = runTestStep( currentStep, true, true );
126 				if( stepResult == null )
127 					return;
128 
129 				if( !isRunning() )
130 					return;
131 
132 				if( gotoStepIndex != -1 )
133 				{
134 					currentStepIndex = gotoStepIndex - 1;
135 					gotoStepIndex = -1;
136 				}
137 			}
138 
139 			runContext.setCurrentStep( currentStepIndex + 1 );
140 		}
141 
142 		if( runContext.getProperty( TestCaseRunner.Status.class.getName() ) == TestCaseRunner.Status.FAILED
143 				&& testCase.getFailTestCaseOnErrors() )
144 		{
145 			fail( "Failing due to failed test step" );
146 		}
147 	}
148 
149 	protected void internalFinally( WsdlTestRunContext runContext )
150 	{
151 		WsdlTestCase testCase = getTestRunnable();
152 		
153 		for( int c = 0; c < initCount && c < testCase.getTestStepCount(); c++ )
154 		{
155 			WsdlTestStep testStep = testCase.getTestStepAt( c );
156 			if( !testStep.isDisabled() )
157 				testStep.finish( this, runContext );
158 		}
159 
160 		try
161 		{
162 			testCase.runTearDownScript( runContext, this );
163 		}
164 		catch( Exception e )
165 		{
166 			SoapUI.logError( e );
167 		}
168 		
169 		notifyAfterRun();
170 
171 		runContext.clear();
172 		listeners = null;
173 	}
174 
175 	public TestStepResult runTestStepByName( String name )
176 	{
177 		return runTestStep( getTestCase().getTestStepByName( name ), true, true );
178 	}
179 
180 	public TestStepResult runTestStep( TestStep testStep )
181 	{
182 		return runTestStep( testStep, true, true );
183 	}
184 
185 	public TestStepResult runTestStep( TestStep testStep, boolean discard, boolean process )
186 	{
187 		for( int i = 0; i < listeners.length; i++ )
188 		{
189 			listeners[i].beforeStep( this, getRunContext(), testStep );
190 			if( !isRunning() )
191 				return null;
192 		}
193 
194 		TestStepResult stepResult = testStep.run( this, getRunContext() );
195 		testStepResults.add( stepResult );
196 		resultCount++ ;
197 		enforceMaxResults( getTestRunnable().getMaxResults() );
198 
199 		for( int i = 0; i < listeners.length; i++ )
200 		{
201 			listeners[i].afterStep( this, getRunContext(), stepResult );
202 		}
203 
204 		// discard?
205 		if( discard && stepResult.getStatus() == TestStepStatus.OK && getTestRunnable().getDiscardOkResults()
206 				&& !stepResult.isDiscarded() )
207 		{
208 			stepResult.discard();
209 		}
210 
211 		if( process && stepResult.getStatus() == TestStepStatus.FAILED )
212 		{
213 			if( getTestRunnable().getFailOnError() )
214 			{
215 				setError( stepResult.getError() );
216 				fail( "Cancelling due to failed test step" );
217 			}
218 			else
219 			{
220 				getRunContext().setProperty( TestCaseRunner.Status.class.getName(), TestCaseRunner.Status.FAILED );
221 			}
222 		}
223 
224 		return stepResult;
225 	}
226 
227 	private void notifyAfterRun()
228 	{
229 		if( listeners == null || listeners.length == 0 )
230 			return;
231 
232 		for( int i = 0; i < listeners.length; i++ )
233 		{
234 			try
235 			{
236 				listeners[i].afterRun( this, getRunContext() );
237 			}
238 			catch( Throwable t )
239 			{
240 				SoapUI.logError( t );
241 			}
242 		}
243 	}
244 
245 	private void notifyBeforeRun()
246 	{
247 		if( listeners == null || listeners.length == 0 )
248 			return;
249 
250 		for( int i = 0; i < listeners.length; i++ )
251 		{
252 			try
253 			{
254 				listeners[i].beforeRun( this, getRunContext() );
255 			}
256 			catch( Throwable t )
257 			{
258 				SoapUI.logError( t );
259 			}
260 		}
261 	}
262 
263 	public WsdlTestCase getTestCase()
264 	{
265 		return getTestRunnable();
266 	}
267 
268 	public long getTimeTaken()
269 	{
270 		long sum = 0;
271 		for( int c = 0; c < testStepResults.size(); c++ )
272 		{
273 			TestStepResult testStepResult = testStepResults.get( c );
274 			if( testStepResult != null )
275 				sum += testStepResult.getTimeTaken();
276 		}
277 
278 		return sum;
279 	}
280 
281 	public List<TestStepResult> getResults()
282 	{
283 		return testStepResults;
284 	}
285 
286 	public int getResultCount()
287 	{
288 		return resultCount;
289 	}
290 
291 	public void gotoStep( int index )
292 	{
293 		gotoStepIndex = index;
294 	}
295 
296 	public void enforceMaxResults( long maxResults )
297 	{
298 		if( maxResults < 1 )
299 			return;
300 
301 			while( testStepResults.size() > maxResults )
302 			{
303 				testStepResults.remove( 0 );
304 			}
305 		}
306 
307 	public void gotoStepByName( String stepName )
308 	{
309 		TestStep testStep = getTestCase().getTestStepByName( stepName );
310 		if( testStep != null )
311 			gotoStep( getTestCase().getIndexOfTestStep( testStep ) );
312 	}
313 }