MashupYourLife.de

Mashups versüßen Dein (online-)Leben!

Amazon-API mit Signatur verwenden

Am Montag um 22:49 von veröffentlicht

Vorwort

Amazon stellt mit seiner API eine Schnittstelle zur Verfügung, mit der man sehr einfach auf alle vorhandenen Artikeldaten zugreifen kann. Diese API wird bevorzugt von Amazon-Partnern verwendet, die von Amazon eine Provision für jeden über sie verkauften Artikel erhalten. So hat jeder was von der API: Amazon und Ihre Partner.

Doch genug der Einführung, worum geht es hier genau?

Amazon hat in den letzten Tagen per E-Mail eine Umbenennung der API bekannt gegeben. Die API lief bisher unter dem Namen "Amazon Associates Web Service" und wird ab jetzt "Product Advertising API" genannt. Dies soll stärker zum Ausdruck bringen, dass diese API zum Bewerben von Amazon-Artikeln dienen soll. Um diesen Zweck noch ein mal Nachdruck zu verleihen, wird auch für die Verwendung der API die Authentifizierung über eine Signatur eingeführt. D.h. ohne einen gültigen Schlüssel ist die Verwendung der API nicht mehr möglich.

Für diese Änderungen gibt es eine Übergangsphase vom 11.05.2009 bis zum 15.08.2009. Ab dem 15.08.2009 sind Daten ohne gültige Signatur über die API nicht mehr abrufbar. Diese Übergangsphase ist insofern wichtig, da alle bisherigen Mashups bzw. Anwendungen, die diese API verwenden angepasst werden müssen. In diesem Tutorial sollen die notwendigen neuen Schritte zum Erhalt der benötigten Daten ein bisschen näher durchleuchtet werden, so dass der Schritt zu einer weiterhin funktionierenden Amazon-Anwendung vereinfacht werden soll. Vorab möchte ich mich bei Ulrich Mierendorff bedanken, der auf seiner Seite eine mögliche Umsetzung des signierten Abrufs von Daten über die Amazon-API in PHP vorstellt. Hier soll das Ganze nochmal auf deutsch ein bisschen genauer beschrieben werden.

Voraussetzungen

  • PHP Grundlagenwissen
  • HTML Grundlagenwissen

Vorbereitungen

Ein bisschen Theorie vorab

Amazon beschreibt in der Dokumentation welche Schritte für einen signierten Aufruf notwendig sind:

  • Ein "kanonisierter", also ein normalisierter Abfrage-String muss erstellt werden. Dieser muss:
    • die Parameter alphabetisch sortiert haben
    • die Parameter und die entsprechenden Werte nach bestimmten Regeln codiert haben
    • die Parameter und die entsprechenden Werte jeweils durch ein Gleichheitszeichen ("=") getrennt haben
    • die Parameter-Wert-Paare durch ein kaufmännisches Und ("&") getrennt haben
  • Dieser Abfrage-String wird in Verbindung mit der Abruf-Methode, des Hosts und der URI zu einem Gesamt-Abfrage-String zusammengesetzt.
  • Dieser Gesamt-Abfrage-String wird mit SHA256 und dem Zugangsschlüssel verschlüsselt.
  • Der verschlüsselte String muss mit Base64 kodiert werden.
  • Das Ergebnis wird als Wert für den Parameter "Signature" an die bisher gewohnt Abruf-URL angehangen.

Das klingt alles sehr theoretisch. Diese Beschreibung hilft aber beim Verständnis des ganzen Vorgehens hier.

Jetzt wird es interessant: Die Praxis

Wie schon erwähnt, hat Ulrich Mierendorff eine sehr schöne Funktion entwickelt, die genau diese gerade beschriebenen Schritte durchführt. Die vollständige Funktion findet Ihr hier. Nachfolgend eine kurze Beschreibung dieser Funktion anhand eines praktischen Beispiel.

Das Beispiel

