Michele Della Mea
Michele Della Mea

Reputation: 1002

laravel cannot post data with ajax server status 419

I am doing a project with Laravel.

When I change the selected option of the following select element I should insert the selected value to mysql database to retrieve all the data about the selected id from the server (for example the name of the user).

This is the select element (adminArea.blade.php):

<select name="employees" onchange="fillEmployeeData(this)" class="form-control col-sm-6" id="employees">
    <option value="0"></option>
    @foreach ($users as $user)
    <option value="{{ $user->id }}">{{ $user->surname . ' ' . $user->name }}</option>
    @endforeach
</select>

And this is the called function (adminArea.blade.php)::

function fillEmployeeData(emp_id) {
    var emp_selected = emp_id.value;
    $.ajax({
        type: "POST",
        url: "{{ route('adminAreaPostEmployee') }}",
        data: 'emp_selected=' + emp_selected,
        success: function (data) {
            var emp_data = JSON.parse(data);
            alert(emp_data);
        }
    });
};

These are my routes (web.php):

Route::get('/adminarea', 'AdminAreaController@index')->name('adminArea');
Route::post('/adminarea/postemployee', 'AdminAreaController@post_employee')->name('adminAreaPostEmployee');

And these are my controller methods (adminAreaController.php):

public function post_employee(Request $request)
{
    $select = $request->get('emp_selected');
    $user = User::where('id', $select);
    echo $user;
}

public function index()
{
    $operations = Operation::all();
    $users = User::all()->sortBy('surname');
    $rooms = Room::all();
    return view('adminArea', compact('users', 'rooms', 'operations'));
}

However, when I change the selected value nothing happens... and if I go to the developer tools I see the following error:

Failed to load resource: the server responded with a status of 419 (unknown status). Symfony\Component\HttpKernel\Exception\MethodNotAllowedHttpException The GET method is not supported for this route. Supported methods: POST.

I don't see any alert. Someone can help me?

Upvotes: 0

Views: 575

Answers (3)

Armen
Armen

Reputation: 1

this is a CSRF protection of laravel, you can add csrf meta tag in the head

<meta name="csrf-token" content="{{ csrf_token() }}">

and in the top of the script write

$.ajaxSetup({
headers: {
    'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content')
   }
});

Upvotes: 0

alprnkeskekoglu
alprnkeskekoglu

Reputation: 318

Try to 'method' instead of 'type' . You should use type if you're using versions of jQuery prior to 1.9.0

function fillEmployeeData(emp_id) {
    var emp_selected = emp_id.value;
    $.ajax({
        method: "POST",
        url: "{{ route('adminAreaPostEmployee') }}",
        data: 'emp_selected=' + emp_selected,
        success: function (data) {
            var emp_data = JSON.parse(data);
            alert(emp_data);
        }
    });
};

Upvotes: 0

Salim Djerbouh
Salim Djerbouh

Reputation: 11034

The HTTP status code for the MethodNotAllowedHttpException is 405

See here

public function __construct(array $allow, string $message = null, \Throwable $previous = null, ?int $code = 0, array $headers = [])
{
    $headers['Allow'] = strtoupper(implode(', ', $allow));
    parent::__construct(405, $message, $previous, $headers, $code);
}

A TokenMismatchException HTTP status code is 419

See here

protected function prepareException(Exception $e)
{
    if ($e instanceof ModelNotFoundException) {
        $e = new NotFoundHttpException($e->getMessage(), $e);
    } elseif ($e instanceof AuthorizationException) {
        $e = new AccessDeniedHttpException($e->getMessage(), $e);
    } elseif ($e instanceof TokenMismatchException) {
        // HTTP Status code is send in the header here
        $e = new HttpException(419, $e->getMessage(), $e);
    } elseif ($e instanceof SuspiciousOperationException) {
        $e = new NotFoundHttpException('Bad hostname provided.', $e);
    }
    return $e;
}

So this appears to be a CSRF token issue

Make sure that you have a meta tag on the head of your document like this

<meta name="csrf-token" content="{{ csrf_token() }}">

Also from the JQuery Ajax Documentation

I think that the HTTP method should be defined as method parameter not type (though type works ¯\_(ツ)_/¯)

// Send a CSRF token header with every Ajax request
$.ajaxSetup({
    headers: {
        'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content')
    }
});
function fillEmployeeData(emp_id) {
    var emp_selected = emp_id.value;
    $.ajax({
        method: "POST",
        url: "{{ route('adminAreaPostEmployee') }}",
        data: 'emp_selected=' + emp_selected,
        success: function (data) {
            var emp_data = JSON.parse(data);
            alert(emp_data);
        }
    });
};

But now you're gonna get an error

Object of class Illuminate\Database\Eloquent\Builder could not be converted to string

Because you're trying to return a query builder instance User::where('id', $select) instead of the user record itself serialized

I think you may want to do this

public function post_employee(Request $request)
{
    $select = $request->get('emp_selected');
    return User::find($select);
}

Hope this helps

Upvotes: 1

Related Questions