【JavaScript/jQuery】非同期で画像アップロード JS

画像アップロードの方法

一例として、以下のようなもの。今回は非同期の場合。

・ファイル選択後に、送信(アップロード、同期)してcontroller側で処理して表示(再読み込み)
・ファイル選択と同時に送信(アップロード、同期)してcontroller側で処理して表示(再読み込み)
・ファイル選択後に、非同期で送信してそのまま表示(APIを含んだり)
・ファイル選択と同時に、非同期で送信してそのまま表示(APIを含んだり)

コード

phpとJSの場合。

JS

//ファイル選択後にclickイベント。あるいはchange。
$('#upload').click(function(){
  let up_file = document.getElementById('upfile1').files[0];
  let form = $('#test_image_form').get()[0];//フォームデータを格納
  var formData = new FromData(form);//FormDataオブジェクト作成

  $.ajax({
    url:'hogehoge',//ファイルorパスor name
    method:'post',
    dataType:'json',
    data:formData,
    processData:false,//ajaxがデータを整形しない
    contentType:false//falseに指定
  }).done(function(){//thenの方が良いかもしれない
    //成功時の処理
    //inputタグのsrcに入れてやる、data属性を使用している場合にはそれに従う
    //JSON.stringfy()でJSON文字列に変換する
    //非同期で画像表示させる場合は別途処理追加
  }).fail(function(jqXHR, textStatus,errorThrown){
    //失敗した時の処理
    console.log('ERROR', jqXHR, textStatus,errorThrown);
  });
  return false;
};

php

ajax用の関数を設定し(url)、$_FILESを使い、データを整形。
APIを使う場合には、それによりデータを取得して整形。

HTML

非同期のため、buttonを使用。

<form id="test_image_form">
  <input id="upfile1" name="upfile" type="file">
  <button id="upload" type="button">送信</button>
</form>

デバッグの重要性

ajaxで思った通りにデータが返って来ずに詰まった。
デバッグを繰り返しながら、設定したデータがどのようにcontrollerに渡されているのかを一つずつ地道に確認しながら作業したところ、データを整形し画像アップロードと表示を非同期ですることができた。慣れていないうちは、一つずつデータの動きを追うことが大事だと実感した。

参照

FormData
ajax(jQuery)でファイルをアップロードする
[JavaScript] Ajaxでファイルをアップロード【jQuery使用】
jQuery.ajax()