中〜大規模な Web スクレイピング・クローリングを行うときに気をつけていること
ざっくりと、数万〜ページくらいを取得したいケースを想定している
最重要:サイトに負荷をかけすぎない
○○秒空ける、ではなく、どの程度のリクエスト頻度であれば自然か?を考えるのが重要
同じサイトであっても、HTML ファイルを Apache が返しているだけなのか、裏で PHP がごちゃごちゃやってるのか、とか
検索結果のページとかは裏で比較的重い処理が走っているだろうと推測できる
身元を明かす
私はスクレイピングしています、問題あったらこちらまで、の意図で連絡先を User-Agent に乗せる
とはいえ UA 見て変だったら拒否してくるサイトも多いので、Chrome の UA の末尾にメアドを書いておくなどするとよい
全てをローカルに保存する
スクレイピングは API ではない。レスポンスの形式について、保証されているものは何ひとつない
?page=4 と ?page=5 で全く違う構造の HTML が返ってきたり、とかよくある
一般的に「HTTP リクエストでファイルを取得する」よりも「取得したファイルを解析する」のほうが、納得の行く結果を得られるまでに多くの試行錯誤を要する
そのため「ページ取得→HTML解析→整形して保存/表示」をワンストップで行うのではなく、取得したファイルをローカルのファイルシステムに保存し、そのローカルファイルで解析を行う
ETL ではなく ELT 、ということ
これを行うに十分なストレージ空間が無い場合は?
まあ HDD でいいから買うとよいのでは、、、
全ての処理は失敗するものとする
失敗する処理の例
HTTP リクエスト
HTML のパース
HTML をパースして抽出した文字列を、数値としてパース
JSON のパース
雑な作りのサイトだと、URL が .json で終わっていてもエラー時は Apache の 400 ページの HTML が返って来る、とかありがち
.json で終わる URL にリクエストしても、エラーだとエラーの HTML のページに 301 とかでリダイレクトさせる、とか
数万~数十万ページ取得して、途中で落ちたら最初からやり直し、は無駄すぎる
最初の段階で、途中から実行できるような仕組みを入れておく
全ての HTTP リクエストをログ出力する
成功したかどうかによらず、全部ログに出しておく
時刻も出す
ロギング系のライブラリでうまく出し分ける、とかできるとベストだけど、まあ適当なヘッダをつけて全部出力して、見る人が頑張ればいい
#スクレイピング