2012-02-25 3 views
2

Я провел целый день, пытаясь исправить проблемы с API-интерфейсом Amazon ECS (Ecommerce Services).API рекламы продукта Amazon ItemSearch Возвращает нуль

Я скачал пример на их сайте для отправки SOAP-запросов с .NET 4.0 и WCF

http://aws.amazon.com/code/Product-Advertising-API/3941

Я ничего не изменил в коде из примера, для AccessKeyID и SecretyKeyID в исключении файл конфигурации.

код Призвание выглядит следующим образом:

 // Instantiate Amazon ProductAdvertisingAPI client 
     AWSECommerceServicePortTypeClient amazonClient = new AWSECommerceServicePortTypeClient(); 

     // prepare an ItemSearch request 
     ItemSearchRequest request = new ItemSearchRequest(); 
     request.SearchIndex = "Books"; 
     request.Title = "WCF"; 
     request.ResponseGroup = new string[] { "Medium"}; 

     ItemSearch itemSearch = new ItemSearch(); 
     itemSearch.Request = new ItemSearchRequest[] { request }; 
     request.Condition = Condition.All; 
     itemSearch.AssociateTag = ""; 
     itemSearch.AWSAccessKeyId = ConfigurationManager.AppSettings["accessKeyId"]; 

     // send the ItemSearch request 
     ItemSearchResponse response = amazonClient.ItemSearch(itemSearch); 
     if (response != null) 
     { 
      // write out the results from the ItemSearch request 
      foreach (var item in response.Items[0].Item) 
      { 
       Console.WriteLine(item.ItemAttributes.Title); 
      } 
     } 
     Console.WriteLine("done...enter any key to continue>"); 
     Console.ReadLine(); 

Зов к ItemSearch() возвращает нулевой объект. Я посмотрел дальше и увидел, что в классе AmazongSigningMessageInspector метод AfterReceiveReply() показывает, что правильный результат ответа SOAP XML возвращается с результатами, поэтому я знаю, что он выполняет вызов службы и правильно возвращается. По какой-то причине, хотя я остался с объектом NULL ItemSearch.

Код для моих классов являются следующим:

class AmazonSigningBehaviorExtensionElement : BehaviorExtensionElement 
{ 
    public AmazonSigningBehaviorExtensionElement() 
    { 
    } 

    public override Type BehaviorType 
    { 
     get 
     { 
      return typeof(AmazonSigningEndpointBehavior); 
     } 
    } 

    protected override object CreateBehavior() 
    { 
     return new AmazonSigningEndpointBehavior(AccessKeyId, SecretKey); 
    } 

    [ConfigurationProperty("accessKeyId", IsRequired = true)] 
    public string AccessKeyId 
    { 
     get { return (string)base["accessKeyId"]; } 
     set { base["accessKeyId"] = value; } 
    } 

    [ConfigurationProperty("secretKey", IsRequired = true)] 
    public string SecretKey 
    { 
     get { return (string)base["secretKey"]; } 
     set { base["secretKey"] = value; } 
    } 
} 


public class AmazonSigningEndpointBehavior : IEndpointBehavior { 
    private string _accessKeyId = ""; 
    private string _secretKey = ""; 

    public AmazonSigningEndpointBehavior() 
    { 
     this._accessKeyId = ConfigurationManager.AppSettings["accessKeyId"]; 
     this._secretKey = ConfigurationManager.AppSettings["secretKey"]; 
    } 

    public AmazonSigningEndpointBehavior(string accessKeyId, string secretKey) { 
     this._accessKeyId = accessKeyId; 
     this._secretKey  = secretKey; 
    } 

    public void ApplyClientBehavior(ServiceEndpoint serviceEndpoint, ClientRuntime clientRuntime) { 
     clientRuntime.MessageInspectors.Add(new AmazonSigningMessageInspector(_accessKeyId, _secretKey)); 
    } 

    public void ApplyDispatchBehavior(ServiceEndpoint serviceEndpoint, EndpointDispatcher endpointDispatcher) { return; } 
    public void Validate(ServiceEndpoint serviceEndpoint) { return; } 
    public void AddBindingParameters(ServiceEndpoint serviceEndpoint, BindingParameterCollection bindingParameters) { return; } 
} 

