スポンサードリンク

Kindle Unlimitedの対象本を検索できるページをPHPで作ってみた

Kindle Unlimitedを契約して使っていますが、
いまいち検索が使いずらいのが玉にキズです。

Amazonで「Kindle本」のカテゴリページを開くと
Kindle Unlimited対象本の一覧を見ることはできます。

ただ、対象件数が非常に多いので、
1ページずつ見ていくのは現実的ではありません。

洋書(英語の本)も多いので、
英語多読用にKindle Unlimitedで良い本を探したいと
思っているのですが、ペンギンリーダーズやラダーシリーズなど
多読用に向いている本は意外にKindle Unlimitedで
対象になっていなかったりします。

英語多読に使いたい本は、絵本などの簡単な英語の本なのですが、
そういう本でKindle Unlimitedの対象本から探すのが
結構めんどくさかったりします。

ペンギンリーダーズやラダーシリーズがいいと思って
Kindle本カテゴリで検索してみますが、
Kindleでは読めますが、読み放題にはなっていません。

Kindle Unlimiteの対象本を探したいということで
「Kindle Unlimited」をキーワードに検索しても、
「Kindle Unlimited」についての解説をしている本
(タイトルに「Kindle Unlimited」が入っているような本)
しか検索リストに出てきません。

カテゴリを「Kindle Unlimited」のみに絞って
その中から入力したキーワードにマッチした
検索を行いたいのですが、Amazonページ上では
なかなかそれができません。

できないならAmazon Product Advertising APIを
使って検索ページを作ってしまえということで、
ちゃちゃっと作ってみました。

とりあえず、キーワードを入力して
Kindle Unlimitedで一致する結果を
一覧で表示させるという簡便な検索システムを
実装してみました。

サイトデザインどうしよう?

とりあえずで作るサイトですが、
あまりにもダサいデザインにはしたくない、
とはいってもデザイナーではないので
自分でちゃちゃっとWEBデザインが
出来るわけではありません。

手軽にできてそれなりの見た目にしたいということで、
Bootstrapを利用しようと思いつきます。

Bootstrapもテーマを利用すると
より手軽に使えるだろうと
Bootstrapテーマを探してみました。

日本語も美しく表示できるという
Honoka
というBootstrapテーマがよさそうなので
これを使ってみることにしました。

プログラムの実装

最初にHonokaをダウンロードします。

ダウンロードしたファイルを解凍すると、
「honoka」フォルダができるので、
このhonokaフォルダ上に以下の
index.phpとrequest.phpを作ります。

index.php

画面表示用のPHPファイルです。

<?php
if (!empty($_POST['keyword'])) {
    include_once('request.php');
}
?>
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1">
<!-- The above 3 meta tags *must* come first in the head; any other head content must come *after* these tags -->
<title>Kindle Unlimited検索ページ</title>

<!-- Bootstrap -->
<link href="css/bootstrap.min.css" rel="stylesheet">
  <style type="text/css">
  .col-lg-4 {
    width: 100%;
  }
  .list-group-item-image {
    float: left;
    padding-right: 10px;
  }
  .list-group-item-image img {
    height: 200px;
  }
  @media ( min-width: 568px ) {
  }
  </style>


<!-- HTML5 shim and Respond.js for IE8 support of HTML5 elements and media queries -->
<!-- WARNING: Respond.js doesn't work if you view the page via file:// -->
<!--[if lt IE 9]>
<script src="https://oss.maxcdn.com/html5shiv/3.7.3/html5shiv.min.js"></script>
<script src="https://oss.maxcdn.com/respond/1.4.2/respond.min.js"></script>
<![endif]-->
</head>
<body>
<div class="container">
  <div class="bs-docs-section clearfix">

    <div class="row">
      <div class="col-lg-12">
        <div class="page-header">
          <h1 id="navbar">Kindle Unlimited検索</h1>
        </div>

        <div class="bs-component">
          <nav class="navbar navbar-default">
            <div class="container-fluid">

              <div class="collapse navbar-collapse" id="bs-example-navbar-collapse-1">
                <form class="navbar-form navbar-left" role="search" action="index.php" method="POST">
                  <div class="form-group">
                    <input type="text" class="form-control" placeholder="Search" name="keyword">
                  </div>
                  <button type="submit" class="btn btn-default">検索</button>
                </form>
              </div>
            </div>
          </nav>
        </div>
      </div>
    </div>

<?php
if (!empty($_POST['keyword'])) {
?>
    <div class="row">
      <div class="col-lg-12">
        <h2>検索結果</h2>
      </div>
    </div>
    <div class="row">
      <div class="col-lg-4">
        <div class="bs-component">
          <div class="list-group">
<?php
    foreach ($item_tags as $item) {
        echo $item;
    }
?>
          </div>
        </div>
      </div>
    </div>
<?php
}
?>
  </div>