Wir wollen das Bild und den Titel eines bestimmten Artikels erhalten und ausgeben. In diesem Fall ist uns die ASIN (=Amazon Standard Identification Number) bekannt. Dies ist normalerweise nicht der Fall, aber hier geht es ja primär darum, die Signatur einzusetzen.

Die Umsetzung

Zunächst einmal definieren wir ein paar Variablen:

$method = "GET";
$host = "ecs.amazonaws.de";
$uri = "/onca/xml";
$public_key = "XXXXXX";
$private_key = "YYYYYY";

"XXXXXX" und "YYYYYY" müsst Ihr natürlich mit Euren Zugangsschlüsseln ersetzen. Jetzt werden die Parameter für die Abfrage definiert:

$params["Service"] = "AWSECommerceService";
$params["AWSAccessKeyId"] = $public_key;
// GMT timestamp
$params["Timestamp"] = gmdate("Y-m-d\TH:i:s\Z");
// API version
$params["Version"] = "2009-03-31";
$params["Operation"] = "ItemLookup";
$params["ResponseGroup"] = "Large";
$params["ItemId"] = "3836401126";

Diese Parameter müssen nun sortiert werden:

ksort($params);

Den normalisierten String erhalten wir mit folgender Schleife:

$canonicalized_query = array();
foreach ($params as $param=>$value) {
  $param = str_replace("%7E", "~", rawurlencode($param));
  $value = str_replace("%7E", "~", rawurlencode($value));
  $canonicalized_query[] = $param."=".$value;
}
$canonicalized_query = implode("&", $canonicalized_query);

Der zu verschlüsselnde String wird jetzt zusammengesetzt, verschlüsselt und kodiert:

$string_to_sign = $method."\n".$host."\n".$uri."\n".$canonicalized_query;
$signature = base64_encode(hash_hmac("sha256", $string_to_sign, $private_key, true));
$signature = str_replace("%7E", "~", rawurlencode($signature));

Diese verschlüsselte String wird nun als Parameter an die Abfrage gehangen:

$request = "http://".$host.$uri."?".$canonicalized_query."&Signature=".$signature;

Mit Hilfe dieses String können die Daten nun abgerufen werden:

//XML-Datei abrufen
$xmlItemResult = simplexml_load_file($request);
//Titel abrufen
$myTitle = $xmlItemResult->Items->Item->ItemAttributes->Title;
//Daten zum Bild abrufen
$myImage = $xmlItemResult->Items->Item->MediumImage->URL;

Mit den erhaltenen Daten können wir nun unsere Ausgabe formen:

echo "<img src='".$myImage."' title='".$myTitle."' />";

Was dann so aussehen sollte:

Das vollständige Skript findet Ihr als vorgefertigte Funktion hier.

Vorteile

Amazon will durch den Einsatz einer Signatur die Fremdverwendung der API vermeiden. So sollen die Daten, die über die API abgerufen werden können, wirklich nur für die Bewerbung von Amazon-Artikeln verwendet werden. Dies ist zunächst einmal nur ein Vorteil für Amazon, kann aber als Folge-Effekt dazu führen, dass die API weiterhin kostenlos zur Verfügung gestellt wird.

Nachteile

Durch die Einführung der Signatur für die Verwendung der API ergibt sich das Problem, dass bestimmte Arten von Anwendungen nicht mehr verteilt werden können. So ist es z.B. nicht mehr so einfach möglich ein Open-Source-Script zu entwickeln und zur freien Verwendung freizugeben, da jeder, der er benutzen möchte, noch zusätzlich einen AWS-Account beantragen muss. Eine etwas extremerer Fall ist z.B. die Programmierung einer Extension für Firefox. Da Amazon es nicht erlaubt den Zugangsschlüssel öffentlich bekannt zu machen, ist die Programmierung einer solchen Extension überhaupt nicht mehr möglich, da die Hürden (sich bei AWS anzumelden) für einen "normalen" Endanwender zu hoch sind.

Links

Info-Box:
Kategorie(n): Allgemein
Sonstiges: Trackback, RSS 2.0.

