ラボ > Laravel、Lumen:ajax、api絡み

Laravel formとajaxのサンプル

作成日:2019-04-03, 更新日:2022-12-30

基本

・状況に応じて使い分けるのが面倒なので、全ページのhead内にcsrfトークンをセット
・form送信もjquery経由で送信(※送信前にバリデーションしたりするため)

ajax送信 form送信
csrfトークン ヘッダにセット input[name=_token]にセット
データの受渡し オブジェクトにしてJSONにして渡す
※配列をJSONにすると受取れない
ただのform

ビュー側

CSRFのトークンはmetaタグにしておく。

<html>
  <head>
    ~ 省略 ~
    <meta name="csrf-token" content="〇〇〇〇〇〇〇〇">
    ~ 省略 ~
  </head>
  <body>
    ~ 省略 ~
    <form>
      <input type="hidden" name="_token" value="" />
      ~ 省略 ~
      <button type="button" id="sendAjax">ajax送信</button>
      <button type="button" id="sendForm">form送信</button>
    </form>
    ~ 省略 ~
    
    <script>
      
      // axax送信のときは「headers」にトークンをセット
      $('form').on('click', '#sendAjax', function(){
        // formの内容はオブジェクトに変換→あとでJSONにする
        var obj_fd = {};
        var fd = $(this).parents('form').serializeArray();
        var max = fd.length;
        for ( var i=0; i<max; i++ ) {
          obj_fd[fd[i]['name']] = obj_fd[i]['value'];
        }
        
        $.ajax({
          url: 〇〇〇,
          ~ 省略 ~
          headers: {
            'Content-Type': 'application/json',
            'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content'),
          },
          data: JSON.stringify(obj_fd) // JSONにしてセット
        }).done(function(data) {
          ~ 省略 ~
        }).fail(function(jqXHR, textStatus, errorThrown) {
          // エラー
          var codeJqXHR = parseFloat(jqXHR.status);
          var errMes = '';
          if(codeJqXHR == 0 || jqXHR.status == 404 || errorThrown == 'Not Found') {
             errMes = 'There was a 404 error.';
          }
          else {
             errMes = 'XMLHttpRequest : ' + jqXHR.status + "\n"
                    + 'textStatus : '     + textStatus   + "\n"
                    + 'errorThrown : '    + errorThrown  + "\n";
          }
          console.log(errMes);
        });
      });
      
      // form送信のときは「input name="_token"」を使う
      $('form').on('click', '#sendForm', function(){
        if ( 〇〇〇 ) {
          $('form').find('[name="_token"]').val($('meta[name="csrf-token"]').attr('content'));
          $('form').submit();
        }
        else {
          // エラーメッセージの出力
        }
      });
      
    </script>
  </body>
</html>

コントローラー側

CSRFのチェックはルーティングのトコでミドルウェアが走るのでそこで対応してくれている。

~ 省略 ~
public function 〇〇〇() {
  $input = array(
    '〇〇〇' => \Request::input('〇〇〇', ''),
    '〇〇〇' => \Request::input('〇〇〇', ''),
  );
  
  ~ 省略 ~
}
~ 省略 ~

関連項目

Laravelでajax