</div>

    <!-- jQuery (necessary for Bootstrap's JavaScript plugins) -->
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.12.4/jquery.min.js"></script>
    <!-- Include all compiled plugins (below), or include individual files as needed -->
    <script src="js/bootstrap.min.js"></script>
  </body>
</html>

検索を行うと、自分自身にPOSTでキーワードを投げます。
POSTがあると、request.phpを呼び出し、
検索結果を表示するとしています。

request.php

続いてはrequest.phpです。
このファイルでは、入力したキーワードに対して
Amazon Product Advertising APIを実行し、
検索結果を一覧に表示します。

<?php
define("BaseUrl", "https://webservices.amazon.co.jp/onca/xml");

// Amazon APIのアクセスキーとシークレットキーを入力
define("Access_Key_ID", "アクセスキー");
define("Secret_Access_Key", "シークレットアクセスキー");
// アソシエイトIDの入力
define("Associate_tag", "アソシエイトID");

define("KINDLE_UMLIMITED_BROWSE_NODE_ID", "4486610051");

// リクエストのパラメータ作成
$params = array();
$params["Service"]          = "AWSECommerceService";
$params["AWSAccessKeyId"]   = Access_Key_ID;
$params["Version"]          = "2013-08-01";
$params["Operation"]        = "ItemSearch";
$params["SearchIndex"]      = "KindleStore";
$params["Keywords"]         = $_POST['keyword'];
$params["AssociateTag"]     = Associate_tag;
$params["ResponseGroup"]    = "ItemAttributes,Offers, Images";
$params["MinimumPrice"]     = "100";
$params["ItemPage"]         = "1";
$params["BrowseNode"]         = KINDLE_UMLIMITED_BROWSE_NODE_ID;


$base_request = "";
foreach ($params as $k => $v) { $base_request .= "&" . $k . "=" . $v; }
$base_request = BaseUrl . "?" . substr($base_request, 1);

$params["Timestamp"] = gmdate("Y-m-d\TH:i:s\Z");
$base_request .= "&Timestamp=" . $params['Timestamp'];

$base_request = "";
foreach ($params as $k => $v) {
	$base_request .= '&' . $k . '=' . rawurlencode($v);
	$params[$k] = rawurlencode($v);
}
$base_request = BaseUrl . "?" . substr($base_request, 1);

$base_request = preg_replace("/.*\?/", "", $base_request);
$base_request = str_replace("&", "\n", $base_request);

ksort($params);
$base_request = "";
foreach ($params as $k => $v) { $base_request .= "&" . $k . "=" . $v; }
$base_request = substr($base_request, 1);
$base_request = str_replace("&", "\n", $base_request);

$base_request = str_replace("\n", "&", $base_request);

$parsed_url = parse_url(BaseUrl);
$base_request = "GET\n" . $parsed_url['host'] . "\n" . $parsed_url['path'] . "\n" . $base_request;

$signature = base64_encode(hash_hmac('sha256', $base_request, Secret_Access_Key, true));
$signature = rawurlencode($signature);

$base_request = "";
foreach ($params as $k => $v) { $base_request .= "&" . $k . "=" . $v; }
$base_request = BaseUrl . "?" . substr($base_request, 1) . "&Signature=" . $signature;

$item_tags = ItemSearch($base_request);

function ItemSearch($base_request) {
    $amazon_xml = simplexml_load_string(file_get_contents($base_request));
    $item_tags = array();
    
	foreach($amazon_xml->Items->Item as $item) {
		$item_title = $item->ItemAttributes->Title; // 商品名
		$item_author = $item->ItemAttributes->Author; // 著者
		$item_publicationdate = $item->ItemAttributes->PublicationDate; // 発売日
		$item_publisher = $item->ItemAttributes->Publisher; // 出版社
		$item_url = $item->DetailPageURL; // 商品のURL
		$item_image	 = $item->LargeImage->URL; // 商品の画像
		
		$item_tags[] = '            <a class="list-group-item clearfix" href="'.$item_url.'" target="_blank">
                <div class="list-group-item-image">
                    <img src="'.$item_image.'" />
                </div>
                <p class="list-group-item-title">
                    '.$item_title.'
                </p>
            </a>';
	}
	return $item_tags;
}

request.phpはGithubの
manabubannai/amazon-api-test-blogを参考にさせていただきました。

サーバーにアップして公開

index.phpとrequest.phpができたら
honokaフォルダごとサーバーにアップします。

試しに作ってみたサイトがこれです。
Kindle Unlimited検索

とりあえず作ったサイトは味も素っ気もありませんが、
ここから英語多読用に使えそうな本など
ピックアップできればと考えています。

スポンサードリンク