Conteúdo de Content-Type em retorno de WebService

6 respostas
G

Prezados,

Tenho um webservice que está publicado com o JBOSS em dois servidores chamados desenv e homolog.
No servidor desenv, as requisições feitas através de dois programas cliente (um em Java e outro em C#) e do SoapUI funcionam perfeitamente.
Já no servidor homolog, ocorre um erro ao executar as requisições pela segunda vez em diante.

Após algumas verificações pude constatar que no servidor desenv o cabeçalho da resposta vem sempre como “text/xml” e o resultado é exibido corretamente. No servidor homolog e cabeçalho retorna “text/xml” na primeira execução e “text/plain” nas demais.

No SoapUI é possível desmarcar a opção “Accept compressed responses from hosts”, que faz com que as respostas das requisições ao servidor homolog passem a vir sempre corretamente.

Estou na dúvida sobre como fazer com que os clientes em java e c# passem a aceitar respostas com compressão assim como o SoapUI ou então fazer com que o servidor responda sempre com o Content-Type = “text/xml”.

Alguém sabe qual é a melhor opção e como faze-lo?

Obrigado!

6 Respostas

Alexandre_Saudate

Bom, a melhor solução, neste caso, seria você verificar porque os ambientes de dev e homologação estão diferentes (já que isso pode trazer outras divergências, que você e sua equipe podem nem ter notado, ainda). De qualquer maneira, tem um work around pra isso; faz o seguinte:

  1. Anote a sua classe com a anotação @HandlerChain:
package com.alesaudate.webservices;

@WebService
@HandlerChain(file="handlers.xml") //Aqui, você referencia um arquivo de configuração. Neste caso, ele precisa estar no mesmo pacote que a classe
public class MyService {

//...


}
  1. Crie um arquivo de configuração, mais ou menos assim:
<?xml version="1.0" encoding="UTF-8"?>
<jws:handler-chains xmlns:jws="http://java.sun.com/xml/ns/javaee">

  <jws:handler-chain>
    <jws:handler>
      <jws:handler-name>MimeHandler</jws:handler-name>
      <jws:handler-class>com.alesaudate.webservices.MimeTypeHandler</jws:handler-class>      
    </jws:handler>
</jws:handler-chain>
  
</jws:handler-chains>
  1. Crie um interceptor para a classe:
package com.alesaudate.webservices;

import java.util.Set;

import javax.xml.namespace.QName;
import javax.xml.soap.SOAPException;
import javax.xml.soap.SOAPMessage;
import javax.xml.ws.handler.MessageContext;
import javax.xml.ws.handler.soap.SOAPHandler;
import javax.xml.ws.handler.soap.SOAPMessageContext;

public class MimeTypeHandler implements SOAPHandler<SOAPMessageContext>{

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

	public void close(MessageContext context) {
		
	}

	public boolean handleFault(SOAPMessageContext context) {
		return true;
	}

	public boolean handleMessage(SOAPMessageContext context) {
		try {
                                          context.getMessage().getMimeHeaders().setHeader("Content-Type", "text/xml");
		} catch (SOAPException e) {
			throw new RuntimeException(e);
		}
		return true;
	}
	

}

Depois de colocar isso, suas mensagens devem passar pelo método handleMessage para setar o content type, OK?

[]´s

G

Ainda não tentei aplicar o workaround do asaudate porque a coisa mudou um pouco de figura nesse momento.

Descobri que utilizando o cliente java eu preciso importar todos os jars do CXF (que foi usado na criação do webservice) para que a leitura da resposta seja feita corretamente.

Teoricamente o problema está somente no cliente em c#/.net, que não possui uma biblioteca CXF para fazer essa tradução da resposta. Utilizando o método tradicional de acessar webservices no .net persiste a mensagem de erro no content-type text/plain quando o esperado era text/xml.

Alguma idéia?

Acredito que simplesmente converter os .jar do CXF para .dll não funcionaria…

G

asaudate, como faço com que as mensagens passem pelo handleMessage da classe MimeTypeHandler?

Alexandre_Saudate

Colocando os arquivos que citei no seu projeto! Coloque o arquivo handlers.xml no mesmo diretório do seu webservice e veja o que acontece.

[]´s

G

Ah sim, fiz exatamente isso que você indicou. O método handleMessage foi acionado e o Content ficou como “text/xml”, mas mesmo assim, na chamada por um cliente continua vindo “text/plain”.
Na verdade é sempre na segunda requisição. A primeira vem como “text/xml” e os clientes conseguem ler. A segunda vem “text/plain”, ai só consigo fazer a consulta novamente se atualizar o wsdl.

Obrigado!

Alexandre_Saudate

gabriel_prn:
Ah sim, fiz exatamente isso que você indicou. O método handleMessage foi acionado e o Content ficou como “text/xml”, mas mesmo assim, na chamada por um cliente continua vindo “text/plain”.
Na verdade é sempre na segunda requisição. A primeira vem como “text/xml” e os clientes conseguem ler. A segunda vem “text/plain”, ai só consigo fazer a consulta novamente se atualizar o wsdl.

Obrigado!

Tente limpar os headers (no método handleMessage, mesmo) e tente de novo. Se mesmo assim você não conseguir, quer dizer que isso é resultado de alguma feature bem específica do seu ambiente e, nesse caso, só checando o ambiente pra saber o que acontece.

[]´s

Criado 3 de novembro de 2010
Ultima resposta 11 de nov. de 2010
Respostas 6
Participantes 2