PyukiWikiにつけたキャッシュ機能用に管理画面を作成する

説明

PyukiWikiにキャッシュ機能をつけるでは, 各ページに対してキャッシュを持ち,次回以降のページ表示時にはキャッシュの内容を表示することで, ページ表示の高速化を図った.

しかしページのキャッシュを更新する方法が,そのページを編集して保存するという操作しかなかった.

普通はそれで問題ないはずだが,ls系,recentプラグイン等を使っていて, 他のページの内容が自ページに影響するという状態の場合は,そうもいかない.

編集したページを,他のページがls系,recentプラグイン等で参照する関係にある場合には, ページの編集後に,参照している側のページも一旦編集で開いて保存してキャッシュを更新するという, 間抜けな操作を行う必要があった.

それを何とかしようというのが,今回の話.

ページ一覧を表示して,そこから任意のページを指定してキャッシュを更新できるようなプラグイン(cacheadmin.inc.pl)を作成した.

ほとんどlistプラグイン(list.inc.pl)を元にしています.

使用例

cacheadminプラグインを直接呼び出せば良い.

カモランドの場合は,以下のURLを呼び出すことになる.

 http://kamoland.com/wiki/wiki.cgi?cmd=cacheadmin

ただし実際にはこのURL↑にはIP制限をかけていますので, 普通はアクセス制限エラーの画面が出ると思います.

pyukiwiki-cache-2a.png [上部]

pyukiwiki-cache-2b.png [中部]

pyukiwiki-cache-2c.png [下部]

便利な使い方

プラグインとは関係なく,ブラウザの操作上の話ですが... 大量のページにチェックを入れる場合は,TABキーとスペースキーを使うのが便利です.

キー操作
TAB
Shift+TAB
スペースON/OFF

TABキーでそういう風に移動できるように,一覧のチェックボックスにtabindexを指定しています. (自分が面倒だったので,必要に迫られてそうしました)

プラグインのソースコード

plugin/cacheadmin.inc.pl
############################################################
# cacheadmin プラグイン
# cacheadmin.inc.pl

use strict;

$cacheadmin::pagename = 'Cache Admin';
$cacheadmin::submit = 'チェックしたページのキャッシュを初期化';
$cacheadmin::submitall = '全ページのキャッシュを初期化';

sub plugin_cacheadmin_action {
	if ($::form{mode} eq 'submit') {
		# 管理者パスワードをチェックする
		if (crypt($::form{admin_pass}, "AA") eq $::adminpass) {
			do_refresh();
		} else {
			# パスワードが正しくない場合は,トップページに戻る
			return ('msg'=>'', 'body'=>'');
		}
	}
	my $body = <<EOD;
<form action="$::script" method="post">
EOD

	my $prev = '';
	my $char = '';
	my $idx = 1;
	my $tabindex = 1;
	foreach my $page (sort keys %::database) {
		next if ($page =~ $::non_list);
		$char = substr($page, 0, 1);
		if (!($char =~ /[a-zA-Z0-9]/)) {
			$char = "日本語";
		}
		if ($prev ne $char) {
			if ($prev ne '') {
				$body .= "  </ul>\n </li>\n</ul>\n";
			}
			$prev = $char;
			$body .= <<"EOD";
<ul>
 <li><strong>$prev</strong>
  <ul>
EOD
			$idx++;
		}
		my($dbmname) = &dbmname($page);
		my($n_dbm_lastmod) = (stat("$::data_dir/$dbmname.txt"))[9];
		my($dbm_lastmod) = &date("Y-m-d H:i:s", $n_dbm_lastmod);
		my($n_cache_lastmod) = (stat("$::cache_dir/$dbmname.cac"))[9];
		my($cache_lastmod) = 'not cached';
		if ($n_cache_lastmod > 0) {
			$cache_lastmod = &date("Y-m-d H:i:s", $n_cache_lastmod);
		}

		$body .= <<EOD;
<li><input type=checkbox @{[$cache_lastmod==0?'disabled':'tabindex="' .$tabindex++ . '" name="rpage" value="' .$dbmname . '"']} />$cache_lastmod &nbsp;
<a href="$::script?@{[&encode($page)]}">@{[&escape($page)]}</a></li>
EOD
	}
	$body .= <<EOD;
</li></ul>
<input type="hidden" name="cmd" value="cacheadmin" />
<input type="hidden" name="mode" value="submit" />
$::resource{frozenpassword}: <input name="admin_pass" size="10" type="password" />
<input type="submit" value="$cacheadmin::submit" />
<input type="submit" name="all" value="$cacheadmin::submitall" />
</form>
EOD

	return ('msg' => $cacheadmin::pagename, 'body' => $body);
}

sub do_refresh {
	my(@refresh_pages) = ();
	if ($::form{all} ne '') {
		# 全ページ対象
		foreach (keys %::database) {
			push(@refresh_pages, dbmname($_));
		}
	} else {
		# チェックページのみ対象
		@refresh_pages = param('rpage');
	}

	foreach (@refresh_pages) {
		if (/^[0-9A-F]+$/) {
			my($cachefile) = "$::cache_dir/$_.cac";
			unlink($cachefile);
		}
	}
}

1;

余談

影響するページのキャッシュを自動的に更新できないか?

この方式で多少便利にはなったが,影響するページを自分で指定するという手作業の要素が残っている.

これが,自動的に影響するページを特定できれば便利なのだが...

初めのうちはこれを何とかできないかと考えていたが,あまりにも面倒なので結局あきらめた.

kamolandをフォローしましょう


© 2017 KMIソフトウェア