J'ai un programme qui est censé envoyer un fichier à un service Web, ce qui nécessite une connexion SSL. Je lance le programme comme suit:
SET Java_HOME=C:\Program Files\Java\jre1.6.0_07
SET com.ibm.SSL.ConfigURL=ssl.client.props
"%Java_HOME%\bin\Java" -cp ".;Test.jar" ca.mypackage.Main
Cela fonctionnait bien, mais lorsque je change la première ligne en
SET Java_HOME=C:\Program Files\IBM\SDP\runtimes\base_v7\Java\jre
Je reçois l'erreur suivante:
com.Sun.xml.internal.ws.client.ClientTransportException: HTTP transport error: Java.net.SocketException: Java.lang.ClassNotFoundException: Cannot find the specified class com.ibm.websphere.ssl.protocol.SSLSocketFactory
at com.Sun.xml.internal.ws.transport.http.client.HttpClientTransport.getOutput(HttpClientTransport.Java:119)
at com.Sun.xml.internal.ws.transport.http.client.HttpTransportPipe.process(HttpTransportPipe.Java:140)
at com.Sun.xml.internal.ws.transport.http.client.HttpTransportPipe.processRequest(HttpTransportPipe.Java:86)
at com.Sun.xml.internal.ws.api.pipe.Fiber.__doRun(Fiber.Java:593)
at com.Sun.xml.internal.ws.api.pipe.Fiber._doRun(Fiber.Java:552)
at com.Sun.xml.internal.ws.api.pipe.Fiber.doRun(Fiber.Java:537)
at com.Sun.xml.internal.ws.api.pipe.Fiber.runSync(Fiber.Java:434)
at com.Sun.xml.internal.ws.client.Stub.process(Stub.Java:247)
at com.Sun.xml.internal.ws.client.sei.SEIStub.doProcess(SEIStub.Java:132)
at com.Sun.xml.internal.ws.client.sei.SyncMethodHandler.invoke(SyncMethodHandler.Java:242)
at com.Sun.xml.internal.ws.client.sei.SyncMethodHandler.invoke(SyncMethodHandler.Java:222)
at com.Sun.xml.internal.ws.client.sei.SEIStub.invoke(SEIStub.Java:115)
at $Proxy26.fileSubmit(Unknown Source)
at com.testing.TestingSoapProxy.fileSubmit(TestingSoapProxy.Java:81)
at ca.mypackage.Main.main(Main.Java:63)
Caused by: Java.net.SocketException: Java.lang.ClassNotFoundException: Cannot find the specified class com.ibm.websphere.ssl.protocol.SSLSocketFactory
at javax.net.ssl.DefaultSSLSocketFactory.a(SSLSocketFactory.Java:7)
at javax.net.ssl.DefaultSSLSocketFactory.createSocket(SSLSocketFactory.Java:1)
at com.ibm.net.ssl.www2.protocol.https.c.afterConnect(c.Java:110)
at com.ibm.net.ssl.www2.protocol.https.d.connect(d.Java:14)
at Sun.net.www.protocol.http.HttpURLConnection.getOutputStream(HttpURLConnection.Java:902)
at com.ibm.net.ssl.www2.protocol.https.b.getOutputStream(b.Java:86)
at com.Sun.xml.internal.ws.transport.http.client.HttpClientTransport.getOutput(HttpClientTransport.Java:107)
... 14 more
Caused by: Java.lang.ClassNotFoundException: Cannot find the specified class com.ibm.websphere.ssl.protocol.SSLSocketFactory
at javax.net.ssl.SSLJsseUtil.b(SSLJsseUtil.Java:20)
at javax.net.ssl.SSLSocketFactory.getDefault(SSLSocketFactory.Java:36)
at javax.net.ssl.HttpsURLConnection.getDefaultSSLSocketFactory(HttpsURLConnection.Java:16)
at javax.net.ssl.HttpsURLConnection.<init>(HttpsURLConnection.Java:36)
at com.ibm.net.ssl.www2.protocol.https.b.<init>(b.Java:1)
at com.ibm.net.ssl.www2.protocol.https.Handler.openConnection(Handler.Java:11)
at Java.net.URL.openConnection(URL.Java:995)
at com.Sun.xml.internal.ws.api.EndpointAddress.openConnection(EndpointAddress.Java:206)
at com.Sun.xml.internal.ws.transport.http.client.HttpClientTransport.createHttpConnection(HttpClientTransport.Java:277)
at com.Sun.xml.internal.ws.transport.http.client.HttpClientTransport.getOutput(HttpClientTransport.Java:103)
... 14 more
Il semble donc que ce problème soit lié au JRE que j'utilise, mais ce qui ne semble pas logique, c'est que le JRE non IBM fonctionne correctement, mais pas le JRE IBM. Des idées ou des suggestions?
Si votre nom de domaine non IBM est Sun, il est déjà livré avec une implémentation de classes SSL fournie.
Il semble que IBM jre ne contienne pas du tout de classes d'implémentation SSL.
Essayez d'ajouter ces deux lignes quelque part dans votre code d'installation:
Security.setProperty("ssl.SocketFactory.provider", "com.ibm.jsse2.SSLSocketFactoryImpl");
Security.setProperty("ssl.ServerSocketFactory.provider", "com.ibm.jsse2.SSLServerSocketFactoryImpl");
Java n'autorise qu'une classe de fabrique de connexions SSL pour une machine virtuelle Java. Si vous utilisez un kit JDK livré avec WebSphere Application Server v6x/7x/8x ou tout autre outil serveur WebSphere de Rational Application Developer, ceux-ci requièrent la classe spécifique de WebSphere Application (com.ibm.websphere.ssl.protocol.SSLSocketFactory) Exécution du serveur. Car le fichier de sécurité Java contient les fabriques de socket JSSE définies comme ci-dessous.
# Default JSSE socket factories
#ssl.SocketFactory.provider=com.ibm.jsse2.SSLSocketFactoryImpl
#ssl.ServerSocketFactory.provider=com.ibm.jsse2.SSLServerSocketFactoryImpl
# WebSphere socket factories (in cryptosf.jar)
ssl.SocketFactory.provider=com.ibm.websphere.ssl.protocol.SSLSocketFactory
ssl.ServerSocketFactory.provider=com.ibm.websphere.ssl.protocol.SSLServerSocketFactory
Ainsi, si vous supprimez la mise en commentaire des usines de socket JSSE par défaut et commentez celles de WebSphere, WAS va vomir.
Un meilleur moyen de contourner le problème serait d’avoir le fichier com.ibm.ws.security.crypto.jar dans votre chemin de classe. Ce fichier jar dépend du fichier com.ibm.ffdc.jar, vous en avez donc bien besoin dans votre chemin de classe. Ces deux fichiers jar sont disponibles sous <WebSphere_Install_Dirctory>/plugins/
vous pouvez définir ces propriétés dans le fichier WAS_HOME/*/Java/jre/lib/security/Java.security en désactivant les propriétés JSSE suivantes.
ssl.SocketFactory.provider = com.ibm.jsse2.SSLSocketFactoryImpl ssl.ServerSocketFactory.provider = com.ibm.jsse2.SSLServerSocketFactoryImpl
Une autre "solution" qui semble fonctionner pour moi. Créez votre propre fichier de propriétés de sécurité, my.Java.security
, avec un contenu tel que:
ssl.SocketFactory.provider=
ssl.ServerSocketFactory.provider=
Lors de l'appel de Java (ou dans mon cas, maven), ajoutez l'option de ligne de commande:
-Djava.security.properties=C:\myfiles\my.Java.security
Cribbed de la documentation IBM Liberty: http://www-01.ibm.com/support/knowledgecenter/was_beta_liberty/com.ibm.websphere.wlp.nd.multiplatform.doc/ae/rwlp_trouble.html?lang=fr
Vous avez trouvé cette rubrique lors de la recherche du même message d'erreur, mais vous avez trouvé une solution différente. Pour tester un service https REST à l'aide du client Apache Wink:
ClientConfig config = new ClientConfig();
config.setBypassHostnameVerification(true);
RestClient client = new RestClient(config);
Et définir l'usine est vide:
Security.setProperty("ssl.SocketFactory.provider", "");
Security.setProperty("ssl.ServerSocketFactory.provider", "");
Mon environnement d'exécution est un test Camel autonome utilisant IBM JRE 1.7 d'IBM WebSphere v8.5.5.
J'avais un problème similaire lorsque mon application Batch essayait d'extraire des données du service Web Restful à l'aide d'Apache Wink. J'utilisais MyEclipse comme environnement de développement. Et utilisait le jre fourni par IBM WebSphere 8.5. Lorsque j'ai changé pour Sun 1.6 jre, le problème a été résolu.