27 Kommentare über “Amazon-API mit Signatur verwenden”

  1. Gravatar von AgentSmith
    AgentSmith schrieb:

    Feinfein, Danke! Heute hab ich erfahren, dass dieses Wochenende an der Uni sogenanntes „Weekend of code“ ist, wo sich lauter Irre drei Tage im Rechnerraum einsperren, um konzentriert an kleinen Projekten zu basteln. Ich bin sehr versucht, hinzugehen und meine Idee umzusetzen. 😉

  2. Gravatar von Chrisostomos
    Chrisostomos schrieb:

    Bleib lieber zuhause uns mach es Dir gemütlich um Deine Idee umzusetzen 😉
    Ne, im Ernst, wenn Du die Idee schon konkret im Kopf hast und Du denkst, in ein paar Tagen was stehen zu haben, dann tu es einfach. Schlimmstenfalls hast Du ein paar Tage an der Amazon API rumgespielt, aber ich bin sicher, dass da was Gutes bei rumkommt!

  3. Gravatar von AgentSmith
    AgentSmith schrieb:

    Du wirst lachen, ich hab grade bemerkt, dass der Part, der mir mehr Sorgen im Vorfeld bereitet hat, sich im Wesentlichen mit _einer_ Zeile Code erledigen lässt. Jetzt fang ich an, am Amazon-Teil zu basteln. Vielleicht hab ich schon morgen (Uni-frei.. harr! 😀 ) eine rudimentäre Testversion der wichtigsten Funktionalität fertig.. du hörst von mir. 😉

  4. Gravatar von fuchzga
    fuchzga schrieb:

    Ich danke ebenso. Schöne Zusammenfassung! Ich glaube ich muss mal wieder meinen AWS-Account rauskramen. 🙂

  5. Gravatar von AgentSmith
    AgentSmith schrieb:

    Arrrr, Weekend of Code is für Anfänger. Die absoluten Grundlagen stehen. Harr. Göttlich. Morgen hab ich frei, wunderbar. *händreib*
    Du bekommst Post. 😉

  6. Gravatar von Chrisostomos
    Chrisostomos schrieb:

    @fuchzga: Gerne! Und immer raus mit dem AWS-Account, schadet ja keinem 😉

    @AgentSmith: Sehr schöne Idee, da werden wir uns den Kuchen wohl teilen müssen 😉

  7. Gravatar von Marco
    Marco schrieb:

    Wirklich schöne Übersicht, danke… Habe bislang noch nicht wahnsinnig viel Erfahrungen mit den Amazon Services gemacht, mir scheint das aber eine wirklich interessante Angelegenheit zu sein, von daher werde ich mich jetzt wohl übers lange Wochenende auch mal eingehender damit beschäftigen. Bin mal gespannt, was man bzw. ich damit alles schönes anfangen kann…

  8. Gravatar von Leon
    Leon schrieb:

    Da muss ich auch erst mal Danke sagen. Werde mir das gleich mal genauer anschauen und mal sehen, ob auch ich wirklich etwas damit anfangen kann.

  9. Gravatar von Amazon Web Services nur noch mit Signatur – Amazon, Signatur, Nutzung, Product, Advertising, Tutorial – Guido Mühlwitz
    Amazon Web Services nur noch mit Signatur - Amazon, Signatur, Nutzung, Product, Advertising, Tutorial - Guido Mühlwitz schrieb:

    […] das Ganze nun wieder aufzuarbeiten, verweise ich auf dieses gute Tutorial zur Nutzung einer geeigneten Signatur für die Kommunikation mit der Product Advertising AP…. Bookmarken bei: Diese Icons verlinken auf Bookmark Dienste bei denen Nutzer neue Inhalte […]

  10. Gravatar von Alexander
    Alexander schrieb:

    🙂 Vielen Dank für die perfekte Aufbereitung! Hat mir ganz viel Arbeit erspart. LG aus Wien, Alexnader

  11. Gravatar von Randy
    Randy schrieb:

    Hat jemand ein Beispiel in Objective-C (fürs iPhone)? Vielen Dank, Randy

  12. Gravatar von Chrisostomos
    Chrisostomos schrieb:

    Ein Beispiel habe ich nicht, aber einen Hinweis 😉
    Die Nutzung der Amazon API auf Mobilgeräten wurde von Amazon vor kurzem eingeschränkt: https://affiliate-program.amazon.com/gp/advertising/api/detail/agreement.html (Punkt 4e).

  13. Gravatar von yves
    yves schrieb:

    Vielen Dank für die gute Erklärung der Benutzung des aws.

    Jetzt hab ich aber ein Problem.

    Die Struktur der xml bekommt man ja auf der Seite:
    http://docs.amazonwebservices.com/AWSEcommerceService/4-0/ApiReference/ItemLookupOperation.html

    damit ist es ja eigentlich kein Problem alle Daten oder Punkte auszulesen, ich bekomm es aber überhaupt nicht hin die Produktbeschreibung auszulesen, aus welchem Grund auch immer.

    Ich spreche z.B. den Title mit:

    $myTitle = $xmlItemResult->Items->Item->ItemAttributes->Title;

    an und versuch es mit der Beschreibung mit:

    $myTitle4 = $xmlItemResult->Items->Item->EditorialReviews->EditorialReview->Content;

    in der ResponseGroup „EditorialReview“.
    Wenn ich die ResponseGroup „Large“ jedoch abänder, bekomm ich nichts mehr ausgegeben.

    Ich hoffe es kann mir jemand helfen.

    danke & gruß
    yves

  14. Gravatar von Daniel
    Daniel schrieb:

    Hallo yves,

    ist der Knoten „EditorialReviews“ in Deinem Ergebnis vorhanden?

    Ich würde versuchen vom Hauptknoten ($xmlItemResult->Items) ausgehend mich durchzuhangeln. Also immer einen Unterknoten dazunehmen und das Ergebnis ausgeben lassen (per print_r()). Dann siehst Du vielleicht auch schon, dass irgendwas im xml fehlt.

    Viel Erfolg!
    Daniel

  15. Gravatar von Rudi
    Rudi schrieb:

    Endlich ne übersichtliche Beschreibung 🙂
    Habe dank dir nen WP Plugin fixen können! Vielen Dank!

  16. Gravatar von Latita
    Latita schrieb:

    Hallo Chrisostomos,

    erst mal vielen Dank für diesen Artikel und den Code 🙂
    Jetzt hab ich noch eine Frage dazu: Ist dir auch schon mal aufgefallen, dass bei einigen Büchern in der Abfrage ein „EditorialReview“ mitgeliefert wird, und bei anderen nicht? Mich würde auch interessieren, wie ich statt an die „ProductDescription“ an die Kurzbeschreibung käme. Aber leider kommt schon ersteres nur sporadisch an.
    In den Parametern hab ich ResponseGroup = Large angegeben. Gibt es da noch mehr Auswahlmöglichkeiten?
    So richtig viele Infos findet man im Netz ja leider nicht 🙁

    Lieben Gruß
    Evelyn

  17. Gravatar von Daniel
    Daniel schrieb:

    Hallo Evelyn,

    stellvertretend für Chrisostomos antworte ich Dir mal 🙂

    Dass die EditorailReview nicht immer auftaucht wird wahrscheinlich daran liegen, dass Amazon nicht zu jedem Buch eine eigen Review geschrieben hat. Du kannst aber davon ausgehen, dass immer alle verfügbaren Informationen geliefert werden, wenn Du immer die gleiche ResponseGroup verwendest.

    Vielleicht hilft Dir diese Übersicht der ResponseGroups weiter: http://docs.amazonwebservices.com/AWSECommerceService/latest/DG/index.html?CHAP_ResponseGroupsList.html

    Viel Erfolg!
    Daniel

  18. Gravatar von artikelunion
    artikelunion schrieb:

    Ich kriege noch Haarausfall. Die Abfrage der Preise funktioniert bei machen Artikeln bzw. Kategorien nicht so wirklich. Oft fehlt der Preis zu allen Artikeln. Habe schon rumprobiert und die ResponceGroup von Medium auf Offers,Medium verändert aber irgendwie will es nicht so recht.

  19. Gravatar von Daniel
    Daniel schrieb:

    Hallo „artikelunion“,

    wenn Du magst kannst Du mal ein paar Beispiele nennen, wo es nicht funktioniert. Dann könnten wir mal schauen, warum die Preise nicht da sind.
    Normalerweise ist die API von Amazon recht zuverlässig.

  20. Gravatar von Ismael
    Ismael schrieb:

    Hi and thanks for making the effort to describe the terminlogy towards the novices!

  21. Gravatar von Xavier
    Xavier schrieb:

    Awesome article, I really enjoy updates from you.

  22. Gravatar von niom
    niom schrieb:

    Wirklich gute Beschreibung, bastel seit einigen Tagen auch schon an einem Skript dazu. Hab nun aber das Problem, dass ich zwar den niedrigsten neuen und den niedrigsten Gebraucht-Preis bekomme. Ich bekomm aber nirgends den Preis, den ich zahlen müsste, wenn ich direkt bei amazon bestell.

    Gut sichtbar bei http://www.amazon.de/gp/product/B005ILK1EG/ref=s9_simh_gw_p63_d3_g63_i1?pf_rd_m=A1IDDPBG1NC5TQ&pf_rd_s=center-2&pf_rd_r=1HKXPNB1E7BK6BQZ3T6B&pf_rd_t=101&pf_rd_p=463375173&pf_rd_i=301128

    Ich bekomm nur:
    Neu: EUR 26,99
    Gebraucht: EUR 20,98

    was ja auch stimmt. Aber ich bekomm nicht den Preis von Amazon, der bei EUR 27,99 liegt.

  23. Gravatar von Daniel
    Daniel schrieb:

    Hallo niom,

    sorry für die sehr späte Antwort!
    Der Kommentar ist leider etwas untergegangen.

    Über die Standard-Schnittstelle ist dieser Preis nicht so einfach abrufbar. Ich müsste jetzt genau gucken, aber ich meine, dass man die Anbieter durchgehen müsste, die eine Artikel anbieten und prüfen, ob es Amazon ist.
    Das ist etwas komplexer weswegen es auch nicht so viele Angebote wie http://www.nomarketplace.com gibt.

  24. Gravatar von Gunnar
    Gunnar schrieb:

    Hallo,

    wird sind auch auf der Suche nach einem funktionierenden abruf der Preise über die ASIN in Massenabfrage über eine CSV Datei.

    Wer mir da helfen kann kann sich gerne melden.
    Derjenige soll es natürlich nicht umsonst machen.
    MFG
    Gunnar

  25. Gravatar von Amazon API: Preis per PHP ausgeben » Technik
    Amazon API: Preis per PHP ausgeben » Technik schrieb:

    […] Nun gibt es glücklicherweise schon ein (oft referenziertes) Script, das zwar aus dem Jahr 2009 stammt und zuletzt Ende Dezember 2012 aktualisiert wurde, dieses tut aber immer noch seinen Dienst und diente mir als Grundlage. Zu finden ist das Script unter: http://www.ulrichmierendorff.com/software/aws_hmac_signer.html. Eine kurze Erläuterung gibt es hier. […]

  26. Gravatar von Amazon API: Preis per PHP auslesen » Technik
    Amazon API: Preis per PHP auslesen » Technik schrieb:

    […] Nun gibt es glücklicherweise schon ein (oft referenziertes) Script, das zwar aus dem Jahr 2009 stammt und zuletzt Ende Dezember 2012 aktualisiert wurde, dieses tut aber immer noch seinen Dienst und diente mir als Grundlage. Zu finden ist das Script unter: http://www.ulrichmierendorff.com/software/aws_hmac_signer.html. Eine kurze Erläuterung gibt es hier. […]

  27. Gravatar von evgens
    evgens schrieb:

    nicen unden postenerun

Kommentar schreiben