Estou tentando localizar um cliente de serviço da web em meu projeto atual. Não tenho certeza da plataforma do servidor de serviço (provavelmente LAMP). Acredito que haja uma falha do lado deles da cerca, pois eliminei os possíveis problemas com meu cliente. O cliente é um proxy de referência da web do tipo ASMX padrão gerado automaticamente a partir do WSDL de serviço.
O que eu preciso é obter as mensagens RAW SOAP (solicitação e respostas)
Qual é a melhor maneira de fazer isso?
Você pode implementar um SoapExtension que registra a solicitação completa e a resposta em um arquivo de log. Você pode então habilitar o SoapExtension no web.config, o que torna mais fácil ligar / desligar para propósitos de depuração. Aqui está um exemplo que encontrei e modifiquei para meu próprio uso. No meu caso, o registro foi feito por log4net, mas você pode substituir os métodos de registro pelos seus.
Em seguida, você adiciona a seguinte seção ao seu web.config, onde YourNamespace e YourAssembly apontam para a classe e o assembly de seu SoapExtension:
fonte
Não tenho certeza por que tanto barulho com web.config ou uma classe de serializador. O código abaixo funcionou para mim:
fonte
myEnvelope
vem?Experimente o Fiddler2, ele permitirá que você inspecione as solicitações e a resposta. Pode ser importante notar que o Fiddler funciona com tráfego http e https.
fonte
Parece que a solução de Tim Carter não funciona se a chamada para a referência da web lançar uma exceção. Tenho tentado obter a ressonância da web bruta para que possa examiná-la (no código) no manipulador de erros, uma vez que a exceção é lançada. No entanto, estou descobrindo que o log de resposta escrito pelo método de Tim está em branco quando a chamada lança uma exceção. Não entendo completamente o código, mas parece que o método de Tim interrompe o processo após o ponto em que .Net já invalidou e descartou a resposta da web.
Estou trabalhando com um cliente que está desenvolvendo um serviço da web manualmente com codificação de baixo nível. Neste ponto, eles estão adicionando suas próprias mensagens de erro de processo interno como mensagens formatadas em HTML na resposta ANTES da resposta formatada em SOAP. Claro, a referência da web automagic .Net explode com isso. Se eu pudesse obter a resposta HTTP bruta após uma exceção ser lançada, eu poderia procurar e analisar qualquer resposta SOAP dentro da resposta HTTP de retorno mista e saber se eles receberam meus dados corretamente ou não.
Mais tarde ...
Esta é uma solução que funciona, mesmo após uma execução (observe que estou apenas após a resposta - também poderia obter a solicitação):
Veja como configurá-lo no arquivo de configuração:
"TestCallWebService" deve ser substituído pelo nome da biblioteca (que por acaso era o nome do aplicativo de console de teste em que eu estava trabalhando).
Você realmente não deveria ter que ir para ChainStream; você deve ser capaz de fazer isso de forma mais simples a partir do ProcessMessage como:
Se você pesquisar SoapMessage.Stream, é suposto ser um fluxo somente leitura que você pode usar para inspecionar os dados neste ponto. Isso é uma bagunça, porque se você ler o fluxo, o processamento subsequente bombeará sem erros de dados encontrados (o fluxo estava no final) e você não pode redefinir a posição para o início.
Curiosamente, se você fizer os dois métodos, ChainStream e ProcessMessage, o método ProcessMessage funcionará porque você alterou o tipo de fluxo de ConnectStream para MemoryStream em ChainStream, e MemoryStream permite operações de busca. (Tentei transmitir o ConnectStream para MemoryStream - não foi permitido.)
Portanto ... a Microsoft deve permitir operações de busca no tipo ChainStream ou tornar o SoapMessage.Stream realmente uma cópia somente leitura, como deveria ser. (Escreva ao seu congressista, etc ...)
Mais um ponto. Depois de criar uma maneira de recuperar a resposta HTTP bruta após uma exceção, ainda não obtive a resposta completa (conforme determinado por um sniffer HTTP). Isso acontecia porque, quando o serviço da web de desenvolvimento incluía as mensagens de erro HTML no início da resposta, ele não ajustava o cabeçalho Content-Length, portanto, o valor Content-Length era menor que o tamanho do corpo da resposta real. Tudo o que consegui foi o número de caracteres do valor Content-Length - o resto estava faltando. Obviamente, quando .Net lê o fluxo de resposta, ele apenas lê o número de caracteres do Content-Length e não permite que o valor do Content-Length esteja possivelmente errado. É assim que deve ser; mas se o valor do cabeçalho Content-Length estiver errado, a única maneira de obter todo o corpo da resposta é com um sniffer HTTP (eu utilizo o HTTP Analyzer dohttp://www.ieinspector.com ).
fonte
Eu preferiria que a estrutura fizesse o registro para você conectando um fluxo de registro que registra como a estrutura processa esse fluxo subjacente. O seguinte não é tão claro quanto eu gostaria, já que você não pode decidir entre solicitação e resposta no método ChainStream. O seguinte é como eu lido com isso. Com agradecimentos a Jon Hanna por substituir uma ideia de fluxo
fonte
Aqui está uma versão simplificada da resposta principal. Adicione isso ao
<configuration>
elemento do seu arquivoweb.config
ouApp.config
. Isso criará umtrace.log
arquivo nabin/Debug
pasta do seu projeto . Ou você pode especificar um caminho absoluto para o arquivo de log usando oinitializeData
atributo.Avisa que os atributos
maxdatasize
etracemode
não são permitidos, mas aumentam a quantidade de dados que podem ser registrados e evitam registrar tudo em hexadecimal.fonte
Você não especificou qual linguagem está usando, mas presumindo que C # / .NET você poderia usar extensões SOAP .
Caso contrário, use um sniffer como o Wireshark
fonte
Percebi que estou muito atrasado para a festa e, como o idioma não foi especificado, aqui está uma solução VB.NET baseada na resposta de Bimmerbound, caso alguém se depare com isso e precise de uma solução. Nota: você precisa ter uma referência à classe stringbuilder em seu projeto, se ainda não tiver.
Simplesmente chame a função e ela retornará uma string com o xml serializado do objeto que você está tentando passar para o serviço da web (realisticamente, isso deve funcionar para qualquer objeto que você queira lançar nele também).
Como uma observação lateral, a chamada de substituição na função antes de retornar o xml é remover os caracteres vbCrLf da saída. O meu tinha um monte deles no xml gerado, no entanto, isso obviamente irá variar dependendo do que você está tentando serializar, e eu acho que eles podem ser removidos durante o envio do objeto para o serviço da web.
fonte