View Javadoc

    1   /*
    2    *  soapUI, copyright (C) 2004-2007 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.endpoint;
    14
    15  import java.beans.PropertyChangeEvent;
    16  import java.beans.PropertyChangeListener;
    17  import java.util.Arrays;
    18  import java.util.HashMap;
    19  import java.util.HashSet;
    20  import java.util.Map;
    21  import java.util.Set;
    22
    23  import org.apache.commons.httpclient.URI;
    24  import org.apache.commons.httpclient.URIException;
    25
    26  import com.eviware.soapui.SoapUI;
    27  import com.eviware.soapui.config.DefaultEndpointStrategyConfig;
    28  import com.eviware.soapui.config.EndpointConfig;
    29  import com.eviware.soapui.config.ProjectConfig;
    30  import com.eviware.soapui.impl.wsdl.WsdlInterface;
    31  import com.eviware.soapui.impl.wsdl.WsdlProject;
    32  import com.eviware.soapui.impl.wsdl.WsdlRequest;
    33  import com.eviware.soapui.impl.wsdl.submit.filters.HttpAuthenticationRequestFilter;
    34  import com.eviware.soapui.impl.wsdl.submit.filters.PropertyExpansionRequestFilter;
    35  import com.eviware.soapui.impl.wsdl.submit.filters.WsSecurityAuthenticationRequestFilter;
    36  import com.eviware.soapui.impl.wsdl.submit.transports.http.BaseHttpRequestTransport;
    37  import com.eviware.soapui.impl.wsdl.submit.transports.http.TimeablePostMethod;
    38  import com.eviware.soapui.model.iface.Interface;
    39  import com.eviware.soapui.model.iface.SubmitContext;
    40  import com.eviware.soapui.model.project.EndpointStrategy;
    41  import com.eviware.soapui.model.project.Project;
    42  import com.eviware.soapui.model.project.ProjectListener;
    43  import com.eviware.soapui.model.support.ProjectListenerAdapter;
    44  import com.eviware.soapui.support.StringUtils;
    45  import com.eviware.soapui.support.types.StringList;
    46
    47  public class DefaultEndpointStrategy implements EndpointStrategy
    48  {
    49  	private WsdlProject project;
    50  	private DefaultEndpointStrategyConfig config;
    51  	private Map<String,EndpointDefaults> defaults = new HashMap<String,EndpointDefaults>();
    52  	private PropertyChangeListener propertyChangeListener = new InternalPropertyChangeListener();
    53  	private ProjectListener projectListener = new InternalProjectListener() ;
    54
    55  	public void configure( Interface iface )
    56  	{
    57  		SoapUI.getActionRegistry().getAction( DefaultEndpointStrategyConfigureAction.SOAPUI_ACTION_ID ).perform( iface, this );
    58  	}
    59
    60  	public void init( Project project )
    61  	{
    62  		this.project = ( WsdlProject ) project;
    63  		initConfig();
    64
    65  		project.addProjectListener( projectListener  );
    66
    67  		for( Interface iface : project.getInterfaces() )
    68  		{
    69  			for( String endpoint : iface.getEndpoints() )
    70  			{
    71  				// ensure we have defaults
    72  				getEndpointDefaults( endpoint );
    73  			}
    74
    75  			iface.addPropertyChangeListener( WsdlInterface.ENDPOINT_PROPERTY, propertyChangeListener );
    76  		}
    77
    78  		removeUnusedEndpoints();
    79  	}
    80
    81  	private void initConfig()
    82  	{
    83  		ProjectConfig projectConfig = this.project.getConfig();
    84
    85  		if( !projectConfig.isSetEndpointStrategy() )
    86  		{
    87  			projectConfig.addNewEndpointStrategy();
    88  		}
    89
    90  		config = ( DefaultEndpointStrategyConfig ) projectConfig.getEndpointStrategy().changeType( DefaultEndpointStrategyConfig.type  );
    91
    92  		for( EndpointConfig endpointConfig : config.getEndpointList())
    93  		{
    94  			defaults.put( endpointConfig.getStringValue(), new EndpointDefaults( endpointConfig ) );
    95  		}
    96  	}
    97
    98  	private void removeUnusedEndpoints()
    99  	{
    100 		if( config == null )
    101 			return;
    102
    103 		Set<String> endpoints = new HashSet<String>();
    104
    105 		for( Interface iface : project.getInterfaces() )
    106 		{
    107 			endpoints.addAll( Arrays.asList( iface.getEndpoints() ));
    108 		}
    109
    110 		StringList keys = new StringList();
    111
    112 		for( String key : defaults.keySet() )
    113 		{
    114 			if( !endpoints.contains( key ))
    115 			{
    116 				keys.add(  key );
    117 			}
    118 		}
    119
    120 		for( String key : keys )
    121 		{
    122 			EndpointDefaults def = defaults.remove( key );
    123 			config.getEndpointList().remove( def );
    124 		}
    125 	}
    126
    127 	public void filterRequest( SubmitContext context, WsdlRequest wsdlRequest )
    128 	{
    129 		TimeablePostMethod postMethod = (TimeablePostMethod) context.getProperty( BaseHttpRequestTransport.POST_METHOD );
    130 		URI uri = null;
    131 		try
    132 		{
    133 			uri = postMethod.getURI();
    134 		}
    135 		catch( URIException e )
    136 		{
    137 			SoapUI.logError( e );
    138 			return;
    139 		}
    140
    141 		if( !defaults.containsKey( uri.toString() ))
    142 		{
    143 			return;
    144 		}
    145
    146 		EndpointDefaults def = defaults.get( uri.toString() );
    147 		applyDefaultsToRequest( context, wsdlRequest, def );
    148 	}
    149
    150 	protected void applyDefaultsToRequest( SubmitContext context, WsdlRequest wsdlRequest, EndpointDefaults def )
    151 	{
    152 		String requestUsername = PropertyExpansionRequestFilter.expandProperties( context, wsdlRequest.getUsername());
    153 		String requestPassword = PropertyExpansionRequestFilter.expandProperties( context, wsdlRequest.getPassword());
    154 		String requestDomain = PropertyExpansionRequestFilter.expandProperties( context, wsdlRequest.getDomain());
    155
    156 		String defUsername = PropertyExpansionRequestFilter.expandProperties( context, def.getUsername());
    157 		String defPassword = PropertyExpansionRequestFilter.expandProperties( context, def.getPassword());
    158 		String defDomain = PropertyExpansionRequestFilter.expandProperties( context, def.getDomain());
    159
    160 		if( (StringUtils.hasContent( defUsername ) && StringUtils.isNullOrEmpty( requestUsername )) ||
    161 			 (StringUtils.hasContent( defPassword ) && StringUtils.isNullOrEmpty( requestPassword )) ||
    162 			 (StringUtils.hasContent( defDomain ) && StringUtils.isNullOrEmpty( requestDomain )) )
    163 		{
    164 			String username = StringUtils.hasContent( requestUsername ) ? requestUsername : defUsername;
    165 			String password = StringUtils.hasContent( requestPassword ) ? requestPassword : defPassword;
    166 			String domain = StringUtils.hasContent( requestDomain ) ? requestDomain : defDomain;
    167
    168 			HttpAuthenticationRequestFilter.initRequestCredentials(
    169 						context, username, project.getSettings(), password, domain );
    170 		}
    171
    172 		// only set if not set in request
    173 		String wssType = StringUtils.isNullOrEmpty( wsdlRequest.getWssPasswordType() ) ? def.getWssType() :
    174 					(StringUtils.hasContent( requestUsername ) && StringUtils.hasContent( requestPassword )) ? null :
    175 						wsdlRequest.getWssPasswordType();
    176
    177 		String wssTimeToLive = StringUtils.isNullOrEmpty( wsdlRequest.getWssTimeToLive() ) ? def.getWssTimeToLive() : null;
    178
    179 		if( StringUtils.hasContent( wssType ) || StringUtils.hasContent( wssTimeToLive ))
    180 		{
    181 			try
    182 			{
    183 				String username = StringUtils.hasContent( requestUsername ) ? requestUsername : defUsername;
    184 				String password = StringUtils.hasContent( requestPassword ) ? requestPassword : defPassword;
    185
    186 				if( StringUtils.hasContent( username ) || StringUtils.hasContent( password ))
    187 					WsSecurityAuthenticationRequestFilter.addWssHeaders( context, username, password, wssType, wssTimeToLive  );
    188 			}
    189 			catch( Exception e )
    190 			{
    191 				SoapUI.logError( e );
    192 			}
    193 		}
    194 	}
    195
    196 	public void release()
    197 	{
    198 		project.removeProjectListener( projectListener );
    199 		for( Interface iface : project.getInterfaces() )
    200 			iface.removePropertyChangeListener( WsdlInterface.ENDPOINT_PROPERTY, propertyChangeListener );
    201 	}
    202
    203 	private class InternalProjectListener extends ProjectListenerAdapter
    204 	{
    205 		@Override
    206 		public void interfaceAdded( Interface iface )
    207 		{
    208 			for( String endpoint : iface.getEndpoints() )
    209 			{
    210 				// ensure we have defaults
    211 				getEndpointDefaults( endpoint );
    212 			}
    213
    214 			iface.addPropertyChangeListener( WsdlInterface.ENDPOINT_PROPERTY, propertyChangeListener );
    215 		}
    216
    217 		@Override
    218 		public void interfaceRemoved( Interface iface )
    219 		{
    220 			iface.removePropertyChangeListener( WsdlInterface.ENDPOINT_PROPERTY, propertyChangeListener );
    221 			removeUnusedEndpoints();
    222 		}
    223 	}
    224
    225 	private class InternalPropertyChangeListener implements PropertyChangeListener
    226 	{
    227 		public void propertyChange( PropertyChangeEvent evt )
    228 		{
    229 			// new endpoint?
    230 			if( evt.getOldValue() == null )
    231 			{
    232 				getEndpointDefaults( evt.getNewValue().toString() );
    233 			}
    234 			// changed endpoint?
    235 			else if( evt.getNewValue() != null )
    236 			{
    237 				String oldValue = evt.getOldValue().toString();
    238 				EndpointDefaults def = getEndpointDefaults( oldValue );
    239 				def.endpointConfig.setStringValue( evt.getNewValue().toString() );
    240 				defaults.remove( oldValue );
    241 				defaults.put( evt.getNewValue().toString(), def );
    242 			}
    243 			else
    244 			{
    245 				removeUnusedEndpoints();
    246 			}
    247 		}
    248 	}
    249
    250 	public class EndpointDefaults
    251 	{
    252 		private final EndpointConfig endpointConfig;
    253
    254 		public EndpointDefaults( EndpointConfig endpointConfig )
    255 		{
    256 			this.endpointConfig = endpointConfig;
    257 		}
    258
    259 		public String getDomain()
    260 		{
    261 			return endpointConfig.getDomain();
    262 		}
    263
    264 		public String getPassword()
    265 		{
    266 			return endpointConfig.getPassword();
    267 		}
    268
    269 		public String getUsername()
    270 		{
    271 			return endpointConfig.getUsername();
    272 		}
    273
    274 		public String getWssTimeToLive()
    275 		{
    276 			return endpointConfig.getWssTimeToLive();
    277 		}
    278
    279 		public String getWssType()
    280 		{
    281 			return endpointConfig.getWssType();
    282 		}
    283
    284 		public void setDomain( String arg0 )
    285 		{
    286 			endpointConfig.setDomain( arg0 );
    287 		}
    288
    289 		public void setPassword( String arg0 )
    290 		{
    291 			endpointConfig.setPassword( arg0 );
    292 		}
    293
    294 		public void setUsername( String arg0 )
    295 		{
    296 			endpointConfig.setUsername( arg0 );
    297 		}
    298
    299 		public void setWssTimeToLive( String arg0 )
    300 		{
    301 			endpointConfig.setWssTimeToLive( arg0 );
    302 		}
    303
    304 		public void setWssType( String arg0 )
    305 		{
    306 			endpointConfig.setWssType( arg0 );
    307 		}
    308
    309 		protected EndpointConfig getConfig()
    310 		{
    311 			return endpointConfig;
    312 		}
    313 	}
    314
    315 	public EndpointDefaults getEndpointDefaults( String endpoint )
    316 	{
    317 		if( config == null )
    318 			initConfig();
    319
    320 		if( !defaults.containsKey( endpoint ))
    321 		{
    322 			EndpointConfig newEndpoint = config.addNewEndpoint();
    323 			newEndpoint.setStringValue( endpoint );
    324 			defaults.put( endpoint, new EndpointDefaults( newEndpoint ));
    325 		}
    326
    327 		return defaults.get( endpoint );
    328 	}
    329
    330 	public void onSave()
    331 	{
    332 		if( config == null )
    333 			return;
    334
    335 		removeUnusedEndpoints();
    336
    337 		// remove unused
    338 		for( int c = 0; c < config.sizeOfEndpointArray(); c++ )
    339 		{
    340 			EndpointConfig ec = config.getEndpointArray( c );
    341 			if( StringUtils.isNullOrEmpty( ec.getDomain() ) && StringUtils.isNullOrEmpty( ec.getUsername() ) &&
    342 						StringUtils.isNullOrEmpty( ec.getPassword() ) && StringUtils.isNullOrEmpty( ec.getWssType() ) &&
    343 						StringUtils.isNullOrEmpty( ec.getWssTimeToLive() ))
    344 			{
    345 				defaults.remove( ec.getStringValue() );
    346 				config.removeEndpoint( c );
    347 				c--;
    348 			}
    349 		}
    350
    351 		if( config.sizeOfEndpointArray() == 0 )
    352 		{
    353 			project.getConfig().unsetEndpointStrategy();
    354 			config = null;
    355 		}
    356 	}
    357
    358 	public void importEndpoints( Interface iface )
    359 	{
    360 		EndpointStrategy ep = iface.getProject().getEndpointStrategy();
    361 		if( ep instanceof DefaultEndpointStrategy )
    362 		{
    363 			DefaultEndpointStrategy dep = ( DefaultEndpointStrategy ) ep;
    364 			String[] endpoints = iface.getEndpoints();
    365
    366 			for( String endpoint : endpoints )
    367 			{
    368 				getEndpointDefaults( endpoint ).getConfig().set( dep.getEndpointDefaults( endpoint ).getConfig() );
    369 			}
    370 		}
    371 	}
    372 }