View Javadoc

1   package com.eviware.soapui.impl.wsdl.teststeps;
2   
3   import com.eviware.soapui.config.RequestStepConfig;
4   import com.eviware.soapui.config.RestRequestStepConfig;
5   import com.eviware.soapui.config.TestStepConfig;
6   import com.eviware.soapui.impl.rest.RestRequest;
7   import com.eviware.soapui.impl.rest.support.XmlBeansRestParamsTestPropertyHolder;
8   import com.eviware.soapui.impl.support.AbstractHttpRequest;
9   import com.eviware.soapui.impl.support.http.HttpRequestTestStep;
10  import com.eviware.soapui.impl.wsdl.AbstractWsdlModelItem;
11  import com.eviware.soapui.impl.wsdl.WsdlSubmit;
12  import com.eviware.soapui.impl.wsdl.submit.transports.http.HttpResponse;
13  import com.eviware.soapui.impl.wsdl.support.assertions.AssertedXPathsContainer;
14  import com.eviware.soapui.impl.wsdl.testcase.WsdlTestCase;
15  import com.eviware.soapui.impl.wsdl.testcase.WsdlTestRunContext;
16  import com.eviware.soapui.impl.wsdl.teststeps.assertions.TestAssertionRegistry.AssertableType;
17  import com.eviware.soapui.model.ModelItem;
18  import com.eviware.soapui.model.iface.Interface;
19  import com.eviware.soapui.model.iface.Request.SubmitException;
20  import com.eviware.soapui.model.iface.Submit;
21  import com.eviware.soapui.model.propertyexpansion.PropertyExpansion;
22  import com.eviware.soapui.model.propertyexpansion.PropertyExpansionContainer;
23  import com.eviware.soapui.model.propertyexpansion.PropertyExpansionUtils;
24  import com.eviware.soapui.model.propertyexpansion.PropertyExpansionsResult;
25  import com.eviware.soapui.model.support.TestPropertyListenerAdapter;
26  import com.eviware.soapui.model.support.TestStepBeanProperty;
27  import com.eviware.soapui.model.testsuite.*;
28  import com.eviware.soapui.model.testsuite.AssertionError;
29  import com.eviware.soapui.model.testsuite.TestStepResult.TestStepStatus;
30  import com.eviware.soapui.support.resolver.ResolveContext;
31  import com.eviware.soapui.support.types.StringToStringMap;
32  import org.apache.log4j.Logger;
33  
34  import javax.swing.*;
35  import javax.xml.namespace.QName;
36  import java.beans.PropertyChangeEvent;
37  import java.beans.PropertyChangeListener;
38  import java.util.Collections;
39  import java.util.List;
40  import java.util.Map;
41  
42  public class HttpTestRequestStep extends WsdlTestStepWithProperties implements PropertyChangeListener,
43          PropertyExpansionContainer, Assertable, HttpRequestTestStep
44  {
45     private final static Logger log = Logger.getLogger( HttpTestRequestStep.class );
46     private RestRequestStepConfig requestStepConfig;
47     private RestTestRequest testRequest;
48     private WsdlSubmit<RestRequest> submit;
49  
50     public HttpTestRequestStep( WsdlTestCase testCase, TestStepConfig config, boolean forLoadTest )
51     {
52        super( testCase, config, true, forLoadTest );
53  
54        if( getConfig().getConfig() != null )
55        {
56           requestStepConfig = (RestRequestStepConfig) getConfig().getConfig().changeType( RestRequestStepConfig.type );
57  
58           testRequest = new RestTestRequest( null, requestStepConfig.getRestRequest(), this, forLoadTest );
59           testRequest.addPropertyChangeListener( this );
60           testRequest.addTestPropertyListener( new InternalTestPropertyListener() );
61  
62           if( config.isSetName() )
63              testRequest.setName( config.getName() );
64           else
65              config.setName( testRequest.getName() );
66  
67           if( testRequest.getPath() != null )
68              testRequest.setEndpoint( testRequest.getPath() );
69        }
70        else
71        {
72           requestStepConfig = (RestRequestStepConfig) getConfig().addNewConfig().changeType( RestRequestStepConfig.type );
73        }
74  
75        for( TestProperty property : testRequest.getProperties().values() )
76        {
77           addProperty( new RestTestStepProperty( (XmlBeansRestParamsTestPropertyHolder.RestParamProperty) property ) );
78        }
79  
80        // init default properties
81        addProperty( new TestStepBeanProperty( "Endpoint", false, testRequest, "endpoint", this ) );
82        addProperty( new TestStepBeanProperty( "Username", false, testRequest, "username", this ) );
83        addProperty( new TestStepBeanProperty( "Password", false, testRequest, "password", this ) );
84        addProperty( new TestStepBeanProperty( "Domain", false, testRequest, "domain", this ) );
85  
86        // init properties
87        addProperty( new TestStepBeanProperty( "Request", false, testRequest, "requestContent", this )
88        {
89           @Override
90           public String getDefaultValue()
91           {
92              return createDefaultRequestContent();
93           }
94        } );
95  
96        addProperty( new TestStepBeanProperty( "ResponseAsXml", true, testRequest, "responseContentAsXml", this )
97        {
98           @Override
99           public String getDefaultValue()
100          {
101             return createDefaultResponseXmlContent();
102          }
103       } );
104 
105       addProperty( new TestStepBeanProperty( "Response", true, testRequest, "responseContentAsString", this )
106       {
107          @Override
108          public String getDefaultValue()
109          {
110             return createDefaultRawResponseContent();
111          }
112       } );
113    }
114 
115    protected String createDefaultRawResponseContent()
116    {
117       return "";
118    }
119 
120    protected String createDefaultResponseXmlContent()
121    {
122       return "";
123    }
124 
125    protected String createDefaultRequestContent()
126    {
127       return "";
128    }
129 
130    public RestRequestStepConfig getRequestStepConfig()
131    {
132       return requestStepConfig;
133    }
134 
135    @Override
136    public WsdlTestStep clone( WsdlTestCase targetTestCase, String name )
137    {
138       beforeSave();
139 
140       TestStepConfig config = (TestStepConfig) getConfig().copy();
141       RequestStepConfig stepConfig = (RequestStepConfig) config.getConfig().changeType( RequestStepConfig.type );
142 
143       while( stepConfig.getRequest().sizeOfAttachmentArray() > 0 )
144          stepConfig.getRequest().removeAttachment( 0 );
145 
146       config.setName( name );
147       stepConfig.getRequest().setName( name );
148 
149       WsdlTestRequestStep result = (WsdlTestRequestStep) targetTestCase.addTestStep( config );
150       testRequest.copyAttachmentsTo( result.getTestRequest() );
151 
152       return result;
153    }
154 
155    @Override
156    public void release()
157    {
158       super.release();
159 
160       // could be null if initialization failed..
161       if( testRequest != null )
162       {
163          testRequest.removePropertyChangeListener( this );
164          testRequest.release();
165       }
166    }
167 
168    @Override
169    public void resetConfigOnMove( TestStepConfig config )
170    {
171       super.resetConfigOnMove( config );
172 
173       requestStepConfig = (RestRequestStepConfig) config.getConfig().changeType( RestRequestStepConfig.type );
174       testRequest.updateConfig( requestStepConfig.getRestRequest() );
175    }
176 
177    @Override
178    public ImageIcon getIcon()
179    {
180       return testRequest == null ? null : testRequest.getIcon();
181    }
182 
183    public RestTestRequest getTestRequest()
184    {
185       return testRequest;
186    }
187 
188    @Override
189    public void setName( String name )
190    {
191       super.setName( name );
192       testRequest.setName( name );
193    }
194 
195    public void propertyChange( PropertyChangeEvent arg0 )
196    {
197       if( arg0.getPropertyName().equals( TestAssertion.CONFIGURATION_PROPERTY ) ||
198               arg0.getPropertyName().equals( TestAssertion.DISABLED_PROPERTY ) )
199       {
200          if( getTestRequest().getResponse() != null )
201          {
202             getTestRequest().assertResponse( new WsdlTestRunContext( this ) );
203          }
204       }
205       else
206       {
207          if( arg0.getSource() == testRequest && arg0.getPropertyName().equals( WsdlTestRequest.NAME_PROPERTY ) )
208          {
209             if( !super.getName().equals( (String) arg0.getNewValue() ) )
210                super.setName( (String) arg0.getNewValue() );
211          }
212 
213          notifyPropertyChanged( arg0.getPropertyName(), arg0.getOldValue(), arg0.getNewValue() );
214       }
215    }
216 
217    public TestStepResult run( TestRunner runner, TestRunContext runContext )
218    {
219       RestRequestStepResult testStepResult = new RestRequestStepResult( this );
220 
221       try
222       {
223          submit = testRequest.submit( runContext, false );
224          HttpResponse response = (HttpResponse) submit.getResponse();
225 
226          if( submit.getStatus() != Submit.Status.CANCELED )
227          {
228             if( submit.getStatus() == Submit.Status.ERROR )
229             {
230                testStepResult.setStatus( TestStepStatus.FAILED );
231                testStepResult.addMessage( submit.getError().toString() );
232 
233                testRequest.setResponse( null, runContext );
234             }
235             else if( response == null )
236             {
237                testStepResult.setStatus( TestStepStatus.FAILED );
238                testStepResult.addMessage( "Request is missing response" );
239 
240                testRequest.setResponse( null, runContext );
241             }
242             else
243             {
244                runContext.setProperty( AssertedXPathsContainer.ASSERTEDXPATHSCONTAINER_PROPERTY, testStepResult );
245                testRequest.setResponse( response, runContext );
246 
247                testStepResult.setTimeTaken( response.getTimeTaken() );
248                testStepResult.setSize( response.getContentLength() );
249                testStepResult.setResponse( response );
250 
251                switch( testRequest.getAssertionStatus() )
252                {
253                   case FAILED:
254                      testStepResult.setStatus( TestStepStatus.FAILED );
255                      break;
256                   case VALID:
257                      testStepResult.setStatus( TestStepStatus.OK );
258                      break;
259                   case UNKNOWN:
260                      testStepResult.setStatus( TestStepStatus.UNKNOWN );
261                      break;
262                }
263             }
264          }
265          else
266          {
267             testStepResult.setStatus( TestStepStatus.CANCELED );
268             testStepResult.addMessage( "Request was canceled" );
269          }
270 
271          if( response != null )
272          {
273             testStepResult.setRequestContent( response.getRequestContent() );
274             testStepResult.addProperty( "URL", response.getURL() == null ? "<missing>" : response.getURL().toString() );
275             testStepResult.addProperty( "Method", String.valueOf( response.getMethod() ) );
276             testStepResult.addProperty( "StatusCode", String.valueOf( response.getStatusCode() ) );
277             testStepResult.addProperty( "HTTP Version", response.getHttpVersion() );
278          }
279          else
280             testStepResult.setRequestContent( testRequest.getRequestContent() );
281       }
282       catch( SubmitException e )
283       {
284          testStepResult.setStatus( TestStepStatus.FAILED );
285          testStepResult.addMessage( "SubmitException: " + e );
286       }
287       finally
288       {
289          submit = null;
290       }
291 
292       testStepResult.setDomain( PropertyExpansionUtils.expandProperties( runContext, testRequest.getDomain() ) );
293       testStepResult.setUsername( PropertyExpansionUtils.expandProperties( runContext, testRequest.getUsername() ) );
294       testStepResult.setEndpoint( PropertyExpansionUtils.expandProperties( runContext, testRequest.getEndpoint() ) );
295       testStepResult.setPassword( PropertyExpansionUtils.expandProperties( runContext, testRequest.getPassword() ) );
296       testStepResult.setEncoding( PropertyExpansionUtils.expandProperties( runContext, testRequest.getEncoding() ) );
297 
298       if( testStepResult.getStatus() != TestStepStatus.CANCELED )
299       {
300          AssertionStatus assertionStatus = testRequest.getAssertionStatus();
301          switch( assertionStatus )
302          {
303             case FAILED:
304             {
305                testStepResult.setStatus( TestStepStatus.FAILED );
306                if( getAssertionCount() == 0 )
307                {
308                   testStepResult.addMessage( "Invalid/empty response" );
309                }
310                else for( int c = 0; c < getAssertionCount(); c++ )
311                {
312                   AssertionError[] errors = getAssertionAt( c ).getErrors();
313                   if( errors != null )
314                   {
315                      for( AssertionError error : errors )
316                      {
317                         testStepResult.addMessage( error.getMessage() );
318                      }
319                   }
320                }
321 
322                break;
323             }
324          }
325       }
326 
327       return testStepResult;
328    }
329 
330    public WsdlMessageAssertion getAssertionAt( int index )
331    {
332       return testRequest.getAssertionAt( index );
333    }
334 
335    public int getAssertionCount()
336    {
337       return testRequest == null ? 0 : testRequest.getAssertionCount();
338    }
339 
340    @Override
341    public boolean cancel()
342    {
343       if( submit == null )
344          return false;
345 
346       submit.cancel();
347 
348       return true;
349    }
350 
351    @Override
352    public boolean dependsOn( AbstractWsdlModelItem<?> modelItem )
353    {
354       return false;
355    }
356 
357    @Override
358    public void beforeSave()
359    {
360       super.beforeSave();
361 
362       if( testRequest != null )
363          testRequest.beforeSave();
364    }
365 
366    @Override
367    public String getDescription()
368    {
369       return testRequest == null ? "<missing>" : testRequest.getDescription();
370    }
371 
372    @Override
373    public void setDescription( String description )
374    {
375       if( testRequest != null )
376          testRequest.setDescription( description );
377    }
378 
379    @Override
380    public List<? extends ModelItem> getChildren()
381    {
382       return testRequest == null ? Collections.EMPTY_LIST : testRequest.getAssertionList();
383    }
384 
385    public PropertyExpansion[] getPropertyExpansions()
386    {
387       PropertyExpansionsResult result = new PropertyExpansionsResult( this, testRequest );
388 
389       result.extractAndAddAll( "requestContent" );
390       result.extractAndAddAll( "endpoint" );
391       result.extractAndAddAll( "username" );
392       result.extractAndAddAll( "password" );
393       result.extractAndAddAll( "domain" );
394 
395       StringToStringMap requestHeaders = testRequest.getRequestHeaders();
396       for( String key : requestHeaders.keySet() )
397       {
398          result.extractAndAddAll( new RequestHeaderHolder( requestHeaders, key ), "value" );
399       }
400 
401 //		result.addAll( testRequest.getWssContainer().getPropertyExpansions() );
402 
403       return result.toArray( new PropertyExpansion[result.size()] );
404    }
405 
406    public AbstractHttpRequest getHttpRequest()
407    {
408       return testRequest;
409    }
410 
411    public class RequestHeaderHolder
412    {
413       private final StringToStringMap valueMap;
414       private final String key;
415 
416       public RequestHeaderHolder( StringToStringMap valueMap, String key )
417       {
418          this.valueMap = valueMap;
419          this.key = key;
420       }
421 
422       public String getValue()
423       {
424          return valueMap.get( key );
425       }
426 
427       public void setValue( String value )
428       {
429          valueMap.put( key, value );
430          testRequest.setRequestHeaders( valueMap );
431       }
432    }
433 
434    public TestAssertion addAssertion( String type )
435    {
436       WsdlMessageAssertion result = testRequest.addAssertion( type );
437       return result;
438    }
439 
440    public void addAssertionsListener( AssertionsListener listener )
441    {
442       testRequest.addAssertionsListener( listener );
443    }
444 
445    public TestAssertion cloneAssertion( TestAssertion source, String name )
446    {
447       return testRequest.cloneAssertion( source, name );
448    }
449 
450    public String getAssertableContent()
451    {
452       return testRequest.getAssertableContent();
453    }
454 
455    public AssertableType getAssertableType()
456    {
457       return testRequest.getAssertableType();
458    }
459 
460    public TestAssertion getAssertionByName( String name )
461    {
462       return testRequest.getAssertionByName( name );
463    }
464 
465    public List<TestAssertion> getAssertionList()
466    {
467       return testRequest.getAssertionList();
468    }
469 
470    public AssertionStatus getAssertionStatus()
471    {
472       return testRequest.getAssertionStatus();
473    }
474 
475    public Interface getInterface()
476    {
477       return null;
478    }
479 
480    public TestStep getTestStep()
481    {
482       return this;
483    }
484 
485    public void removeAssertion( TestAssertion assertion )
486    {
487       testRequest.removeAssertion( assertion );
488    }
489 
490    public void removeAssertionsListener( AssertionsListener listener )
491    {
492       testRequest.removeAssertionsListener( listener );
493    }
494 
495    public Map<String, TestAssertion> getAssertions()
496    {
497       return testRequest.getAssertions();
498    }
499 
500    @Override
501    public void prepare( TestRunner testRunner, TestRunContext testRunContext ) throws Exception
502    {
503       super.prepare( testRunner, testRunContext );
504 
505       for( TestAssertion assertion : testRequest.getAssertionList() )
506       {
507          assertion.prepare( testRunner, testRunContext );
508       }
509    }
510 
511    public String getDefaultSourcePropertyName()
512    {
513       return "ResponseAsXml";
514    }
515 
516    public String getDefaultTargetPropertyName()
517    {
518       return "Request";
519    }
520 
521    public String getDefaultAssertableContent()
522    {
523       return testRequest.getDefaultAssertableContent();
524    }
525 
526    public void resolve( ResolveContext context )
527    {
528       super.resolve( context );
529 
530       testRequest.resolve( context );
531    }
532 
533    private class InternalTestPropertyListener extends TestPropertyListenerAdapter
534    {
535       @Override
536       public void propertyAdded( String name )
537       {
538          addProperty( new RestTestStepProperty( getTestRequest().getProperty( name ) ), true );
539       }
540 
541       @Override
542       public void propertyRemoved( String name )
543       {
544          HttpTestRequestStep.this.deleteProperty( name, true );
545       }
546 
547       @Override
548       public void propertyRenamed( String oldName, String newName )
549       {
550          HttpTestRequestStep.this.propertyRenamed( oldName );
551       }
552 
553       @Override
554       public void propertyValueChanged( String name, String oldValue, String newValue )
555       {
556          HttpTestRequestStep.this.firePropertyValueChanged( name, oldValue, newValue );
557       }
558 
559       @Override
560       public void propertyMoved( String name, int oldIndex, int newIndex )
561       {
562          HttpTestRequestStep.this.firePropertyMoved( name, oldIndex, newIndex );
563       }
564    }
565 
566    private class RestTestStepProperty implements TestStepProperty
567    {
568       private XmlBeansRestParamsTestPropertyHolder.RestParamProperty property;
569 
570       public RestTestStepProperty( XmlBeansRestParamsTestPropertyHolder.RestParamProperty property )
571       {
572          this.property = property;
573       }
574 
575       public TestStep getTestStep()
576       {
577          return HttpTestRequestStep.this;
578       }
579 
580       public String getName()
581       {
582          return property.getName();
583       }
584 
585       public String getDescription()
586       {
587          return property.getDescription();
588       }
589 
590       public String getValue()
591       {
592          return property.getValue();
593       }
594 
595       public String getDefaultValue()
596       {
597          return property.getDefaultValue();
598       }
599 
600       public void setValue( String value )
601       {
602          property.setValue( value );
603       }
604 
605       public boolean isReadOnly()
606       {
607          return false;
608       }
609 
610       public QName getType()
611       {
612          return property.getType();
613       }
614 
615       public ModelItem getModelItem()
616       {
617          return getTestRequest();
618       }
619    }
620 }