« P::Planetの雛形 | メイン | DBIx::Class::UTF8Columns 便利 »

RightFieldsで作ったフィールドにアップロードした写真をリサイズする

MovableTypeのRightFields Pluginでファイル形式のフィールドを作って、 エントリーごとに写真をアップロードしたらリサイズさせて、サムネイルも作るというプラグイン。RightFieldsのデータタイプはSQLの方じゃなくてPlugin領域を使う、configはめんどいのでプラグイン.plファイルに直書き、アップロード先・変換したファイルの保管場所固定という方針。 MT::Imageなんてのがあるんだね。便利だ。

package MT::Plugin::FieldThumb;
use strict;
use MT;
use MT::Image;
use Path::Class qw(file);

#settings
my $source_dir = 'files';
my $output_dir = 'photo';
my $main_photo_width = '400';
my $thumbnail_photo_width = '60';

my $plugin = new MT::Plugin({
                                                         name => "FieldThumb",
                                                         version => '0.01',
                                                         author_name => "Yusuke Wada",
                                                         author_link => "http://yusukebe.com",
                                                 });
MT->add_plugin($plugin);
my $mt = new MT;
my $rf_dir =  $mt->mt_dir . "/plugins/RightFields/lib" ;
use RightFields;

MT::Entry->add_callback('pre_save',1,undef,\&pre_save_hdlr);

sub pre_save_hdlr{
    my ($eh, $entry) = @_;
        my $cfg = RightFields::blog_data('extra', $entry->blog_id);
        my $obj = RightFields::new_obj($cfg,$entry->id);
        my $column_value = $obj->column_values();
        my $source_photo = $column_value->{'photo'};
        my $pad_id = _pad_id($entry->id);
        make_thumbnail($source_photo,$pad_id,$entry,$main_photo_width);
        make_thumbnail($source_photo,$pad_id."-thumb",$entry,$thumbnail_photo_width);

#$output_name : do not include .jpg 
sub make_thumbnail{
        my ($input_name,$output_name,$entry,$width) = @_;
        my $archive_path = $entry->blog->archive_path;
        #my $output_file = $archive_path . "/" . $output_dir ."/" . $output_name . ".jpg";
        my $output_file =  file($archive_path, $output_dir, $output_name . ".jpg");
        #if(-f $output_file){ return };
        #my $filename = $archive_path . "/" . $source_dir . "/" . $input_name
        my $filename = file($archive_path,$source_dir, $input_name);
        my $img = MT::Image->new( Filename => $filename );
    my($blob, $w, $h) = $img->scale( Width => $width );

    open FH, ">$output_file" or die $!;
    binmode FH;
    print FH $blob;
    close FH;
}

sub _pad_id{
        my $old_id = shift;
        my $zero_num = 6 - length($old_id);
        my $new_id = "0" x $zero_num . $old_id;
        return $new_id;
}

テンプレートファイルで

<img src="<$MTBlogURL$>photo/<$MTEntryID pad="1"$>-thumb.jpg" alt="<$MTEntryTitle$>" />

みたいにアクセスできる。割とニッチなPlugin。

トラックバック

このエントリーのトラックバックURL:
http://yusukebe.com/mt/mt-tb.cgi/2037

コメント (11)

wo_moon:

はじめまして。
RightFieldsはとても便利ですが画像のリサイズが出来ないのが不自由で、ぜひこちらのプラグインを使わせていただきたいと思っています。
(htmlのタグが少し分かるくらいで、専門的な知識がありません。すいません。)

上のソースをコピーして「FieldThumb.pl」というファイル名で保存。
MTのPluginフォルダにアップロードしました。
しかし次のようなエラーが出てしまいます。

プラグイン・エラー:
Can't locate Path/Class.pm in @INC (@INC contains: /xxxx/plugins/spamlookup/lib /xxxx/plugins/WidgetManager/lib /xxxx/plugins/RightFields/lib /xxxx/plugins/GoogleSearch/lib /xxxx/plugins/MailForm/lib /xxxx/extlib lib /usr/local/lib/perl5/5.8.8/i686-linux /usr/local/lib/perl5/5.8.8 /usr/local/lib/perl5/site_perl/5.8.8/i686-linux /usr/local/lib/perl5/site_perl/5.8.8 /usr/local/lib/perl5/site_perl .) at /xxxx/plugins/FieldThumb.pl line 4.
BEGIN failed--compilation aborted at /xxxx/plugins/FieldThumb.pl line 4.
Compilation failed in require at lib/MT.pm line 619.

failed--compilation aborted at /xxxx/plugins/FieldThumb.pl line 4.の記述を見て、自分の使っているサーバにはMT::Image;が入ってないのかな?と思いましたがそれをどう確認すればよいかもわかりません。
mt-check.cgiでImage::SizeとImage::Magickがインストールされていることだけは確認したのですが…

これはどのようにすれば解決できるでしょうか?
スキルの無い私が使うのは無理でしょうか?
お時間があるときにアドバイスいただけると助かります。

Path::Classが入ってないからですね。MTのexlibディレクトリに
http://search.cpan.org/src/KWILLIAMS/Path-Class-0.16/lib/Path/Class.pm
このファイルをダウンロードして入れるとOKなはずですよー。

追記です。
extlibの中にPathというディレクトリが無かったら作ってその中にPath.pmを入れてみてください。

wo_moon:

ゆーすけべー様

ふただび失礼します。wo_moonです。
ご教授ありがとうございました。
さっそくダウンロードして入れてみたのですが、やはり上手く行きません。
少しは自分でも努力しようと悪戦苦闘してみたのですが、基礎知識の無い悲しさ、手詰まりでどうにもならなくなってしまいました。何度も申し訳ありませんが、ご助言いただけると嬉しいです。

教えていただいたファイルを入れたところ、

プラグイン・エラー:
Can't locate Path/Class/File.pm in @INC (@INC contains: /xxxx/plugins/spamlookup/lib /xxxx/plugins/WidgetManager/lib /xxxx/plugins/RightFields/lib /xxxx/plugins/GoogleSearch/lib /xxxx/plugins/MailForm/lib /xxxx/extlib lib /usr/local/lib/perl5/5.8.8/i686-linux /usr/local/lib/perl5/5.8.8 /usr/local/lib/perl5/site_perl/5.8.8/i686-linux /usr/local/lib/perl5/site_perl/5.8.8 /usr/local/lib/perl5/site_perl .) at /xxxx/extlib/Path/Class.pm line 10.
BEGIN failed--compilation aborted at /xxxx/extlib/Path/Class.pm line 10.
Compilation failed in require at /xxxx/plugins/FieldThumb.pl line 4.
BEGIN failed--compilation aborted at /xxxx/plugins/FieldThumb.pl line 4.
Compilation failed in require at lib/MT.pm line 619.

というメッセージが出たので、今度は「ああ、 Path/Class/File.pmが必用なんだな」と分かったので検索して
http://search.cpan.org/CPAN/authors/id/K/KW/KWILLIAMS/Path-Class-0.15.tar.gz
をダウンロードし、Classフォルダを入れてみました。

すると今度は
Global symbol "$main_photo_width" requires explicit package name at /xxxx/plugins/FieldThumb.pl line 27.
Missing right curly or square bracket at /xxxx/plugins/FieldThumb.pl line 48, at end of line
syntax error at /xxxx/plugins/FieldThumb.pl line 48, at EOF
Compilation failed in require at lib/MT.pm line 619.

とメッセージが出ます。
そこで8行目の
my $photo_width = '400';

my $main_photo_width = '400';
に書き換え、
末尾に
}
を書き足してみたところ、ようやくプラグイン・エラーは解消されました。