public class AmazonSigningMessageInspector : IClientMessageInspector { 
    private string _accessKeyId = ""; 
    private string _secretKey = ""; 

    public AmazonSigningMessageInspector(string accessKeyId, string secretKey) { 
     this._accessKeyId = accessKeyId; 
     this._secretKey  = secretKey; 
    } 

    public object BeforeSendRequest(ref Message request, IClientChannel channel) { 
     // prepare the data to sign 
     string  operation  = Regex.Match(request.Headers.Action, "[^/]+$").ToString(); 
     DateTime now    = DateTime.UtcNow; 
     string  timestamp  = now.ToString("yyyy-MM-ddTHH:mm:ssZ"); 
     string  signMe   = operation + timestamp; 
     byte[]  bytesToSign  = Encoding.UTF8.GetBytes(signMe); 

     // sign the data 
     byte[]  secretKeyBytes = Encoding.UTF8.GetBytes(_secretKey); 
     HMAC  hmacSha256  = new HMACSHA256(secretKeyBytes); 
     byte[]  hashBytes  = hmacSha256.ComputeHash(bytesToSign); 
     string  signature  = Convert.ToBase64String(hashBytes); 

     // add the signature information to the request headers 
     request.Headers.Add(new AmazonHeader("AWSAccessKeyId", _accessKeyId)); 
     request.Headers.Add(new AmazonHeader("Timestamp", timestamp)); 
     request.Headers.Add(new AmazonHeader("Signature", signature)); 

     return null; 
    } 

    public void AfterReceiveReply(ref Message reply, object correlationState) 
    { 


    } 
} 

Я видел эту проблему во всем мире, но никто не разместил исправление для него в любом месте. Кто-нибудь, пожалуйста, помогите мне с этим.

+0

У меня точно такой же вопрос из того же примера проекта. Поиск решения привел меня сюда. Я установил itemSearch.AssociateTag перед вызовом ItemSearch ... Я также вижу правильные результаты как в Fiddler, так и в AfterReceiveReply. Когда я включаю Debug-> Exceptions, я получаю FileNotFoundException для AmazonSOAP.XmlSerializers. Прошли ли вы по этому поводу? –

+0

У меня такая же проблема, сообщите нам, когда получите решение – ikbal

ответ

4

Моя проблема заключалась в том, что мне не хватает связанного тега.

itemSearch.AssociateTag = "213";

Есть определенно проблемы с сгенерированным кодом, ItemSearchResponse содержит коллекцию об ошибке, которая не подвергается кодом. Это было через просмотр необработанного сообщения в инспекторе, который указал мне в правильном направлении.

+1

У Amazon есть умение создавать ужасные API ... если кто-то также использовал эту библиотеку: http://flyingpies.wordpress.com/2009/08/ 13/signature-amazon-product-advertising-api-cwcf-part-2/помимо добавления ассоциированного тега вам также потребуется изменить WSDL - https://forums.aws.amazon.com/thread.jspa?threadID = 72429 – kape123

2

Ответ на отсутствующий ассоциированный тег поможет мне, но я также должен был убедиться, что URL-адрес WSDL и адрес конечной точки соответствуют сайту Amazon, который вы зарегистрировали. Я зарегистрировался на сайте Великобритании, поэтому мне нужно использовать.

WSDL
Endpoint Address

0

Текущий проект к этому заданию вы можете найти здесь: Nager.AmazonProductAdvertising github. Библиотека также доступна по nuget

NuGet

PM> Install-Package Nager.AmazonProductAdvertising 

Пример

var authentication = new AmazonAuthentication(); 
authentication.AccessKey = "accesskey"; 
authentication.SecretKey = "secretkey"; 

var wrapper = new AmazonWrapper(authentication, AmazonEndpoint.US); 
var result = wrapper.Search("canon eos", AmazonSearchIndex.Electronics, AmazonResponseGroup.Large);