Hatena::Groupfragments

甘くておいしいおイモだよー このページをアンテナに追加 RSSフィード

2006-11-01

Filter::ForcePermalink 21:00 Filter::ForcePermalink - 甘くておいしいおイモだよー を含むブックマーク はてなブックマーク - Filter::ForcePermalink - 甘くておいしいおイモだよー

【追記(11/14 13:28)】このエントリの最新版は Filter::ForcePermalink - SweetPotato::Plagger - Plaggerグループに移動しました。以後,こちらのエントリは更新しません。

「強制的にPermalinkを指定するFilterが欲しい」とか言ったら「自分で作れ」とか言われそうだけど - 甘くておいしいおイモだよー - 断片部の続き。

家に帰ってさくっと作った。Filter::ForcePermalinkと命名。Permalinkを持たない各Entryに対して,FeedLink#EntryDigestのような形式のPermalinkを設定する。既にPermalinkを持っているEntryに対しては何もしない。

EntryDigestの算出にはPlagger::Entry->digestを使用しているが,これはEntryのタイトルと内容に依存しているため,いずれかが変われば設定されるPermalinkも変わることに注意。Dedupeする分には,タイトルや内容の変更がPermalinkの変更に現れるので,実用上は問題ない。

Plagger/Plugin/Filter/ForcePermalink.pm

package Plagger::Plugin::Filter::ForcePermalink;
use strict;
use base qw( Plagger::Plugin );

use URI;

sub register {
    my ($self, $context) = @_;
    $context->register_hook(
        $self,
        'update.entry.fixup' => \&filter,
    );
}

sub filter {
    my ($self, $context, $args) = @_;

    if($args->{entry}->permalink) {
        Plagger->context->log(debug => "Entry " . $args->{entry}->title . " already has permalink. Skipped");
        return;
    }

    my $permalink = URI->new($args->{feed}->link);
    $permalink->fragment($args->{entry}->digest);
    $args->{entry}->permalink($permalink);
}

1;

利用方法はこんな感じ。特にconfigとかもなし。

  - module: Subscription::Config
    config:
      feed:
        - url: http://www.hogehoge.com/
  - module: CustomFeed::Config
  - module: Filter::ForcePermalink

上記の場合,CustomFeed::ConfigによってPermalinkを設定されなかったEntryに対して,http://www.hogehoge.com/#c7a0b4ec2e3e6d8e9effc5d1696f1728のようなPermalinkが割り当てられる。

URLの形式を統一すれば分散ブクマが避けられるわけだ 12:21 URLの形式を統一すれば分散ブクマが避けられるわけだ - 甘くておいしいおイモだよー を含むブックマーク はてなブックマーク - URLの形式を統一すれば分散ブクマが避けられるわけだ - 甘くておいしいおイモだよー

例えばURLの末尾のスラッシュの有無で,同じ内容のエントリなのにブクマが分散されてしまうことがある。SBMのシステム側でそれを吸収できないならば,それぞれのブロガーが自分のエントリURLの形式を統一する必要がある。これもある意味SBOのひとつだろう。

URLの形式の統一の際には,エントリのテンプレートはもちろんのこと,ブログがRSSリーダーでブログが読まれる可能性を考えれば,フィードに記述されているエントリのURLにも気をつけなければならない。前者は大抵カスタマイズ可能だが,後者はそうでないことが多いからだ。さらにRSSリーダーから直接ブクマされる可能性も考えれば,URLは後者に合わせるべきだろう。

というか,末尾にスラッシュつけるのなんてそれPlaじゃん。

「強制的にPermalinkを指定するFilterが欲しい」とか言ったら「自分で作れ」とか言われそうだけど 00:39 「強制的にPermalinkを指定するFilterが欲しい」とか言ったら「自分で作れ」とか言われそうだけど - 甘くておいしいおイモだよー を含むブックマーク はてなブックマーク - 「強制的にPermalinkを指定するFilterが欲しい」とか言ったら「自分で作れ」とか言われそうだけど - 甘くておいしいおイモだよー

【追記(11/1 22:01)】作りました→Filter::ForcePermalink - 甘くておいしいおイモだよー - 断片部

Plagger::Rule::Dedupedまわりのソースを見たら,Filter::RuleでDedupedを用いる場合,重複チェックのキーがエントリのURL(日付が存在する場合はURLと日付の連接)になっていることが分かった。

ただ,CustomFeed::Configでパースされた各エントリに必ずURLがあるかと言うとそうではないわけで。でもURLを指定しないとDedupeってくれないから,いつもextract_after_hookで無理矢理URLを作るわけですよ。こんな具合に。

extract_after_hook: |
  use Digest::MD5;
  my $seed = $data->{title};
  Encode::_utf8_off($seed);
  my $md5 = Digest::MD5::md5_hex($seed);
  $data->{link} = "http://www.hogehoge.com/\#$md5";

で,いつもこんなコードを書くのは面倒なので,Filter辺りでできないのかなあと思った。Filter::ForcePermalinkみたいな。

今のPlaggerにはないっぽいので,気が向いたらFilterの書き方を調べて書いてみるつもり。