しかし実際にRightfieldsのファイルアップロードをしてみても、リサイズされません(サムネールも生成されません)。
Rightfieldsで作ったファイルアップロード用の項目は4つ、うち2つをJPEG用に使用しています。
ファイルのUpload path:はarchives/imgです。
サムネールとリサイズ画像はarchives/img-thに保存したいと考えています。
その場合のFieldThumb.plはこれで良いのでしょうか?

package MT::Plugin::FieldThumb;
use strict;use MT;
use MT::Image;
use Path::Class qw(file);
#settings
my $source_dir = 'archives/img';
my $output_dir = 'archives/img-th';
my $main_photo_width = '720';
my $thumbnail_photo_width = '120';
my $plugin = new MT::Plugin({
name => "FieldThumb",
version => '0.01',
author_name => "Yusuke Wada",
author_link => "http://yusukebe.com", });
MT->add_plugin($plugin);
my $mt = new MT;
my $rf_dir = $mt->mt_dir . "/plugins/RightFields/lib" ;
use RightFields;
MT::Entry->add_callback('pre_save',1,undef,\&pre_save_hdlr);
sub pre_save_hdlr{
my ($eh, $entry) = @_;
my $cfg = RightFields::blog_data('extra', $entry->blog_id);
my $obj = RightFields::new_obj($cfg,$entry->id);
my $column_value = $obj->column_values();
my $source_photo = $column_value->{'archives/img'};
my $pad_id = _pad_id($entry->id);
make_thumbnail($source_photo,$pad_id,$entry,$main_photo_width);
make_thumbnail($source_photo,$pad_id."-thumb",$entry,$thumbnail_photo_width);
#$output_name : do not include .jpg
sub make_thumbnail{
my ($input_name,$output_name,$entry,$width) = @_;
my $archive_path = $entry->blog->archive_path;
#my $output_file = $archive_path . "/" . $output_dir ."/" . $output_name . ".jpg";
my $output_file = file($archive_path, $output_dir, $output_name . ".jpg");
#if(-f $output_file){ return };
#my $filename = $archive_path . "/" . $source_dir . "/" . $input_name
my $filename = file($archive_path,$source_dir, $input_name);
my $img = MT::Image->new( Filename => $filename );
my($blob, $w, $h) = $img->scale( Width => $width );
open FH, ">$output_file" or die $!;
binmode FH;
print FH $blob;
close FH;}sub _pad_id{
my $old_id = shift;
my $zero_num = 6 - length($old_id);
my $new_id = "0" x $zero_num . $old_id;
return $new_id;
}
}


