頑張らない!でも諦めない!必死にならずにええかげん

APIのリクエスト要求に署名を付加する手順(Amazonアソシエイト)

AmazonアソシエイトAPI(Amazon Product Advertising API)で商品情報を取得するには、
要求するURLにタイムスタンプと署名キーを付加する必要があります。
この署名ステップがおそらくやり始めのころには大きな障壁になる事と思います。
ここでは詳しく解説されている公式ヘルプのリンクを交えてご紹介します。

APIのリクエスト要求に署名を付加する手順(Amazonアソシエイト)

公式のヘルプでは以下のように処理ステップが説明されています。

サンプルリクエストに署名を行うためのステップ|アソシエイト・セントラル – ヘルプ

(Evernote)https://www.evernote.com/shard/s380/u/0/sh/3963feb0-55ba-43a8-918a-78ee2b6ce617/4f01deab684aac501e5e1451bd1dca56

 

各ステップはこのような順番として書かれています。

1. タイムスタンプを挿入します。以下の例では、GMT 2009-01-01T12:00:00Z を使用しています。

http://webservices.amazon.com/onca/xml?Service=AWSECommerceServic e&AWSAccessKeyId=00000000000000000000&Operation=ItemLookup&ItemId =0679722769&ResponseGroup=ItemAttributes,Offers,Images,Reviews&Ve rsion=2009-01-06&Timestamp=2009-01-01T12:00:00Z

まず、タイムスタンプはGMT(UTC±0)を利用して現在日時を生成し、
「YYYY-MM-DDThh:mm:ssZ」の形式にすればいい事がわかります。

※赤文字は固定で詳細は「ISO 8601|wikipedia」を参照の事。

これによれば、例えばPHPなどでデフォルトタイムゾーンを日本(Asia/Tokyo)としていて、
タイムゾーンをUTCに換算するのが面倒なら、以下が役に立つと考えられます。

協定世界時は、歴史的な理由から特定の分野で同義語として扱われるいくつかの用語が存在する。

GMT と Z は、航法や通信の分野で UTC と同義語として認められる[10][11]。子午線を1時間ごとの時刻差で英字一文字に対応させて東経を正数、西経を負数で表記すると、15=A、30=B、45=C、60=D、75=E、90=F、105=G、120=H、135=I、150=K、165=L、180=M、-15=N、-30=O、-45=P、-60=Q、-75=R、-90=S、-105=T、-120=U、-135=V、-150=W、-165=X、-180=Y、0=Z となる[12]。本初子午線を中心とする時間帯は Z で表され、通信で通話表の文字 Z に使用する語は Zulu であることから[13]「UTC」を「Z時」や “Zulu time” と表すことがある。

(抜粋引用)ISO 8601|wikipedia

日本の経度は、およそ東経123度から東経154度のあいだにあり、
東経135度が日本標準時子午線(明石)なので、「整数の135」が該当する。

よって「135=I」を末尾に付ければよい事になります。
これで日本時間を利用して、APIのリクエストをすることができるようになります。

2. リクエスト内のコンマ (,) およびコロン (;) をURLエンコードし、誤った処理が行われないようにします。RFC 3986 への変換に関する詳細な情報については、ご利用のプログラム言語のコードサンプルやドキュメントをご参照ください。

http://webservices.amazon.com/onca/xml?Service=AWSECommerceService&AWSAccessKeyId=00000000000000000000&Operation=ItemLookup&ItemId=0679722769&ResponseGroup=ItemAttributes%2COffers%2CImages%2CReviews&Version=2009-01-06&Timestamp=2009-01-01T12%3A00%3A00Z

次に、リクエストを行うパラメータの中に「,」や「;」のURLエンコードを行う。

通常は「変数名=値」の1ペアであることが多いはずですが、
よく出てくるパターンとしてサンプルにもある「ResponseGroup=ItemAttributes,Offers,Images,Reviews」と、
カンマ区切りで複数値を指定できるパラメータがあるので、
そのような場合には適切にエンコードをする必要がある。

またタイムスタンプの時刻区切り「:」もエンコードする必要があるので、
エンコードが不要なURLパターンはないことになりますので、この作業も必須です。

3. パラメータと値のペアをそれぞれ分割し、アンドマーク(&)を削除して、以下のような形状にします:

Service=AWSECommerceService AWSAccessKeyId=00000000000000000000 Operation=ItemLookup ItemId=0679722769 ResponseGroup=ItemAttributes%2COffers%2CImages%2CReviews Version=2009-01-06 Timestamp=2009-01-01T12%3A00%3A00Z

4. パラメータと値のペアをバイト順(アルファベット順とは異なり、大文字のパラメータは小文字のパラメータの前に並ぶ形式です)に並べ替えます。

