LoginSignup
21
17

More than 3 years have passed since last update.

【Rails】Amazon PA API v5.0 で書籍検索

Last updated at Posted at 2020-08-19

amazonの書籍検索のAPIで少々てこずったのでメモ。
他に日本語の記事が見つからなかったので参考にしていただけると幸いです。

はじめに

書籍検索にはGoogleやAmazonなどのAPIを使うことができるのですが、Google(Google Books API)では物足りない部分もあったのでAmazonのPA(Product Advertising)APIを使うことにしました。

しかし2020年の4月からPA APIのバージョンが変わって、amazon-ecsのgemを使ったやり方だとうまく行かないという事態に…
この記事のやり方を参考にしたのですがデータが取得できなかった…)

amazon-ecsのリファレンスをみると別のgem(paapi)を使うと良いと書かれていたのでそれを使ってみることにしました。
paapiのリファレンス

ちなみにこのAPIを利用するためには、先にアマゾンアソシエイトへの登録、申請が必要なので、まだの方はこちらの記事を参考ください。
審査のハードルが割と高めなので、すぐ使いたいという方は厳しいと思います。
(自分の場合は1ヶ月くらいかかりました)

完成イメージ

検索の完成イメージはこんな感じです。
ちゃんと画像やURLが取得できているのがわかると思います。
85a1b44b0aecfa2b419158ec43da4af8.gif

実装方針

今回は以下のような処理を実装していきます
1. フォームにキーワードを入力してリクエストを送る
2. APIを叩いて入力されたキーワードで検索
3. APIからのレスポンスを加工してデータを表示

各種ファイル

Gem

Gemfile
gem 'paapi'

忘れずにbundle installしましょう。(サーバー起動していたら再起動も忘れずに)

config

config/initializers直下にpaapi.rbを作成して鍵やIDの設定を書きます。
・access_key:  アクセスキー
・secret_key:  シークレットキー
・partner_tag: アソシエイトID(22で終わる自分のID)

config/initializers/paapi.rb
Paapi.configure do |config|
  config.access_key  = Rails.application.credentials[:pa_api][:access_key_id]
  config.secret_key  = Rails.application.credentials[:pa_api][:secret_key]
  config.partner_tag = Rails.application.credentials[:pa_api][:associate_tag]
end

自分の場合はcredentialsから呼び出して使ってます。(流出するとなんとなく嫌なので)
credentialsの使い方がわからない場合はこちらを参考にしてください。

コントローラー

今回はサンプルなので適当にsearchesコントローラを作成しました。
実際はbookディレクトリ内に作成して何の検索かわかりやすくしたほうが良いです。

ターミナル
$ rails g controller searches
searches_controller
class SearchesController < ApplicationController
  before_action :call_client, only: :index

  def index
    si = @client.search_items(keywords: keyword_params, SearchIndex: "Books")
    @items = si.items
  end

  private

  def call_client
    require 'paapi'
    @client = Paapi::Client.new(access_key: Rails.application.credentials[:pa_api][:access_key_id],
                                secret_key: Rails.application.credentials[:pa_api][:secret_key],
                                market: :jp,
                                partner_tag: Rails.application.credentials[:pa_api][:associate_tag])
  end

  def keyword_params
    params.require(:keyword)
  end

end

clientのインスタンスを作成し、それに対して検索メソッドを適用して商品情報を取得しています。
今回は商品検索でジャンルを本に限定していますが、商品番号を指定して情報を取得したり、別のジャンルを指定したりできるので用途に合わせて使い分けください。

商品検索すると10件分のデータが取得され、レスポンスクラスのデータになります。
この中にitemsのデータが入ってるので.itemsで取り出せばItemクラスのデータとして取り扱うことができます。
(Itemクラスはgemで用意されているもので、便利なメソッドが使えます。後ほどまた説明します。)

ルーティング

忘れずに設定しておきましょう。

routes.rb
Rails.application.routes.draw do
  # (略)
  resources :searches, only: [:index]
end

ビューファイル

まずは検索フォームを用意しておきます。

検索フォーム
.book-search
  = form_with url: {controller: 'searches', action: 'index' }, method: :get, local: true do |f|
    = f.text_field :keyword
    = f.submit "検索"

次に検索して取得したデータを表示するページです。
今回はsearches/indexに表示させます。

views/searches/index
- @items.each do |item|
  .url
    = "url: #{item.detail_url}"
  .title
    = "title: #{item.title}"
  .author
    - authors = item.contributors.select { |e| e['RoleType'] == "author" }&.map { |e| e.dig('Name') }&.reject {|n| n.to_s.empty?}
    = "author: #{authors[0]}"
  .image
    = image_tag "#{item.image_url}", height: '170px', width: '120px'
  .asin
    = "asin: #{item.asin}"

titleメソッドやdetail_urlメソッド、image_urlメソッドを使うと、Itemクラスのデータから商品タイトルやURL、画像などを簡単に取得することができます。

他にもいろいろ取得できるので、リファレンスを見て試してみると良いかと思います。

ちなみにauthorsはリファレンスどおりに(authorsメソッドを使って)やってもうまくいかなかったので、自分で調整しました。
(RoleTypeがauthorであるものを探さないといけないのに、用意されたメソッドではRoleがAuthorであるものを探している)

【2020.08.21追記】
gemの管理者に報告したら直してくれました!
item.authorsでデータ取得できるようになりました。
gemのバージョンは0.1.2以上である必要があります。

参考

・Scratchpad
 APIを叩いてどんなデータが取得されるか試せるページです。
 https://webservices.amazon.co.jp/paapi5/scratchpad/

・APIリファレンス
 Product Advertising API 5.0の公式リファレンスです。
 https://webservices.amazon.com/paapi5/documentation/api-reference.html

21
17
3

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
21
17