клиент gsoap2.8 и служба wcf()

У меня проблема с вызовом C++ клиента gsoap для моей простой службы wcf, которая выставляет:

public double Add(double n1, double n2) {
    double result = n1 + n2;
    return result;
}

Ниже приведен тестовый код моего клиента gsoap:

BasicHttpBinding_USCORERestaurantService svc;
_ns1__Add         request;
_ns1__AddResponse response;

//svc->endpoint
double n1 = 1.12;
double n2 = 2.32;

request.n1 =&n1;
request.n2= &n2;
svc.soap->keep_alive=1;
int iResult = svc.__ns1__Add(&request, &response); // response result always return 0

У меня точка останова на сервисе, параметр для n1,n2 всегда 0;

Ниже мой файл wsdl:

<?xml version="1.0" encoding="utf-8" ?> 
 <wsdl:definitions name="RestaurantService" targetNamespace="http://www.thinktecture.com/services/restaurant/2006/12" xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/" xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/" xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap12="http://schemas.xmlsoap.org/wsdl/soap12/" xmlns:tns="http://www.thinktecture.com/services/restaurant/2006/12" xmlns:wsa="http://schemas.xmlsoap.org/ws/2004/08/addressing" xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy" xmlns:wsap="http://schemas.xmlsoap.org/ws/2004/08/addressing/policy" xmlns:wsaw="http://www.w3.org/2006/05/addressing/wsdl" xmlns:msc="http://schemas.microsoft.com/ws/2005/12/wsdl/contract" xmlns:wsa10="http://www.w3.org/2005/08/addressing" xmlns:wsx="http://schemas.xmlsoap.org/ws/2004/09/mex" xmlns:wsam="http://www.w3.org/2007/05/addressing/metadata">
 <wsdl:types>
 <xsd:schema elementFormDefault="qualified" targetNamespace="http://www.thinktecture.com/services/restaurant/2006/12">
 <xsd:element name="Add">
 <xsd:complexType>
 <xsd:sequence>
  <xsd:element minOccurs="0" name="n1" type="xsd:double" /> 
  <xsd:element minOccurs="0" name="n2" type="xsd:double" /> 
  </xsd:sequence>
  </xsd:complexType>
  </xsd:element>
 <xsd:element name="AddResponse">
 <xsd:complexType>
 <xsd:sequence>
  <xsd:element minOccurs="0" name="AddResult" type="xsd:double" /> 
  </xsd:sequence>
  </xsd:complexType>
  </xsd:element>
  </xsd:schema>
  </wsdl:types>
 <wsdl:message name="RestaurantService_Add_InputMessage">
  <wsdl:part name="parameters" element="tns:Add" /> 
  </wsdl:message>
 <wsdl:message name="RestaurantService_Add_OutputMessage">
  <wsdl:part name="parameters" element="tns:AddResponse" /> 
  </wsdl:message>
 <wsdl:portType name="RestaurantService">
 <wsdl:operation name="Add">
  <wsdl:input wsaw:Action="http://www.thinktecture.com/services/restaurant/2006/12/RestaurantService/Add" message="tns:RestaurantService_Add_InputMessage" /> 
  <wsdl:output wsaw:Action="http://www.thinktecture.com/services/restaurant/2006/12/RestaurantService/AddResponse" message="tns:RestaurantService_Add_OutputMessage" /> 
  </wsdl:operation>
  </wsdl:portType>
 <wsdl:binding name="BasicHttpBinding_RestaurantService" type="tns:RestaurantService">
  <soap:binding transport="http://schemas.xmlsoap.org/soap/http" /> 
 <wsdl:operation name="Add">
  <soap:operation soapAction="http://www.thinktecture.com/services/restaurant/2006/12/RestaurantService/Add" style="document" /> 
 <wsdl:input>
  <soap:body use="literal" /> 
  </wsdl:input>
 <wsdl:output>
  <soap:body use="literal" /> 
  </wsdl:output>
  </wsdl:operation>
  </wsdl:binding>
 <wsdl:service name="RestaurantService">
 <wsdl:port name="BasicHttpBinding_RestaurantService" binding="tns:BasicHttpBinding_RestaurantService">
  <soap:address location="http://localhost:3456/WebHost/Service.svc/RS" /> 
  </wsdl:port>
  </wsdl:service>
  </wsdl:definitions>

Ниже мыльное сообщение о том, что я включил ведение журнала:

call from gsoap c++ client
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:ns1="http://www.thinktecture.com/services/restaurant/2006/12">
<s:Header xmlns:s="http://schemas.xmlsoap.org/soap/envelope/">
<To s:mustUnderstand="1" xmlns="http://schemas.microsoft.com/ws/2005/05/addressing/none">http://localhost:3456/WebHost/Service.svc/RS</To>
<Action s:mustUnderstand="1" xmlns="http://schemas.microsoft.com/ws/2005/05/addressing/none">http://www.thinktecture.com/services/restaurant/2006/12/RestaurantService/Add</Action>
</s:Header>
<SOAP-ENV:Body>
<ns1:Add>
<n1 xsi:type="xsd:double" xmlns="">1.1200000000000001</n1>
<n2 xsi:type="xsd:double" xmlns="">2.3199999999999998</n2>
</ns1:Add>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>

ответное сообщение от сервиса:

<s:Envelope xmlns:s="http://schemas.xmlsoap.org/soap/envelope/">
<s:Header>
<ActivityId CorrelationId="ac83c5fa-e518-4883-a381-f5ec63411226" xmlns="http://schemas.microsoft.com/2004/09/ServiceModel/Diagnostics">dddc227b-82e3-4578-b282-572017003943</ActivityId>
</s:Header>
<s:Body>
<AddResponse xmlns="http://www.thinktecture.com/services/restaurant/2006/12">
<AddResult>0</AddResult>
</AddResponse>
</s:Body>
</s:Envelope>

person John H    schedule 20.12.2012    source источник
comment
У меня есть подозрение, что это связано с пространствами имен. Попробуйте удалить «xmlns=» для n1 и n2 в запросе (например, перехватите и измените запрос с помощью Fiddler) и посмотрите, изменится ли что-нибудь.   -  person Eugene Osovetsky    schedule 21.12.2012
comment
Спасибо Евгений за помощь. Мне удалось сравнить сообщение заголовка мыла для 2.7 и 2.8: ниже заголовка soap2.8: ‹SOAP-ENV:Body› ‹ns1:Add› ‹n1 xmlns=›1.1200000000000001‹/n1› ‹n2 xmlns=›2.3199999999999998‹/n2 › ‹/ns1:Add› ‹/SOAP-ENV:Body› ниже находится заголовок soap2.7: ‹SOAP-ENV:Body› ‹ns1:Add› ‹ns1:n1›13.18‹/ns1:n1› ‹ns1:n2 ›24.359999999999999‹/ns1:n2› ‹/ns1:Add› ‹/SOAP-ENV:Body› ‹/SOAP-ENV:Envelope›   -  person John H    schedule 27.12.2012
comment
разница составляет ‹ns1:n1› против ‹n2 xmlns=›. Как изменить wsdl, чтобы тело мыла изменилось с ‹n2 xmlns=› на ‹ns1:n1›?   -  person John H    schedule 27.12.2012


Ответы (2)


У меня такая же проблема, когда служба WCF всегда возвращает 0 по запросу Add (int n1, int n2). После долгой работы я нашел решение, мой обходной путь - применить gSoap 2.7.16 вместо последнего 2.8.1_2, он работает безупречно.

person dzzunga    schedule 25.12.2012
comment
Большое спасибо... Вы спасли мой день... Это работает после того, как я изменил gSoap-2.7.16. Еще раз спасибо. - person John H; 26.12.2012
comment
Здорово. Спасибо Тимил. Используя ваш XmlSerializerFormat(...) Я вернулся к gSOAP версии 2.8.12_2 без проблем, RPC мне подходит. - person dzzunga; 27.12.2012

после нескольких часов работы я исправил эту вещь, если вы используете WCF, вам нужно добавить атрибут в свою операцию, например:

[ServiceContract]
    public interface IMyService
    {
        [OperationContract]
        [XmlSerializerFormat(Style = OperationFormatStyle.Rpc, Use = OperationFormatUse.Literal)]
        long Method1(int a, int b, long c, string d);
     }

поэтому gsoap может правильно отправить значение аргумента на сервер.

person timiil    schedule 27.12.2012