Est-ce que $ SERVER['HTTP X REQUESTED WITH'] existe en PHP ou non?

partout sur Internet, même ici à Stack Overflow, les gens déclarent qu'une bonne façon de vérifier si une requête est AJAX ou non est de faire ce qui suit:

if (strtolower($_SERVER['HTTP_X_REQUESTED_WITH']) == 'xmlhttprequest' ) {...}

Cependant, je ne vois pas $_SERVER['HTTP_X_REQUESTED_WITH'] dans le documentation officielle de PHP

Et quand j'essaie de faire ce qui suit:

echo $_SERVER['HTTP_X_REQUESTED_WITH'];

Rien n'est sorti.

est-ce que je fais quelque chose de mal? Parce que j'avais vraiment aimer pouvoir utiliser $_SERVER['HTTP_X_REQUESTED_WITH'] si elle est disponible.

62
demandé sur brasofilo 2010-04-05 19:38:39

10 réponses

les variables de $_SERVER ne font pas vraiment partie de PHP, c'est pourquoi vous ne les trouverez pas dans la documentation PHP. Ils sont préparés par le serveur Web qui transmet le langage de script.

pour autant que je sache, le X-Requested-With est envoyé par les fonctions Ajax de la plupart des cadres principaux mais pas tous (Dojo, par exemple, il a ajouté Il ya seulement deux ans: #5801 ). En tant que tel, et en tenant compte des commentaires de @bobince, c'est sans danger pour dire que ce n'est généralement pas une méthode fiable à 100% pour déterminer si une requête est une requête AJAX ou non.

le seul moyen sûr à 100% est d'envoyer un drapeau prédéfini (par exemple une variable GET) avec la requête et que la page de réception vérifie la présence de ce drapeau.

57
répondu Pekka 웃 2010-04-05 16:02:43

n'oubliez pas que vous pouvez facilement spoof n'importe quel en-tête avec cURL comme ainsi

curl_setopt($ch,CURLOPT_HTTPHEADER,array("X-Requested-With : XMLHttpRequest"));
27
répondu J. Michael Wilson 2011-02-24 18:50:25

$_SERVER les clés qui commencent par HTTP_ sont générées à partir des en-têtes de requête HTTP. Dans ce cas, l'en-tête X-Requested-With .

17
répondu Ignacio Vazquez-Abrams 2010-04-05 15:40:20

cet en-tête est une standardisation en cours de toutes les bibliothèques AJAX là-bas.

il ne sera pas documenté dans la documentation php en soi, mais plutôt dans les différentes bibliothèques AJAX qui ont défini cet en-tête. Les bibliothèques courantes ont envoyé cet en-tête: jQuery, Mojo, Prototype,...

habituellement, ces bibliothèques définiront l'en-tête en utilisant

xhrobj.setRequestHeader("X-Requested-With", "XMLHttpRequest");
11
répondu Jerome WAGNER 2014-08-22 20:57:44

Voici une fonction rapide avec un exemple d'utilisation:

function isXmlHttpRequest()
{
    $header = isset($_SERVER['HTTP_X_REQUESTED_WITH']) ? $_SERVER['HTTP_X_REQUESTED_WITH'] : null;
    return ($header === 'XMLHttpRequest');
}

// example - checking our active call
if(!isXmlHttpRequest())
{
    echo 'Not an ajax request';
}
else
{
    echo 'is an ajax request';
}
4
répondu tfont 2014-02-25 22:16:09
echo $_SERVER['HTTP_X_REQUESTED_WITH'];

Qu'attendez-vous d'un tel code? Supposons que vous l'exécutez directement à partir du navigateur, pas en utilisant la requête AJAX. Alors, comment se fait cet en-tête peut être réglé?

bien la réponse à la question ultime de la vie, L'Univers, et tout - un HTTP sniffer ! Prenez-en un et oubliez l'impression de la variable $_SERVER.

Firebug en a un, ou vous pouvez utiliser Fiddler HTTP proxy ou LiveHTTPHeaders Mozilla plugin. Je m'ennuie à faire des liens mais il facilement googlé.

donc, avec HTTP sniffer vous pouvez être sûr de n'importe quel en-tête HTTP jamais.

notez que vous ne pouvez empêcher aucun" accès direct "en utilisant XHR, car chaque requête HTTP sur votre serveur est déjà"directe".

3
répondu Your Common Sense 2010-04-05 16:01:23

vous pouvez aussi blâmer certains bugs de navigateur - voir cette question et sa solution pour Firefox""

Firefox ne préserve pas les en-têtes personnalisés pendant la redirection de requête Ajax: an ASP.NET MVC solution

C'est à dire aussi avoir problème de cache qui est plus grave que la détection de la méthode de la requête.

vous devez quand même ajouter des Busters de cache pour éviter la mise en cache, alors pourquoi ne pas utiliser un autre drapeau pour spécifier l'appel ajax - ou mieux, vous pouvez utiliser différentes URL comme http://ajax.mysite.com/endpoint/sevice?params

1
répondu EGL 2-101 2017-05-23 11:54:18
$headers = apache_request_headers();
$is_ajax = (isset($headers['X-Requested-With']) && $headers['X-Requested-With'] == 'XMLHttpRequest');
1
répondu revoke 2014-06-25 13:27:34

la meilleure solution pour s'assurer qu'une requête HTTP est vraiment envoyée via AJAX est d'utiliser la vérification de SESSION , vous envoyez session_id dans un paramètre get et vous vérifiez cette session si elle est autorisée ou non !

0
répondu The Evil Thinker 2013-01-03 13:18:10

Je suis D'accord avec Pekka. Il n'y a pas de méthode native fiable entre le côté avant et le côté arrière qui peut auto-détecter si un client appelle vraiment un point final en utilisant AJAX.

pour mon propre usage, je dispose de peu de moyens principaux pour vérifier si un client demande l'un de mes paramètres:

  1. je peux utiliser HTTP_X_REQUESTED_WITH quand je ne suis pas dans un contexte de domaine croisé.

  2. au lieu de vérifier "X-requested-with", je vérifie $_SERVER['HTTP_ORIGIN'] (qui est envoyé depuis AJAX request) avec l'intention de gérer les permissions de domaines croisés. La plupart du temps, la raison principale pour laquelle je vérifie si une requête est une requête AJAX, est en particulier à cause des permissions entre domaines, en utilisant ce code PHP: header('Access-Control-Allow-Origin:').$_SERVER['HTTP_ORIGIN']); // Si cette "HTTP_ORIGIN" est dans ma liste blanche

  3. mes IPA s'attendent du client à être explicites, en quelques cas, le type de données (JSON, HTML etc.) dans un GET ou un POST var. Par exemple, je vérifie si $_REQUEST['ajax'] n'est pas vide ou égal à une valeur attendue.

0
répondu FragBis 2016-08-16 17:08:40