電子書籍の厳選無料作品が豊富!

CGIメールです。
元々shiftjisなので、これをiso-2022-jpに変換させようとしてます。

$charset = "iso-2022-jp";
open(MAIL,"| $sendmail -t") || &error("失敗");
print MAIL "To: <$to>\n";
print MAIL "From: <$from>\n";
&jis("タイトル"); &base64("$msg"); print MAIL "Subject: $str\n";
print MAIL "MIME-Version: 1.0\n";
print MAIL "Content-type: text/plain; charset=$charset\n";
print MAIL "Content-Transfer-Encoding: 7bit\n";
foreach ( split(/\n/, $body) ) {
&jis("$_");
print MAIL $_, "\n";
}
close(MAIL);

sub jis{
$msg = $_[0];
Encode::from_to($msg, "shiftjis", $charset);
####1####
}

sub base64 {
use MIME::Base64;
$str = $_[0];
if($str =~ /[^!-~\s]/){
$str = encode_base64($str, "");
if($charset eq "utf8"){
$str = '=?utf-8?B?' . $str . '?=';
}else{
$str = '=?iso-2022-jp?B?' . $str . '?=';
}
}
}

このようにしてみたのですが、タイトル部分はきちんと表示されるのですが、ボディー部分が文字化けしてしまいます。(メーラーで手動にてshit-jisにエンコードしたらボディー部分が読めタイトル部分は文字化けする)

Encode::from_to($msg, "shiftjis", $charset);
の$charsetを"$charset"にしても同じ現象です

また、元々参考にしたものでは####1####に
retern $msg;
があったのですが、これを入れるとsyntax errorになったので、これをコメントアウトしたらエラーにはならず送信そのものはできました

ただ目的の文字変換ができないのですが、どこをどう改善すればいいでしょうか。
どうかご存じの方ぜひ教えてください。
よろしくお願いします。

A 回答 (1件)

> foreach ( split(/\n/, $body) ) {


> &jis("$_");
> print MAIL $_, "\n";
> }

Shift_JISの$_をそのまま出力してるから。

現在の&jisの仕様は
・引数: shift_jisの文字列
・戻り値:無し
・副作用: グローバル変数 $msgが、入力引数のshift_jis文字列をISO-2022-JPに変換した文字列になる
です。

> また、元々参考にしたものでは####1####に
> retern $msg;
> があったのですが、これを入れるとsyntax errorになったので、これをコメントアウトしたらエラーにはならず送信そのものはできました

「return」 です。スペルが違います。
エラーになったからコメントアウト、では何の解決にもなりません。

「なんでもOK」なPerlですが、ある程度のものを作ろうと思ったら、やはり、プログラム構造はちゃんとした方がよいです。
グローバル変数は必要以上に使わないことです。
use strict ; を入れて変数宣言を強制するのもいいでしょう。

一例です

# 引数: shift_jisの文字列
# 戻り値:ISO-2022-JPに変換された文字列
sub jis{
my $msg = $_[0];
Encode::from_to($msg, "shiftjis", $charset);
return $msg ;
}

# $_は便利なのですが、
# 注意して使わないと意図しないところで置き換わってしまいます
foreach my $l ( split(/\n/, $body) ) {
print MAIL &jis($l) . "\n";
}


なお、base64にも同様の問題(グローバル変数 $strの使用) があります。
    • good
    • 0
この回答へのお礼

大変ご丁寧な解説ありがとうございました。
ご解説頂いてから、内容を自分なりに噛み砕き、きちんと理解し全て解決するまでに時間がかかってしまったため、お礼も遅くなってしまいました。

以前base64や&jisは教えて頂いたりネットに載っていたものを、特に$_の使い方が非常に苦手なため(相変わらず$_とすべきところと$_[0]とすべきところがよく分かっていませんが)、内容を理解しないまま使用し、そのためreturnのスペルに間違いがあることすら気づかず自分の仕様にはどこかマッチしないんだと頭から決めつけておりました。

今回グローバル変数を必要以上に使わないことも非常に勉強になりました。
本当にありがとうございました。

お礼日時:2011/04/30 15:45

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!