🎄teratailクリスマスプレゼントキャンペーン2024🎄』開催中!

\teratail特別グッズやAmazonギフトカード最大2,000円分が当たる!/

詳細はこちら
PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

文字コード

文字コードとは、文字や記号をコンピュータ上で使用するために用いられるバイト表現を指します。

VPS

VPS(バーチャル・プライベート・サーバ)は、仮想化されたサーバをレンタルするサービスで、共有サーバでありながら専門サーバと同等の機能を果たします。物理的な専門サーバより安価で提供できるメリットがあります。

Q&A

解決済

2回答

2629閲覧

PHPSpreadsheet ファイル名の文字化け

Take_it

総合スコア357

PHP

PHPは、Webサイト構築に特化して開発されたプログラミング言語です。大きな特徴のひとつは、HTMLに直接プログラムを埋め込むことができるという点です。PHPを用いることで、HTMLを動的コンテンツとして出力できます。HTMLがそのままブラウザに表示されるのに対し、PHPプログラムはサーバ側で実行された結果がブラウザに表示されるため、PHPスクリプトは「サーバサイドスクリプト」と呼ばれています。

文字コード

文字コードとは、文字や記号をコンピュータ上で使用するために用いられるバイト表現を指します。

VPS

VPS(バーチャル・プライベート・サーバ)は、仮想化されたサーバをレンタルするサービスで、共有サーバでありながら専門サーバと同等の機能を果たします。物理的な専門サーバより安価で提供できるメリットがあります。

0グッド

0クリップ

投稿2019/10/20 22:52

編集2019/10/21 08:14

ConohaVPSで、同一設定のVPSサーバーを2つ用意しています。(同スペックのもの)

サーバーAは本番環境で、サーバーBはAの保存イメージからセットアップした試験環境のものです。
両者の違いは異なるサブドメインを設定してあるだけ(のはず)です。

PHP

1//monthly_excel.php の一部抜粋 2 3$now = new DateTime(); 4$ts = $now->format('Y-m-d_H_i_s'); 5$target_y = $target_y;//2019 6$target_m = $target_m;//9 7$target_ym = $target_y."年".$target_m."月度"; 8 $fileName = $target_ym."_勤務管理表_".$ts.".xlsx"; 9else: 10 $fileName = "[未確定]".$target_ym."_勤務管理表_".$ts.".xlsx"; 11endif;

PHPSpreadsheetを用いてExcelファイルへのデータの書き出しをしているのですが、

イメージ説明

上がサーバーA、下がサーバーBから出力したものです。
文字コードの問題だろうなとは思うのですが、monthly_excel.phpのファイル自体は全く同じものですし。。
(サーバーBにて正常動作を確認後、ローカルにダウンロード→そのままサーバーAへアップロードしたものです)

確認すべき点などありましたら教えてください。

###2019-10-21 17:10追記

出力部分は下記のようになっています。

PHP

1header('Content-Type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheet'); 2header('Content-Disposition: attachment;filename="'.$fileName.'"'); 3header('Cache-Control: max-age=0'); 4header('Cache-Control: max-age=1'); 5header('Expires: Mon, 26 Jul 1997 05:00:00 GMT'); 6header('Last-Modified: ' . gmdate('D, d M Y H:i:s') . ' GMT'); 7header('Cache-Control: cache, must-revalidate'); 8header('Pragma: public'); 9 10$writer = new Xlsx($spreadsheet); 11$writer->save('php://output');

文字化けしないサーバーB、文字化けするサーバーA共に、Windows10+GoogleChrome(77.0.3865.120(Official Build)(64 ビット)) でアクセスしています。同一PCです。
なのでそもそもurlencodeとか関係ない気がしますが、urlencodeしたら化け方は変わりましたが化けたままです。。
生成されたExcelファイルそのものは何の問題もなく(中身の文字化けもない)、ファイル名のみの問題なので半角英数のみのファイル名にすれば問題は回避できるのですが。。

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

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

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

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

takasima20

2019/10/20 23:00

