• aboutabout
  • servicesservices
  • worksworks
  • mediamedia
  • contactcontact
  • homeサイトトップ
  • about会社概要
  • services業務内容
  • works実績紹介
  • mediaメディア
  • contactお問い合わせ
ja/

media

メディア

  1. サイトトップ
  2. メディア
  3. プログラミングの記事
  4. PHPでフォームからのファイルアップロードとメールでの添付送信を実装する

PHPでフォームからのファイルアップロードとメールでの添付送信を実装する

  • 2020.03.05
  • プログラミング
  • PHP
Updated: 2020.03.05
今回はPHPでフォームからローカルのファイルをメールで送信できる機能を実装してみたいと思います。お問い合わせフォームなどでもファイル添付の機能が備わっているケースもありますね。お問い合わせフォームについては過去の記事でも紹介していますのでご参考に。 (参考記事) PHPで自動返信メール機能付きのコンタクトフォームを作成する(入力画面) PHPで自動返信メール機能付きのコンタクトフォームを作成する(確認画面) PHPで自動返信メール機能付きのコンタクトフォームを作成する(送信画面) PHPでサーバーサイドのフォームバリデーションを実装する   フォームからファイルを添付したメールを送信するには、一度サーバー上にファイルをアップロードする必要があるようです。ですので、ファイルのアップロード機能も合わせて実装することになります。今回は上記の過去記事で紹介しているメールフォームに合わせて、入力画面、確認画面、完了画面の3ページ遷移する形で作成していきます。なお、実用においてはこれ以外にも十分なセキュリティ対策が必要となるので、あらかじめご注意ください。   今回まとめているファイル・フォルダの構成は以下のようになります。入力・確認・送信画面用のphpファイルと、「attachment」と名付けているアップロード先フォルダをメールフォーム用のphpプログラムと同階層に用意しておきます。
┳ form.php
┣ check.php
┣ thanks.php
┗ attachment
   
添付ファイルの選択を行う入力画面
最初に入力画面からのコードを見ていきます。今回はわかりやすいように必要最低限の表記にしています。まずはformタグを用意し、その中にファイルを使うinput要素を設置します。合わせて送信ボタンも並べておきます。 【form.php】※一部抜粋
<form method="post" action="./check.php" enctype="multipart/form-data">
 <input type="file" name="input_file" value="">
 <input type="submit" value="確認画面へ">
</form>
  この時に注意するのはformタグの中に「enctype属性」を忘れないようにします。値には「multipart/form-data」を指定することでファイルの送信ができるようになります。  
バリデーションとサーバーへのアップロードを行う確認画面
続いて確認画面です。入力画面でサブミットされるとこのページが表示されます。それではコードを見ていきます。まずは処理部分のソースコードです、最初にセットされたファイルのバリデーションを行います。ここでチェックするのは「ファイルサイズの容量が制限内か?」「ファイルの形式が問題ないか?」の2つをチェックしていきます。   入力画面から確認画面へ送信されたファイルの情報は「$_FILES」というスーパーグローバル変数を参照することで確認できるようになります。後述のバリデーションやファイルアップロードもこの中に含まれている情報を使う形となります。   まずはバリデーションの関数を用意していきます。1つめは添付ファイルのサイズをチェックします。ファイルのサイズを参照し、指定した値より低いかをtrueもしくはfalseで返すようにしておきます。2つめは添付ファイルの形式をチェックします。許可するファイル形式のMINEタイプファイルの形式をMIMEタイプで指定し、配列としてまとめておきます。そしてファイルのタイプを参照し「in_array()」で配列内に指定したファイル形式が含まれるかを見ていきます。これらの関数には引数に対象となるファイルが入れるようにしておきます。 【check.php(処理部分)】※一部抜粋
<?php
 //添付ファイルバリデーション 
 function fileValidatorSize($data) {
  //ファイルサイズの上限をMB単位で指定
  $allowMaxSize = 2;
  if($data['size'] < $allowMaxSize * 1000000) {
   return false;
  } else {
   return true;
  }
 }
 function fileValidatorType($data) {
  //許可するファイルのMIMEタイプを指定
  $allowFileType = array(
   'image/jpeg',
   'image/png',
   'image/gif',
   'text/plain',
   'text/csv',
   'application/pdf',
   'application/zip'
  );
  if(in_array($data['type'], $allowFileType)) {
   return false;
  } else {
   return true;
  }
 }
 $isErrorFileSize = fileValidatorSize($_FILES['input_file']);
 $isErrorFileType = fileValidatorType($_FILES['input_file']);

 //添付ファイルアップロード
 $fileTempName = $_FILES['input_file']['tmp_name'];
 $fileName = $_FILES['input_file']['name'];
 $attachedFile = "";
 $fileType = "";
 if(!$isErrorFileSize && !$isErrorFileType) {
  if(!empty($fileTempName)) {
   $isUploaded = move_uploaded_file($fileTempName, 'attachment/'.$fileName);
   if($isUploaded) {
    $attachedFile = $fileName;
    if(strpos($_FILES['input_file']['type'], 'image') !== false) {
     $fileType = 'image';
    } else {
     $fileType = 'other';
   }
    $uploadError = false;
   } else {
    $uploadError = true;
   } 
  }
 } else {
  $uploadError = true;
 }

 //SESSIONへ受け渡し
 if(!$uploadError) {
  $_SESSION['input_file'] = $attachedFile;
 }
