php - headers - Laravel csrf token no coincide para la solicitud POST ajax
laravel post token (11)
Acabo de agregar
headers:
en la llamada ajax:
headers: {''X-CSRF-TOKEN'': $(''meta[name="csrf-token"]'').attr(''content'')},
en vista:
<div id = ''msg''>
This message will be replaced using Ajax. Click the button to replace the message.
</div>
{{ Form::submit(''Change'', array(''id'' => ''ajax'')) }}
función ajax:
<script>
$(document).ready(function() {
$(document).on(''click'', ''#ajax'', function () {
$.ajax({
type:''POST'',
url:''/ajax'',
headers: {''X-CSRF-TOKEN'': $(''meta[name="csrf-token"]'').attr(''content'')},
success:function(data){
$("#msg").html(data.msg);
}
});
});
});
</script>
en el controlador:
public function call(){
$msg = "This is a simple message.";
return response()->json(array(''msg''=> $msg), 200);
}
en routes.php
Route::post(''ajax'', ''AjaxController@call'');
Estoy tratando de eliminar datos de la base de datos a través de ajax.
HTML:
@foreach($a as $lis)
//some code
<a href="#" class="delteadd" id="{{$lis[''id'']}}">Delete</a>
//click action perform on this link
@endforeach
Mi código ajax:
$(''body'').on(''click'', ''.delteadd'', function (e) {
e.preventDefault();
//alert(''am i here'');
if (confirm(''Are you sure you want to Delete Ad ?'')) {
var id = $(this).attr(''id'');
$.ajax({
method: "POST",
url: "{{url()}}/delteadd",
}).done(function( msg ) {
if(msg.error == 0){
//$(''.sucess-status-update'').html(msg.message);
alert(msg.message);
}else{
alert(msg.message);
//$(''.error-favourite-message'').html(msg.message);
}
});
} else {
return false;
}
});
Esta es mi consulta para obtener datos de la base de datos ...
$a = Test::with(''hitsCount'')->where(''userid'', $id)->get()->toArray();
Pero cuando hago clic en Eliminar los datos del enlace no se eliminan y muestran csrf_token no coinciden ...
Agregue una
id
al
meta
que contiene el token
$(''#deleteMeal'').click(function(event) {
var theId = $(event.currentTarget).attr("data-mealId");
$(function() {
$( "#filler" ).dialog({
resizable: false,
height:140,
modal: true,
buttons: {
"Are you sure you want to delete this Meal? Doing so will also delete this meal from other users Saved Meals.": function() {
$(''#deleteMealLink'').click();
// jQuery.ajax({
// url : ''http://www.mealog.com/mealtrist/meals/delete/'' + theId,
// type : ''POST'',
// success : function( response ) {
// $("#container").replaceWith("<h1 style=''color:red''>Your Meal Has Been Deleted</h1>");
// }
// });
// similar behavior as clicking on a link
window.location.href = ''http://www.mealog.com/mealtrist/meals/delete/'' + theId;
$( this ).dialog( "close" );
},
Cancel: function() {
$( this ).dialog( "close" );
}
}
});
});
});
Y luego puedes obtenerlo en tu Javascript
<p><a href="http://<?php echo $domain; ?>/mealtrist/meals/delete/{{ $meal->id }}" id="deleteMealLink" data-mealId="{{$meal->id}}" ></a></p>
Creo que es mejor poner el token en el formulario y obtener este token por id
<input type="hidden" name="_token" id="token" value="{{ csrf_token() }}">
Y el JQUery:
var data = {
"_token": $(''#token'').val()
};
de esta manera, su JS no necesita estar en sus archivos Blade.
Debe incluir un campo de token CSRF (falsificación de solicitud de sitio cruzado) oculto en el formulario para que el middleware de protección CSRF pueda validar la solicitud.
Laravel genera automáticamente un "token" CSRF para cada sesión de usuario activa administrada por la aplicación. Este token se utiliza para verificar que el usuario autenticado es el que realmente realiza las solicitudes a la aplicación.
Entonces, al hacer solicitudes ajax, deberá pasar el token csrf a través del parámetro de datos. Aquí está el código de muestra.
<script>
$(document).ready(function() {
let token = $(''form'').find(''input[name="_token"]'').val();
let myData = $(''form'').find(''input[name="my_data"]'').val();
$(''form'').submit(function() {
$.ajax({
type:''POST'',
url:''/ajax'',
data: {_token: token, my_data: myData}
// headers: {''X-CSRF-TOKEN'': $(''meta[name="csrf-token"]'').attr(''content'')}, // unnecessary
// other ajax settings
});
return false;
});
});
</script>
En realidad tuve este error y no pude encontrar una solución. De hecho, terminé sin hacer una solicitud ajax. No sé si este problema se debió a que este es un subdominio en mi servidor o qué. Aquí está mi jquery.
var request = $.ajax({
url : "http://localhost/some/action",
method:"post",
data : {"_token":"{{ csrf_token() }}"} //pass the CSRF_TOKEN()
});
Así que configuré un ancla para ir a mi API en lugar de hacer una solicitud posterior, que es lo que creo que hacen la mayoría de las aplicaciones.
<form>
<input name="_token" type="hidden" value="cf54ty6y7yuuyyygytfggfd56667DfrSH8i">
<input name="my_data" type="text" value="">
<!-- other input fields -->
</form>
La mejor manera de resolver este problema "X-CSRF-TOKEN" es agregar el siguiente código a su diseño principal y continuar haciendo sus llamadas ajax normalmente:
En encabezado
<meta name="csrf-token" content="{{ csrf_token() }}" />
En script
<script type="text/javascript">
$.ajaxSetup({
headers: {
''X-CSRF-TOKEN'': $(''meta[name="csrf-token"]'').attr(''content'')
}
});
</script>
Para Laravel 5.8, configurar la metaetiqueta csrf para su diseño y configurar el encabezado de solicitud para csrf en la configuración de ajax no funcionará si está utilizando ajax para enviar un formulario que ya incluye un campo de entrada
_token
generado por el motor de plantillas de cuchilla Laravel.
Debe incluir el token csrf ya generado del formulario con su solicitud ajax porque el servidor lo esperaría y no el que está en su metaetiqueta.
Por ejemplo, así es como se
_token
el campo de entrada
_token
generado por Blade:
<form> <input name="_token" type="hidden" value="cf54ty6y7yuuyyygytfggfd56667DfrSH8i"> <input name="my_data" type="text" value=""> <!-- other input fields --> </form>
Luego envía su formulario con ajax de esta manera:
<script> $(document).ready(function() { let token = $(''form'').find(''input[name="_token"]'').val(); let myData = $(''form'').find(''input[name="my_data"]'').val(); $(''form'').submit(function() { $.ajax({ type:''POST'', url:''/ajax'', data: {_token: token, my_data: myData} // headers: {''X-CSRF-TOKEN'': $(''meta[name="csrf-token"]'').attr(''content'')}, // unnecessary // other ajax settings }); return false; }); }); </script>
El token csrf en el meta encabezado solo es útil cuando envía un formulario sin un campo de entrada
_token
generado por Blade.
Sepa que hay una cookie X-XSRF-TOKEN configurada para su comodidad. Marco como Angular y otros lo configuran por defecto. Verifique esto en el documento https://laravel.com/docs/5.7/csrf#csrf-x-xsrf-token Puede usarlo.
La mejor manera es usar el meta, en caso de que las cookies estén desactivadas.
var xsrfToken = decodeURIComponent(readCookie(''XSRF-TOKEN''));
if (xsrfToken) {
$.ajaxSetup({
headers: {
''X-XSRF-TOKEN'': xsrfToken
}
});
} else console.error(''....'');
Aquí la meta manera recomendada (puede poner el campo de cualquier manera, pero la meta es bastante agradable):
$.ajaxSetup({
headers: {
''X-CSRF-TOKEN'': $(''meta[name="csrf-token"]'').attr(''content'')
}
});
Tenga en cuenta el uso de
decodeURIComponent()
, es decodificar desde el formato uri que se utiliza para almacenar la cookie.
[de lo contrario, obtendrá una excepción de carga útil no válida en laravel].
Aquí la sección sobre la cookie csrf en el documento para verificar: https://laravel.com/docs/5.7/csrf#csrf-x-csrf-token
También aquí cómo laravel (bootstrap.js) lo está configurando para axios por defecto:
let token = document.head.querySelector(''meta[name="csrf-token"]'');
if (token) {
window.axios.defaults.headers.common[''X-CSRF-TOKEN''] = token.content;
} else {
console.error(''CSRF token not found: https://laravel.com/docs/csrf#csrf-x-csrf-token'');
}
puedes ir a ver
resources/js/bootstrap.js
.
Y aquí lee la función de cookies:
function readCookie(name) {
var nameEQ = name + "=";
var ca = document.cookie.split('';'');
for (var i = 0; i < ca.length; i++) {
var c = ca[i];
while (c.charAt(0) == '' '') c = c.substring(1, c.length);
if (c.indexOf(nameEQ) == 0) return c.substring(nameEQ.length, c.length);
}
return null;
}
Si está utilizando archivos de plantilla, puede colocar su
meta
en la
section
cabecera (o como quiera que la nombre) que contiene sus
meta
.
@section(''head'')
<meta name="csrf_token" content="{{ csrf_token() }}" />
@endsection
A continuación, debe colocar el atributo de
headers
en su
ajax
(en mi ejemplo, estoy usando
datatable
con procesamiento del lado del servidor:
"headers": {''X-CSRF-TOKEN'': $(''meta[name="csrf_token"]'').attr(''content'')}
Aquí está el ejemplo completo de
datatable
ajax:
$(''#datatable_users'').DataTable({
"responsive": true,
"serverSide": true,
"processing": true,
"paging": true,
"searching": { "regex": true },
"lengthMenu": [ [10, 25, 50, 100, -1], [10, 25, 50, 100, "All"] ],
"pageLength": 10,
"ajax": {
"type": "POST",
"headers": {''X-CSRF-TOKEN'': $(''meta[name="csrf_token"]'').attr(''content'')},
"url": "/getUsers",
"dataType": "json",
"contentType": ''application/json; charset=utf-8'',
"data": function (data) {
console.log(data);
},
"complete": function(response) {
console.log(response);
}
}
});
Después de hacer esto, debe obtener el
200 status
para su solicitud
ajax
.
Si está utilizando jQuery para enviar publicaciones AJAX, agregue este código a todas las vistas:
$( document ).on( ''ajaxSend'', addLaravelCSRF );
function addLaravelCSRF( event, jqxhr, settings ) {
jqxhr.setRequestHeader( ''X-XSRF-TOKEN'', getCookie( ''XSRF-TOKEN'' ) );
}
function getCookie(name) {
function escape(s) { return s.replace(/([.*+?/^${}()|/[/]////])/g, ''//$1''); };
var match = document.cookie.match(RegExp(''(?:^|;//s*)'' + escape(name) + ''=([^;]*)''));
return match ? match[1] : null;
}
Laravel agrega una cookie XSRF a todas las solicitudes, y las agregamos automáticamente a todas las solicitudes AJAX justo antes de enviarlas.
Puede reemplazar la función getCookie si hay otra función o el complemento jQuery para hacer lo mismo.
Tiene que agregar datos en su solicitud ajax. Espero que así sea el trabajo.
data: {
"_token": "{{ csrf_token() }}",
"id": id
}