AWSAccessKeyId=00000000000000000000 ItemId=0679722769 Operation=ItemLookup ResponseGroup=ItemAttributes%2COffers%2CImages%2CReviews Service=AWSECommerceService Timestamp=2009-01-01T12%3A00%3A00Z Version=2009-01-06

3、4は元々プログラムで生成する際に連想配列でURLを組み立てていくはずなので、
「&」で連結する前に、連想配列の段階で並べ替えておけば問題はありませんが、

パラメータの変数名を昇順でソートしておく必要があるという事です。

PHPであれば「ksort($params);」が利用可能です。

 

5. 並べ替えが終わったら、パラメータと値のペアのリストを再度アンドマーク(&)でつなぎ直します。この段階で、AWSの署名対象となる正規化されたリクエストが作成されます。

AWSAccessKeyId=00000000000000000000&ItemId=0679722769&Operation=I temLookup&ResponseGroup=ItemAttributes%2COffers%2CImages%2CReview s&Service=AWSECommerceService&Timestamp=2009-01-01T12%3A00%3A00Z& Version=2009-01-06

並び替えた変数と値のペアを「&変数=値」の形式で繋ぎ合わせます。

 

6. 以下の3行(改行はそのまま使用してください)を正規化されたリクエストの前に追加します。

GET

webservices.amazon.com

/onca/xml

この3行をクエリの頭に付けたします。
改行を含めてと書かれていますので、ヒアドキュメント構文で改行を含ませて組み立てるか、
「\n」などで改行コードを含ませてあげればいいでしょう。

 

7. 署名対象のリクエスト文字列は以下の通りです:

GET

webservices.amazon.com

/onca/xml

AWSAccessKeyId=00000000000000000000&ItemId=0679722769&Operation=I temLookup&ResponseGroup=ItemAttributes%2COffers%2CImages%2CReview s&Service=AWSECommerceService&Timestamp=2009-01-01T12%3A00%3A00Z& Version=2009-01-06

これで署名対象のURLが組みあがった事になります。

8. 上記のリクエスト文字列とダミーの秘密キーである、1234567890を利用して、RFC2104準拠のHMAC-SHA256ハッシュアルゴリズムの計算を行います。このステップの詳細な情報については、ご利用のプログラミング言語のコードサンプルおよびドキュメントをご参照ください。

Nace+U3Az4OhN7tISqgs1vdLBHBEijWcBeCqL5xN9xg=

リクエストの文字列とシークレットキーを使ってハッシュ値を求めます。
シークレットキー(秘密キー)は以下で確認できますが、
キー生成時に一度しか表示されませんので、CSVでダウンロードして保管しておきます。

PHPでハッシュを求める場合、以下の関数が利用できます。

hash_hmac("sha256", $string_to_sign, $secret_key, true);

 

9. 署名に含まれているプラス (+) とイコール (=) をURLエンコードする。

Nace%2BU3Az4OhN7tISqgs1vdLBHBEijWcBeCqL5xN9xg%

署名(ハッシュ値)に含まれている「+」や「=」をURLエンコードします。

base64_encode();

10. リクエストにURLエンコードが完了した署名を追加すると、正しくフォーマットされた署名認証リクエストが完成します。

http://webservices.amazon.com/onca/xml?AWSAccessKeyId=00000000000 000000000&ItemId=0679722769&Operation=ItemLookup&ResponseGroup=It emAttributes%2COffers%2CImages%2CReviews&Service=AWSECommerceServ ice&Timestamp=2009-01-01T12%3A00%3A00Z&Version=2009-01-06&Signatu re=pwqYQRc3RepIrf7m%2BVMRy%2FjFXx%2FZBSPsaSFFexIUoSI%3D

最後に「&Signature=」として、署名キーを付加する事で、
APIの要求URLが組みあがります。

 

プロモーション(btm)

Google or AdMax Promotion (it)

要求URLはタイムスタンプによって一定時間のみ有効

やっている事は難しい事はないのですが、
なかなかとっつきにくい部分があるので、最初のうちは苦労するかもしれません。

また最初に求めたタイムスタンプによって、
得られたURLが一定時間しか利用できません。

※1時間か、10分程度かは分かりかねますが風呂入って戻ってきたらエラーになった気がします。

タイムスタンプが無効になった場合、
レスポンスのXMLには以下の様なエラーメッセージが返されるようになります。

 

この事からも、APIでデータを要求するには毎回URLを組み立てる必要があります。

都度現在のタイムスタンプでURLを生成し署名をする為、
二度と同じURLが生成されることはありません。

 

こうした署名ステップをWebで簡単に動作確認ができるサイトが、
Amazonで公開されています。

 


公開日:

最後までお読みいただきありがとうございました。

ページ
すべて展開 | すべて省略

Rakuten Promotion

ブログ記事のご紹介
すべて展開 | すべて省略