web-dev-qa-db-fra.com

Obtenir une mauvaise requête (# 400) sur des appels Ajax utilisant Yii 2

Ceci est mon code:

$(document).on('change', '#tblhotel-int_zone_id', function(e){
    var zoneId = $(this).val();
    var form_data = {
        zone: zoneId
    };
    $.ajax({
        url: "state",
        type: "POST",
        data: form_data,
        success: function(response)
        {
            alert(response);
        }
    });
});

Ceci montre:

Requête incorrecte (# 400): Impossible de vérifier votre soumission de données.

Et j'ai déjà <?= Html::csrfMetaTags() ?>. Comment puis-je résoudre ce problème?

16
Kartz

Remarque: voir la réponse de Skullcrasher pour résoudre le problème de manière correcte, car ma réponse suggère de désactiver le falsification de requête entre sites .


Vous avez un problème avec enableCsrfValidation. Pour en savoir plus à ce sujet, vous pouvez lire ici .

Pour désactiver CSRF, ajoutez ce code à votre contrôleur:

public function beforeAction($action) {
    $this->enableCsrfValidation = false;
    return parent::beforeAction($action);
}

Cela désactivera toutes les actions. Selon l'action $, vous devriez probablement la désactiver uniquement pour des actions spécifiques.

39
Mihai P.

Comme le dit Mihai P., votre problème est la validation CSRF. Il est également vrai que vous pouvez désactiver la validation de vos actions, mais cela n’est pas considéré comme une bonne solution.

Comme vous avez un problème avec votre demande Ajax avec la validation, vous pouvez également utiliser une fonction JavaScript Yii pour ajouter le jeton CSRF à vos données de formulaire que vous envoyez dans la demande Ajax.

Essayez simplement d’ajouter le jeton à vos données de formulaire comme suit:

var form_data = {
    zone: zoneId,
    _csrf: yii.getCsrfToken()
};

J'espère que cela aide et que vous n'avez donc pas à désactiver la validation CSRF.

En plus d'ajouter manuellement le jeton CSRF, vous pouvez vérifier si un en-tête X-CSRF est défini dans la demande.

26
Faenor

Ajoutez ce code au bas de votre mise en page:

<script>
    $.ajaxSetup({
        data: <?= \yii\helpers\Json::encode([
            \yii::$app->request->csrfParam => \yii::$app->request->csrfToken,
        ]) ?>
    });
</script>
8
Oleg

Utilisation:

var csrfToken = $('meta[name="csrf-token"]').attr("content");
$.ajax({
    url: 'request',
    type: 'post',
    dataType: 'json',
    data: {param1: param1, _csrf : csrfToken},
});

Plus de détails: Yii2: utilisation du jeton csrf

5
Ngô Văn Thao

Vous devez désactiver la validation CSRF dans la fonction before action:

public function beforeAction($action) {
    if($action->id == "action name need to disable")
        $this->enableCsrfValidation = false;
    return parent::beforeAction($action);
}

Ou en utilisant la méthode GET .

2
Hồn Âm

Cela marche. Changez le csrfParam avec votre propre in Config/main.php

'components' => [
    'request'=>[
        'csrfParam'=>"othername"
    ],
    ...

Rappelez-vous que vous devez inclure dans vos demandes le jeton portant le même nom que celui que vous avez défini dans config.

1
Prescol

Bien que ce soit un ancien message avec beaucoup de réponses mais qu'il manque quelque chose à toutes les réponses postées, ils ont tous répondu au bon moment, mais lorsque vous appelez la demande ajax POST avec vos données, vous devez utiliser les fonctions yii.js fournies

  • yii.getCsrfParam() pour obtenir le nom du paramètre du jeton
  • yii.getCsrfToken() pour obtenir le jeton ou la valeur réelle du jeton csrf

Comme si vous aviez un nom de paramètre différent pour le front-end défini dans config.php ou web.php dans les configurations de composants request 

components=>[
.......
.......
    'request' => [
        'csrfParam' => '_csrf-frontend',
    ],
.......
.......
]

alors vous devez obtenir ce nom dynamiquement et la fonction ci-dessus vous aide.

Vous devriez 

var form_data = {
    zone: zoneId
};
form_data[yii.getCsrfParam()]=yii.getCsrfToken();
0
Muhammad Omer Aslam

/backend/config/main-local.php

'components' => [
    'request' => [
        'cookieValidationKey' => 'unique code',
        'csrfCookie' => ['httpOnly' => true, 'path' => '/admin/'],
    ],
],

/frontend/config/main-local.php

'components' => [
    'request' => [
        'cookieValidationKey' => 'unique code',
        'csrfCookie' => ['httpOnly' => true, 'path' => '/'],
    ],
],
0
Алексей