Comment puis-je appeler un web service à partir d'un autre web-service (à l'intérieur de la même GUERRE)
Contexte: le Serveur d'Applications Glassfish 3.1.2. La technologie est JavaEE JAX-WS. L'IDE Netbeans 7.1.1.
J'ai créé 2 services web à partir de WSDL à l'aide wsimport. Ni sont les EJB. Ils utilisent tous les deux le @WebService annotation. Ils vivent tous deux dans la même GUERRE (pas sûr que doit être pertinente, mais il pourrait l'être). Je peux déployer et de tester les services très heureux individuellement, à l'aide de SOAP-UI en tant que client.
Je souhaite maintenant obtenir WebService1 appeler WebService2 au moment de l'exécution. Je ne veux pas simplement appeler l'impl de webservice2 à l'aide de java (localement façon de parler) - j'aimerais appeler les webservice2 correctement, comme un service web, afin de créer un looser de couplage.
Dans l'IDE, je peux générer le code nécessaire pour le webservice appel à l'aide de la condition de "générer du code: web service opération d'appel". Cela a ajouté une @WebServiceRef(wsdlLocation = "WEB-INF/wsdl/nom_service.wsdl") et un peu de code pour créer un port et d'appeler la cible d'un webservice opération.
//Call Web Service Operation
Identity port = service.getIdentityPort();
String req = "";
javax.xml.ws.Holder<StructureMessageHeader> idHeader = new javax.xml.ws.Holder<StructureMessageHeader>();
String result = port.getIdentifier(req, idHeader);
Cette compile bien, mais à l'exécution, il échoue. Le déploiement est une réussite, et les services sont à la fois haut et en général heureux individuellement (tant que vous n'appelez pas ce code), mais quand un webservice tente d'appeler l'autre-je obtenir un
ClientTransportException: The server sent HTTP status code 404: Not Found.
Plus de détails ci-dessous.
Personne ne sait à quoi cela peut-il se passe? Où ai-je fait de mal? Qu'ai-je oubliée?
Toute aide, beaucoup apprécié.
------------------------ EXCEPTION ---------------------
com.sun.xml.ws.client.ClientTransportException: The server sent HTTP status code 404: Not Found at com.sun.xml.ws.transport.http.client.HttpTransportPipe.checkStatusCode(HttpTransportPipe.java:321) at com.sun.xml.ws.transport.http.client.HttpTransportPipe.createResponsePacket(HttpTransportPipe.java:270) at com.sun.xml.ws.transport.http.client.HttpTransportPipe.process(HttpTransportPipe.java:228) at com.sun.xml.ws.transport.http.client.HttpTransportPipe.processRequest(HttpTransportPipe.java:143) at com.sun.xml.ws.transport.DeferredTransportPipe.processRequest(DeferredTransportPipe.java:110) at com.sun.xml.ws.api.pipe.Fiber.__doRun(Fiber.java:961) at com.sun.xml.ws.api.pipe.Fiber._doRun(Fiber.java:910) at com.sun.xml.ws.api.pipe.Fiber.doRun(Fiber.java:873) at com.sun.xml.ws.api.pipe.Fiber.runSync(Fiber.java:775) at com.sun.xml.ws.api.pipe.helper.AbstractTubeImpl.process(AbstractTubeImpl.java:116) at com.sun.enterprise.security.webservices.ClientSecurityPipe.processSecureRequest(ClientSecurityPipe.java:196) at com.sun.enterprise.security.webservices.ClientSecurityPipe.process(ClientSecurityPipe.java:184) at com.sun.xml.ws.api.pipe.helper.PipeAdapter.processRequest(PipeAdapter.java:119) at com.sun.xml.ws.api.pipe.Fiber.__doRun(Fiber.java:961) at com.sun.xml.ws.api.pipe.Fiber._doRun(Fiber.java:910) at com.sun.xml.ws.api.pipe.Fiber.doRun(Fiber.java:873) at com.sun.xml.ws.api.pipe.Fiber.runSync(Fiber.java:775) at com.sun.xml.ws.client.Stub.process(Stub.java:429) at com.sun.xml.ws.client.sei.SEIStub.doProcess(SEIStub.java:168) at com.sun.xml.ws.client.sei.SyncMethodHandler.invoke(SyncMethodHandler.java:119) at com.sun.xml.ws.client.sei.SyncMethodHandler.invoke(SyncMethodHandler.java:102) at com.sun.xml.ws.client.sei.SEIStub.invoke(SEIStub.java:151) at $Proxy219.getIdentifier(Unknown Source) at com.soagrowers.r20121231.product.master.services.ProductsEntityService.createProduct(ProductsEntityService.java:138) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39) at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25) at java.lang.reflect.Method.invoke(Method.java:597) at org.glassfish.webservices.InstanceResolverImpl$1.invoke(InstanceResolverImpl.java:143) at com.sun.xml.ws.server.InvokerTube$2.invoke(InvokerTube.java:149) at com.sun.xml.ws.server.sei.SEIInvokerTube.processRequest(SEIInvokerTube.java:94) at com.sun.xml.ws.api.pipe.Fiber.__doRun(Fiber.java:961) at com.sun.xml.ws.api.pipe.Fiber._doRun(Fiber.java:910) at com.sun.xml.ws.api.pipe.Fiber.doRun(Fiber.java:873) at com.sun.xml.ws.api.pipe.Fiber.runSync(Fiber.java:775) at com.sun.xml.ws.api.pipe.helper.AbstractTubeImpl.process(AbstractTubeImpl.java:116) at org.glassfish.webservices.MonitoringPipe.process(MonitoringPipe.java:142) at com.sun.xml.ws.api.pipe.helper.PipeAdapter.processRequest(PipeAdapter.java:119) at com.sun.xml.ws.api.pipe.Fiber.__doRun(Fiber.java:961) at com.sun.xml.ws.api.pipe.Fiber._doRun(Fiber.java:910) at com.sun.xml.ws.api.pipe.Fiber.doRun(Fiber.java:873) at com.sun.xml.ws.api.pipe.Fiber.runSync(Fiber.java:775) at com.sun.xml.ws.api.pipe.helper.AbstractTubeImpl.process(AbstractTubeImpl.java:116) at com.sun.enterprise.security.webservices.CommonServerSecurityPipe.processRequest(CommonServerSecurityPipe.java:212) at com.sun.enterprise.security.webservices.CommonServerSecurityPipe.process(CommonServerSecurityPipe.java:144) at com.sun.xml.ws.api.pipe.helper.PipeAdapter.processRequest(PipeAdapter.java:119) at com.sun.xml.ws.api.pipe.Fiber.__doRun(Fiber.java:961) at com.sun.xml.ws.api.pipe.Fiber._doRun(Fiber.java:910) at com.sun.xml.ws.api.pipe.Fiber.doRun(Fiber.java:873) at com.sun.xml.ws.api.pipe.Fiber.runSync(Fiber.java:775) at com.sun.xml.ws.server.WSEndpointImpl$2.process(WSEndpointImpl.java:386) at com.sun.xml.ws.transport.http.HttpAdapter$HttpToolkit.handle(HttpAdapter.java:640) at com.sun.xml.ws.transport.http.HttpAdapter.handle(HttpAdapter.java:263) at com.sun.xml.ws.transport.http.servlet.ServletAdapter.handle(ServletAdapter.java:163) at org.glassfish.webservices.JAXWSServlet.doPost(JAXWSServlet.java:145) at javax.servlet.http.HttpServlet.service(HttpServlet.java:688) at javax.servlet.http.HttpServlet.service(HttpServlet.java:770) at org.apache.catalina.core.StandardWrapper.service(StandardWrapper.java:1542) at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:281) at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:175) at org.apache.catalina.core.StandardPipeline.doInvoke(StandardPipeline.java:655) at org.apache.catalina.core.StandardPipeline.invoke(StandardPipeline.java:595) at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:161) at org.apache.catalina.connector.CoyoteAdapter.doService(CoyoteAdapter.java:331) at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:231) at com.sun.enterprise.v3.services.impl.ContainerMapper$AdapterCallable.call(ContainerMapper.java:317) at com.sun.enterprise.v3.services.impl.ContainerMapper.service(ContainerMapper.java:195) at com.sun.grizzly.http.ProcessorTask.invokeAdapter(ProcessorTask.java:849) at com.sun.grizzly.http.ProcessorTask.doProcess(ProcessorTask.java:746) at com.sun.grizzly.http.ProcessorTask.process(ProcessorTask.java:1045) at com.sun.grizzly.http.DefaultProtocolFilter.execute(DefaultProtocolFilter.java:228) at com.sun.grizzly.DefaultProtocolChain.executeProtocolFilter(DefaultProtocolChain.java:137) at com.sun.grizzly.DefaultProtocolChain.execute(DefaultProtocolChain.java:104) at com.sun.grizzly.DefaultProtocolChain.execute(DefaultProtocolChain.java:90) at com.sun.grizzly.http.HttpProtocolChain.execute(HttpProtocolChain.java:79) at com.sun.grizzly.ProtocolChainContextTask.doCall(ProtocolChainContextTask.java:54) at com.sun.grizzly.SelectionKeyContextTask.call(SelectionKeyContextTask.java:59) at com.sun.grizzly.ContextTask.run(ContextTask.java:71) at com.sun.grizzly.util.AbstractThreadPool$Worker.doWork(AbstractThreadPool.java:532) at com.sun.grizzly.util.AbstractThreadPool$Worker.run(AbstractThreadPool.java:513) at java.lang.Thread.run(Thread.java:662)
OriginalL'auteur benwilcock | 2012-05-24
Vous devez vous connecter pour publier un commentaire.
Je pense que j'ai fixé
Il y avait 2 problèmes, et après correction de ces erreurs de mon code fonctionne maintenant comme il se doit.
Question #1. (mineur)
L'jax-ws-catalog.xml ne contient pas de référence à l'WSDL ou les fichiers XSD pour WebService2. Ce qui est nécessaire pour aider JAX-WS cadre à utiliser une copie locale du fichier WSDL à l'exécution sans avoir à charger le WSDL ou XSD sur HTTP.
Question #2. (major)
Le "Service" de la section dans le fichier WSDL référencé dans la jax-ws-catalogue doit avoir une précision de point de terminaison de l'emplacement à l'intérieur. Au moment de l'exécution des serveurs de réécrire ce peu de WSDL pour le bon point de terminaison http emplacement du service, comme par diverses configurations (comme les détails dans le @webservice annotation par exemple). Bien sûr, lorsque vous démarrez à partir de WSDL' cet effet pourrait être entièrement ficticious parce que le contrat de service est découplée de toute mise en œuvre (comme il l'a été dans mon cas). Par conséquent, lorsque JAX-WS ramasse le WSDL à partir de l'emplacement spécifié dans le jax-ws-catalogue, on trouve un emplacement http qui n'existe pas et ne peut pas être résolu. D'où le "
ClientTransportException: The server sent HTTP status code 404: Not Found.
" - l'URL dans le fichier WSDL à la faute.Résumé.
La solution était d'ajouter une précision d'extrémité de l'emplacement pour le webservice pour le WSDL du service section de définition, et assurez-vous que le WSDL et XSD ont été correctement indiquée dans le jax-ws-catalogue.
OriginalL'auteur benwilcock
Une meilleure façon de procéder est de faire le service web d'une couche qui appelle ensuite dans la logique de l'application. Puis, quand un seul jeu de logique métier besoins à l'appel de l'autre, il n'est pas avoir à passer par une inutiles http aller-retour. Envisagez d'utiliser quelque chose comme le Printemps avec @Service et @Autocâblés. Dans EJB monde (et je sais que vous avez dit que vous n'utilisez pas que), c'est fait avec @interfaces Locales et @EJB session d'injection, de sorte que vous n'allez pas grâce à une énorme distance de l'API de la pile juste pour appeler une méthode d'une autre classe.
Je n'ai pas de plaider pour que le client s'adresser directement à un Printemps
@Service
ou à un@Stateless
session bean. Je dis que la logique d'entreprise doit être considérée comme un service que la couche web parle à. Puis un des appels de service web un service de l'entreprise, ne rien savoir sur ce que les entreprises de service est en train de faire à l'interne. L'entreprise de service peut être une composition de services d'affaires.OriginalL'auteur Jim
L'on doit intégrer un client web dans le premier service web, qui demande de l'information à partir de la deuxième service web. Ce client de apache a été utilisé avec de bons résultats.
Occasionnellement un service web de la bibliothèque contient également un embedded web client pour faciliter les tests. Si votre libararies contenir un tel client, vous n'avez même pas besoin d'ajouter un supplément de client web de mise en œuvre.
--- Modifié pour répondre à la question sur si le JAXWS API fournit "client" support ---
Certainement JAX-WS a tout pour configurer un service web, mais je suis incertain si elle fait partie de la spécification également contenir tout ce qui est à l'appel d'un service web. Je n'ai pas vu une mise en œuvre qui ne possède pas un tel établissement, afin de répondre que "de temps en temps", la bibliothèque contient un client était un peu exagéré sur la chance, il est manquant.
Dans tous les cas, les classes à l'appui d'un client enroulez simplement XML générateurs et les clients HTTP.
Si ma mémoire est bonne, que vous obtenez une copie du fichier WSDL, qui est lu par un "compilateur" qui affiche le code source de Java dans un package spécifié espace de noms. Ensuite, en utilisant les classes générées, vous avez une API d'accès au niveau du service web distant. Le résultat final ressemble à ce
Où vous créez le "côté client en vue du service" en construisant un XXXService objet, puis l'attacher à lui céder un délégué objet de type XXXDelegate. Les méthodes le délégué de générer de nouveaux objets (un objet existe pour chaque port de liaison "SomeCall.java") qui encapsulent la demande, et la réponse est gérée par un "SomeCallReply.java" fichier, le délégué utilise ensuite pour décompresser la réponse et le retour de la valeur pour le "client" du code.
Un exemple peut être trouvé au bas de ce tutoriel. Encore une fois, ceci est ma compréhension de haut niveau stuff, les détails ont changé dans les versions plus récentes de JAXWS. Quand j'ai creusé profondément, il était assez tôt dans le jeu. Il y a eu beaucoup de versions de JAXWS depuis.
J'étais certain que le JAX-WS cadre de tout ce que je besoin de consommer un autre service, sans avoir à recourir à d'autres HTTP cadres. N'est-ce pas vrai?
Autant que je sache, il est vrai, mais je ne savais pas si c'était toujours true, donc désolé si j'ai surestimé le "parfois". Le lire à nouveau, je peux facilement voir comment je me laisse entendre qu'il est rarement vrai. Désolé pour la confusion.
OriginalL'auteur Edwin Buck