?>
  後半はファイルのアップロードの処理が書かれています。ファイルのアップロードは「move_uploaded_file()」という関数で実装できます。第一引数にはファイルのtmp_nameを指定します、そして第二引数にはファイルアップロード先のディレクトリを指定します。また上記ではアップロード完了後にファイルタイプが画像か、画像以外かを判断できるようにしています。合わせて、送信失敗した場合には、送信失敗を示す状態を値で出力しておきます。最後に$_SESSIONに値を入れられるようにしておきます。実際にサーバー上にあるアップロード用フォルダを確認してみると、セットしたファイルがアップロードされているのが確認できます。   そして、入力内容確認の部分では添付ファイルの情報を表示させていきます。ここでは添付ファイルの形式が画像だった場合にプレビューできるようimg要素を用意しています。そしてイメージ要素のsrc属性にアップロード先を指定することで、アップロード完了後にページ上でプレビュー画像として確認できるようになります。   【check.php(表示部分)】※一部抜粋
<form method="post" action="./thanks.php">
 <?php if(!$uploadError && $fileType === 'image'): ?>
  <img src="./attachment/<?php echo $attachedFile; ?>" alt="<?php echo $attachedFile; ?>">
  <span><?php echo $attachedFile; ?></span>
 <?php else: ?>
  <span><?php echo $attachedFile; ?></span>
 <?php endif; ?>
 <input type="submit" value="送信する">
</form>
  実際に画面上でこのように表示されます。プレビュー画像などの添付ファイルの情報はアップロードの結果で表示が変えられるようにしておくと良いですね。    
