2008-07-29
■ Web::Scraper で全ての following/followers の screen_name を取得する

Twitter が SPAM アカウント削除施策とかをやりまくってるせいなのか、あまりに「バキニゲ」を連呼したりして remove されたせいなのか、following と followers の数が何もしてなくても結構変動してしまうことがある。
なので、following とか followers の差を取って、follow してくれてるのにこちらからしていない人を follow したり、こちらから follow しているのに相手から follow されてない人を remove したりとかを、たまにやっている。
- http://twitter.com/statuses/followers.json
- 自分を follow してくれている人を取る API
- http://twitter.com/statuses/friends.json
- 自分が follow している人を取る API
これとかを使えば良いんだけど、一回のリクエストで remaining_hits (API 回数制限) を消費してしまう。しかも API のクセに paginate するからツライ。それに、別に screen_name ぐらいしか必要ないのに色々な情報を返してくれるのも実に無駄。こんなことのために、ベホマズンを使いまくるほどの消費っぷりは嫌だから、WWW::Mechanize と Web::Scraper を使って、following とか followers の screen_name のリストを取ってくれば良いんだということに気付いた。
こういう DIY なら消費 MP 0 で済む。
まずは、自分を follow してくれている人を取る。
#!/usr/local/bin/perl use strict; use warnings; use WWW::Mechanize; use Web::Scraper; use URI; my $mech = WWW::Mechanize->new; $mech->agent_alias('Mac Safari'); $mech->get('http://twitter.com/'); $mech->submit_form( form_number => 2, fields => +{ 'session[username_or_email]' => 'username', 'session[password]' => 'password', }, ); my $s = scraper { process 'tr.vcard > td.thumb > a', 'screen_names[]' => sub { $_->attr('href') =~ m{([^/]+)$}; }; process 'div.pagination > a[rel="me next"]', next => '@href'; }; my @screen_names = (); my $url = URI->new('http://twitter.com/followers'); while (1) { warn "fetching: $url\n"; $mech->get($url->as_string); die $mech->res->status_line unless $mech->success; my $res = $s->scrape($mech->content); push @screen_names, @{$res->{screen_names}}; last unless $res->{next}; $url->path_query($res->{next}); } print "$_\n" for sort @screen_names;
途中でクジラが出たりしなければきっとうまくいく。
逆に自分が follow している人を取る。
これは、驚いたことに、上記の
my $url = URI->new('http://twitter.com/followers');
の行を
my $url = URI->new('http://twitter.com/friends');
にするだけで動く。
それぞれの標準出力をファイルとかにリダイレクトして diff 取れば、誰を (follow|remove) し忘れているかがきっとわかるはずさ。
% diff -U 0 following.txt followers.txt
とかすれば、follow し忘れてる人に + がついてて、remove し忘れている人に - がついてるよ。
アイツめ!いつの間にか俺を remove しやがったな!とかに気付いても恨みっこナシだよ!
落ち込んだり、攻撃したりしたらダメ!絶対!!