Можно ли использовать jax-ws для генерации XML, но НЕ отправлять его - PullRequest
5 голосов
/ 03 февраля 2012

Итак, вот сценарий: у нас есть PeopleSoft, и мы хотим отправлять сообщения туда и обратно из отдела продаж.К сожалению, PeopleSoft не имеет такого инструмента, как wsimport, который использует wsdl и генерирует классы для вас.Есть что-то, что потребляет wsdl, но все, что он делает, это генерирует объекты-заглушки.Разработчику все равно придется написать код для ручной генерации строки сообщения XML.

Я, очевидно, не хочу делать все это.Так что я знаю, что Java можно вызывать из PeopleSoft.Я также знаю, что могу отправлять сообщения, используя только сгенерированные классы, но я хотел бы использовать функции мониторинга сообщений, встроенные в PeopleSoft.

Итак, возможное решение, о котором я думаю, будет:

  1. вызов метода webservice в java (без отправки сообщения)
  2. Получение xml
  3. отправка xml с помощью механизмовoplesoft
  4. получение ответа xml
  5. передать XML-ответ обратно в Java-класс ответа
  6. Использовать Java-классы для получения значений в XML-файле

Я сумасшедший или это возможно?

ps Я новичок в Java-разработке

Вот мой класс-обработчик для захвата xml, но нужен какой-то способ предотвращения отправки сообщения.

public class LoggingHandler implements SOAPHandler<SOAPMessageContext> {
 // change this to redirect output if desired
private static PrintStream out = System.out;
private String xmlOut = null;

public Set<QName> getHeaders() {
    return null;
}

public boolean handleMessage(SOAPMessageContext smc) {
    logToSystemOut(smc);
    return true;
}

public boolean handleFault(SOAPMessageContext smc) {
    logToSystemOut(smc);
    return true;
}

// nothing to clean up
public void close(MessageContext messageContext) {
}

public String getXmlOut() {
    return xmlOut;
}

/*
 * Check the MESSAGE_OUTBOUND_PROPERTY in the context
 * to see if this is an outgoing or incoming message.
 * Write a brief message to the print stream and
 * output the message. The writeTo() method can throw
 * SOAPException or IOException
 */
private void logToSystemOut(SOAPMessageContext smc) {
    Boolean outboundProperty = (Boolean)
        smc.get (MessageContext.MESSAGE_OUTBOUND_PROPERTY);


    SOAPMessage message = smc.getMessage();
    try {
        ByteArrayOutputStream baOut = new ByteArrayOutputStream();
        message.writeTo(baOut);
        xmlOut = new String(baOut.toByteArray());


    } catch (Exception e) {
        out.println("Exception in handler: " + e);
    }
}

}

Ответы [ 3 ]

2 голосов
/ 07 февраля 2012

Существует систематический способ сделать это в веб-сервисах Java, JAX-WS.Просто примените шаблон перехватчика с помощью SOAP Handler.Класс обработчика будет перехватывать сообщение в методе handleMessage (SOAPMessageContext mc), делать все, что вы хотите, с телом XML конверта SOAP.и остановите SOAPMessage для дальнейшей обработки.

Затем вы можете обрабатывать XML так, как вам нравится (например, отправка с использованием механизмаoplesoft).И когда ответ приходит отoplesoft, обходят цепочку обработчиков исходящих сообщений (мне действительно нужно посмотреть, как обойти цепочку).Я просто воплощаю идею, ты должен сделать POC.Я никогда не делал этого, иначе у меня был бы общий код.Но это абсолютно выполнимо.

1 голос
/ 08 февраля 2012

Когда вы говорите, что вам нужен только XML, вы говорите о сообщении SOAP или просто о типах запроса / ответа?Я не уверен, что вы говорите о втором случае, но если вам нужен только XML, почему бы не использовать JAXB напрямую?

В этом случае вы можете извлечь схемы из WSDL, сгенерировать ваши типы (допустим, у вас есть RequestA и ResponseA для операции "A" в WSDL) и использовать маршаллер / unmarshaller JAXB для сериализации /разбирать XML.Затем отправьте его через протокол, который вы хотите.

1 голос
/ 03 февраля 2012

Одним из решений может быть замена SocketFatory JAX-WS.Примерно это будет выглядеть так:

javax.net.SocketFactory socketFactory = new MySocketFactory();
Service service = Service.create(new URL(wsdl), new QName(namespace, servicename));
Dispatch<SOAPMessage> dispatch = service.createDispatch(methodToBeCalled, SOAPMessage.class, Service.Mode.MESSAGE);
dispatch.getRequestContext().put(com.sun.xml.ws.developer.JAXWSProperties.SSL_SOCKET_FACTORY, socketFactory);
// or ((BindingProvider) Service.getPort(SEIInterface.class)).getRequestContext().put(...);

И в MySocketFactory вы можете создавать сокеты, которые будут передавать сообщение на другой канал.

...