しかし、現在のところエラーチェックが殆どされていない。これはまずい。
そして、式の中の変数が評価できない場合の対応が難しい。
MTタグに関しては、文字列が帰ってきた場合、コンテナタグなどを呼んだ場合、そもそも存在しないタグを呼んだ場合など。
VAR変数でも、文字列の場合と、存在しない場合がある。
現状では、すべて 0 扱いして無理やり評価させているのだが、実運用においては再構築時にエラーを出したほうがよいように思える。
これもアトリビュートで指定して、処理を選択できるようにするのがいいだろうか。とりあえず現在のコード。
#Calc Plugin of Movable Type 3.2 #aklaswad 2006 feb
package MT::Plugin::Calc; #このソースコードのモジュール名を宣言
use strict; #紳士的に定義を行うことをコードに対して強制する
use base 'MT::Plugin'; #謎
use vars qw($VERSION); #バージョン
$VERSION = '0.7';
use MT; #MTのモジュールを使用
use MT::Template::Context; #タグを追加するときに必要?
#プラグインのコンストラクタ
my $plugin = MT::Plugin::Calc->new({
name => 'MT Calculator',
description => "calculator",
doc_link => 'http://www.sixapart.jp',
author_name => 'aklaswad',
author_link => 'http://www.aklaswad.com/',
version => $VERSION,
});
#プラグインのクラスを Movable Type に渡す
MT->add_plugin($plugin);
#追加するタグの名前とメソッドのアドレスを渡す
MT::Template::Context->add_tag(Calc => \&tag_calc);
#タグを処理するメソッド
#戻り値がそのままドキュメントに書き出される
sub tag_calc {
#引数を取り出す
my ($ctx, $args) = @_;
my $exoriginal = $args->{"expr"};
my $ex = $args->{"expr"};
#MTタグを検索・置換
while( $ex =~ /MT([A-Za-z]+)/ ){
my $handler = $ctx->handler_for($1);
if (defined($handler)) {
my $tagvalue = $handler->($ctx, { %$args });
$ex =~ s/MT$1/$tagvalue/;
} else{
$ex =~ s/MT$1/0/;
}
}
#MTGetVar変数を検索・置換
while( $ex =~ /VAR([A-Za-z0-9]+)/ ){
my $varvalue = $ctx->{__stash}{vars}{$1};
$ex =~ s/VAR$1/$varvalue/;
}
#式を評価
my $ret = eval($ex);
die "MTCalc can't evaluate this line:$ex:" if $@;
if ($args->{"setvar"}){
$ctx->{__stash}{vars}{$args->{"setvar"}} = $ret;
}
$ret;
#デバッグ用の戻り値
#"$exoriginal == $ex = $ret";
}
1;