お客様から、
既存システムにPDFファイルをアップロードする機能を追加したという依頼を頂きました。
その機能について少し説明したいと思います。
まず、
ファイルの選択画面のHTMLは、
<head> ・ ・ <form action="check.php" method="POST" enctype="multipart/form-data"> <input type="file" name="pdf_file"><br> <input type="submit" value="アップロード"> </form> ・ ・ </head>
みたいになりますね。
それで、
ファイルのアップロード処理を行うPHP側のコードは、
<?php if(is_uploaded_file($_FILES["pdf_file"]["tmp_name"])){ if(move_uploaded_file($_FILES["pdf_file"]["tmp_name"], "ファイルの移動先のパス")){ echo "アップロード完了です。"; }else{ echo "アップロードに失敗しました。"; } } ?>
みたなコードになりますね。
※かなり雑なコードですが。。。
これで完了であれば非常に簡単なんですが、
当然PDFファイルのアップロード機能なので、
アップロード処理を行う前に、
PDF以外のファイルをアップロードしていないかのチェックを行わないといけません。
※例えば、悪意のあるスクリプトを記述したHTMLなどをアップロードされると深刻な脆弱性になってしまうこともあるので、
アップロードするファイルの種類が決まっているのであれば、必ずファイルのチェック処理は行って下さい。
で、
今回ここで問題が1点発生しました。。。
まずは、以下のコードで拡張子のチェックを行います。
//拡張子をチェック $ext = pathinfo($_FILES["pdf_file"]["name"], PATHINFO_EXTENSION); if($ext != "pdf"){ echo "ファイルの拡張子が不正です。\n"; }
これは問題なし!!
次に、以下のコードでファイルタイプのチェックを行います。
//ファイルのMINEタイプをチェック if($_FILES["pdf_file"]["type"] != "application/pdf"){ echo "ファイルのMINEタイプが不正です。\nアップロード可能なファイルはPDFのみです。\n"; }
これも問題が無いように思いますが、
テストしてみるとまずい動作が見つかりました。
テストの為に画像(今回はJPEGファイル)の拡張子を無理やり「.pdf」に変更してアップロードしてみたのですが、
なぜかこのチェック処理を抜けてアップロードできてしまいます。
どうも、
$_FILES["pdf_file"]["type"]に入っているファイルタイプが、
「image/jpeg」ではなく「application/pdf」になってしまっているようです。
拡張子を無理やり変えただけのファイルまでPDFファイルとして認識されてしまうのは気持ちが悪いので、
このコードはまずいです。
そこで、
今回は以下のコードに書き換えてやることで、
こちらの意図通りの処理を行うことが出来ました。
//ファイルのMINEタイプをチェック $fileinfo = finfo_open(FILEINFO_MIME_TYPE); $mimeType = finfo_file($fileinfo, $_FILES["pdf_file"]["tmp_name"]); finfo_close($fileinfo); if($mimeType != "application/pdf"){ echo "ファイルのMINEタイプが不正です。\nアップロード可能なファイルはPDFのみです。\n"; exit; }
ブログに全コードを記載するのは大変なので、
かなりおおざっぱなコードになってしまいましたが、
取りあえずこんな感じで機能追加は可能です。
この記事へのコメントはありません。