[餅] 餅空 blog / Blogger支店

Bloggerの使い勝手を試しつつ記す日記です。

2005-02-08

Amazon Webサービスで困ったこと

 プログラム上で、Amazonの書籍やDVDの検索、詳細、出荷時期、レビューの取得等ができるウェブサービスというAPIをAmazonは提供している。サイト側で動的な表示ができるという点で大変重宝するサービスで、各blogのAmazon plugin等はみんなこのサービスを使っているようだ。

 ウェブサービスは他にもGoogleの検索・AdWordsや、オークションのBiddersも提供しているため、プログラムさえ組めば自サイトでGoogleの検索を利用したり、AdWordsの結果を知ったりキャンペーンを作ったり、Biddersの出品物を並べたりすることができる。
 中でもAmazonが一番人気なのはアソシエイト(アフィリエイト)と組み合わせて実利に直結させることができるからだろう。最近ではMac用の独立したアプリケーションまで存在するらしい

 私も以前PHPとnusoapを使って検索できるものを試しに作ったものの、そのままほったらかしていたのだが、ついにこの機能を実装する必要が出てきてしまったので、再度Amazonウェブサービスを弄る事となった。

 取得したいデータは、「書籍名」「著者名」「新品価格」「ユーズド価格」「発送時期」「おすすめ度」「レビューした人数」で、複数のキーワードでの検索結果をマージして売れ筋ランキング順に10件分が必要。これらは、Amazon Webサービス ECS4.0だとオペレーションがItemSearch、SortがSalesRank、ResponseGroupを Medium,Reviews,Offerfull とすれば取得できる。

 …いや、できるはずだった。

 いざ PHP+nusoap.phpで取り組んでみたところ、売れ筋ランキング(SalesRank)がおかしい。ソート順をSalesRankとしても、一つ一つのデータを見てみるとSalesRankが昇順に並んでない。Google先生に聞いてみたところ、SalesRankでの結果はいつのランキングかわからないデータを元にしているらしい。
 返される結果の順序が正しいのか、一つ一つの書籍が持っているSalesRankが正しいのか判断できないが、画面に表示される順位(とも必ずしも整合しないのだが)をベースにしたいと考えて、30位までのデータを取得後、各書籍のSalesRankを元にソートする事にした。これはこれで解決した事にしよう。

 複数のキーワードで検索した場合に同じ書籍が登場する事があり、それは当たり前の事なので構わないのだが、同じ書籍なのに違うSalesRankが得られる事があった。データベースの更新時間帯だったのだろうか。この場合は、順位が上のものを優先する事にして解決。この方法だと、違う書籍でも同じ順位になる可能性があるが、そこまで厳密である必要はどこにもないので構わないだろう。

 次に大きく悩んだのは「レビュー」の扱い。ResponseGroupにReviewsをつけたり、MediumをLargeに変えると結果が返ってこない…事がある。
 検索キーワードによって結果が返ってきたり来なかったりで、このままだと正しい結果を得ることができない。例えばItemSearchでキーワードを[YMO]、mediaを[DVD]、ResponseGroupを[Reviews]にすると、結果が返ってこない。(このキーワードは一例で今回の仕事とは関係無い)
 Google先生に聞いてみたところ、レビューのテキストの中に本来使用できない文字コードが混じってしまっていてエラーが発生しているらしい。発生した場合は、ECSフォーラムにASIN番号を書き込む事により修正してもらえるとの事で、より一般的な解決策も検討中との事。また、XSLTで結果を処理している場合にも弊害が生じるらしい。とりあえずパース中にエラーとなっているようだ。…Googleでは以上の事がわかった。

 フォーラムで報告するのはやぶさかではないが、仕事なので未知のものにも対応しなければいけない。レビューが取得できないと、「おすすめ度」や「レビューした人数」を得ることができないぞ。う~ん、困った。

 私がやってみた事

1. ItemSearchでItemIdsだけ取得し、ASINを元にItemLookupでデータを一つ一つ取得しなおす。
  結果: 失敗
  Reviewsで取得し損ねると10個のデータを失うが、この方法だと
  レビューが取得できないアイテムだけ失うことになり被害は最
  小限に留められる。しかし、データが揃わない事に代わりは無
  いので意味が無い。

2. ECS4.0に問題があるのではないかと考えてECS3.0で組みなおす。
  結果: 失敗
  Largeに相当するheavyを指定するとやはり結果が返ってこない。

3. nusoap.phpをPEAR:SOAPに変えてみる。
  結果: 失敗
  ECS4.0 だと何故かparse errorが発生。PEAR:SOAPの方にバグ
  レポートもあがっているようだが、如何ともしがたい。
  ECS3.0 だとレビューが入っているデータは取得できない。

4. ECS4.0での取得をSOAPからRESTにしてみる。
  結果: 失敗?
  socketで接続してGETでパラメータを送信するとXMLな結果が
  返ってきた。レビューも取得できてる。しかし、XMLparser
  を通した時点でエラー発生。
  必要な部分だけ自前で切り出せばOKそうだが、データが沢山
  あるのでめんどくさそう。

 なかなかうまくいかず時間を無駄にしたが、4.のあとでふと思いついた。

 「取得したXMLデータの中からエラーの原因となるレビューの中身だけ削除しちゃえ!そうするとParserがちゃんと処理してくれるんでは!?」

 「いやいや、いっその事 nusoap.php でその処理をしちゃえば普通にSOAPで扱えるのでは?」

 という事で、1行追加して<Content></Content>間のデータを削除するようにしたところ、最初にやろうとした方法で必要なデータが得られることができるようになりました。今回はレビューの内容を使わないからいいんですけど、必要な時はどう処理すればいいんでしょうかね?その時は、また改めて考える事にします。

 というわけで無事に処理できるようになりましたが、とても疲れました。レビューからイケナイ文字が早くなくなることを祈ってます。または、あってもエラーにならない抜本的な対策の早期導入を望みます。

 追記(2005/2/13)
 [Amazon Web サービスがレビューの文字化けに対応]のエントリーで書きましたが、不正な文字が混ざると正しい結果が得られない不具合は、[2005-01-19バージョン]で修正され、nusoapを改造したり悩んだりすることなく正しいデータが得られるようになりました。お試しあれ。

2005-02-02

ギロロ伍長のラジオ


ギロロ伍長のラジオ

 1/29のケロロ軍曹のAパート「ギロロ 泣けない赤鬼 であります」を見ていたら、ギロロ伍長がラジオを聞いているシーンが出てきた。ん~~?ギロロのラジオ…これって…これって…松下のBCLラジオじゃない?でも、名前が思い出せん!「クーガ」ではなかったような気がする。スカイセンサーはソニーだし。………………で、ぐぐったらいっぱい出てきました。この機種です!

ギロロ伍長のラジオの正体(1977年発売)

 そう!松下のデジタル周波数カウンタがついたBCLラジオ「プロシード2800」なんですよ!当時のラジオはみんなアナログのダイヤル式だったわけですが、この機種の前に登場したソニーのデジタル周波数カウンタのラジオと、このプロシードはBCLerにとっては画期的な製品でした。なんせ電卓のように数字を押せば周波数が合うのですから…。当時、Daiichi(第一産業・現デオデオ)のBCLラジオコーナーでこれらの機種を前に涎たらしてました…。

 原作者(吉崎観音)さんは1971年生まれとの事で、このラジオを知るにはちょっと若すぎるような… これってアニメだけですか!?きっとこれの作画をした人もこのラジオを登場させるにあたって検索して調べたに違いないと思うんですがどうでしょう?それにしてもマニアック過ぎというか、作ってる人の年齢層の高さを感じます。(……っていうか狙ってますよね)

 当時、一世を風靡したBCLですが、考えてみればあの頃BCLやってた子供たちはあまり深く考えずに朝鮮中央放送(北朝鮮)とかモスクワ放送(ソ連(当時))の日本語放送にかじりついてたわけで、あの頃から北朝鮮による拉致が行われていたという事実と考え合わせると恐ろしい事この上ないですな。まぁ、日本語放送の中での人気は下のほうでしたし、どれだけ放送内容を理解していたかは謎ですが。

 BCLをやっていた人の多くは雑誌「ラジオの製作」(電波新聞社)や「初歩のラジオ」を購読しており、ワンボードマイコンTK-80の登場と共にそのままコンピュータの世界に足を踏み入れたんではないでしょうか。私の周りにも一人そのような人がいます。ところで、「影の声」さんはお元気なんでしょうかねぇ…。


500mlビッギー

 ケロロともBCLとも全然関係ありませんがこちらは500mlのビッギー。なんとなく500mlのビール風雑酒と並べてみました。さすがのビッキーもこれ以上大きいサイズは無いようです。

 明日の朝はこれを一気飲みして仕事に励むとしましょう!