ヤマト運輸の荷物検索サイトをWeb APIとして使う

# はじめに

「クロネコヤマトの荷物お問い合わせシステム」
みなさん色んなときに参照すると思います。
伝票番号を10件まで一画面で検索できます。
https://toi.kuronekoyamato.co.jp/cgi-bin/tneko

こんなやつですね。
![toi.kuronekoyamato.co.jp_cgi-bin_tneko.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24333/51a574a0-02cf-b6b9-f584-d4126e76bcc4.png)

システム経由で伝票番号を検索したいことあると思います。
このサイトをWeb APIとして使うための公式ドキュメントが見つからなかったのですが、色々と調べて仕組みを暴いたので、ノウハウとして載せておきます。
（予告なく変更される可能性もありますので、ご利用はくれぐれも自己責任で！）

# やり方

## Web API的な仕様

* URL: `https://toi.kuronekoyamato.co.jp/cgi-bin/tneko`
* メソッド: `POST`
* リクエストヘッダ
    * `Content-Type: application/x-www-form-urlencoded`
* リクエストボディ
    * `number00`
        * 詳細情報の有無を切り替え
        * `1`なら「詳細情報：あり」
        * `1`以外の値 or パラメータ省略なら「詳細情報：なし」
    * `number01`～`number10`
        * 「1件目」～「10件目」の伝票番号入力欄に相当
        * たとえば途中が抜けて`number05`だけ設定とかもOK
        * `number11`以降は設定しても無視される（当たり前か）
* レスポンス: `HTML`
    * JSONじゃないのでHTMLのDOMをゴリゴリ解析してデータ抽出が必要です！
    * これをWeb APIと呼んでよいのか微妙ですが・・・


## サンプル

### curlコマンドで実行

```shell
curl https://toi.kuronekoyamato.co.jp/cgi-bin/tneko \
-X POST \
-d 'number00=1' \
-d 'number01=123456789001' \
-d 'number02=123456789002'
```

### Chromeアプリ[Advanced REST client](https://chrome.google.com/webstore/detail/advanced-rest-client/hgmloofddffdnphfgcellkdfbfbjeloo?hl=ja)で実行

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24333/9a621e30-c45c-f63b-45a2-e0521c49e17e.png)

## レスポンスをブラウザで開と
こんな感じ。あとはDOMを解析してよしなに。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24333/e7913749-9433-5ba7-6bab-245a2bf0100f.png)

# GETパラメータで伝票番号を指定できるjizen.kuronekoyamato.co.jp

本題ではないので最後に書きますが、こちらのURLを使うと、GETパラメータに伝票番号を指定することで直接検索ができます。（複数番号の一括検索には未対応）
https://jizen.kuronekoyamato.co.jp/jizen/servlet/crjz.b.NQ0010?id=123456789001

でもこれ、システム経由で叩こうとするととっても扱いにくいんですよね。
ブラウザで上記URLに接続すると、一瞬画面が開いて、すぐに下記の本家URLにリダイレクトするのが分かると思います。
https://toi.kuronekoyamato.co.jp/cgi-bin/tneko

サブドメインが違ってることからもわかるように、これは単なる中継サイトで、間接的にPOSTリクエスト投げるだけなんですね。なんらかの技術的な理由で本家のGETパラメータ対応ができなかったから、苦肉の策で中継サイトを別途作ったのではないかと妄想・・・

そんな仕様のため、`curl`コマンドなどブラウザ外からGETでアクセスした場合は、「一瞬表示される中継画面のHTML」がレスポンスとして返ってくるだけなのです。
前述の`number01`なんかが`FORM`タグにしっかり書かれていますよｗ

```html
<FORM name="main_form" action="http://toi.kuronekoyamato.co.jp/cgi-bin/tneko" method="post">
        <INPUT TYPE="HIDDEN" VALUE="1" NAME="number00">
        <INPUT TYPE="HIDDEN" VALUE="123456789001" NAME="number01">
</FORM>
```

システムからこのURLを使って情報取得するのはスクレイピングの次元になっちゃうので、やめておいた方が良いでしょうねー。最初から本家URLに対してPOSTするのが確実です。

あとこのサイト自体はhttpsに対応しているものの、リダイレクト先の本家URLが絶対httpになってしまうのでセキュリティ的にもイマイチ。本家もhttps接続は可能なので、これは早めにリダイレクト処理を直してもらいたいところですねー。

# 参考サイトと雑感

[宅配便の荷物検索をURLに伝票番号をつけて一発でジャンプ - odawaraの「はてな de メモ」](https://odawara.hatenadiary.org/entry/20101017/1287331467)
ヤマト以外も色々な業者のURLが紹介されています。

[クロネコヤマト伝票番号からリンクを作る。専用リダイレクタはこちら - それマグで！](https://takuya-1st.hatenablog.jp/entry/yamato-checker)
jQueryを使ったコードが公開されています。
仕組みを暴く手掛かりとして大変参考になりました。感謝。


[YamaTrack | クロネコヤマト荷物問合せ](http://nanoappli.com/tracking/)
[[WebAPI]ヤマト運輸の配送状況を確認するAPIを作ってみた](http://nanoappli.com/blog/archives/603)

このWeb APIはとても便利なのですが、ヤマトの公式ではないですし、https化もされていないので、荷物情報が盗聴されるリスクがあります。
個人ユースでリスク承知で使うなら良いですが、プロダクトコード内で使うのはやめておいた方が良さそう。
自分でヤマトのURLに直接リクエスト投げましょう。

ではまた～。