メールへのファイル添付とメール送信を行う完了画面
最後の完了画面ではファイルをメールへ添付する処理などを書いていきます。コードを見ていくとまずはメール送信設定に関する記述が並びます。この時にメールヘッダ設定でContent-Typeの項目が通常のメールフォームと異なるので注意します。   その次には自動返信メールなどの内容を指定していきます。ファイルのメール添付は、基本的にbase64のエンコードを行い、本文内に追記する形で添付されます。なので、この部分に添付する処理も含まれることになります。変数に格納された本文に続けて「chunk_split(base64_encode(file_get_contents());」とあり、ここで添付ファイルが指定されています。 【thanks.php(処理部分)】※一部抜粋
<?php
 //セッション開始
 session_start();

 //メール差出人
 $sender = "メール差出人";

 //メール送信元
 $mailFrom = "info@example.com";

 //メール送信先
 $mailTo = "user@example.com";

 //メール返信先
 $replyTo = "info@example.com";

 //管理者メールアドレス
 $adminEmail = "info@example.com";

 //メールヘッダ設定
 $addHeader = "MIME-Version: 1.0n";
 $addHeader .= "Content-Type: multipart/mixed; boundary="__BOUNDARY__"n";
 $addHeader .="From:".mb_encode_mimeheader($sender)."<".$mailFrom.">n";
 $addHeader .= "Reply-to: ".$replyTo."n";
 $addHeader .= "X-Mailer: PHP/". phpversion();

 // 迷惑メール対策
 $addOption = '-f'.$mailFrom;

 //データの変数化
 $file = htmlspecialchars($_SESSION['input_file'], ENT_QUOTES, 'UTF-8');

 //自動返信メール本文
 $messageUser = "--__BOUNDARY__n";
 $messageUser .= "Content-Type: text/plain; charset="ISO-2022-JP"nn";
 $messageUser .= <<< EOD
下記の添付ファイルを送信しました

----------------------------------------------------

【添付ファイル】{$file}

----------------------------------------------------

EOD;
 $messageUser .= "--__BOUNDARY__n";

 //管理者確認用メール本文
 $messageAdmin = "--__BOUNDARY__n";
 $messageAdmin .= "Content-Type: text/plain; charset="ISO-2022-JP"nn";
 $messageAdmin .= <<< EOD
ウェブサイトより下記の内容でファイルが送信されました

----------------------------------------------------

【添付ファイル】{$file}

----------------------------------------------------

EOD;
 $messageAdmin .= "--__BOUNDARY__n";

 //メール共通送信設定
 mb_language("ja");
 mb_internal_encoding("UTF-8");

 //ファイルデータ添付
 if(!empty($_SESSION['input_file'])) { 
  $messageUser .= "Content-Type: application/octet-stream; name="{$file}"n"; 
  $messageUser .= "Content-Disposition: attachment; filename="{$file}"n";
  $messageUser .= "Content-Transfer-Encoding: base64n";
  $messageUser .= "n";
  $messageUser .= chunk_split(base64_encode(file_get_contents('attachment/'.$file)));
  $messageUser .= "--__BOUNDARY__n";

  $messageAdmin .= "Content-Type: application/octet-stream; name="{$file}"n"; 
  $messageAdmin .= "Content-Disposition: attachment; filename="{$file}"n";
  $messageAdmin .= "Content-Transfer-Encoding: base64n";
  $messageAdmin .= "n";
  $messageAdmin .= chunk_split(base64_encode(file_get_contents('attachment/'.$file)));
  $messageAdmin .= "--__BOUNDARY__n";
 }

 if(!empty($mailTo)) {
  //自動返信メール送信設定
  mb_send_mail($mailTo,"ファイルを送信しました",$messageUser,$addHeader,$addOption);
  // 管理者確認用メール送信設定
  mb_send_mail($adminEmail,"ファイルを受信しました",$messageAdmin,$addHeader,$addOption); 
  $isSend = true;
 } else {
  $isSend = false;
 }

 //セッション終了
 session_destroy();
?>
  あとは「mb_send_mail()」で本文と一緒にメールで送信するとファイルが添付された状態でメールが送信されます。この時に送信結果のステータスも出力できるようにしておきます。そして結果表示に使うHTML側では送信結果に合わせて表示するメッセージを切り替えられるようにします。 【thanks.php(結果表示部分)】※一部抜粋
<h1>ファイルデータ送信完了</h1>
<?php if($isSend): ?>
 <p>ファイルがフォームより送信されました。
 </p>
<?php else: ?>
 <p>送信エラー:フォームからの送信に失敗しました。お手数ですが再度お試しください。
 </p>
<?php endif; ?>
  これで実際に送信されたメールを確認すると、問題なくファイルが添付されているのが確認できました。  
  今回はフォームでのファイルアップロードとメール添付の機能を実装してみました。お問い合わせ用のフォームなどでもファイルが添付できるようになるとユーザビリティも向上し、親切なフォームになります。過去記事でも紹介しているメールフォームと併用すると、ファイル添付機能がついたコンタクトフォームが完成しますので、ぜひ試してみてはいかがでしょうか?   (関連記事) PHPで自動返信メール機能付きのコンタクトフォームを作成する(入力画面) PHPで自動返信メール機能付きのコンタクトフォームを作成する(確認画面) PHPで自動返信メール機能付きのコンタクトフォームを作成する(送信画面) PHPでサーバーサイドのフォームバリデーションを実装する   (参考にさせて頂いたサイト) アップロードしたファイルをメールに添付する
XでシェアLINEで送るはてブに追加

この記事を書いた人オガワ シンヤ

合同会社デザインサプライ代表兼CEO / ディレクター・ウェブデザイナー・フロントエンドエンジニアをやっています。「ウェブとデザインでヒト・モノ・サービスを繋げ新しい価値を生み出す」をコンセプトに日々奮闘中!制作中はダイエットコーラとチョコレートが欠かせないアラフォーWebクリエイター。

Sponsored Link

  • Showcase
  • Startify UI
  • Functional Gradation Generator
  • Coloooors

keyword search

categories

  • WordPress(61)
  • JavaScript(49)
  • Vue.js(48)
  • CSS(46)
  • jQuery(34)
  • Nuxt.js(22)
  • Sass(21)
  • Gulp(17)
  • webpack(16)
  • PHP(14)
  • HTML(14)
  • GSAP(11)
  • React(10)
  • Vite(9)
  • Pug(9)
  • Laravel(8)
  • Cordova(8)
  • Linux(7)
  • Next.js(6)
  • Apache(5)
  • Shopify(4)
  • REST API(4)
  • Node.js(4)
  • Smarty(3)
  • Git(3)
  • JSON(3)
  • その他プログラミング(3)
  • Google Apps API(3)
  • Bootstrap(3)
  • 環境構築・システム(3)
  • TypeScript(2)
  • EJS(2)
  • RMS(2)
  • Docker(2)
  • Instagram API(2)
  • Excel VBA(2)
  • SVG(1)
  • Dart(1)
  • ECカートASP(1)
  • Markdown(1)
  • AMP(1)
  • Nginx(1)
  • XML(1)
  • shellscript(1)
  • Ruby(1)
  • MySQL(1)

recent articles

  • Next.jsとWordPressでヘッドレスCMSのサイトを作成する#6:PWA対応とビルド時のエラー
    read more

    Next.jsとWordPressでヘッドレスCMSのサイトを作成する#6:PWA対応とビルド時のエラー

    2024.12.25/Next.js
  • Next.jsとWordPressでヘッドレスCMSのサイトを作成する#5:アナリティクス・アドセンスの導入とサイトマップ作成
    read more

    Next.jsとWordPressでヘッドレスCMSのサイトを作成する#5:アナリティクス・アドセンスの導入とサイトマップ作成

    2024.08.26/Next.js
  • Next.jsとWordPressでヘッドレスCMSのサイトを作成する#4:静的・動的ルーティングとページ作成
    read more

    Next.jsとWordPressでヘッドレスCMSのサイトを作成する#4:静的・動的ルーティングとページ作成

    2024.07.31/Next.js
  • Next.jsとWordPressでヘッドレスCMSのサイトを作成する#3:メタ情報設定・ファイル最適化・ステート管理
    read more

    Next.jsとWordPressでヘッドレスCMSのサイトを作成する#3:メタ情報設定・ファイル最適化・ステート管理

    2024.06.30/Next.js
  • Next.jsとWordPressでヘッドレスCMSのサイトを作成する#2:コーディング環境の構築
    read more

    Next.jsとWordPressでヘッドレスCMSのサイトを作成する#2:コーディング環境の構築

    2024.05.29/Next.js
  • Next.jsとWordPressでヘッドレスCMSのサイトを作成する#1:インストール・導入
    read more

    Next.jsとWordPressでヘッドレスCMSのサイトを作成する#1:インストール・導入

    2024.04.30/Next.js
  • 次の記事
  • 一覧に戻る
  • 前の記事

まだ依頼内容が決まっていなくても、ご相談ください。

課題の整理や小さな検証、UI/UX・フロントエンドの部分的な支援から始められます。

お問い合わせやご相談はこちらから

Webサイト・プロダクトの企画設計/UI・UXデザイン/フロントエンド開発合同会社デザインサプライ(DesignSupply. LLC)

Office:大阪府大阪市天王寺区清水谷町3-22
Email:info@designsupply-web.com
home
  • サイトトップ
about
  • 3つのポリシー
  • 経営理念
  • 代表・クリエイター紹介
  • 会社概要
services
  • ビジネス・プロダクト支援
  • UI/UX・フロントエンド開発支援
  • プロジェクトの進め方・支援体制
  • エデュケーション事業
works
  • 開発プロジェクト支援
  • クリエイティブ制作
  • 自社プロダクト
media
  • デザイン
  • プログラミング
  • マーケティング
  • Web開発
  • 写真・動画制作
contact
  • お問い合わせ
news
  • インフォメーション
privacy
  • プライバシーポリシー

WE THINK WITH YOU, DESIGN FOR PEOPLE, AND BUILD WHAT WORKS.

WE THINK WITH YOU, DESIGN FOR PEOPLE, AND BUILD WHAT WORKS.

© 2013 - 2026 DesignSupply.LLC
サイトトップへ
contact