Kentaro Kuribayashi's blog

Software Engineering, Management, Books, and Daily Journal.

自 Blog のエントリを自動的にブックマークすることにより、ソーシャルブックマーク最適化を施す

Tim O'Reilly さんが "What Is Web 2.0" で SEO (Search Engine Optimization) を Web 2.0 の構成要素として挙げてるけど、僕ら日本の Blogger にとって重要なのはむしろ SBO (Social Bookmark Optimization) なんだよね。実際問題、いかにしてはてなブックマークで取り上げられる記事を書くか、そのことだけにみんな心血を注いでいるわけだし。
SBO については「「ソーシャルブックマーク最適化(SBO)」を考えてみよう」というエントリを始めとして、現在までに非常に多くのノウハウが蓄積されてきたんだけど、いまアツイのはやっぱ、自分で自分のエントリを一番乗りでぶっくまする手法だよね。あの miyagawa さんも活用しているし、これはもう真似っこするしかない!
でもここでちと考えた。どうせやるなら楽ちんにやりたいものだ。そこで、これは!というエントリを書いたときに、ブックマークサービスに自動的にぶっくまするプロクシスクリプトを書いてみた。この日記、つまりはてなダイアリの場合、更新の通知を行える機構はトラックバックしかない。そこで、トラックバックの本来の目的からいってどうかとは思われたものの背に腹は代えられない、受信したトラックバックのデータを元に、はてなブックマークと delicious に投稿する仕組みにした。以下のスクリプトを設置し、エントリを書いたときにトラックバック先に設置 URL を指定すれば、そのエントリを自動的にブックマークしてくれる。

#!/usr/bin/env perl

use strict;
use warnings;
use Readonly;
use CGI;
use DateTime;
use LWP::UserAgent;
use HTTP::Request::Common;
use XML::Atom::Client;
use XML::Atom::Entry;
use XML::Atom::Link;
use Net::Trackback::Server;

Readonly my $hatena_username    => 'はてなのユーザ名';
Readonly my $hatena_password    => 'はてなのパスワード';
Readonly my $delicious_username => 'delicious のユーザ名';
Readonly my $delicious_password => 'delicious のパスワード';
Readonly my @tags               => qw(selfbookmark sbo);

my $query = CGI->new;
$query->param('tb_id' => 1); # なんか tb_id 必須らしいのでてけとうに設定しとく

if (my $ping = Net::Trackback::Server->receive_ping($query)) {
    if (do_post($ping)) {
        Net::Trackback::Server->send_success;
    }
    else {
        Net::Trackback::Server->send_error;
    }
}
else {
    Net::Trackback::Server->send_error;
}

sub do_post {
    my $ping = shift;

    post_delicious($ping) or return;
    post_hatena($ping)    or return;

    return 1;
}

sub post_delicious {
    my $ping = shift;

    my $uri = URI->new('http://del.icio.us/api/posts/add');
    $uri->query_form(
        url         => $ping->url,
        description => $ping->title,
        tags        => join(' ', @tags),
        dt          => DateTime->now,
    );

    my $ua = LWP::UserAgent->new;
    $ua->credentials(
        'del.icio.us:80',
        'del.icio.us API',
        $delicious_username,
        $delicious_password
    );
    my $res = $ua->get($uri);

    return $res->is_success;
}

sub post_hatena {
    my $ping = shift;

    my $link = XML::Atom::Link->new;
    $link->href($ping->url);
    $link->rel('related');
    $link->type('text/html');

    my $entry = XML::Atom::Entry->new;
    $entry->add_link($link);
    $entry->summary(join '', map "[$_]", @tags);

    my $client = XML::Atom::Client->new;
    $client->username($hatena_username);
    $client->password($hatena_password);
    $client->createEntry('http://b.hatena.ne.jp/atom/post', $entry) or return;
}

del.icio.us と はてなブックマークに cross-post: blog.bulknews.net」と激しく酷似してるとかゆって叩くの勘弁だよ!やってることほとんど同じだし、しかたないじゃんすか!!!つかまぁ、僕も以前に「del.icio.us からはてなブックマークへデータを移行する」とかゆって似たようなもの書いてたりするので、そのおさらいつーことで。
というよりもむしろ、miyagawa さんのスクリプトとブックマークレットを併用して、自分のエントリを二方向ポストすればいいだけじゃんってことに気づいたが後の祭り。