Почему JAX-WS зависает при развертывании любого сервиса, использующего привязку данных JAXB?
Я пытаюсь создать службу JAX-WS, которая использует привязку данных JAXB к объектам, сгенерированным из очень большого (более 900 классов) набора схем Opentravel Alliance.
Я могу успешно развернуть войну (с соответствующими web.xml и sun-jaxws.xml), содержащей мою службу JAX-WS, на различных контейнерах сервлетов (Jetty, Tomcat6/7 и т. Д.), Если мой веб-метод не ссылается любой из моих объектов JAXB. Например, это работает:
@WebService(serviceName = "OTAService",
targetNamespace = "http://www.opentravel.org/OTA/2003/05")
@Addressing
@SOAPBinding(parameterStyle = SOAPBinding.ParameterStyle.BARE)
public class OTAService {
public String sayHello(final String name) {
return "Hello " + name + "!";
}
}
Однако если я изменю веб-метод на использование привязки данных JAXB, добавив @XmlSeeAlso
аннотации или ссылки на объекты напрямую, все контейнеры сервлетов, которые я пробовал, зависают бесконечно (1+ часа), без ошибок и никогда не запускаются:
@WebService(serviceName = "OTAService",
targetNamespace = "http://www.opentravel.org/OTA/2003/05")
@Addressing
@SOAPBinding(parameterStyle = SOAPBinding.ParameterStyle.BARE)
@XmlSeeAlso({OTAHotelResNotifRQ.class, OTAHotelResNotifRS.class})
public class OTAService {
@Action(input = "OTA_HotelResNotif")
@WebMethod(operationName = "OTA_HotelResNotif", action = "OTA_HotelResNotif")
public @WebResult OTAHotelResNotifRQ tokenizeOtaHotelResNotifRq(
@WebParam(partName = "OTA_HotelResNotifRQ", name = "OTA_HotelResNotifRQ",
targetNamespace = "http://www.opentravel.org/OTA/2003/05")
final OTAHotelResNotifRQ request) {
return request;
}
}
Я проверил, что все необходимые jar-файлы, включая JAXB и JAX-WS API и jar-файлы времени выполнения, присутствуют в каталоге /lib war.
Банку с моими объектами JAXB, которая является необходимой зависимостью для моего проекта JAX-WS, можно создать и установить в локальный репозиторий, запустив mvn clean install
на этом проекте.
Мой проект JAX-WS, который доступен здесь, можно запустить в Jetty, вызвав mvn clean package jetty:run-war
,
Вы заметите, что Jetty запускается, если только простое sayHello
метод присутствует. Однако, если вы раскомментируете метод JAXB, Jetty и все другие контейнеры сервлетов, которые я пробовал, будут зависать навсегда при попытке создания экземпляра сервлета JAX-WS. Может кто-нибудь объяснить, почему веб-методы с привязкой данных JAXB препятствуют развертыванию моей войны? Поскольку поведение замораживания одинаково для различных контейнеров сервлетов, я чувствую, что должен быть какой-то важный шаг, который я пропускаю; однако, так как об ошибках не сообщается, и запуск контейнера просто зависает, я не знаю, как продолжить.
1 ответ
Похоже, это было связано с большим количеством объектов JAXB в моем проекте opentravel. Когда я подключил VisualVM к процессу запуска и сэмплировал память, это выглядело так, как будто JAXB шел и предварительно загружал / кэшировал все дерево объектов по какой-то причине (возможно, чтобы реконструировать схему для включения в WSDL?).
настройка -Dcom.sun.xml.bind.v2.runtime.JAXBContextImpl.fastBoot=true
как описано в ответе на этот вопрос и увеличение памяти с -Xmx1024m -XX:PermSize=256m -XX:MaxPermSize=512m
заставил Джетти начать быстро.
Я еще не уверен, будет ли компромисс приемлемым для производительности времени выполнения.