質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

89.72%

php5.4からphp7.0へバージョンアップしたら文字化けした

解決済

回答 3

投稿 編集

  • 評価
  • クリップ 0
  • VIEW 3,941

sake

score 14

最近phpをバージョンアップしたら、受信メールのアカウントの名前と件名と本文の半角カタカナが文字化けするようになりました。
メール受信するときは、ReceiptMailDecoder.class.phpを使わせていただいています。
OSは、Centos7です。
インターネットの情報では「php.iniのdefault_charsetというパラメーターがデフォルト値が空から"UTF-8"に変更されているようです」とあったので、php.iniのdefault_charsetを「空」にしましたが、改善されませんでした。
どなたか情報をお持ちの方がおられましたら力を貸してください。
よろしくお願いします。

require_once('/usr/local/bin/ReceiptMailDecoder.class.php');

//X-Original-Toを取得する
$deliveredto = $decoder->getDeliveredTo( 'x-original-to' );

//$deliveredtoからアカウントを取得
$deliveredaccount = strstr($deliveredto, "@", true);

//Fromから「名前<アカウント@ドメイン>」を取り出す
$fromtxt = $decoder->getDecodedHeader('from');
$fromtxt = mb_convert_encoding($fromtxt,"UTF-8",mb_detect_encoding($fromtxt, "ASCII,JIS,UTF-8,CP51932,SJIS-win,iso-2022-jp", 'true'));

//件名を取得する
$subject = $decoder->getDecodedHeader( 'subject' );
$subject = mb_convert_encoding($subject,"UTF-8",mb_detect_encoding($subject, "ASCII,JIS,UTF-8,CP51932,SJIS-win,iso-2022-jp", true));

//本文を取得する
$body = mb_convert_encoding($decoder->body['text'],'UTF-8','auto');
$body = mb_convert_encoding($body,'UTF-8',mb_detect_encoding($body, 'ASCII,JIS,UTF-8,CP51932,SJIS-win,iso-2022-jp','auto'));

$subto='<'.$deliveredaccount.'@xxxxxxx.com>';

mb_language("japanese");
mb_internal_encoding("UTF-8");

//メール送信
$atesaki = $subto;
$kenmei = $subject;
$naiyou = $body;
$from = $txtfrom;

//送信します
echo mb_send_mail($atesaki,$kenmei,$naiyou,'From:'.$from);


受信したメール
受信したメール

変換後のメール
![変換後のメール

  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

質問への追記・修正、ベストアンサー選択の依頼

  • m6u

    2018/03/26 10:01

    どのような文字化けが発生しているか画像で示したりできますか?

    キャンセル

  • sake

    2018/03/26 12:22

    質問に画像を追加したので、見ていただけますか? よろしくお願いいたします。

    キャンセル

回答 3

+4

ドキュメントを読みましょう

default_charset string
PHP 5.6.0 以降は "UTF-8" がデフォルトになり、 htmlentities() や html_entity_decode() そして htmlspecialchars() で encoding パラメータを省略した場合は、このデフォルト値を利用します。 また、default_charset の値は、 iconv 関数で iconv.input_encoding、 iconv.output_encoding、 iconv.internal_encoding が未設定の場合や、 mbstring 関数で mbstring.http_input mbstring.http_output mbstring.internal_encoding が未設定の場合のデフォルトとしても用いられます。

すべてのバージョンの PHP は、PHP から送信する Content-Type ヘッダのデフォルト値としてこれを使います。 ただし、header() で上書きされている場合は別です。

default_charset に空文字列を指定することは、おすすめしません。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2018/03/25 17:02

    デフォルト値とは空にしたときの値である

    キャンセル

+2

その文字化けは、UTF-8(BOMなし)の文字列が
西ヨーロッパ言語(iso-8859-1)として扱われているためですので、
From:やSubject:ヘッダーに記載する箇所に
「=?charset?encoding?encoded-text=?=」
みたいな形式で埋め込めば済む話のように見えます。

PHP: mb_encode_mimeheader - Manual
を使えば解決しそうです。

<?php

$text = 'テストメール';

echo mb_encode_mimeheader($text, 'iso-2022-jp') . PHP_EOL;
echo mb_encode_mimeheader($text, 'UTF-8') . PHP_EOL;

エンコード結果

MIMEエンコード/デコードのテストに、
MIMEエンコード・デコード | WEBシステム開発のWELLHAT
を活用すると良いでしょう。
あるいは、簡単なテストコードはOnline PHP editor | Run code in 200+ PHP & HHVM versions でもよろしいかと。

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2018/03/26 18:34

    下記をコメントアウトして
    //$subject = mb_convert_encoding($subject,"UTF-8",mb_detect_encoding($subject, "ASCII,JIS,UTF-8,CP51932,SJIS-win,iso-2022-jp", true));
    再度試してみました。結果は、
    件名: =?UTF-8?B?w6PCg8KGw6PCgsK5w6PCg8KIw6PCg8Khw6PCg8K8w6PCg8Kr?=
    変化ありませんでした。???????

    キャンセル

  • 2018/03/26 18:44

    申し訳ないけど、100%ズバリの回答までは期待しないでください、再現できる環境がないので。
    mb_detect_encoding()はなぜ必要ですか、そこで本来のエンコーディングと違う結果を返して文字化けを誘発していたりしないでしょうか。
    UTF-8の「テストメール」を変換すると「=?UTF-8?B?44OG44K544OI44Oh44O844Or?=」になるはずなのに、そうならない、ということは余計な変換や加工が加わっていると考えるのが筋だと思います。
    送信されるメールの中に「=?UTF-8?B?44OG44K544OI44Oh44O844Or?=」のまま含まれないと、受信側でデコードできません。
    変換元文字列のエンコードが処理する都度変わってしまうのですか? そんなことはないでしょう。

    キャンセル

  • 2018/03/26 19:04

    ここまでいったら「ReceiptMailDecoder.class.php」がデータをこわしてんじゃないのと疑いたいよな・・・

    キャンセル

check解決した方法

0

自己解決しました。
m6uさんの

UTF-8の「テストメール」を変換すると「=?UTF-8?B?44OG44K544OI44Oh44O844Or?=」になるはず
なのに、そうならない、ということは余計な変換や加工が加わっていると考えるのが筋だと思います。

が参考になりました。

ReceiptMailDecoder.class.php の
function getDecodedHeader( $header_name ) {
    return mb_decode_mimeheader($this->getRawHeader( $header_name ));
}
を
function getDecodedHeader( $header_name ) {
    return $this->getRawHeader( $header_name );
}
に変更して
//件名を取得する
$subject = $decoder->getDecodedHeader( 'subject' )


この変更がどこに影響するかは、これからの検証になりますが、一先ず一件落着です。
回答を寄せていただいた皆さん、ありがとうございました。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 89.72%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる