persistent or non persistent connection in testing web service - web-services

I have a webservice. I am creating a test application to get response from this webservice. Added service reference to the web service application.
Logic in my test appplication is below.
for(int i=0;i<100;i++)
{
MyServiceSoapClient wsClient = new MyServiceSoapClient();
wsClient.Endpoint.Address = new EndpointAddress(serverAddress);
MyLoginResponse loginResp=wsClient.Login("X","X");
}
Just wanted to know whether I am making a persistent connection or a non persistent connection in this approach. Any help?

Test your webservice using curl. Pass curl the -v (verbose) flag. If you see Connection: close in the response header, your web service does not support persistent connections.

Related

WSO2 ESB Unit Testing

We've developed a Proxy Service into WSO2 ESB which is an orchestrator, and calls multiple services aggregating the response.
How can I test each single step (or mediator) of the proxy flow, and how the system reacts to each possible situation (e.g. Success, Failure, Slow response time...)?
We are trying to mock the behaviour of each service called by the proxy (with Wiremock), for each step, but we are not able to dynamically change the endpoints (or the ports) pointed by each call.
Example:
Real service is listening on port 8280
Wiremock is listening on port 8281
We need to dynamically change the endpoint within the Proxy, to let it call the Wiremock service (8281) instead of the real one (8280)
If there are other ways to test, I'm happy to explore different solutions...
I am unable to get your question correctly... can't you in Your proxy service you mention the endpoint url with port as 8281...??
Finally found the solution to the problem.
Using the endpoints of the registry, you are able to get the resources from the registry, change them and update it.
For example you could do something like:
AutomationContext esbContext = new AutomationContext("ESB", TestUserMode.SUPER_TENANT_ADMIN);
String esbSession = esbContext.login();
ResourceAdminServiceClient resourceClient = new ResourceAdminServiceClient(esbContext.getContextUrls().getBackEndUrl(),
esbSession);
String endpoint = resourceClient.getTextContent("/_system/governance/endpoints/HelloService.xml")
.replace(":8280", String.format(":%s", port));
resourceClient.updateTextContent("/_system/governance/endpoints/HelloService.xml", endpoint);

Azure web service as a client to an external service, using a client-side certificate

I need to write a web service and host it in Azure. This service in turn consumes another service from an external site. Therefore, my azure-hosted service is a client to this externally-hosted service. When I make a request of the other service, I need to include a client-side certificate in my request.
Has anybody successfully done this? Is it possible to install a certificate in a web instance in azure? Would it survive the instance restarting? If so, pointers would be appreciated.
I have never worked with client-side certificates (even on a "real" client) so please forgive me if this is a newbee question.
The certificates that are uploaded in the cloud service (see the certificates tab under that cloud service in azure portal), which will host your webrole, will be available in the VM of that webrole. So you can access it from the certificate store and use it while making the external web service call.
A sample is given in this stackoverflow post.
Accessing a web service and a HTTP interface using certificate authentication
You can either add certificate via azure management portal, and azure will add it to machine certificate store once it deploy your application on the VM, or you can keep it with your application, for example as embedded resource and load it manually and use with your webservice call. Like this :
private X509Certificate2 GetAuthCertificate()
{
var assembly = Assembly.GetExecutingAssembly();
Stream stream = null;
var resources = assembly.GetManifestResourceNames();
foreach (var resource in resources)
{
if (resource.EndsWith(certificateFilename))
{
stream = assembly.GetManifestResourceStream(resource);
break;
}
}
if (stream == null)
throw new Exception("Certificate not found in embedded rersources");
using (var ms = new MemoryStream())
{
stream.CopyTo(ms);
var result = new X509Certificate2(ms.ToArray(), "password", X509KeyStorageFlags.Exportable);
return result;
}
}

Jetty 9.0 embeded config with SPDY but without SSL/NPN

