Firefox のアドオン PicLens.これはすごい.ぐっと来た.
あまりにぐっと来たので,衝動的にこのサイトでも対応してみた.対応のしかたは以下のページに書いてある.
要は,画像の場所を列挙した Media RSS という XML ファイルを作って, RSS Autodiscovery で見つけさせればよい.うちの Media RSS はこんな感じになった.
Firefox で PicLens をインストール済みの方は,メニューバーの右側
(Firefox の場合) や ボタンバー内 (IE の場合) にある青い矢印ボタンを押してみてください.なんかダーっと写真が流れるはず.
(追記・訂正) すみません,当初 Firefox 専用だと思ってこの記事書いてたのですが,実は IE でも Safari でも動くようです.というわけで一部修正.
Storable の互換性の問題 [2006-03-25-3] で「Byte order is not compatible」とか言われるため perl 5.005_03 で使い続けていた tb.cgi だが,さくらインターネットで使われている OS が FreeBSD 6.x になり perl 5.005_03 が無くなったため,動かなくなっていた.というわけでしばらくトラックバックを送ることも受け取ることも,過去のものを表示することもできなくなっていたのだけど,ようやく重い腰を上げて対応することにした.
ここにある「$Storable::interwork_56_64bitをtrue値に設定」は,Out of memory とか言われてダメだった.
というわけでここの真似をして,いったん perl 5.6.2 で読んでから Data::Dumper で Dump して,改めて perl 5.8.8 で store し直すことにした.
*.stor を *.stor.old にリネームしてから dump.pl,restore.pl の順に走らせる.一応うまくいったっぽい.
dump.pl:
#!/usr/local/bin/perl5.6.2 use strict; use lib "."; # 古い Storable 一式をカレントディレクトリに置いた use Storable; use Data::Dumper; $Data::Dumper::Indent = 0; $Data::Dumper::Useqq = 1; while (<*.stor.old>) { my $new_file = $_; $new_file =~ s/stor$/txt/; open(NF, "> $new_file") or die; my $data = Storable::retrieve($_); print NF Data::Dumper->Dump([$data], ["data"]), "\n"; close(NF); }
restore.pl:
#!/usr/local/bin/perl5.8.8 use strict; use Storable; while (<*.txt>) { my $new_file = $_; $new_file =~ s/txt$/stor/; open(OF, $_) or die; my ($line, $data); $line = <OF>; eval $line; close(OF); Storable::store($data, $new_file); }
いろいろとありまして,しばらく放置しておりましたが,なにやら巷では 「3ヵ月空白があると連続したブログとは見なされない」という定義があるらしく,まあどうでもいいっちゃどうでもいいのですが,継続は力なりとか唱えながら再開してみます.
この辺の対策 [2007-05-05-1] [2007-04-30-1] [2007-04-21-1] を入れて以降 1ヵ月半ほど,コメントスパムは完全にブロックできていたのですが,ついに来ました.
アクセス元ホストはわりとバラバラな感じ.ただし 6/23 の 8 件はぜんぶ一緒のところだった.はてさて.
* [Eber] It\'s good to see somenoe thinking it th... (2012-12-30 23:40:45)
というわけで [2007-04-30-1],まず世の中の CAPTCHA とかではどうやっているかというと,どうやらワンタイムトークンとするのが普通らしい.
今回のケースに置き換えると,サーバは計算問題を生成して (これがトークン),それをサーバ側に保存しておき,ユーザから送られて来た答えと,その保存しておいた問題 (の正解) と照合する.
ということでそれを実装すればよいのだけど,どうもぐっと来ない.なぜぐっと来ないのか考えた結果,思い当たったのは以下の 2 点:
ぐっと来ないものを作ってもろくなことにならないのでとっとと却下する.
というわけで考え方を変えてみる.要は,投稿のリクエストに関して,
という条件を満たせばよいのかな.これでどうだろう.
実装はとりあえず以下のような感じ.$page_template_default には
<div class="arith"> <br> コメントスパム回避のため,以下の足し算の答えを半角でご記入下さい: <br> $arith_x + $arith_y = <input class="field" name="arith" value=""> <input type="hidden" name="arith_token" value="$arith_token"> <input type="hidden" name="arith_hash" value="$arith_hash"> </div>
を仕込み,これを表示する直前に
my $arith_x = int(rand(9)) + 1; my $arith_y = int(rand(9)) + 1; my $accepted_tokens = {}; if (-e $arith_token_file) { $accepted_tokens = Storable::lock_retrieve($arith_token_file); } my $arith_token; do { $arith_token = Digest::MD5::md5_hex($logid . $q->remote_host() . int(rand(2 ** 32))); } while (defined($accepted_tokens->{$arith_token})); my $arith_hash = Digest::MD5::md5_hex($arith_token . $arith_passph . ($arith_x + $arith_y));
とする.ここでは token ファイルは読み込んでいるだけなのに注意. if ($mode eq "write") { のときの処理は,
my $arith = $q->param('arith') + 0; my $arith_token = $q->param('arith_token'); my $arith_hash = $q->param('arith_hash'); my $accepted_tokens = {}; if (-e $arith_token_file) { $accepted_tokens = Storable::lock_retrieve($arith_token_file); } if (defined($accepted_tokens->{$arith_token})) { exit; } elsif ($arith_hash ne Digest::MD5::md5_hex($arith_token . $arith_passph . $arith)) { exit; } else { $accepted_tokens->{$arith_token} = 1; Storable::lock_store($accepted_tokens, $arith_token_file); }
とした.
トークンの生成は適当で構わないのだけど,発行済みのトークンで過去に受理されたもの,および受理される可能性のあるものと重複しないようにだけは気をつける必要があるので,何かむにゃむにゃな処理をやっている.
うーむ,ちっともお手軽じゃなくなってきた.いろいろ工夫してみたところで所詮足し算を実行されたら終わりですからね.なんかベクトルが間違っている気がしないでもない.
現状の問題点:
というか何か根本的に見過ごしていることがあるような気がしてならない….どんなもんでしょ.
(追記)
2007年05月06日 kazuhooku しょうもないつっこみしてすみません。よっぱらいつつの感想: syncookies のようなゼロ記憶だと難しいのかな。
http://b.hatena.ne.jp/entry/http://www.kagami.org/diary/2007-05-05-1.html
恥ずかしながら syncookies って初耳だったのでちょっと勉強.
なるほど.トークンを乱数を使って作る代わりに時刻を使うことにして,一定時間経過してたら reject するってことになりますかね.ハッシュ値の計算に時刻をつっこんでおくことで,サーバ側の保存無しで expire をチェックできるところがミソだと理解しました.
「一定時間」をうまく設定してあげる必要があるかも.短いとコメントを書いているうちに expire しちゃうし,長いとその間は固定パラメータ攻撃されちゃいますよね.まあ 1 時間くらいにしておけば実用上十分な気がしますが.
…というのが SYN cookies の動作を単純にマッピングした場合の話だと思いますけど,もしかするともっとうまい応用のしかたがあったり…?
というわけで [2007-04-21-1] 一週間ちょい使ってみているのだけど,今のところ完全封鎖できている.ここ程度の零細サイトであれば,それなりの効果が見込めると見てよいのではなかろうか.ちなみに一日あたりの攻撃数は,日によってばらつきというか波があるんだけど,50〜400 程度.
気になるのは,そもそもスパムでないコメントすら一切届いていないことなのだが,まあ普段からコメントを頂くことは稀なのでよしとしよう.
というわけで実装の話.くっつきBBSの $page_template_default に
<div class="arith"> <br> コメントスパム回避のため,以下の足し算の答えを半角でご記入下さい: <br> $arith_x + $arith_y = <input class="field" name="arith" value=""> <input type="hidden" name="arith_x" value="$arith_x"> <input type="hidden" name="arith_y" value="$arith_y"> </div>
みたいなのを仕込み,これを表示する直前に
my $arith_x = int(rand(9)) + 1; my $arith_y = int(rand(9)) + 1;
とする.んで,if ($mode eq "write") { のときの処理として
my $arith = $q->param('arith'); my $arith_x = $q->param('arith_x'); my $arith_y = $q->param('arith_y'); if (!$arith || $arith != $arith_x + $arith_y) { exit; }
を加える.実際には単に exit するのではなくて,ログを取るようにしてあるけど省略.
(追記) はてブでコメントを頂きました.
2007年05月02日 kazuhooku ?arith_x=1&arith_y=1&arith=2 みたいな固定化への対策が望ましいんじゃないかと思った。実質的には「何か」の入力を求めている時点でスパムよけとしては十分だろうけれども
http://b.hatena.ne.jp/entry/http://www.kagami.org/diary/2007-04-30-1.html
まったくおっしゃる通りで,パラメータの意味を理解すれば固定パラメータによる攻撃は可能です.パラメータとして渡すべき「問い」は「そこに書いてある」ので,原理的にはまあ同じことかと思ってたけど,実際の攻撃手順を考えてみるとそこにはちょっと敷居の差があるかなあと改めて思った.
というわけでちょっくら修正してみようかと思ったのですが,考え始めるといろいろややこしいので,別記事 [2007-05-05-1] で.
* [Williamtut] Nice blog ) http://anmdcf7i.com my blog (2015-03-28 19:43:21)
コメント欄 (くっつきBBS) に対する SPAM が多すぎて困る.以前いろいろ試してみたのだが [2006-04-09-2],やはり完全ではない.
というわけで,アクセシビリティは落ちてしまうけど,簡易 CAPTCHAもどき (?) を入れてみた.といっても画像とかを使うのではなくて,単に足し算の課題を出すだけ.真面目に破ろうと思ったら簡単に破れる類のものである.
で,果たして真面目に破ろうとしてくるスパマーがいるのかどうかに興味がある.しばらく様子を見よう.
chalow の「Referrer (Inside)」機能を常用している話は以前書いた [2006-05-05-1].
でもこの [YYYY-MM-DD-I] みたいな文字列を書くのって面倒くさくないすか? エディタ上で作業するなら該当記事を探して,日付を確認して,何番目の記事かを確認して…になるわけだけど面倒くさすぎる.そんなわけで,ブラウザで自分のページを開いて clsearch.cgi で検索してコピーペースト…ってのが最近の自分的主流なのですが,やっぱり作業は emacs の中で閉じている方が楽だ.
とここまで書いて,w3m.el でも使えばいいんじゃね? とか思ったがそれは気づかなかったことにして,
この [YYYY-MM-DD-I] な文字列を kill-ring につっこむ elisp を書いてみました.勢いだけで書いたので処理が汚いのは勘弁して頂くとして,というかあまりテストしてないのですが,一応動いている模様なので貼っておく.
(defvar chalow-date-regexp "^[01-9]+-[01-9][01-9]-[01-9][01-9]") (defvar chalow-itembullet-regexp "^\t\\*") (defun chalow-date-to-datestr (str) str) (defun chalow-kill-datestr () (interactive) (save-excursion (let ((curpos (point))) (if (re-search-backward chalow-date-regexp nil t) (let ((itemnum 1) (dstr (buffer-substring (match-beginning 0) (match-end 0)))) (goto-char curpos) (if (not (re-search-forward chalow-date-regexp nil t)) (goto-char (point-max))) (while (re-search-backward chalow-itembullet-regexp (1+ curpos) t) (setq itemnum (1+ itemnum))) (kill-new (format "[%s-%d]" (chalow-date-to-datestr dstr) itemnum)) (message (car kill-ring))) (message "date not found")))))
Ctrl-S とかで (別に他の何でもいいですが) 該当記事を探して,その記事の途中のどこかで M-x chalow-kill-datestr すると kill-ring に [YYYY-MM-DD-I] が追加されるので,Ctrl-Y で貼りつけます.
先頭の方の変数とかをいじれば,ChangeLog とは違うフォーマットで書いている場合にもある程度適用できるんではないかと思います.(というか私がそうしてます)
最近,copyurl+ とかでページタイトルをコピーしたり,bloglines のアイテム名をコピーしたりして,そのまま ChangeLog メモに貼りつけている場合が多い (いったん俺フォーマットを経由してですが).
コピーしたページによっては,タイトルの先頭にカテゴリ名がついている場合とか (tDiary なんかが典型),ちょっと前に流行った一文字 blog 略号 (?) がついている場合がある.それを ChangeLog メモ記法にそのままコピーして,末尾にカテゴリ名をつけるとこうなる.
* [を] chalow でアスキーアートを表示するためのプラグイン [tech][aa]:
- http://nais.to/~yto/clog/2006-09-23-3.html
これを chalow の ChangeLogReader.pm でそのまま読み込むと [を]〜 [tech][aa] 全体がカテゴリリストと認識されて,ちょっこすおかしなことになることに気づいた.
というわけで修正してみる.ややこしいな.合ってますかこれ?
- if ($ih =~ s/\s*\[(.+)\]$//) { # category + if ($ih =~ s/\s*\[(([^\[\]]+\]\s*\[)*[^\[\]]+)\]$//) { # category @cat = split(/\s*\]\s*\[\s*/, $1); }
ここしばらく,外部に公開する記事しか chalow を通していなくて,外部に公開する記事の場合タイトルとかは自分で整理し直すので気づいていなかった.ふと久しぶりに全記事を chalow に通したら「File name too long」なエラーが出て気づいた.
(追記) 例が適切でなくて誤解を招いてしまったのでちょっと修正.カテゴリは複数つく場合があるんです.まとめて切り出した後,split する処理が続いているコードでした.
* [かがみ] ああなるほど.空白に対してロバストにするなら s/(?>[^\\s\\]]... (2006-10-13 06:33:05)
* [otsune] それでsplitするのなら s/(?>\\s\\[)(.+)\\]$//で... (2006-10-12 05:05:59)
* [かがみ] すみません.わかりにくかったので本文修正しました.私の元の書き方では伝わるはずが... (2006-10-12 03:34:37)
* [otsune] ああ、勘違いしてました。s/(?<=\\s\\[)([^\\]]+)\\]... (2006-10-11 23:08:01)
* [かがみ] 試してみましたが,うまくいかないようです.% perl -e \'$ih = &... (2006-10-11 04:00:17)
* ...
ついで [2006-10-08-2] に bloglines アイテムをクリップボードにコピーする方も改版.こちらは bloglines の変更じゃなくて,Firefox の変更に対する対応になっていると思う.変更箇所は
というわけで以下を bookmark してください.
javascript:(function(){ /* setClipboard for Firefox LastModified : 2006-01-10 http://la.ma.la/misc/js/setclipboard.txt */ function setClipboard(text){ var url = [ 'data:text/html;charset=utf-8;base64,PGJvZHk+PC9ib2', 'R5PjxzY3JpcHQgdHlwZT0idGV4dC9qYXZhc2NyaXB0Ij4KKGZ1', 'bmN0aW9uKGVuY29kZWQpe3ZhciBzd2ZfZGF0YSA9IFsKICdkYX', 'RhOmFwcGxpY2F0aW9uL3gtc2hvY2t3YXZlLWZsYXNoO2Jhc2U2', 'NCxRMWRUQjJ3JywKICdBQUFCNG5EUGdZbGpBd01qSTRNejAlMk', 'YlMkY5JTJGZTJaZkJnYUdhV3dNRE1uNUthJywKICdrTU10TjRH', 'ZGdaZ1NJTXdaWEZKYW01UUFFJTJCQm9iaTFCTG5uTXlDcFB6RW', '9oU0dJJywKICdQRnAlMkZBeHNEREJRa3BGWkRGUUZGQ2d1eVM4', 'QXlqSTRBRVVCaXkwVndBJTNEJTNEJwpdLmpvaW4oIiIpOwpkb2', 'N1bWVudC5ib2R5LmlubmVySFRNTCA9IFsKICc8ZW1iZWQgc3Jj', 'PSInLHN3Zl9kYXRhLCciICcsCiAnRmxhc2hWYXJzPSJjb2RlPS', 'csZW5jb2RlZCwnIj4nLAogJzwvZW1iZWQ+JwpdLmpvaW4oIiIp', 'Owp9KSgi',btoa(encodeURIComponent(text)+'")</'+'script>') ].join(""); var tmp = document.createElement("div"); tmp.innerHTML = '<iframe src="'+url+'" width="0" height="0"></iframe>'; with(tmp.style){ position ="absolute"; left = "-10px"; top = "-10px"; visibility = "hidden"; }; var b; try { /* modified by swk */ b = top.frames[0].document.body; } catch (e) { b = document.body; } b.appendChild(tmp); setTimeout(function(){b.removeChild(tmp)},1000); } function extractText(node) { var text = ''; if (node.nodeType == 3) { /* TEXT_NODE */ text = node.nodeValue; } else if (node.hasChildNodes()) { var n = node.childNodes.length; for (var i = 0; i < n; i++) { text = text + extractText(node.childNodes[i]); } } return text; } function fmt(title, href) { return '\r\n\t* ' + title + ':\r\n\t- ' + href + '\r\n'; } var clog = ''; var h3s = top.basefrm.document.getElementsByTagName("h3"); for (var i = 0; i < h3s.length; i++) { var a = h3s[i].getElementsByTagName("a")[0]; clog = clog + fmt(extractText(a), a.href); } setClipboard(clog); })();
しかしこう bloglines や Firefox に仕様変更がある度に振り回されるのは何とかならんものか.何か根本的に方針を間違っている気がしないでもないなあ.
いろいろ文句言いながらも,しつこく bloglines 使ってます.
以前書いた keep new を解除する bookmarklet [2006-07-08-1] が動かなくなっていたので修正.
今までの bloglines では keep new のチェックボックスをクリックするとそのたびにページ遷移が発生していたのだけど,最近 Ajax 対応したらしくページ遷移しなくなった.というわけで bookmarklet の方で自前で Ajax 化する必要はなくなって,本家が用意してくれている JavaScript 関数を呼びまくるだけでよい.ずいぶんシンプルになった.
javascript:(function(){ var ipts = top.basefrm.document.getElementsByTagName("input"); for (var i = 0, k = 0; i < ipts.length; i++) { if (ipts[i].type == "checkbox" && String(ipts[i].onclick).match(/markUnreadItem\(\s*(\d+)\s*,\s*(\d+)\s*,\s*(\d+)\s*,.*\)/) && ipts[i].checked == true) { var siteid = RegExp.$1; var subid = RegExp.$2; var itemid = RegExp.$3; ipts[i].checked = false; top.treeframe.keepItem(siteid, subid, itemid, false); } } })();
* [Pragnesh] Wow, this is in every rseepct what I nee... (2013-01-01 19:28:22)
ソースコードなどを blog などに貼りつけるときにどうするのがよいか,という話がちょっと前に話題になっていたりして,その論点の一つに「横に長すぎる場合」をどう扱うかが挙がっていたりするのだけど,実は似たような問題はほかにもある.連続するASCII 文字列である.
典型的には,長ーい URL 文字列を表示した場合に,枠からはみ出したり,枠自体がびろーんと伸びて見ずらくなったりする.といっても Firefox の場合だけなのだけど.
対策法がこちらによくまとまっている:
ざっくり要約すると,まず Firefox ユーザ側の立場としては,
一方,Firefox を使っているかどうかに関らず,ウェブサイトの運営側の立場としては,
ちょっとややこしいのは,url_breaker には「A要素のみを処理するもの」と「全文を処理するもの」という 2 系統があり,さらに「xpi版 (つまり普通の拡張機能)」と「Greasemonkey版」の 2 系統がある,のだが,それらが直交していない.えーと,こんな感じ?
A要素のみ処理 | 全文を処理 | |
xpi | url_breakerの Ver.0.2.2以降 | 同左 (オプション設定) |
Greasemonkey | url_breakerの Ver.0.2.1 | url_breaker_plus |
というわけで,実はしばらく前からウェブページ側に仕込んでみている. url_breaker_plus の方です.各 HTML ファイルの body 要素の一番最後辺りに,
<script src="/js/url_breaker_plus.user.js" type="text/javascript"> </script>
と入れる. url_breaker_plus.user.js はこちら.オリジナルのままだと開き括弧 {, {, [ の直後でも改行しちゃって(個人的に)気持ち悪いので,正規表現を以下のようにちょっと修正して使っている.
// var regexp = new RegExp("([!-%'-/:=\\?@\\[-`\\{-~]|&)"); var regexp = new RegExp("([!-%'\\)-/:=\\?@\\\\-`\\|-~]|&)");
さて,実は長い文字列が横に伸びちゃうのが一番うっとうしいと個人的に思っているのは bloglines なのけど,url_breaker の効果は有ったり無かったりでどうも挙動が謎である.bloglines の記事表示が table レイアウトなのが問題なのかも.
blog に限らずウェブサイト全般の話やけども,実名を晒して運営するのか,それともあくまで匿名で運営するかは,
自由だ─────!!
という犬井ヒロシ風の前フリは置いといて,実名サイトと匿名サイトの間のインタフェースには,たまにややこしい場合があるという話.
ここは実名サイトなのでそっち側の立場からの見方だけど,匿名サイトの中には,たとえば個人的人間関係とかによって「実は誰がやっているか」を知っているサイトがあります.そういう場合,そのサイトの記事にリンクを張ったりトラックバックしたりとかするときに,その文脈によっては人間関係に関する情報を含んでしまうことがあり得て,結果として相手の素性をバラしてしまうことになるのではないかと躊躇することがあります.
というかその辺に無頓着だったせいでバラしてしまったことが過去におそらく多数あります.すんません.今もやってるかもしれません.
逆に言うと,そういう (つまり個人的知合いの) 匿名サイトの場合,面白い話があっても,紹介しようかしまいか迷って,どういう文脈で紹介すれば「安全」か迷って,迷うこと自体が面倒くさくなって結局紹介しないってことが割と多いです.いや,それがよいとか悪いとかではなくて,事実そうなってますという話なので,ご理解ください.
あと,そもそも実名を隠したいのかどうなのかよくわからなくて悩むこともありますが,まあそれはそれということで.
(以下やや私信)
というわけで「site:foo.bar.example.com 実名」とかでぐぐったりした形跡が残っているのは,単に上記のような目的の調査の結果なので,あまり深く考えないでください.
ついでに書くと,「でもこの人,トップページには名前書いてるよなー」とか疑問に思いました.
(私信おわり)
「画像で取得するAPI」ではてなブックマーク件数をお手軽に表示してみた矢先なのだが [2006-07-15-3],やっぱりやめた.
はてなが重いときとか反応しないときに,自分のページの表示が影響を受けるのが嫌だってのがまずあるけど,そのときに,あー,俺いまはてなサーバに無駄に負担かけてるーという罪悪感があって精神衛生上よろしくない. (いや,もちろんトラフィック全体からみると,うちから発生する分なんて誤差に過ぎないわけですが,単に気持ちの問題なので)
つうわけで真面目にはてなブックマーク件数取得APIを叩いてみることにしたですよ.
やり方はいろいろあると思いますが,定期的に件数を取りに行っておいて, HTML から SSI で include することにしてみた.こんなのを cron で定期的に走らせます:
#!/usr/bin/perl use strict; use XMLRPC::Lite; my $html_clog_url = 'http://www.kagami.org/diary'; # don't add trailing slash my $html_clog_dir = '/home/swk/www/diary'; my $hatebu_count_dir = '/home/swk/www/hatebu_count'; my $EndPoint = 'http://b.hatena.ne.jp/xmlrpc'; my @urls = (); while (<$html_clog_dir/*.html>) { next unless /\/(\d{4}-\d{2}-\d{2}-\d+)\.html$/; my $ymdi = $1; push(@urls, "$html_clog_url/$ymdi.html"); if (@urls == 50) { &writecount(\@urls); @urls = (); sleep(3); } } if (@urls > 0) { &writecount(\@urls); @urls = (); } sub writecount { my ($uref) = @_; my $map = XMLRPC::Lite->proxy($EndPoint) ->call('bookmark.getCount', @{$uref})->result; foreach (@{$uref}) { my $url = $_; my $count = $map->{$_}; my ($ymdi) = ($url =~ /\/(\d{4}-\d{2}-\d{2}-\d+)\.html$/); if ($count > 0) { my $str_count = $count . " user" . (($count > 1)? 's': ''); my $str = << "HTML"; <span class="hatebu_count"> <a href="http://b.hatena.ne.jp/entry/$html_clog_url/$ymdi.html"> $str_count</a></span> HTML ; &save_file("$hatebu_count_dir/$ymdi.htmlin", \$str); } elsif (-e "$hatebu_count_dir/$ymdi.htmlin") { unlink("$hatebu_count_dir/$ymdi.htmlin"); } } } sub save_file { # from kuttukibbs-1.0rc3 my ($fn, $strp) = @_; open(F, "> $fn") or die "can't open $fn : $!\n"; flock(F, 2); print F $$strp; close F; }
chalow のテンプレートは,
... <h3 class="subtitle"><TMPL_VAR name=header> <TMPL_VAR name=cat> <!--#include virtual="../hatebu_count/<TMPL_VAR name=ymdi>.htmlin" --> </h3> ...
な感じにする.
* [Jace] This is just the perfect aswner for all ... (2013-01-01 17:56:57)
chalow のテンプレートの <h3> の辺りに入れてみた ($item_page_template と $item_template の両方).ちっともブックマークされていないのが火を見るより明らかになった.
... <h3 class="subtitle"><TMPL_VAR name=header> <TMPL_VAR name=cat> <span class="hatebu"> <a href="http://b.hatena.ne.jp/entry/$clog_url<TMPL_VAR name=ymdi>.html"> <img src="http://b.hatena.ne.jp/entry/image/large/$clog_url<TMPL_VAR name=ymdi>.html" alt="See Hatena bookmark comments"></a></span> </h3> ...
1 件ずつリクエストが発生するのがちょっと微妙かも.はてなサーバ側の負担も結構馬鹿にならないだろうなあ,などと余計なことを心配してしまうけど,こういう API を公開する時点で,その辺の目処は立ってるのだろう.
cf. はてなブックマーク件数取得API: http://d.hatena.ne.jp/keyword/%A4%CF%A4%C6%A4%CA%A5%D6%A5%C3%A5%AF%A5%DE%A1%BC%A5%AF%B7%EF%BF%F4%BC%E8%C6%C0API
(追記) やっぱやめた → [2006-07-16-1]
* [Matias] I never thought I would find such an evr... (2012-12-30 15:20:09)
* [かがみ] ついに来たですね.そちらではいかがでしょう? (2007-06-28 04:15:46)
* [ドタドン] ついにスパマーが! (2007-06-23 11:34:29)
改版しました [2006-10-08-2]
他人様のコードをいじっているうちに [2006-07-05-2] [2006-07-05-3] 何となく勘がつかめてきたような気がするので,調子に乗って懸案事項に手をつけてみる.
以前,bloglines で表示中の記事のタイトル名,URL をまとめてクリップボードにコピーする bookmarklet (Firefox 専用) を書いた [2006-02-11-1] [2006-04-22-1].これ使うときは,
という流れが多くて,何とかならんかなと思ってたのだ.
というわけでこんな感じ.
onload を使っているので MSIE では動作しないはず.直すのは簡単だと思うけど,とりあえず放置.
ソース:
javascript:(function(){ function phandler (paths) { if (paths.length < 1) { return; } else if (paths.length == 1) { top.treeframe.location = paths[0]; return; } var p = paths.shift(); var xhr = new XMLHttpRequest(); xhr.onload = function () { phandler(paths); }; xhr.open('GET', p, true); xhr.send(null); } var paths = new Array; var ipts = top.basefrm.document.getElementsByTagName("input"); for (var i = 0, k = 0; i < ipts.length; i++) { if (ipts[i].type == "checkbox" && String(ipts[i].onclick).match(/markUnreadItem\(\s*(\d+)\s*,\s*(\d+)\s*\)/) && ipts[i].checked == true) { var subid = RegExp.$1; var itemid = RegExp.$2; ipts[i].checked = false; paths[k++] = '/myblogs_subs?ui=1&subid='+subid+'&itemid='+itemid; } } phandler(paths); })();
期せずして Ajax デビューしてしまった.(XML 使ってないから Aj デビューか?)
やってることは単純で,keep new のチェックボックスについている onclick 属性から,その記事の subid と itemid を取り出して,それらからパス名 '/myblogs_subs?ui=1&subid='+subid+'&itemid='+itemid を生成して,GET しに行っている.
bloglines で実際に keep new のボタンを押した場合は, parent.treeframe.location にこのパス名を直接代入するコードが実行されるのだけど,複数の記事についてこれを単純に繰り返すと,前のやつの読み込みが終わる前に次のやつを読みに行ってしまってうまく行かない.というわけで XMLHttpRequest を使ってみた.
(open の第3引数を false にすればもっと簡単に書けるかと思ったけど,そうすると解除がすべて終わるまで操作を受け付けなくなってしまって,使いにくかった)
ついでなので,まとめてクリップボードにコピーする方もちょっとだけ書き直しておく.以前のは正規表現で無理矢理抽出してたけど,真面目に DOM ツリーをたどるようにした.
ソース:
javascript:(function(){ function setClipboard(text){ /* 省略 (http://la.ma.la/misc/js/setclipboard.txt) */ } function fmt(title, href) { return '\r\n\t* ' + title + ':\r\n\t- ' + href + '\r\n'; } var clog = ''; var h3s = top.basefrm.document.getElementsByTagName("h3"); for (var i = 0; i < h3s.length; i++) { var a = h3s[i].getElementsByTagName("a")[0]; clog = clog + fmt(a.firstChild.nodeValue, a.href); } setClipboard(clog); })();
ChangeLogメモ以外の形式に変換したい場合は,fmt() の中身を適当にいじってください.
* [Sandroo] An inetlglinet point of view, well expre... (2013-01-01 20:46:17)
chalow では,[2006-05-05-1] のように書くと他の記事が参照できて,逆に参照された側の記事の一番下には参照元一覧が表示される (デフォルトのテンプレートだと「Referrer (Inside)」).後で読むときにとても便利なので使いまくり.
参照記事に飛ぶ場合は,文脈から飛ぶ先の内容がある程度予測できるのだけど,Referrer (Inside) 一覧の方は,クリックしてみるまで内容が分からない.ここに記事タイトルでも表示されてると便利かな,などとふと思ったので試してみた.
まず parse_entry() の for ループの中,「ハッシュに格納」と「日付リンク情報の格納」の位置を入れ換えて,後者を次のように変更.入れ換えるのは,$ent->{$i}{h} を使いたいから.($ent->{$i}{ho} でもいいのかも知れないけど,念のため)
# ハッシュに格納 $ent->{$i}{h} = okikae($ent->{$i}{ho}); $ent->{$i}{c} = okikae($c); # 日付リンク情報の格納 while ($c =~ /\[((\d\d\d\d-\d\d)-\d\d(-\d+)?)\]/g) { $inside_ref{$1}{"$ymd-$i"} = $ent->{$i}{h}; }
で,get_inside_ref() を以下のように変更.(変わってるのは return map ... の行だけ)
sub get_inside_ref { my ($id) = @_; if (defined $inside_ref{"$id"}) { return map { "<br> " . datestr2anchor("[".$_."]") . " " . $inside_ref{"$id"}{"$_"} } (sort {$b cmp $a} keys %{$inside_ref{"$id"}}); } return (); }
というわけでこんな感じ↓の表示になるはず.これは自己参照だけど.
以前公開して [2006-02-11-1],その後 Firefox 1.5.0.1 だと動かないことが判明した [2006-03-08-2] bloglines to ChangeLogMemo な bookmarklet ですが,Firefox が 1.5.0.2 に自動更新されてから試してみたところ,普通に動くことが判明.なんですかこれ.
実はちょうど動かない原因を調査していて,回避策が分かった矢先だった. Firefox のJavaScript コンソールによると,フレームのあるページで document.body.appendChild と document.body.removeChild を呼び出そうとすると
エラー: uncaught exception: [Exception... "Node was not found" code: "8" nsresult: "0x80530008 (NS_ERROR_DOM_NOT_FOUND_ERR)" location: (コード略) Line: 1"]
となっていたらしい.
バグフィクスリストを見ても,とくに該当しそうなものに見当がつかないんだけどな.まいいか.
というわけで,Firefox 1.5.0.1 で動かさない限りは動作は変わりませんが,一応新しいの置いておきます.
以前のは,sacja TTT-protokolo さんの bookmarklet が元ネタでしたが,上記の原因調査の過程で,そのさらに元ネタである 最速インターフェース研究会さんの に遡りました.
中身は
javascript:(function(){ function setClipboard(text){ (略) } var src = top.frames[1].document.body.innerHTML; var pat = /<h3><a title=%22.*href=%22(.*)%22 target=%22_blank%22>(.*)<\/a>.*<\/h3>/g; var clog = ''; var result; while ((result = pat.exec(src)) != null) { clog = clog + '\r\n\t* ' + result[2] + ':\r\n\t- ' + result[1] + '\r\n'; }; setClipboard(clog); })();
setClipboard() の中身は http://la.ma.la/misc/js/setclipboard.txt です.途中の appendChild, removeChild するところをいじってますが,敢えて Firefox 1.5.0.1 で使わない限りはオリジナルのままでよいです.
ChangeLog じゃなくて他のフォーマット変換したいときは clog = clog + ... のあたりを適当に.
* [Nickey] The expertise shines through. Thanks for... (2012-12-30 17:30:07)
結論から言うと,敗北です.
kuttukibbs に,できるだけ簡単な修正を加えるだけでどこまでコメントスパムをブロックできるか試してみた.
巷でよく行われているのは,「2 byte 文字がいっさい含まれていないものは無条件で弾く」というもの.日本語サイトの場合,ほぼこれで問題無いわけなのだけど,なんていうか,ほら,技術的に 負け って感じがするじゃないですか(ぉ.というわけでもう少しギリギリの所で戦えないかと試してみたかったわけですよ.
戦略は以下の通り:
やってみるといずれもそれなりに有効で,そこそこ引っかかってくれる.最初の hidden なタグを埋め込んどく程度の低レベルなやつでも,全く無力というわけではないみたい.
だけど,ある特定の記事 (具体的には [2006-03-07-2] なのだが) については,これらをすり抜けて来る奴ら続出.強力なのにマトかけられちゃったっぽい.というわけで「この記事限定」で「2 byte 文字が含まれておらず,かつ URL らしき文字列で終わっているもの」はすべて弾くことにした.
一応これでいまのところ完全封殺.なのだけど,勝ち負けで言ったら敗北ですな.
Movable Type とかだと,いったん必ず Preview ページを表示して,そこで hidden なパラメータを配るなんて方法がよく使われているらしい.でもこれも対策が取られるのは時間の問題かなという気もする.
結論:
* [Pd8ruxef2l] goose jacket yoke wong improvisation in ... (2014-10-23 18:38:30)
* [Whktjmfl] France - In the past few months, we expe... (2014-04-25 18:41:30)
* [Fkhluizl] , <a href="">オ... (2014-04-14 22:49:27)
えらく古い話ですが,
可能であれば http://www.example.com/ と http://example.com/ の両方でアクセスできるようにする方がいいし,またその場合は,単に両方の URL でアクセスできるだけじゃなくて,片方に redirect するようにした方が SEO 的によろしいという話.
うちは今までは www.kagami.org でしか答えてくれないレンタルサーバだったので気にしていなかったけど,サーバ移転後は kagami.org でもアクセス可能になった.というわけで .htaccess で
RewriteEngine on RewriteCond %{HTTP_HOST} sakura\.ne\.jp$ [NC,OR] RewriteCond %{HTTP_HOST} ^kagami\.org$ [NC] RewriteRule .* http://www.kagami.org%{REQUEST_URI} [L,R=301]
と設定.
ところで,
「同じ内容を返す URL は常に一つ」という概念のことを“Permalink”といい
http://labs.cybozu.co.jp/blog/akky/archives/2005/12/url_2_www.html
ほんと?
ある URL が指す記事が唯一に定まるのであって,ある記事を指す URL が唯一に定まるわけではなかろう.それじゃあいわゆる「blog のトップページ」とか「月ごとページ」とかが存在できなくなっちゃう.
というか,URL が唯一じゃないから,そのうち 1 つを選んで「これが permalink ですよ」と明示する必要が生じるわけで,むしろ「同じ内容を返す URL が唯一ではない」(かつそれら複数の URL の中には,今後同じ内容を返すとは限らないものが含まれている) ことが permalink という概念がわざわざ発生した前提になっているといえるんじゃないかな.
というわけで,この話と permalink は無関係だと思うのです.
今まで使ってたメイルネットのサーバでは perl 5.005_03 (i386-freebsd) が使われていた.モジュール群はあまり揃っていなかったので,必要なものは ~/lib/perl に自分でインストールして使っていた.
さくらインターネットでは,/usr/bin/perl は v5.8.4 (i386-freebsd-64int).モジュールもそこそこ揃っている.これなら自前でモジュールをインストールする必要はないかなと思っていたけど,甘かった.
Storable に互換性がない.
tb.cgi では,トラックバックのデータの保存に Storable が使われている.そのデータが読めなくなってしまった.Storable::retrieve が「Byte order is not compatible」とおっしゃっている.うーむ.
幸い,さくらインターネットのサーバには perl 5.005_03 built for i386-freebsd も /usr/bin/perl5 としてインストールされているので,こっちを使うことにした.こっちのバージョンではモジュールがあまり揃っていないらしい.というわけでメイルネットのサーバで使っていた ~/lib/perl 以下をごっそりコピーして使うことにする.再コンパイルとかせずにそのままで動くのはありがたい.
他の CGI (clsearch, kuttukibbs, noascii) は perl v5.8.4 で問題なく動くようなのでそちらで動かす.ただし use lib で ~/lib/perl を指定しているとモジュールの互換性の問題で動かないので,指定を止める.
とりあえずはこれでいいけど,いつまでもこのままってわけにもいかないかな.過去データをまとめて新しいファイル構造に変換して,v5.8.4 に移行するようにした方がいいかも知れない.調べてみると,Data::Dump を使って一旦テキストとして吐き出させるという方法があるらしい.そのうち試してみるか.
おまけ.というかちょっとだけはまった落とし穴.
さくらインターネットのサーバには,以下の 2 種類の perl がインストールされている.
そして以下のような symlink がある.
/usr/local/bin/perl5 は 5.005_03 を指しているのが自然だよなあ.どうしてこんなことになっているんだか.
* [かがみ] なるほど,そうかも知れませんね.しかしそうだとすると /usr/bin/perl... (2006-03-27 04:45:47)
* [otsune] >どうしてこんなことになっているんだか.おそらく、/usr/local/b... (2006-03-26 21:21:18)
今まで使っていたレンタルサーバの契約 (年更新) が来月切れる.ちなみにここ:
メールサービスだけ 4 年前に使い始めて [2002-04-19-1],その後 1 年ちょっと前からウェブを使い始めた [2004-11-14-2].そして現在,ウェブ容量の 50MB はだいたい使い切りそうな状態に至っている.容量の大きなコースは,競合他社と比べてあまりに割高だ (まあ現コースもだけど).
というわけで,他社サービスに乗り換えることに決めました.メイルネットさん今まで大変お世話になりました.
移転先はさくらインターネットのスタンダードプラン (http://www.sakura.ne.jp/).以下のような辺りが決め手となって選んだ.
最初の 2 つは,まあ個人的な趣味.やっぱり使い慣れている環境に近いのはありがたい.3 つめは直接的な要因ではないけど,ちゃんとした (?) ユーザ層に支持されているんだなあというのが伝わって来て,決心が後押しされた感じ.
設定の話.ウェブ関連の修正は以下の通り.
最後の CGI 関連についてちょっと補足説明が必要だと思うけど,長くなるので別記事で[2006-03-25-3].
というわけで,この辺を変更して動作が確認できたので,旧サーバのコメントとトラックバックを停止 [2006-03-25-1] して,DNS 情報を更新.新しい情報が伝播して新サーバにつながるようになれば,コメントとトラックバックも復活したように見えるという寸法.もしこの記事が読めているのであれば,新サーバにつながっているはずです.
メールの方は,単に同じ名前のアカウントを作るだけで,何の苦労もなく移行できた,はず.
メンテナンスのため一時停止します.
(追記) 再開しました.たぶん.
* [Lena] Your posting is absulotely on the point!... (2013-07-03 18:54:44)
* [かがみ] あーあー,てすとてすと (2006-03-25 18:40:41)
新しくなりました.こちらへ [2006-10-08-3].
bloglines で開いているフィードのアイテムをごっそり ChangeLog 形式に変換して,クリップボードへコピーする bookmarklet を書いてみた.ただし firefox 専用.
書いてみたというか,下記の「ページタイトル+選択文字列+リンクを clipboardにコピーするbookmarklet」をちょっと書き換えてみただけです. bl2clog() って関数が新しいところで,他はほとんど同じ.
bl2clog() の中の clog = clog + ... のところをいじれば,違う出力フォーマットにも簡単に対応できるはず (実際,自分では ChangeLog とはちょっと違うフォーマットでメモを取っている).
JavaScript は読むことも書くこともできないので,なんか変なことやってる可能性大.実際,正規表現で力まかせに処理しているのがちょっとダサい感じ.bloglines のページ構成が変わったらアウト.もっと真面目に element や attribute を抽出するのが正しいんだろうなとか思うのだけど,まあ当面はこれでいいか.
最近は,気になったアイテムはとりあえず keep new しておいて,時間があるときにまとめて読むことが多いんだけど,ふと気づくと数十個 keep new されていて自分のメモに転記するのも億劫になってしまう(で,さらにたまる).というわけで,keep new なものをまとめて自分メモに変換する手段が欲しかった.
ついでに keep new の一斉解除もできるといいんだけど,どうすればいいのかな… (追記: できました [2006-07-08-1])
(追記) Firefox 1.5.0.1 だと動かないようです [2006-03-08-2].付け焼き刃なのでどこをどう直せばよいのかさっぱり分かりません…
(追記) Firefox 1.5.0.2 だと普通に動くようです [2006-04-22-1].なんだかさっぱり分かりません.
* [online pharmacy] food allergy rash hair transplant surgeo... (2019-02-27 08:11:26)
* [Consuelo Hornibrook] Hello, it\'s Consuelo here!I\'m pinging ... (2019-02-20 13:05:58)
* [Manueltak] [url=http... (2019-02-20 10:36:13)
* [JesusAvemn] [url=http... (2019-02-20 00:53:25)
* [asiameewz] amazon online and as a result Flipkart i... (2019-02-19 18:32:43)
* ...
ごあいさつ文化圏から spam 文化圏への矢印は,ちょっとカルチャーショックかも.
ちなみに私の場合は,他の記事に言及した際に,その元記事の筆者に積極的にフィードバックしたい内容があるときだけトラックバックを送信することにしてます.まあ面倒くさいからってのが大きいけど.あと送信先の空気も読むけど.
トラックバックをもらった場合の対応は,(少なくとも今のところ)もらうこと自体があまりないので,別に考えてません.
* [Gmira] Last one to utiilze this is a rotten egg... (2013-03-22 07:42:42)
はんげ …って何だろう?
とナチュラルに思いました.私だけですかそうですか.
やろうやろうと思ってて放置していた.本当は受付時に処理するのが正しいと思うのだけど,とりあえず表示時で対応する.tb.cgi の sub enc の定義を除去して,代わりに以下を挿入.
my $enc_maxlen = 512; sub round_utf8 { # http://www.akatsukinishisu.net/itazuragaki/id/round_utf-8.html my $str = shift; return $str if ($str =~ /[\x00-\x7F]$/); $str =~ s/[\xC0-\xFD]$//; $str =~ s/[\xE0-\xFD][\x80-\xBF]$//; $str =~ s/[\xF0-\xFD][\x80-\xBF]{2}$//; # $str =~ s/[\xF8-\xFD][\x80-\xBF]{3}$//; # $str =~ s/[\xFC-\xFD][\x80-\xBF]{4}$//; $str; } sub enc { use Jcode; my $str_orig = $_[0] ? Jcode->new($_[0])->utf8 : $_[0]; my $str = &round_utf8(substr($str_orig, 0, $enc_maxlen)); if ($str ne $str_orig) { $str .= " ..."; } return $str; }
utf8 の末尾切り落とし処理はぐぐって見つけたものを頂きました.自分では理解してませんのでそのままこぴぺしてます.
chalow に付属する検索 CGI の clsearch.cgi が,いつの頃からか詳細モード ($mode == 1) だと記事タイトルや日付を表示してくれなくなってて,あれ? とか思いつつ放置していた.
で,ふと思い立って中身を読んでみたところ,ページの最小単位が日ごとからアイテムごとに変わったときの副作用だと理解した.
詳細モードの動作は,
となっている.日ごとページから抜き出していたときは記事タイトルが start: 〜 end: 間に含まれていたけど,アイテムごとページの場合,デフォルトのテンプレートだと記事タイトルは <h1>〜</h1> の方にあるので,結果として記事タイトル無しのまま抽出されて並ぶことになる.
というわけでアイテムページのテンプレートでも,start: 〜 end: 間に記事タイトルとかを書いてやるようにすれば,clsearch.cgi はちゃんと表示してくれる.<h1>〜</h1>の方はどうしましょうかね,と思ったけど,両方に書いておくことにした.ちょっと変かな.まあいいよな.
さて日付はどうしよう.というか仕組みを考えると,アイテムごとページが導入される前から日付は表示されていなかったってことになるな.よく覚えてないけど.一番簡単なのは,start: 〜 end: 間に日付も入れてしまうって方法かな.
<!-- start:<TMPL_VAR name=ymdi> --> <div class="day"> <h2><span class="date"><a href="<TMPL_VAR name=ymd>.html"> <TMPL_VAR name=ymd></a></span></h2> <div class="body"> <div class="section"> <h3 class="subtitle"><TMPL_VAR name=header> <TMPL_VAR name=cat></h3> <TMPL_VAR name=content> (中略) </div><!-- section --> </div><!-- body --> </div><!-- day --> <!-- end:<TMPL_VAR name=ymdi> -->
start: 〜 end: の意味を変えちゃうのでちょっと危険な香りもする.日ごとページの方の start: 〜 end: と構造が変わっちゃうし.これが嫌な場合は clsearch.cgi をいじるしかないかなあ.
(実は最初は clsearch.cgi をいじってたんだけど,結局元に戻して以上のような対処に落ち着いた)
chalow で %all_entries をキャッシュするようにしたら高速化できないかな,とふと思って,とりあえずやってみたけど 40 秒 → 30 秒程度だった.残りの内訳は HTML 生成ループと write_*_page 群がそれぞれ 10 秒強って感じ (← コード書く前に計れと小1時間).やはりそっちもキャッシュしないとダメか.それはめんどくさそう.
カレンダーとか月別リストとか inside refer とか same day とかは, JavaScript のくっつきなり SSI なりとしてファイル分離するのが正しいのかなあとか漠然と思った.
--stop-date でいいじゃんと言われるとそれまでなんですけどね.なんとなく,あの敗北感がいや.
ブログデザインの間違いトップ10.
ふーん,そんなもんなのかな.よく分からんけど.
とりあえず,
5. Classic Hits are Buried
これは趣旨が理解できた.よく考えると,そもそも自分が書いた記事ごとのアクセス数の分布ってちゃんと見たことなかったな.
というわけで手抜きワンライナーを書く.
% ( cd /path/to/chalow_output/; awk '{print $7}' /path/to/apache_log_archive/*.combined_log | egrep '^/diary/....-..-..-[01-9]+\.html"' | sort | uniq -c | sort -rn | sed 's#/diary/##' | sed 's/"//' | awk '{print $2}' | xargs grep '<title>' | sed 's/:<title>/ /' | sed "s# - swk's log</title>##" ) | less
まあこんなもんかな.タイトル表示とアクセス数の表示が一緒にできるといいけど,ワンライナーだと難しいかな.
というわけで,この手抜き状態のまま加工して,サイドバーに「アクセスの多い記事」一覧として埋め込むことにしてみました.1 週間ごとに更新されます (サーバのログが 1 週間ごとにしか手に入らないので).
ネタバレ記事を書くのをどうしようかと悩んでいたわけなのだが [2005-10-20-2],まあいいやということで,ごく普通にテキストと背景の色を同じにして書いてみた[2005-10-21-2].しばらくして
RSS リーダならそのまま読めてしまう
ことに気づいた.のわー.読みたくないのに読んじゃった人ごめんなさい.
応急措置ということで,chalow の write_rss_file() の中に
$coen =~ s!<img src="([^h].+?)"!<img src="$clog_url_pref$1"!g; +$coen =~ s!<div class="hidden">.*?</div><\!--hidden-->!<div>\(hidden\)</div>!gsm; my $cont = $all_entries{$ymd}{$i}{c}; +$cont =~ s!<div class="hidden">.*?</div><\!--hidden-->!<div>\(hidden\)</div>!gsm; $cont = html2xmlstr($cont);
な処理をつっこんで,ネタバレ部分を
[esc]<div class="hidden">[/esc] はうン [esc]</div><!--hidden-->[/esc]
な感じで囲んでおくことにする.うーん,アドホック.
まあ,そもそもビジュアルでないブラウザの人や CSS 切ってる人は読めちゃうわけですが.前回も書いたけどどうしたものか.
えーと,vi の話の件ですが [2005-08-28-1],ここのアクセスログは 1 週間ごとにしか見れないので全然気づいてなかったんだけど,blogmap に載ってるよとか yendot に載ってるよとか教えられて,ようやく状況に気づきました.
つうかどっちのサイトも初めて知りました,すんません.何かトラックバックが妙に多いなとは思ってたのですが.
リンク元をいろいろ見て回ると,引用ばかりで読みにくいという指摘なども頂いていたりして,実際おっしゃる通りなわけです.もう少し読み手のことを考えて書くべきなのかなあとも思うのですが,あまりそんな文才も余力もないので,まあ当面は今まで通りマイペースで,自分用メモの延長ってことで書いていきます.
関連しつつちょっと脱線しますが,「引用だけ」てのは「そもそも引用とは認められない」かも [2005-06-13-1] って話もあるので,ちょっと考えねばならんのは確かなんですよね.
でも,「ささっと取ったメモ」を「as is で公開する」ことによる情報の流通ってのも,いわゆる blog の重要な側面な気はするんです.誰かの権利を侵害しているのでない限り,あまり杓子定規に著作権法とか考えてても生産的じゃないと思うので.んー,もしかして自分で気づいてないだけで何か侵害してます?
あと,見ずらい一因は,blockquote な部分と,そのネタ元の URL を書いてる部分が分離している点にもあると思うので,そこは何とかしようと思ってます.これは,プレインテキストで書き続けて来たメモを chalow で公開するようになる以前からの書き方を,そのまま踏襲していることによります. [category: logging]
他人事だと思ってた Musical Baton が回ってきた.まあ chain mail みたいなもんだからいつかはやってきても不思議はないんですが.
ん,musical button なの? ずっと baton だと思ってた…ていうかやっぱ baton が正しそうじゃん.まあどっちでもいいけど.
古い人間なので電子ファイルではあまり持ってません.試聴のために取って来て,そのまま残っているものがポツポツとある感じ.しかも ls *.mp3 すると,なんか perry.mp3 とか harada.mp3 とかが混ざってて正確に計測できないんですがどうしましょう.まあ面倒なんでそういうのもひっくるめて測りましょうか.
% ls -l *.mp3 | awk 'BEGIN{s=0}{s += $5}END{print s}' 64263257
というわけで 64MB.
ちなみに一番小さい音楽ファイルは napalm_death-you_suffer.mp3 で 100KB.演奏時間 5 秒 (そのうち無音部 4 秒).
「ちょうど今」というのを「baton を渡された記事を読んだ瞬間」だとすると,何も聴いてませんでした,ってのが答えです.これだけとつまんないので,そのとき CD ドライブに入ってたのを見るとこれでした.
これを書いてる今聴いてるのはこれ↓だったりしますが,まあいくらでも恣意的に選べるから (要するに,聴くもの選んでから書けるから) 面白くないよね…
Zero Hour / The Towers of Avarice
Amazon で予約して購入.
あ,アルバム 5 枚じゃなくて 5 曲ですか.難しすぎ.いや 5 枚でも難しいけど,さらに難しすぎ.
「よく聴く」ってのはその時期によって変わるので思い入れの方でいきますか.悩ましいけど悩んでもしかたないのでざっくりと.
ここを読んでそうでかつ blog 書いてそうな知人の心当たりがほとんどありません.ヒロシです…
んーと,
まずは,その数少ない心当たりの 2 人に:
次に,面識はないのですが,時々引用してくださる chalower で,まだバトンが来てなさそうな方に勝手に渡してみます:
ラスト,ここは読んでないと思うけど学生時代のサークル関係へ投げてみる.音楽人脈を生かした,濃い方面への baton 渡しを期待します:
だいぶ前にいじった気がするけど,書き忘れてたので思い出しながらメモしておく.
月ごとの日付一覧をカレンダ風に表示するときに,ちまたの blog ツールだと,前月や翌月へのリンクが表示されていたりする.無きゃ困るわけでも,あるとすごく便利なわけでもないけど,何となく欲しくなったのでつけてみた.もうちょっときれいに作れたかもしれないけど,とりあえずこんな感じ. chalow-1.0rc4 がベース.
まず
### HTML ファイルの出力 write_index_page();
の直前に
my @month_array = sort keys %month_page; my %month_array_rev = (); for (my $i = 0; $i < @month_array; $i++) { $month_array_rev{$month_array[$i]} = $i; }
を入れる.同じようなものを write_month_page でも作っているので実は二度手間.ここで作ったものを write_month_page でも使うようにすればいいんだけど,面倒なので放っとく.
次に make_calendar_table 内の
my @wn = ("Su", "Mo", "Tu", "We", "Th", "Fr", "Sa");
の直前に,
my $idx = $month_array_rev{$ym}; my ($link_before, $link_after) = ('<<', '>>'); if ($idx > 0) { $link_before = '<a href="' . $month_array[$idx - 1] . '.html"><<</a>'; } if ($idx < @month_array - 1) { $link_after = '<a href="' . $month_array[$idx + 1] . '.html">>></a>'; }
を入れる.
同関数のヒアドキュメント内で
<caption><a href="$ym.html">$ym</a></caption>
の代わりに
<tr> <td align="center" colspan=2>$link_before</td> <td align="center" colspan=3><a href="$ym.html">$ym</a></td> <td align="center" colspan=2>$link_after</td> </tr>
とする.以上.
しかしアレだ.自分仕様パッチが複数の改造目的から成り立っていると,そのうち一部の目的のものだけ切り出して配布するってのが面倒だな.各要素ごとにオリジナルからのパッチの形でまとめて,かつそれらを順不同で適用できるように直交化しておく…とかできると理想だけど,そういうの自動化できたりしませんか.つうかできたら cvs の手動マージ機能とか要らないって話ですかそうですか.
はっとさせられたのはこれだ.
著作権法で認められるところの引用とは、何か本人が主張する主体部分の文章があって、それを補足するための「従」であることが前提となっている。主体がなく、ただ抜き出しただけでは、引用とは認められないのである。
んーと?
(著作権法 第三十二条) 公表された著作物は、引用して利用することができる。この場合において、その引用は、公正な慣行に合致するものであり、かつ、報道、批評、研究その他の引用の目的上正当な範囲内で行なわれるものでなければならない。
blog における「公正な慣行」てのが確立してないのが難しいところかな.いずれにせよ,その引用する目的がはっきり分かるようでないと,「引用の目的上正当」かどうかは判断できないので,その点ははっきりさせる必要があるのは確かかも.
法的なことはともかくとしても,自分がどう考えたか,何を思って引用したかは記録しておく価値があるのは確かかも知れない.たとえそれが「私的な備忘録」だったとしても.まあついついコピーペーストしてそのままにしちゃうんだけど.
今まで使い続けていた 1.0rc2 から更新.自前の改造パッチもだいたい当て終えたはず.
カテゴリリストや最近の記事などは,JavaScript feed ではなく静的に挿入されるように変わっている.実は rc3 で既に変更されていて私が知らなかっただけのようだ.じゃあ自前の改造 [2004-11-14-1] は捨ててもいいかな,と一瞬思ったけど,カテゴリ順序の制御とか,<ul> や <dl> によるリストへの変更とかをどうやって本家ロジックに組み込むかを考える気力がなかったので,自前改造をしばらくは生かし続けることにした.本当はできるだけ本家に追従した方が,後々楽なんだけど….
今回の目玉はアイテムごとページを出せるようになったことだと勝手に思ってるんだけど,その実装のしかたにちょっととまどった.あれー, $item_template が適用されないのはどうして?
で,よくよく考えてみたのだが,$item_template は アイテムのタイトルとかを含んだ "section" div まるごとになっているため,それと互換性を保ったままアイテムごとページに使うことはできない (例えば,$item_template では h3 になっているものを,アイテムページで h1 にするのは困難) ということなのだと理解した.継続してソフトウェアをメンテナンスすることの大変さを改めて思い知った(つもり).
まあ昔から SPAM はいっぱい来るんだけど,最近は特に日本語のが増えた.アダルトサイトとか,あとは女の子個人を装ったやつとか.出会い系の掲示板で見てメールしました,みたいな.書き込んでない書き込んでない.
どうもここにログを公開してから増え始めたような気がする.気のせいかも知れないけど.というわけで,とりあえず各ページに含まれているメールアドレスをちょっとだけ偽装することにした (「@」→「 _at_ 」).どのくらい効果があるかは不明だけど,結構よく見かけるので,それなりに効果があるのではなかろうか.
あと,procmail のルールをちょっとアグレッシブなものに変えてみた.どんな変更かはまだ伏せておく.効果があったら報告したい.しかしこういう対策ルールが広まると,送り側もそれを避けようとするからなあ.結局いたちごっこに….
[2005-01-10] の tb_standalone 導入時のメモ.
まずくっつきトラックバックのページの通りにインストール.ただし SSI 化するため,js ファイルではなくて htmlin ファイルを作って,数字のみを書くように変更.あと,同じ変更を $mode eq delete の場合にも入れる. (でないと削除した場合に数字が変わらない)
うちのサーバだと perl module が足りなかったり古かったりで動かない.以下を make して,ユーザスペースに置いておく.tb.cgi の先頭で use lib "/path/to/libdir"; しておく (デフォルトの CGI.pm が古いので,ユーザスペースに入れた方を優先する).
perl module (*.pm) だけじゃなく,loadable object (*.so) も必要なのが悩ましい.たまたまサーバと同じ OS 環境が手元にあったから,手元でコンパイルしてアップロードするという手が使えた.綱渡りだなあ.
DataDir と RSSDir は / で終わらないとダメなので注意.NotifyEmail は,不要なときは空文字列にしておけば無視される.
送信が誰でもできるのは,踏台にされたりしそうでいやなので,send_form と send_ping は is_logged_in() が真のときしかできないようにしておく.あとは,list mode の出力スタイルをちょっといじったりとか.
一応動くようにはなったけど,list mode の出力が utf-8 なのがあまり気に入らない.他のページは EUC-JP なのでそれに統一したいなあとか思ってみたり.
というわけで,trackback と文字コードの話をちょっと勉強してみた.
ふむ,trackback の仕様上は文字コードの規定はない.慣習上は送信は utf-8 で,受信は charset パラメータを見るか,自動判定するからしい.
一般に HTTP の user agent は form を送信するときにどの文字コードで送るか? form 要素に accept-charset 属性が指定されていないときは,デフォルト値 UNKNOWN であり,UA はこれを「form を含む文書が送信された charset」と解釈してよい (may).とされている.あくまで「してよい」なんだよな.ほとんどの UA はこの慣習に従っている.でも lynx はダメ(しかも accept-charset も無視する)らしい.そうか,lynx は form 送信には使わないほうが安全なんだな.メモメモ.
ていうことは,list mode だけ EUC-JP に変換して表示するとかってのは問題なくできそうな感じ.そのうち気が向いたらやろうかな気味.
* [asJepj95e27] <a href=http... (2016-04-08 22:53:01)
くっつき BBS を SSI (server-side include) 化してみた.ってもしかして既に「くっつき」と呼べなくなってますか? 作者さんに怒られそうだ….一応このような改造をしようと考えた理由を議論しておこう.
一言でいうとページ表示の速度改善が目的.もちろんメリット・デメリットがあって,このサイトにとってはメリットの方が大きいと判断したというだけ.
まずメリット: くっつき BBS が採用する CSI (client-side include) だと, include ごとに js ファイルを取ってくるための HTTP request/response が発生する.大抵は日ごと,あるいは記事ごとに include する使い方なので結構な数になる.ブラウザがそれらを受け取ってレンダリングを完了するまでユーザは待たされる.レスポンスの悪いサーバだとこれがかなりいらつく.SSI 化すればこの点が改善される.(というわけなので,インライン画像などをいっぱい貼っているサイトだと,いずれにせよ HTTP トラフィックが多数発生するので,改善率は低いと思う) あとは当り前だけど, JavaScript が使えないクライアントでも大丈夫.
逆にデメリット: サーバに HTML ファイルを parse するための負荷をかけてしまう.HTTP のハンドリングよりこっちの方が遅い状況だと,上記メリットが完全にスポイルされる.でも普通に考えて,かたや system call をばりばり呼び出すネットワーク処理,かたやユーザ空間で閉じた単純な文字列マッチング,後者の方が重いという状況は限られていると思う.よっぽどでかいファイルで,かつ含まれている include の数が少なかったりするとこれが起きるかな. あとはこっちも当り前な点として,そもそも SSI が使えるサーバじゃないと使えない.
というわけでケースバイケースなんだけど,うちの場合は明らかに SSI の方が向いている.ちゃんと測定してないけど体感速度で 1 桁は違う感じ.結果として,javascript feed は一切なくなりました.今後どうなるかわからないけど.
変更点としては,kuttukibbs.cgi の中で js ファイルを書き出すところで生 HTML も別ファイルに書き出すようにしておいて,呼び出したいところで <!--#include virtual="..."--> するだけ.注意点としては
<!--#config errmsg="" -->
を入れておくってのがミソ.これがないと include するものがないときにエラーメッセージが表示されてうっとうしい.
RDF の文法チェックを試してみた.
で,Error とか Warning が出てたので直してみる.直したのは
<rdf:RDF ... xmlns:lang="ja"> → <rdf:RDF ... xml:lang="ja">
と
<rdf:li resource="..."/> → <rdf:li rdf:resource="..."/>
の 2 ヶ所.
* [Thewichayank] No complaints on this end, silmpy a good... (2012-12-30 05:18:44)
chalow アンテナに捕捉して頂きました(ありがとうございました).
それはよいのだが,見てみると何やらだーーーーっと数字の羅列が….あー,カレンダー (day_list) が表示されているのか.しかも SMTWTFS という謎な文字列から始まって,1 から 31 まで各 1 行ずつ….どうやったら表示されなくなるのか他の人の書き方を見比べてみたけど,何だかよくわからない….
と思ってたら,どうやら「更新チェック範囲」というのを,アンテナ編集作業の一環として指定できるというからくりらしい.ということは捕捉される側としては特に何も気にしなくてよいってことですかね.
でもあまりにも見苦しくて申し訳ないので,カレンダーはサイドバーにでも入れておくことにしてみた.さてどうなるかな.
どうも今まで,このログを MSIE でスクロールをぐりぐりするともたつくなあと思っていた.ちなみにもたつくのは 2 段組になっているトップページだけで,月ごとのページやカテゴリページは問題ない.chalow を使っている人のページをいくつか見て回ったけど,もたつくページとそうでないページがある.で,それぞれの css 見比べてみて気づいた.
#content に position: relative が指定されていると遅い.
chalow-1.0rc2 に付属してくるデフォルトの diary.css ではこれが指定されている.これを外すと MSIE での表示が格段に軽くなる.見ためも特に変化ないような気がする.(そもそも #content のところでは top とか left とかが指定されていないので仕様上は auto になって,MSIE だとこれが position: static と変わらないような実装になっている,という理解でよいかな? てことは他の UA の挙動も調べといた方がいいかも)
* [Christian] Holy Toledo, so glad I cilcekd on this s... (2012-12-30 23:22:19)
くっつき BBS を導入してコメント記入欄を作ってみた.
このサイトのコンテンツは,自宅の PC からレンタルサーバにアップロードされていて,ログデータはその中のサブディレクトリに置かれる.このサブディレクトリはアップロードで上書きしちゃダメなので特別扱いする必要がある.むしろ,このサブディレクトリはダウンロードして,手元にバックアップを取っておきたい.
ところが sitecopy はどうもこれには向いていないっぽい. ~/.sitecopyrc でディレクトリまるごと ignore に指定してみたのだが,うまく動いてくれない.
sitecopy の man には ``Ignored files will be created, moved and deleted as normal'' って書かれていて,要するに ignore は単に内容の変更が無視されるだけなのかな.ファイルがどんどん増えて行くケースは想定外っぽい.本家のメーリングリスト眺めると,似たような質問は出てるんだけど無視されてるし.
結局以下のようにした,まず自宅 PC 側でログデータをバックアップするディレクトリは,公開ディレクトリツリーの外に置くことにした.これは ftpmirror でサーバから自宅側へ sync する.
一方,公開ディレクトリツリーの中のログデータ置場は,自宅 PC 側では初期状態(管理用ログファイルだけがある)のままで触らないようにしておく.このままでは管理用ログファイルが上書きされるので,~/.sitecopyrc でこのファイルを ignore 指定しておく.sitecopy は,サーバ側で生成される新しいファイルの存在は関知しないので,これでとりあえず問題ない.
というわけですごく面倒くさかった.やはり ssh + rsync が使えるサーバに移るのが正しいのかな.
皆さん普通はどうやってるんでしょうか? てことで早速コメントキボンヌ↓.
chalow に -u をつけるとサイズが変わったときだけファイルを書き出すようになるんだけど,当然これは変更の検出としては完全ではなくて,たまにこける.これが気に食わないんだけど,じゃあ -u をつけないとどうなるかというと,すべてのファイルが書き出されて,かつそれらの「最終更新時間: 20YY-MM-DD HH:MM」の部分が書き変わっちゃうので,sitecopy で差分アップロードするときに全部対象になっちゃって嫌.
というわけで,真面目に内容を比較するようにした.output_to_file の中で,古いファイルの内容と新しいファイルの内容のそれぞれについて,更新時刻の部分を除いて比較.一致してたら return とする.
今のこのログの分量で,処理時間の増加は 1 秒以内だから,まあこれでいいかな.ついでに念のため直接比較ではなくて MD5 の比較を試してみたけど,ほとんど変化なしというかむしろ悪いかも.
実はここにログを持って来る前に,blog サイトの利用をちょっとだけ検討していた.
最初にちょっと試してみたのが goo blog.少し試行錯誤したが,自動改行がオフにできなかったのが致命的で,結局やめた.
次に試したのが昨今話題の livedoor の blog.ここはまず,登録した瞬間にメールでパスワードを送って来て,それでだいぶ引いたんだけど,やっぱりしばらく試行錯誤してみる.フォーマットは割と自由に制御できるのだが,どうにもインタフェースが使いにくい.
で,さすがに 2 つくらい試すと自分の指向性が分かって来る.押し着せのインタフェースで,しかもブラウザからアップロードなんていうのは,性に合うはずがないのだ.というわけで,自分の手元ですべて制御できて,かつ改造が楽そうな chalow に落ち着いた.
というわけでこの環境もだいぶ収束してきたので,残したままだった goo とか livedoor のコンテンツを全消去した.アカウントはどうしようかな.削除してもいいんだけど.
* [Alexavia] Thanky Thanky for all this good ifnormta... (2013-07-04 08:18:30)
chalow のカテゴリ一覧は JavaScript による client side include で実装されているのだが,これがどうにも気に食わない.何が気に食わないって,私は lynx とか w3m とかのテキストブラウザが大好きなのだ.
というわけで改造する.まず write_index_page の実行を最後に持って来て,その直前あたりでカテゴリ一覧の HTML コードを生成するようにする. index page の template を呼び出すときにこの HTML コードを渡してやって,中に挿入する.
ついでなので,自分の好きな順番に並べたり,エイリアス(partita → SONY VAIO C1VJ/BP,とか)をつけたりできるようにしてみた.
最終更新時間: 2009-01-04 15:31
* [Cryptogeox] Bitcoin tradicionalmente relacionam-se a... (2018-08-17 12:29:42)
* [KulDole] Lump armpit brings discomfort, hurts whe... (2018-08-13 19:23:19)
* [MirkaFele] Peels can help to eliminate from the gre... (2018-07-26 03:16:04)
* [KIRANags] To determine internal swelling is diffic... (2018-07-09 10:37:45)
* [FimaInabs] Useful information for every pregnant. D... (2017-11-03 19:01:15)
* ...