PHPスクリプト以外の違いはどこまで確認したの? またPHPスクリプトに違いがないってのは誰が保証してるの? クライアント(PCやブラウザ)は同じものを使ってるよね?
Take_it

2019/10/20 23:48 編集

サーバーAのイメージバックアップからサーバーBを構築、apacheのドメイン設定のみ書き換えたものなので、phpスクリプト以外の違いは発生し得ないと思うのですが、、、 スクリプトに差異がないことを、、誰も保証はしてくれないでしょうが、サーバーBからwinscpにてダウンロードしたものをそのままサーバーAにあげてます。 クライアント環境は当然同一です。
tacsheaven

2019/10/21 00:07 編集

「書き出している」のは、サーバー上にファイルとしてですか、それともブラウザのレスポンスとしてですか、どちらですか? 前者ならば PHP の文字コードと、サーバの文字コードが疑われますし、後者ならばブラウザが疑わしいです。 ※IE の場合、URL エンコードしてやらないと文字化けすることがあります
退会済みユーザー

退会済みユーザー

2019/10/21 01:03

ファイルをダウンロードするところのHTTPレスポンスヘッダーがどうなっているのか、ブラウザ拡張など駆使してウォッチできないでしょうか。
Take_it

2019/10/21 01:41

Excelはサーバーへ記録ではなくブラウザのレスポンスとして出力しています。(monthly_excel.phpへアクセスするとダウンロードが勝手に始まる) レスポンスヘッダの件、夕方以降になりますが見てみます。
takasima20

2019/10/21 13:24

「サーバーAのイメージバックアップからサーバーBを構築」が、どういった作業か気になりますが、とりあえず phpinfo() を比較してみたら?
Take_it

2019/10/21 16:27

conoha vpsには、VPSのイメージをまるっとバックアップする機能があるんです。vpsシャットダウンしないとイメージ取得できないんで、いわゆる単純なディスクイメージだと思いますが。 で、新規にVPSを増やす場合や、既存のVPSであっても、別のVPSのイメージから環境構築ができるんです。 何もいじらなければ完璧なクローンになるようですが、それだとドメインの設定がアレなので、イメージから構築後、ドメインの設定のみ書き換えてSSLも再設定をしましたが、OS/Apache/PHPのバージョンなんかは全部全く同じ状態です。 phpinfo()を比較しましたが差異はServer Administrator、Hostnameなど、異なるドメイン設定にした部分のみでした。 文字コードに関係しそうな箇所は、差異がありません。
Volrath

2019/10/25 06:20

回答ではありませんが、参考までに。 エンコードマニアックス(http://www.encodemaniax.com)さんで確認したところ、 文字化けしたファイル名はUTF-8の文字列をMIME Decodeした文字列と同じに見えます。 サーバやブラウザが勝手に解釈している部分で動作の差が出ているのかもしれませんので、エンコード/デコードの設定を明示的に行ってやると変化があるかも?
guest

回答2

0

自己解決

urlencode()を使う提案を頂きましたが、元々化けてなかったほうでもエンコードされたままのファイル名になってしまうなど、解決には至りませんでした。

日本語を使用しなければ問題ないので、とりあえず日本語を使わない方法で実装を進めることにしました。

(これは解決というのだろうか・・・?)

投稿2019/10/25 05:01

Take_it

総合スコア357

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

出力がブラウザのレスポンスとしてということですから、ファイル名を Content-Disposition ヘッダを使用して指定していると仮定します。

この場合、ヘッダの値としては直接 UTF-8(や、他のマルチバイト文字列)を使うのではなく、US-ASCII に収まるように変換をかけておく方がよいです。ブラウザによっては解釈に失敗してしまうことがあり得ます。
(また、HTML の header は、8bit 表現で 0~31、127 になる文字は使用できないので、それらを避けるようにする必要もあります)

urlencode() を使うか、MIME の規約に従って変換してください。

投稿2019/10/21 02:30

tacsheaven

総合スコア13703

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.36%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問