C# Sabre Web服务-属性描述服务身份验证错误-ERR.SWS.CLIENT.VALIDATION\u失败
我正在尝试使用C#调用HotelPropertyDescriptionLLSRQ Sabre Web服务。我已经让其他API使用类似的代码,但我一直得到相同的客户端验证失败错误,即使在检索有效的安全令牌之后也是如此 我想我在代理模型中遗漏了一些小部分,如下所示 搜索条件对象:C# Sabre Web服务-属性描述服务身份验证错误-ERR.SWS.CLIENT.VALIDATION\u失败,c#,.net,web-services,soap-client,sabre,C#,.net,Web Services,Soap Client,Sabre,我正在尝试使用C#调用HotelPropertyDescriptionLLSRQ Sabre Web服务。我已经让其他API使用类似的代码,但我一直得到相同的客户端验证失败错误,即使在检索有效的安全令牌之后也是如此 我想我在代理模型中遗漏了一些小部分,如下所示 搜索条件对象: HotelSearchCriteria searchCriteria = new HotelSearchCriteria { hotelCode = "1191",
HotelSearchCriteria searchCriteria = new HotelSearchCriteria
{
hotelCode = "1191",
inDate = "8-22",
outDate = "8-25"
};
然后是代理类:
public class HotelPropertyDescriptionReq
{
private HotelPropertyDescriptionService service;
private HotelPropertyDescriptionRQ req;
public HotelPropertyDescriptionRS response;
public string xmlResponse;
public bool searchPerformed = false;
public HotelPropertyDescriptionReq()
{
//parameterless constructor for serialization
}
public HotelPropertyDescriptionReq(SessionToken token, HotelSearchCriteria searchCriteria)
{
//argument validation - must have a location of some sort and some dates for search to work. Throw exception here if none found
if (searchCriteria.hotelCode == null && searchCriteria.cityCode == null)
{
//no search can take place if this is null...send back an empty response with searchPerformed == fals
throw new ArgumentException("Cannot search hotel availability without hotelCode or cityCode");
}
else if (searchCriteria.inDate == null || searchCriteria.outDate == null)
{
throw new ArgumentException("Cannot serach hotel availability without inDate and outDate");
}
//MessageHeader
MessageHeader mHeader = new MessageHeader();
PartyId[] pId = { new PartyId() };
pId[0].Value = "SWS";
From from = new From();
from.PartyId = pId;
To to = new To();
to.PartyId = pId;
mHeader.Action = "HotelPropertyDescriptionLLSRQ";
mHeader.version = "2.3.0";
mHeader.Service = new Service()
{
Value = mHeader.Action
};
mHeader.ConversationId = token.conversationID;
mHeader.CPAId = token.ipcc;
mHeader.From = from;
mHeader.To = to;
mHeader.MessageData = new MessageData()
{
Timestamp = DateTime.UtcNow.ToString(),
};
//Security
//Security sec = new Security();
Security1 sec = new Security1();
sec.BinarySecurityToken = token.securityToken;
//Service
service = new HotelPropertyDescriptionService();
service.MessageHeaderValue = mHeader;
//service.SoapVersion = System.Web.Services.Protocols.SoapProtocolVersion.Soap11;
service.Security = sec;
//request
req = new HotelPropertyDescriptionRQ();
req.AvailRequestSegment = new HotelPropertyDescriptionRQAvailRequestSegment();
req.AvailRequestSegment.GuestCounts = new HotelPropertyDescriptionRQAvailRequestSegmentGuestCounts();
req.AvailRequestSegment.GuestCounts.Count = "1";
req.AvailRequestSegment.HotelSearchCriteria = new HotelPropertyDescriptionRQAvailRequestSegmentHotelSearchCriteria();
req.AvailRequestSegment.HotelSearchCriteria.Criterion = new HotelPropertyDescriptionRQAvailRequestSegmentHotelSearchCriteriaCriterion();
req.AvailRequestSegment.HotelSearchCriteria.Criterion.HotelRef = new HotelPropertyDescriptionRQAvailRequestSegmentHotelSearchCriteriaCriterionHotelRef();
req.AvailRequestSegment.HotelSearchCriteria.Criterion.HotelRef.HotelCode = searchCriteria.hotelCode;
req.AvailRequestSegment.TimeSpan = new HotelPropertyDescriptionRQAvailRequestSegmentTimeSpan();
req.AvailRequestSegment.TimeSpan.Start = searchCriteria.inDate;
req.AvailRequestSegment.TimeSpan.End = searchCriteria.outDate;
string requestXML = Serializer.toXML(req);
string headerXML = Serializer.toXML(mHeader);
//send the request
try
{
response = service.HotelPropertyDescriptionRQ(req);
searchPerformed = true;
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
throw;
}
}
}
这是一个工作请求-您的负载与您创建的负载看起来有点不同。只需尝试复制这一点-需要设置PCC和SecurityRedentials:
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:eb="http://www.ebxml.org/namespaces/messageHeader" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:xsd="http://www.w3.org/1999/XMLSchema">
<SOAP-ENV:Header>
<eb:MessageHeader SOAP-ENV:mustUnderstand="1" eb:version="2.0">
<eb:From>
<eb:PartyId type="urn:x12.org:IO5:01">1212</eb:PartyId>
</eb:From>
<eb:To>
<eb:PartyId type="urn:x12.org:IO5:01">2323</eb:PartyId>
</eb:To>
<eb:CPAId>YOURPCCHERE</eb:CPAId>
<eb:ConversationId>XXX-dd74-4500-99d6-1e746b8876cc1507217090989</eb:ConversationId>
<eb:Service eb:type="OTA">HotelPropertyDescriptionLLSRQ</eb:Service>
<eb:Action>HotelPropertyDescriptionLLSRQ</eb:Action>
<eb:MessageData>
<eb:MessageId>1001</eb:MessageId>
<eb:Timestamp>2016-06-07T10:00:01</eb:Timestamp>
<eb:TimeToLive>2017-06-06T23:59:59</eb:TimeToLive>
</eb:MessageData>
</eb:MessageHeader>
<wsse:Security xmlns:wsse="http://schemas.xmlsoap.org/ws/2002/12/secext" xmlns:wsu="http://schemas.xmlsoap.org/ws/2002/12/utility">
<wsse:BinarySecurityToken EncodingType="wsse:Base64Binary" valueType="String">YOURSECRETHERE</wsse:BinarySecurityToken>
</wsse:Security>
</SOAP-ENV:Header>
<SOAP-ENV:Body>
<HotelPropertyDescriptionRQ xmlns="http://webservices.sabre.com/sabreXML/2011/10" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" ReturnHostCommand="false" TimeStamp="2015-11-30T12:00:00-06:10" Version="2.3.0">
<AvailRequestSegment>
<GuestCounts Count="1"/>
<HotelSearchCriteria>
<Criterion>
<HotelRef HotelCode="0022426" UnitOfMeasure="KM"/>
</Criterion>
</HotelSearchCriteria>
<POS>
<Source>
<CompanyName Division="BER"/>
</Source>
</POS>
<TimeSpan End="04-24" Start="04-22" />
</AvailRequestSegment>
</HotelPropertyDescriptionRQ>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>
1212
2323
你在这儿吗
XXX-dd74-4500-99d6-1e746b8876cc1507217090989
HotelPropertyDescriptionLLSRQ酒店
HotelPropertyDescriptionLLSRQ酒店
1001
2016-06-07T10:00:01
2017-06-06T23:59:59
你的秘密
您能否发布生成的Soap请求?从那里调试更有意义。我使用Pastebin在线抛出XML,因为它不适合注释-如果这不是提供它的最有用的方式,请告诉我。谢谢大家的意见!我不知道你的请求中的“-”是从哪里来的,但他们肯定会去的。整体看起来有点畸形。将添加一个工作请求。这很好-感谢您的回复。我认为破折号是我从VS复制/粘贴的方式产生的工件。我重新处理了一些请求,并将元素添加到请求的POS级别,现在似乎正在返回结果。文档确实将POS和Source列为必填项,但我完全不知道CompanyName和部门成员指的是什么,因为我不知道对应的Sabre host命令。Sabre示例有效载荷没有在请求中包含任何POS级别的信息,这让我非常困惑。是的,Sabre文档没有那么好-对于部门,您应该使用“代理”/“票务合作伙伴”的城市代码,在我们的案例中,BerlinThanks的BER获取该信息。这些节点被列为必填项,但它们在当前文档中列出的示例有效载荷中没有一个包含它()。令人沮丧。欢迎使用sabre webservices进行开发/集成任何GDS;)