Reputation: 2875
Before you down-vote me for posting another question about this error, or mark this as duplicate or anything, my question is a bit different
These are my known causes for this error:
POST
, route uses GET
csrf
token in meta or in form fieldI have checked both of those causes:
csrf
validation by commenting csrf
validation middleware in app/Http/Kernel.php
, but still got this error (is this correct method?)Basically, those two are what I know, and what I found when searching here.
So my question is:
In case you want to see my code:
Route::post('/export', [
'as' => 'export.csv',
'uses' => 'ToolsController@export'
]);
<form class="form-inline" action="{{ route('export.csv') }}" id="csv_export" method="post">
{{ csrf_field() }}
<input type="hidden" name="type" value="site_maps">
<input type="hidden" name="id" value="{{ request('id') }}">
<button type="submit" class="btn btn-primary">Export to CSV</button>
</form>
namespace App\Http\Controllers;
class ToolsController extends Controller
{
public function export(Request $request)
{
// some function
}
}
There is an XSRF-TOKEN
cookie set, have tried to delete it on browser, but it shows up again.
POST /export HTTP/1.1
Host: somehost.com
Connection: keep-alive
Content-Length: 68
Pragma: no-cache
Cache-Control: no-cache
Origin: http://somehost.com
Upgrade-Insecure-Requests: 1
Content-Type: application/x-www-form-urlencoded
Save-Data: on
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.77 Safari/537.36
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8
Referer: http://somehost.com/map/47
Accept-Encoding: gzip, deflate
Accept-Language: en-US,en;q=0.9,id-ID;q=0.8,id;q=0.7
Cookie: sso_token_33=--some-key--; XSRF-TOKEN=--some-token--; somehost_session=--some-cookie--
_token=--some-other-token--&type=site_maps&id=47
no route grouping
i have a weird case, as you can see in image below, the browser is correctly send a POST request, but laravel seems to see it as GET request, is there any Apache settings that can cause this behaviour?
route list:
+--------+----------+----------------+----------------+-------------------------------------------------+--------------+
| Domain | Method | URI | Name | Action | Middleware |
+--------+----------+----------------+----------------+-------------------------------------------------+--------------+
| | POST | export | export.csv | App\Http\Controllers\ToolsController@export | web |
| | GET|HEAD | map/{id} | pages.show | App\Http\Controllers\PagesController@show | web |
| | GET|HEAD | tree | pages.tree | App\Http\Controllers\PagesController@tree | web |
+--------+----------+----------------+----------------+-------------------------------------------------+--------------+
Upvotes: 2
Views: 369
Reputation: 5552
MethodNotAllowedHttpException
is only thrown when the method doesn't match the route definition. That means all of these conditions are true:
_method
form field was not sentX-HTTP-Method-Override
header was not sentOPTIONS
Some route definitions allow multiple methods. For example, Route::get()
defines GET and HEAD as acceptable.
The error is actually clear (the request used the wrong method), but the cause is sometimes more subtle. Starting from most obvious to least obvious, here are common causes:
Route::post()
_method
field in an HTML form:path
and :method
with the URI and Method columns of php artisan route:list
Route::group()
might have added a url prefix such as api/
or admin/
- this will be visible with route:list
users/active
needs to be defined before users/{user}
otherwise the {user}
route variable will match 'active'
If you still don't see a problem, try tinker against the path you copy from the Request Headers in the network tab of your developer tools:
$ php artisan tinker
>>> $uri = '/your/requested/path'
>>> $method = 'POST'
>>> app('router')->getRoutes()->match(app('request')->create($uri, $method))
=> Illuminate\Routing\Route {#191
+uri: "...",
...
If everything still looks correct, it might be time to start examining your Apache/Nginx/IIS configurations, specifically looking for redirect/rewrite situations such as adding/removing subdomains (like www) or https.
Or, if that threw the same exception then try without the $method and carefully examine the response:
>>> app('router')->getRoutes()->match(app('request')->create($uri))
A problem with the csrf token would not cause this error. Instead, that would throw a different exception such as TokenMismatchException
, or in some cases maybe an authorization error. Likewise, cookie issues should not cause an error like this.
Since this is a Laravel/Symfony exception, it should rule out an IIS/Apache/Nginx problem (unless a rewrite rule is intercepting the request). For example, IIS has some verbs disabled by default (PUT, DELETE, etc.) but instead would display an IIS 405 error page in that case.
Upvotes: 1