私が簡易なクローラをつくるとき

はじめに

お盆の前後にまとまった自由時間があり、久しぶり (といっても数ヶ月ぶりくらい) に Web クローラ的なものを書いた。大量のデータが収集されていくログの様子を眺めるのは楽しい。今回も楽しかった。

f:id:june29:20160818001157p:plain

再利用するかどうかもその時点ではわからない簡易な Web クローラを書くとき「だいたいこんな感じだな」というのを言語化してみる試み。この内容は、何度かいっしょにクローリング業務をこなしたことのある @darashi に大きく影響を受けているだろうな、ってことは最初に書いておこう。最近は共同クローリングがごぶさたなので、またいっしょにやりたいなって思っています。

作業の流れ

  • (01) あんまりクラス設計とか気にせず、処理の流れを思いつくままに書いていく
    • 最初のエントリポイントにアクセスして、データを取得して、ストレージに保存して、ってな感じで
  • (02) 効率のよいクローリング戦略を考えながら、ページングやループの終了条件のロジックを書く
  • (03) こんなもんかな〜っていう処理が書けたら、とにかく起動して適当に動かしてみる
  • (04) 想定した通りのデータの形をしているときはいい感じに動くものの、ほぼ間違いなく想定外の形のデータに遭遇してエラーを吐いて死ぬ
  • (05) 遭遇した想定外の形のデータに合わせて処理をプチ更新する
  • (06) 何度か (04)〜(05) を繰り返しているうちに、次第にしっかりと動くクローラの姿になってくる
  • (07) ある程度の量のデータを収集できてくると、このデータの持ち方じゃ破綻するな〜とわかってくるタイミングが訪れる
  • (08) ここまでに収集したデータをぜんぶ捨てるつもりで、最新の知見をもとにデータの持ち方を設計して実装に反映させる
  • (09) ここまでくると、動かせば動かすだけデータを集められるようになるので、スクリプトを再起動したときにいい感じに続きから実行してくれるようなレジューム機構を入れる
  • (10) そろそろけっこう堅牢なクローラになっているので、ひたすら動かしておいて、外的要因で止まったら自動で再起動するような仕組みを入れて動かし続ける
  • (11) お目当てのデータがたくさん集まってきて、桶屋が儲かる

コツっぽいもの

  • (A) 取得したデータは、なるべく取得したまんまの生データを保存しておく
    • 加工した上で保存すると、加工方法を変えたときに最初からデータを取り直す羽目になる
    • データの取得と加工は別工程と考えておくのが吉
    • 特に HTML は「スクレイピングして、必要なデータだけ保存」って、昔のぼくはやりがちだった、今はとりあえず HTML を丸ごと保存する
    • これは @darashi がそうしているのを見て真似した
  • (B) スクリプトの起動時とか「データ取得10,000件ごと」とか例外発生時とか、わかりのいいタイミングで Slack 等へ通知させるとよい
    • 基本は放置で動かしておきたいけど、進捗とか異常系はちょいちょい把握したいときに便利
    • 手元の開発マシンを離れて VPS なんかで動かす場合にも、コンソールへのログ以外に Slack 等に通知しておくと移動中にも確認できて便利だったり

他にもある気がするので、思い付いたら追記したい。

しかし、最近は Web API が豊富で、きれいにフォーマットされた JSON が簡単に手に入るから、昔みたいに「クローラとスクレイパの両方をがんばらなきゃいけない」ってことが減ってきた。スクレイピング職人は働き口も後継者も見つからず、このまま絶滅してしまいそう。