I have a .net 4.0 web app which needs to connect to a customer's web service, written in Java (it has cxf in the service endpoint)
Their service endpoint is https, and ultimately I will need to supply an x509 credential, but not yet.
They do not allow discovery, they dont expose a mex endpoint, they have supplied us with a wsdl and xsds, and I've managed to create a client proxy.
I'm struggling to set the right wcf client configuration. What I have so far is this: (names changed for obvious reasons).
<system.serviceModel>
<bindings>
<basicHttpsBinding>
<binding name="CUSwsBinding" />
</basicHttpsBinding>
</bindings>
<client>
<endpoint address="https://customer.com/cxf/customerMaintenance/"
binding="basicHttpsBinding" bindingConfiguration="CUSwsBinding"
contract="CUSCustomer.Customerxxx" name="CUSCustomerWS" />
</client>
</system.serviceModel>
When I try and execute, it says the basicHttpBinding extension is not recognised. I see there are some bindings that only are supported in .net 4.5, however my manager has Fear, Uncertainty and Doubt, and our web app has to stay on 4.0
Not an expert in WCF, so any help welcome.
As someone suggested, one can create an instance of the proxy class:
var client = new proxy.ClientClass();
At this line it throws a Configuration binding extension 'system.serviceModel/bindings/basicHttpsBinding' could not be found.
The endpointaddress needs to be in config, as its currently pointing at a test environment, will be poiting at production
Related
I am trying to consume web service using CXF component in mule(Anypoint Studio).
So I tried genrating the WSDL file from URL but I was getting this errror: Rpc/encoded wsdls are not supported in CXF so I followed this answer.
It worked and it generated client stubs, then copied the files into my mule project.
but I am getting this error:
Service.SomeService.<init>(java.net.URL, javax.xml.namespace.QName) (java.lang.NoSuchMethodException)
This is my flow:
<flow name="WebServiceTest">
<cxf:jaxws-client
clientClass="service.SomeService"
wsdlLocation="http://127.0.0.1:8000/api/v2_soap/?wsdl"
operation="test"/>
<outbound-endpoint address="http://127.0.0.1:8000/api.php/?type=v2_soap"/>
</flow>
Any ideas?
Your configuration is not correct specially your outbound endpoint url.
You can try configuring a CXF client as per Mule documentation.
You can also build a client for your JAX-WS services without generating a client from WSDL. Here you need a copy of your service interface and all your data objects locally to use something like this :-
<flow name="csvPublisher">
...
<cxf:jaxws-client serviceClass="org.example.HelloService" operation="sayHi"/>
<outbound-endpoint address="http://localhost:63081/services/greeter"/>
</flow>
Another approach is you can use a CXF-generated client as an outbound endpoint. First, you need to generate a CXF client using the WSDL to Java tool from CXF or the Maven plugin.
Then you need to configure something like the following :-
<flow name="csvPublisher">
...
<cxf:jaxws-client
clientClass="org.apache.hello_world_soap_http.SOAPService"
port="SoapPort"
wsdlLocation="classpath:/wsdl/hello_world.wsdl"
operation="greetMe"/>
<outbound-endpoint address="http://localhost:63081/services/greeter"/>
</flow>
It is better to put the wsdl in your local classpath.
Please checkout the full documentation here as reference to get it configured :-
https://docs.mulesoft.com/mule-user-guide/v/3.7/consuming-web-services-with-cxf
and
Consuming a Webservice Using Mule 3.4
I am working on understanding how SOAP services work.My client is in Java and the service is using WCF (although in theory this shouldn't matter). If I am given an example of a SOAP envelope and do the following:
-Build a SOAP envelope that exactly follows the example
-Use an HttpPost object to post the data to www.service.com/service.svc
Is this a correct (although improper) way to call the service? Because when I do this, I receive a 400 response, even though my SOAP envelope is the exact same as the example.
It should work. You are probably missing some required headers. I suggest to use a TCP monitor, intercept a working request and analize its content.
I think the reason you are getting an HTTP 400 (Bad Request) is that your service is using BasicHttpBinding which is SOAP 1.1, and you are most likely sending a SOAP 1.2 message (as you indicated in the comments that you are using SOAP 1.2). The message formats are different between the two.
The simplest solution would be to use SOAP 1.1, but if you must (or want) to use SOAP 1.2, the following may help.
In your config file, you haven't defined any endpoints or bindings - which is ok, as WCF will use defaults in 4.0 and later.
However, the default binding for HTTP is BasicHttpBinding. You need to use a binding that supports SOAP 1.2 (or change your message to SOAP 1.1). You could use WSHttpBinding, which does support SOAP 1.2, but you mau have to change the security setting (by default it's Windows).
Another option is to use a custom binding that implements SOAP1.1.
I'll give a couple of examples (I've never written a non-.NET client for a WCF service, so I can't say for certain that it will work but it should at least get you going in the right direction.
WSHttpBinding
Change the default protocol mapping for HTTP requests from BasicHttpBinding to WsHttpBinding by overriding the protocol mapping in your config file:
<protocolMapping>
<addBinding protocol="wsHttpBinding" scheme="http" />
</protocolMapping>
Add a binding section to your config file so you can set the security mode to None. This goes under the <system.serviceModel> section:
<bindings>
<wsHttpBinding>
<binding>
<security mode="None" />
</binding>
</wsHttpBinding>
</bindings>
Notice that I didn't set a value for the name attribute on the binding. This will set the binding definition as the default, and in conjunction with changing the default protocol for HTTP to wsHttpBinding should enable you to send SOAP 1.2.
SECURITY NOTE* Setting security to none is fine if you're just trying to get a better understanding of SOAP, but I would highly recommend doing it in production.
Custom Binding
I've never used a custom binding, but something like this should work:
<bindings>
<customBinding>
<binding name="Custom">
<textMessageEncoding messageVersion="Soap12" />
<httTransport />
</binding>
</customBinding>
</bindings>
You will need to explicitly set this to your endpoint (using the bindingConfiguration attribute of the endpoint), which means you'll need to create an endpoint definition in your config file.
The custom binding idea is from SOAP 1.2 message format with BasicHttpBinding
Hopefully this will give you some ideas and get you going again.
I'm using CXF to to communicate with a WSDL made in WCF. The WCF side of things was created following a tutorial. The Java code has been generated using a Maven script.
I have gotten things working using HTTPS for encryption. I have gotten authentication working. However, I would like to have the WSDL metadata turned off on the WCF side and still be able to use the Java side to talk to the service.
Currently, I can access the service with metadata publishing on from the Java side using this code:
URL wsdlLocation = new URL("https://server.com:7010/Hservice?wsdl");
HttpsURLConnection connection = (HttpsURLConnection) wsdlLocation.openConnection();
HService service = new HService(wsdlLocation);
HAdminService calc = service.getHAdminService();
... (authentication using WSS4JOutInterceptor code and unrelated code here)
System.out.println(calc.add(new Double(5), new Double(5)));
However, when I turn off metadata publishing on the WCF side I get this error:
Exception in thread "main" javax.xml.ws.WebServiceException:
org.apache.cxf.service.factory.ServiceConstructionException: Failed to create service.
at org.apache.cxf.jaxws.ServiceImpl.<init>(ServiceImpl.java:149)
at org.apache.cxf.jaxws.spi.ProviderImpl.createServiceDelegate(ProviderImpl.java:90)
at javax.xml.ws.Service.<init>(Service.java:56)
at com.blah.hservice.v_1_0.HService.<init>(HService.java:49)
at Main.main(Main.java:85)`
The page the wsdl is on displays this with metadata publishing turned off (this is an excerpt):
This is a Windows© Communication Foundation service.
Metadata publishing for this service is currently disabled.
If you have access to the service, you can enable metadata publishing by completing the following steps to modify your web or application configuration file:
I expected to be able to search "CXF metadata unpublished" and see lots of people doing this...but have not found anything. How do I communicate with this service without the WSDL being published?
You really have two options:
Copy the wsdl locally and point the client at the local wsdl. This is likely the "best" option as it makes sure all the information in the wsdl (like policies and such) is used.
Use "null" for the wsdl location (note: not JAX-WS portable). You will need to call service.addPort(....) after creating the service and before calling getHAdminService to add the port with the appropriate binding and endpoint address. CXF can work most of the time without the WSDL (will internally generate what is needed from the annotations). However, if things like policies are defined in the WSDL, then it cannot.
I got this to work with Client code I generated using CXF 2.6.5
Make sure the QName(first argument) matches the QName the getHAdminService() method references. The bindingId(second argument) should be one of the constants defined in SOAPBinding Interface (javax.xml.ws.soap.SOAPBinding).
I have an ASP.NET application hosting a few WCF services, using ASP.NET Membership for security. I've exposed the System.Web.ApplicationServices.AuthenticationService through an SVC file (AuthenticationService.svc) as shown below:
<%# ServiceHost Language="C#" Debug="true" Service="System.Web.ApplicationServices.AuthenticationService" %>
My WCF configuration for this service is as follows:
<service name="System.Web.ApplicationServices.AuthenticationService" behaviorConfiguration="AuthenticationServiceBehaviors">
<endpoint contract="System.Web.ApplicationServices.AuthenticationService" binding="basicHttpBinding"/>
</service>
...
<behavior name="AuthenticationServiceBehaviors">
<serviceMetadata httpGetEnabled="true"/>
<serviceDebug httpHelpPageEnabled="true" includeExceptionDetailInFaults="true"/>
</behavior>
...
<bindings>
<basicHttpBinding>
<binding allowCookies="true"></binding>
</basicHttpBinding>
</bindings>
I've enabled the authentication service in my web.config as shown below:
<system.web.extensions>
<scripting>
<webServices>
<authenticationService enabled="true" requireSSL="false"/>
</webServices>
</scripting>
</system.web.extensions>
I created a .NET console application to test the service. Visual Studio generated a client, and the service worked as expected. My problem is that I need to use this service from a Java application, but when I try to generate a client in Eclipse using Apache Axis, I get the following error:
IWAB0399E Error in generating Java from WSDL: java.io.IOException: Emitter failure.
There is an undefined portType (AuthenticationService) in the WSDL document
http://localhost:17637/Services/AuthenticationService.svc?wsdl=wsdl0.
Hint: make sure <binding type=".."> is fully qualified.
I've tracked it down to Apache Axis needing different namespace and name in the ServiceContract and ServiceBehavior, thanks to this post. I've changed other WCF services as that post shows, and they work just fine. The problem is that System.Web.ApplicationServices.AuthenticationService looks like this (from http://msdn.microsoft.com/en-us/library/system.web.applicationservices.authenticationservice.aspx):
[ServiceBehaviorAttribute(Namespace = "http://asp.net/ApplicationServices/v200", InstanceContextMode = InstanceContextMode.Single, ConcurrencyMode = ConcurrencyMode.Multiple)]
[AspNetCompatibilityRequirementsAttribute(RequirementsMode = AspNetCompatibilityRequirementsMode.Required)]
[ServiceContractAttribute(Namespace = "http://asp.net/ApplicationServices/v200")]
public class AuthenticationService
Notice the ServiceBehaviorAttribute namespace is the same as the ServiceContractAttribute namespace? I need them to be different so I can get Eclipse (Apache Axis) to generate a client. Any ideas?
I do not think is possible to change name of built-in service. You should be allowed for wrapping built-in service in other service or for writing custom service handle authentication.
I need to call a web service with a java client.
This service authenticates clients through certificates at the message level (Ws-Security, not SSL).
It should be possible since, I can generate web services with JAX-WS with mutual certificate security in this dialog.
But I don't manage to create a client. Does anyone has an idea ?
I did not tried it myself, but from http://download.oracle.com/docs/cd/E17802_01/webservices/webservices/docs/2.0/tutorial/doc/ :
Configuring Message Security Using XWSS
The Application Server contains all of the JAR files necessary to use XWS-Security for securing JAX-WS applications, however, in order to view the sample applications, you must download and install the standalone Java WSDP bundle. You can download the Java WSDP from http://java.sun.com/webservices/downloads/webservicespack.html.
To add message security to an existing JAX-WS application using XWSS, follow these steps on the client side:
Create a client security configuration. The client security configuration file specifies the order and type of message security operations that will be used for the client application. For example, a simple security configuration to perform a digital signature operation looks like this:
<xwss:Sign id="s" includeTimestamp="true">
<xwss:X509Token encodingType="http://docs.oasis-
open.org/wss/2004/01/oasis-200401-wss-soap-message-security-1.0#Base64Binary"
valueType="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-
x509-token-profile-1.0#X509SubjectKeyIdentifier"
certificateAlias="xws-security-client"
keyReferenceType="Identifier"/>
</xwss:Sign>
</xwss:SecurityConfiguration>
</xwss:Service>
<xwss:SecurityEnvironmentHandler>
simple.client.SecurityEnvironmentHandler
</xwss:SecurityEnvironmentHandler>
For more information on writing and understanding security configurations and setting up SecurityEnvironmentHandlers, please see the Java Web Services Developer Pack 1.6 Tutorial at http://java.sun.com/webservices/docs/1.6/tutorial/doc/index.html.
In your client code, create an XWSSecurityConfiguration object initialized with the security configuration generated. Here is an example of the code that you would use in your client file. For an example of a complete file that uses this code, look at the example client in the \jaxws2.0\simple-doclit\src\simple\client\ directory.
FileInputStream f = new FileInputStream("./etc/client_security_config.xml");
XWSSecurityConfiguration config = SecurityConfigurationFactory.newXWSSecurityConfiguration(f);
Set security configuration information on the RequestContext by using the XWSSecurityConfiguration.MESSAGE_SECURITY_CONFIGURATION property. For an example of a complete file that uses this code, look at the example client in the \jaxws2.0\simple-doclit\src\simple\client\ directory.
// put the security config info
((BindingProvider)stub).getRequestContext().put(
XWSSecurityConfiguration.MESSAGE_SECURITY_CONFIGURATION,
config);
Invoke the method on the stub as you would if you were writing the client without regard to adding XWS-Security. The example for the application from the \jaxws2.0\simple-doclit\src\simple\client\ directory is as shown below:
Holder<String> hold = new Holder("Hello !");
stub.ping(ticket, hold);