2
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

Laravel API 何故かコントローラーの関数を用いて値を返すと405エラーを返す

Posted at

概要

  • LaravelをAPIサーバーとして用いてとあるルーティングにリクエストを送ったが405を返す問題が発生してちょっと詰まったので原因をまとめる。

問題発生までの経緯

  • 下記の様にルーティング、コントローラーに記載を行った。

    • ルーティング

      web.php
      // thunder client動作確認用
      Route::get('/get_test', function(){
          return 'ROOT GET OK';
      });
      Route::post('/post_test', function(){
          return 'ROOT POST OK';
      });
      
      Route::post('/send', [LineMessageController::class, 'send']);
      
    • コントローラー

      TestController.php
      public function send(GetSendRequest $request)
      {
          return 'XXX';
      }
      
  • DockerでPHPコンテナ内にApacheを立てている。

  • ローカルの8000ポートをコンテナ内の80ポートにフォワーディングしている。

  • app/Http/Middleware/VerifyCsrfToken.php$exceptの配列にpost_testsendを追加した。

  • VScodeのThunder Clientを用いてそれぞれ下記のURLにリクエストを投げた。

問題発生

  • http://localhost:8000/sendにリクエストを投げたときだけ405 Method Not Allowedが帰ってきた。

    Symfony\Component\HttpKernel\Exception\MethodNotAllowedHttpException: The POST method is not supported for this route. Supported methods: GET, HEAD. in file /var/www/html/vendor/laravel/framework/src/Illuminate/Routing/AbstractRouteCollection.php on line 118
    

問題解消までの経緯

  1. Thunder Clientに登録しているリクエストのURLに誤りが無いことを確認 → 問題なさそう。

  2. ルーティングファイルで当該のルート情報がpostになっている事を確認 → 問題なさそう。(なぜ「Supported methods: GET」と言われているのか分からない。)

  3. 「Supported methods: GET」と言われているので当該のルート情報のgetで受け付ける様に修正して実行してみた。

    web.php
    Route::get('/send', [LineMessageController::class, 'send']);
    
  4. 下記のエラー405 Method Not Allowedが帰ってきた。

    Symfony\Component\HttpKernel\Exception\MethodNotAllowedHttpException: The GET method is not supported for this route. Supported methods: POST. in file /var/www/html/vendor/laravel/framework/src/Illuminate/Routing/AbstractRouteCollection.php on line 118
    
  5. 「Supported methods: POST.」と帰ってきてプチパニック(「Supported methods: GET.」って言われたからGETにしてリクエスト送ったのに「Supported methods: POST.」ってなんでや)

  6. 下記の知見を発見したが、自分のリクエストを確認して問題無かった。

  7. 下記の様にルーティングに記載して、コントローラーを呼び出しているルーティングはコメントアウトした。

    Route::post('/send', function(){
        return 'ROOT SEND POST OK';
    });
    
  8. ↑これだと「ROOT SEND POST OK」の文字が帰ってくる。どうやらコントローラーのメソッドに問題がありそう。

  9. もう一度当該のコントローラーの当該の関数をよく見てみる。

    TestController.php
    public function send(GetSendRequest $request)
    {
        return 'XXX';
    }
    
  10. よく見たら独自に作成したリクエストクラスであるGetSendRequestを通してデータが当該関数に入ってきている。

  11. GetSendRequestを見たところ、Postしていない値が必須バリデーションされていた。下記の様に修正したら「XXX」の文字が返された。

    TestController.php
    use Illuminate\Http\Request;    
    
    public function send(Request $request)
    {
        return 'XXX';
    }
    

原因

  1. 意図しないバリデーションが設定されていた。
  2. リクエストのテストでは何も値をPostしていなかったため、バリデーションエラーが発生 → エラー画面へのリダイレクトが行われたが、リダイレクト先のルーティングがGETで定義されていたため「Supported methods: GET,」のエラーが出たものと思われる。
2
0
1

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?