2010-08-25 25 views
10

Estoy intentando escribir un módulo para una aplicación Java que accede a un servicio web descrito por WSDL. La fuente WSDL se descargó directamente de lo que creo que es un servicio web ASP.NET; la URL del servicio finaliza en una extensión .asmx, y al ver la URL del servicio en un navegador, se muestra un enlace que se puede usar para descargar el WSDL.Cambio de la URL en un cliente de servicio web generado con wsimport

Un requisito clave para mí es poder cambiar la URL del servicio sin volver a compilar. La URL que se me da es obviamente un servidor de prueba y sé que en producción recibiré una URL de producción para usar. También me gustaría poder crear un servidor simulado para probarlo y conservar la capacidad de especificar una nueva URL en el futuro sin volver a compilar si se mueve el servicio. De hecho, me gustaría que una instalación de nuestra aplicación pueda instanciar instancias múltiples del servicio web en diferentes URL.

Pero mi concepción no parece coincidir con lo que la herramienta wsimport está haciendo por mí. A raíz de la respuesta de f1sh here, me genera código Java de mi WSDL descargado con este comando:

wsimport -Xnocompile -keep -b binding.xml wsdlFile.wsdl 

Lo que me parece es que el código generado tiene una referencia codificada a mi wsdlFile.wsdl descargado, que contiene la URL del servicio. Nuestra aplicación no se ejecutará de tal manera que se configure editando un archivo WSDL en tiempo de ejecución. Necesito tener un código que esté compilado en mi aplicación en tiempo de compilación y pueda tener la URL del servicio establecida en el momento de creación de instancias.

No estoy del todo seguro de por qué el WSDL incluso necesita ser analizado en tiempo de ejecución; entendí que WSDL proporciona suficiente información para generar código que puede acceder al servicio web, por lo que no estoy seguro de lo que está proporcionando al código generado que no sea la URL del servicio, y no estoy seguro de por qué la URL del servicio no se proporciona en un constructor o configurable a través de un método en la clase de servicio web generada. Debo estar perdiendo algo.

¿Cuál es la práctica general para este escenario? ¿La mayoría de las personas regenera el código para cada URL individual que van a usar? ¿Se genera código en tiempo de ejecución? ¿Hay alguna otra herramienta WSDL que pueda usar que genere código de cliente con una URL configurable?

Respuesta

3

Este enfoque requiere que también proporcione un objeto javax.xml.namespace.QName, que aún no entiendo, como el segundo argumento.

Copie el de su fuente generada. A QName es un XML qualified name - una identidad "única".

Todavía no entiendo por qué se necesita WSDL en tiempo de ejecución.

No puedo decirlo, estoy seguro, pero un WSDL es básicamente un esquema. Al proporcionarlo, supongo que le das a JAX-WS un mecanismo para validar la respuesta SOAP. No creo que las uniones JAXB sean suficientes para hacer esto.

Siempre uso el constructor de dos argumentos en el servicio generado para proporcionar una URL a través del método para incrustar el WSDL en mi jar. Al igual que con cualquier esquema, el uso de una URL de sistema remoto o de archivo para esto es estúpido menos que óptimo.

Ver this question for how to set the end-point at runtime.

10

Esta respuesta me ha estado eludiendo durante un par de días, pero de alguna manera el acto de escribir la pregunta siempre me centra en la búsqueda de una respuesta, y un par más websearches han señalado que:

http://www.fransvanbuul.net/?p=98

Parece que wsimport creó una clase, com.example.WebService, que amplía javax.xml.ws.Service. Esta clase de WebService tiene dos constructores. El constructor no-arg está codificado con un archivo: // URL para usar el WSDL original que he generado. (Supongo que si hubiera proporcionado una URL https: // en la línea de comando wsimport, esa sería la URL que está codificada). Alternativamente, puedo usar un constructor de dos arcos y suministrar una URL WSDL en el momento de creación de instancias. Este enfoque requiere que también proporcione un objeto javax.xml.namespace.QName, que todavía no entiendo, como el segundo argumento.

El uso de este constructor de dos arcos probablemente resolverá mi problema.

Parece que wsimport, que estoy utilizando desde JDK 1.6, es una parte del paquete JAX-WS. JDK 1.6, en versiones recientes, contiene JAX-WS 2.1, y JAX-WS 2.2 abordará las dificultades que estoy planteando en esta pregunta.

Estaré encantado de aceptar cualquier respuesta que explique parte o la totalidad del resto de esta situación. Aún no entiendo por qué se necesita WSDL en tiempo de ejecución.De manera más práctica, me sería útil que alguien me mostrara cómo usar el constructor de dos argumentos, o cómo generar mi código con JDK 1.6 y JAX-WS 2.2.

Cuestiones relacionadas