SSL/NPN will be handled via our loadbalancer (Haproxy), so I don't really need Jetty to do this for us.
But all the examples I can see on the web only show how to do this with SSL/NPN, not without.
Here's what I've attempted so far:
Server server = new Server();
HTTPConfiguration httpConfig = .... // set up some additional http config here
PushStrategey push = new ReferrerPushStrategy();
List<ConnectionFactory> factories = new ArrayList<>();
factories.add(new HTTPSPDYServerConnectionFactory(SPDY.V3, httpConfig, push));
factories.add(new HTTPSPDYServerConnectionFactory(SPDY.V2, httpConfig, push));
factories.add(new HTTPConnectionFactory(httpConfig));
ServerConnector connector = new ServerConnector(server, factories.toArray(new ConnectionFactory[factories.size()]));
connector.setPort(port);
server.addConnector(connector);
connector.start();
....
Unfortunately, it seems something is wrong, when I try to access the server via clients like curl or my browser they hang indefinitely. What am I doing wrong?
Thanks
When you configure a ServerConnector to speak clear-text SPDY, your clients must also speak clear-text SPDY.
If you use clients like curl or the browser, they don't speak clear-text SPDY. The clients will send a HTTP request which is not understood (the server expects SPDY), and that's why your connection "hangs".
Only Chromium/Chrome has a mode where you can make it speak clear-text SPDY, using the --use-spdy=no-ssl parameter as described here.
Therefore, if you're using clear-text SPDY there is no point in configuring multiple ServerConnectionFactory because there is no way to select one based on the protocol being negotiated, because there is no protocol negotiation.
The protocol negotiation only happens when using SSL+NPN.
Your code is basically correct (apart the unnecessary multiple ServerConnectionFactory) if you really want to setup a clear-text SPDY ServerConnector; this is an example of how the same is setup in the Jetty SPDY test suite.
Finally, see also the reference documentation about SPDY.

Axis2 multiple connection authentication issue

I have two servlets that access two corresponding Axis2 web services on the same host. One of the servlets is read-only, while the other writes to a database.
Each of the Axis2 web services uses BASIC authentication. The read-only web service uses a system account, while the write web service uses the user's credentials (which are submitted as part of a web form).
The problem I'm running into is that the servlet called second always fails authentication to its web service. For example, I can query the read-only service through it's servlet all I want, but I get a "401: Authorization Required" when I try to use the write service. If I call the write service first, I get the same error when I try to use the read-only service.
Here is how I am setting the credentials for the connections in the servlets:
Stub service = new Stub(serviceUrl);
HttpTransportProperties.Authenticator auth = new HttpTransportProperties.Authenticator();
auth.setUsername(username);
auth.setPassword(password);
auth.setPreemptiveAuthentication(true);
service._getServiceClient().getOptions().setProperty(HTTPConstants.AUTHENTICATE, auth);
The servlet that accesses the read-only service has this code in it's constructor. The servlet that accesses the write service has this code in it's doGet/doPost method.
It seems that the credentials for the first service called are getting cached somewhere, but I can't find where that could be. I saw a possible solution here, but I can't find where WSClientConstants.CACHED_HTTP_STATE is defined. The comments in this JIRA issue seems to imply that it's part of org.apache.axis2.transport.http.HTTPConstants but it's not there.
Specifics:
Axis version: 1.5.1
Tomcat Version: 6.0.26
Java version: 1.6.0_23
It turns out the connections to the two different services were using the same JSESSIONID. Thus, the connection to the second web service was trying to use a session authenticated for the first web service, causing the error.
My solution for this was to define an HttpClient for each service, done by the following
MultiThreadedHttpConnectionManager manager = new MuliThreadedHttpConnectionManager();
HttpClient client = new HttpClient(manager);
ConfigurationContext context = ConfigurationContextFactory.createDefaultConfigurationContext();
context.setProperty(HTTPConstants.CACHED_HTTP_CLIENT, client);
context.setProperty(HTTPConstants.REUSE_HTTP_CLIENT, true);
Stub service = new Stub(context, serviceUrl);
This allows both servlets to have a separate session for their corresponding services.
The important point is to create a dedicated ConfigurationContext.
I've solved in a simpler way using a default config context when creating the stub without the multithreaded connection factory
stub = new MyStub(ConfigurationContextFactory.createDefaultConfigurationContext(), myServicesUrl);

calling a session based web service using ksoap2

My webservice uses soapsession as the session mechanism. I want to call that web service using ksoap2 api. How can I call that web service so that session will be maintained? ya, one more question. Now the web service is not returning the ServiceGroupId to the client written in ksoap2 api unlike it sends the same when I write the client using the axis2 api (ServiceClient). This is because in ksoap2 client, I am not engaging the addressing module. So, my question is Can I engage the addressing module using ksoap2 ?
You can use a KeepAliveHttpsTransportSE, but you can only use this one connection then.
Else you need to get the sessionID from your auth call.
When you have made the auth call with your HttpsTransportSE transport use this:
List<HeaderProperty> hp = (List<HeaderProperty>)transport.getConnection().getResponseProperties();
for (int i = 0; i < hp.size(); i++) {
if (hp.get(i).getKey().equals("set-cookie")){
SESSION_ID = hp.get(i).getValue();
break;
}
}
And set the sessionID into the header when you make a new WebService Call.