なんどもお手を煩わせて申し訳ないのですが、なんとかこのプラグインを使わせていただきたくて一生懸命です。よろしくお願いいたします。

$main_photo_widthの件は僕のタイポでした。
以下多分ですが、考えられる解決策。

MTでアーカイブの設定「アーカイブをサイト・パスとは別のパスで公開する場合に選択してください。」というのをオンにしてarchivesというディレクトリにHTMLなどを保存しているような場合は
my $source_dir = 'archives/img';
my $output_dir = 'archives/img-th';

my $source_dir = 'img';
my $output_dir = 'img-th';
でよいはずです。あと
my $source_photo = $column_value->{'archives/img'};
ここの部分archives/imgですが、この値はRightFieldsで作ったフィールド名にしてください。
imgという名前でフィールドを作ってhttp://sitepath/archives/imgディレクトリにファイルをアップロードするという設定にして、
my $source_photo = $column_value->{'img'};
とすればいけるんじゃないかなー。

あ、あと、これ作って後ほど発覚したことがあって

MT::Entry->add_callback('pre_save',1,undef,\&pre_save_hdlr);

の部分が実は

MT->add_callback('CMSPostSave.entry', 9 , undef, \&handler);

の方がいいっぽいんですよ。このPluginも修正したバージョンがあるんですが、見せられる状態じゃないので、もし整ったらそのうち公開しますね。

wo_moon:

本当に何度もすみません。
アドバイスしていただいたとおり、

my $source_dir = 'img';
my $output_dir = 'img-th';

MT->add_callback('CMSPostSave.entry', 9 , undef, \&handler);

my $source_photo = $column_value->{'img'};

と修正して再チャレンジしてみましたが、やはりimg-thには何も生成されません。
Rightfieldsの設定はこちらのようになっています。

http://picasaweb.google.com/ningetsu/fBIAkK/photo#5050243463566977762

他に原因は何か考えられるでしょうか?
お手を煩わせて本当に申し訳ないのですが、どうかよろしくお願いします。

my $source_photo = $column_value->{'img'};

my $source_photo = $column_value->{'photo_ex'};
とRightfieldsのコラム名にしたらどうでしょうかね?

wo_moon:

ご助言の通りやってみましたが、リサイズだけでなくアップロードそのものが出来なくなってしまいました。仮にこれで成功したとしても、アップロード&リサイズしたい画像は1エントリーにつき2つあるので、私にこれを使いこなすのはやはり無理かもしれませんね…。
とても残念です。
もう少し勉強してから再チャレンジしてみます。
何度もお手を煩わせて申し訳ありませんでした。

wo_moon:

本当に何度も申し訳ないのですが、もうひとつだけ教えてください。
諦めてpluginsフォルダからFieldThumb.plを削除しても、photo_exにファイルをアップロードできなくなってしまいました。
これだけは何とか元に戻したいのです。

原因と対処方法について、お心当たりがおありでしたらご助言をお願いします。

>photo_exにファイルをアップロードできなくなってしまいました。
それは困りましたね。こうなると基本的なことしか助言はできないですね。例えば、RightFieldsの設定を確認する、MTのエラーログを見てみる、ディレクトリのパーミッションを確認する、等です。

#このpluginはうまく機能すればRightFieldsのアップロード機能には干渉しないはず。

そういえば、申し訳ないです。。。僕が返信したところにミスがありました。
MT->add_callback('CMSPostSave.entry', 9 , undef, \&handler);
に修正した場合
sub pre_save_hdlr{

sub handler{
にしないと動かないですね。

wo_moon:

ゆーすけべー様
本当に何度も申し訳ありません。

>photo_exにファイルをアップロードできなくなってしまいました
RightFields設定「photo_ex」のUpload pathがいつの間にか削除されていました。
このうっかりさを直さないと、MovableTypeを勉強する以前の問題ですね。
お騒がせしてすみません。

何とか元に戻ったので、改めて
MT->add_callback('CMSPostSave.entry', 9 , undef, \&handler);
sub handler{
で再度チャレンジしてみました。やはり結果は同じでアップロードはされますがリサイズした画像は生成されません。
システムログを確認すると以下のエラーが出ていました。

「プラグイン名がありません」は、次の理由で使えません: Can't locate object method "blog_id" via package "MT::App::CMS" at /xxxx/plugins/FieldThumb.pl line 23,

FieldThumb.plの行目の表記は
my ($eh, $entry) = @_;
ですが、ここまで来ると私レベルでは手も足も出ません。
お尋ねするばかりで大変申し訳ないので、基礎から勉強して再チャレンジします。

いろいろご面倒をおかけしました…

コメントを投稿

(いままで、ここでコメントしたことがないときは、コメントを表示する前にこのブログのオーナーの承認が必要になることがあります。承認されるまではコメントは表示されません。そのときはしばらく待ってください。)


ブログSEO対策:track word seo