web-dev-qa-db-fra.com

php $ _POST tableau vide lors de la soumission du formulaire

J'ai un CMS personnalisé que j'ai construit qui fonctionne parfaitement sur ma boîte de développement (Ubuntu/PHP5 +/MySQL5 +).

Je viens de le placer dans la boîte de production de mon client et maintenant, toutes les soumissions de formulaire s'affichent sous la forme de tableaux $ _POST vides.

J'ai trouvé une astuce pour vérifier que les données sont effectivement transmises à l'aide de file_get_contents('php://input'); et que les données s'affichent correctement - les tableaux $_POST/$_REQUEST sont toujours vides.

J'ai également vérifié que les en-têtes de type de contenu sont également corrects via firebug (application/x-www-form-urlencoded; charset=utf-8).

Ce problème se produit, qu'un formulaire soit soumis via AJAX ou par un formulaire standard.

Toute aide est grandement appréciée!

78
Mike D

Je sais que cette question concernait POST via un formulaire, mais je suis venue ici pour chercher des réponses à un problème similaire lors de la publication avec le type de contenu JSON. J'ai trouvé la réponse et je voulais la partager car cela m'a coûté beaucoup de temps.

Lors de l'utilisation du type de contenu JSON, le tableau $ _POST ne sera pas peuplé (uniquement avec les formulaires en plusieurs parties, je crois)

Voici ce qui a fonctionné pour corriger le problème:

$rest_json = file_get_contents("php://input");
$_POST = json_decode($rest_json, true);

espérons que cela aide quelqu'un!

152
tiltem

Voici une autre cause possible - mon formulaire était soumis à domain.com sans le WWW. et j'avais mis en place une redirection automatique pour ajouter le "WWW". Le tableau $ _POST a été vidé au cours du processus. Donc, pour résoudre ce problème, tout ce que j'avais à faire était de le soumettre à www.domain.com

82
icesar

J'avais un problème similaire. S'est avéré être une solution simple. Dans la forme que j'avais 

<formulaire action = "répertoire" method = "post"> 

où répertoire était le nom de ... le répertoire. Mon tableau POST était totalement vide. Quand j'ai regardé l'URL dans mon navigateur, il a été affiché avec une barre oblique à la fin. 

L'ajout de la barre oblique à la fin de mon action a fait l'affaire - 

<formulaire action = "répertoire /" méthode = "post">

Mon tableau $ _POST était à nouveau plein!

19
Randy Kilwag

Assurez-vous que, dans php.ini:

  • track_vars (disponible uniquement sur les très anciennes versions PHP) est défini sur On
  • variables_order contient la lettre P
  • post_max_size est défini sur une valeur raisonnable (par exemple 8 Mo)
  • (si vous utilisez suhosin patch) suhosin.post.max_vars et suhosin.request.max_vars sont suffisamment grands.

Je suppose que ma deuxième suggestion résoudra votre problème.

11
MrMage

Je suis tombé sur un problème similaire mais légèrement différent et il a fallu 2 jours pour comprendre le problème.

  • Dans mon cas aussi le tableau POST était vide.

  • Puis vérifié avec file_get_contents ('php: // input'); et c'était également vide.

Plus tard, j'ai découvert que ce navigateur ne demandait pas de confirmation de la soumission des données de formulaire après l'actualisation de la page chargée après la soumission de POST. C'était une page directement rafraîchissante. Mais lorsque j'ai changé l'URL du formulaire en un autre, il transmettait POST correctement et demandait de soumettre à nouveau les données lorsqu'il tentait d'actualiser la page.

Ensuite, j'ai vérifié ce qui ne va pas avec l'URL réelle. Il n'y avait aucun défaut avec l'URL, cependant il pointait vers un dossier sans index.php dans l'URL et je vérifiais POST à index.php.

Ici, je doutais que la redirection de/vers /index.php provoque la perte de données POST et une URL testée avec l’ajout du fichier index.php.

Ça a marché.

Posté ici pour que quelqu'un trouve cela utile. 

5
GUIR

J'ai constaté que lors de la publication de HTTP à HTTPS, le $_POST est vide ..__ Ceci s'est produit lors du test du formulaire, mais m'a pris un certain temps avant que je m'en rende compte.

4
Marcos

Pour le moment, je n'ai pas de solution élégante, mais je voulais partager mes découvertes pour que d'autres personnes confrontées à ce problème puissent s'y reporter. La source du problème était 2 valeurs PHP annulées dans un fichier .htaccess. J'avais simplement ajouté ces 2 valeurs pour augmenter la limite de taille de fichier pour les téléchargements de fichiers par défaut, de 8 Mo à quelque chose de plus grand. .

php_value post_max_size xxMB
php_value upload_max_filesize xxMB

J'ai ajouté des variables supplémentaires pour augmenter, espérons-le, les limites de tous les vars de suhosin.post.xxx/suhosin.upload.xxx, mais celles-ci n'ont malheureusement aucun effet sur ce problème. 

En résumé, je ne peux pas vraiment expliquer le "pourquoi" ici, mais j'ai identifié la cause première. Mon sentiment est que ceci est finalement un problème suhosin/htaccess, mais malheureusement, je ne pouvais pas résoudre autre chose que de supprimer les 2 valeurs dépassées de php ci-dessus. 

J'espère que cela aidera quelqu'un dans le futur, car j'ai passé une poignée d'heures à comprendre cela. Merci à tous ceux qui ont pris le temps de m'aider (MrMage, Andrew)

4
Mike D

Avoir le paramètre enable_post_data_reading désactivé entraînera ceci. Selon la documentation:

enable_post_data_reading

Si vous désactivez cette option, les champs $ _POST et $ _FILES ne seront pas renseignés. Le seul moyen de lire les données postérieures sera alors via l'encapsuleur de flux d'entrée php: //. Cela peut être utile pour les requêtes proxy ou pour traiter les données POST de manière efficace en mémoire.

4
Luke A. Leber

Je pourrais résoudre le problème en utilisant enctype = "application/x-www-form-urlencoded", la valeur par défaut étant "text/plain". Lorsque vous enregistrez $ DATA, le séparateur est un espace pour "text/plain" et un caractère spécial pour "urlencoded". 

Cordialement Frank

4
RudeUrm

Si vous publiez dans un fichier index.php dans un répertoire, par exemple /api/index.php, assurez-vous que le formulaire contient le répertoire complet, par exemple

Ce 

<form method="post" action="/api/index.php"> 
</form>

OR

<form method="post" action="/api/"> 
</form>

travaux.

Mais cela échoue

<form method="post" action="/api"> 
</form>
3
Sunday G Akinsete
<form action="test.php" method="post">
                        ^^^^^^^^^^^^^

Ok, c’était stupide et je me suis embarassé en public, mais j’ai lancé un petit script de test pour quelque chose dans PHP et lorsque mon tableau $_POST était vide, StackOverflow est le premier endroit où j’ai regardé et je ne l’ai pas fait. trouvez la réponse dont j'avais besoin.

J'avais seulement écrit 

<form action="test.php">

et oublié de spécifier la méthode comme étant POST!

Je suis sûr que quelqu'un va ricaner, mais si cela aide quelqu'un d'autre qui fait la même chose, alors ça ne me dérange pas! Nous le faisons tous de temps en temps!

3
user3070485

même problème ici!

j'essayais de me connecter au code de mon serveur local via une demande de poste dans le facteur, et ce problème m'a fait perdre beaucoup de temps!

pour toute personne utilisant un projet local (par exemple postman): utilisez votre adresse IPv4 (tapez ipconfig dans cmd) au lieu du mot clé "localhost" .

avant:

localhost/app/login

après:

192.168.1.101/app/login
2
Ali Shariati

REFERENCE: http://www.openjs.com/articles/ajax_xmlhttp_using_post.php

Méthode POST

Nous allons faire quelques modifications afin que la méthode POST soit utilisée lors de l'envoi de la requête ...

var url = "get_data.php";
var params = "lorem=ipsum&name=binny";
http.open("POST", url, true);

//Send the proper header information along with the request
http.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
http.setRequestHeader("Content-length", params.length);
http.setRequestHeader("Connection", "close");

http.onreadystatechange = function() {//Call a function when the state changes.
  if(http.readyState == 4 && http.status == 200) {
    alert(http.responseText);
  }
}
http.send(params);

Certains en-têtes HTTP doivent être définis avec toute demande POST. Nous les avons donc placés dans ces lignes ...

http.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
http.setRequestHeader("Content-length", params.length);
http.setRequestHeader("Connection", "close");

Avec les lignes ci-dessus, nous disons essentiellement que l'envoi de données est au format d'une soumission de formulaire. Nous donnons également la longueur des paramètres que nous envoyons.

http.onreadystatechange = function() {//Call a function when the state changes.
  if(http.readyState == 4 && http.status == 200) {
    alert(http.responseText);
  }
}

Nous avons défini un gestionnaire pour l'événement de changement «état prêt». C'est le même gestionnaire que nous avons utilisé pour la méthode GET. Vous pouvez utiliser le http.responseText ici - insérer dans un div en utilisant innerHTML (AHAH), l’évaluer (JSON) ou toute autre chose.

http.send(params);

Enfin, nous envoyons les paramètres avec la demande. L'URL donnée n'est chargée qu'après l'appel de cette ligne. Dans la méthode GET, le paramètre sera une valeur nulle. Mais dans la méthode POST, les données à envoyer seront envoyées comme argument de la fonction d'envoi. La variable params a été déclarée dans la deuxième ligne sous la forme lorem=ipsum&name=binny - nous envoyons donc deux paramètres - 'lorem' et 'name' avec les valeurs 'ipsum' et 'binny' respectivement.

1
Chandu

Pour moi, .htaccess était en train de rediriger quand mod_rewrite n'était pas installé. Installez mod_rewite et tout va bien.

Plus précisément:

<IfModule !mod_rewrite.c>
  ErrorDocument 404 /index.php
</Ifmodule>

était en train d'exécuter.

1
Martin Fisher

Dans mon cas, c'était parce que j'utilisais jQuery pour désactiver toutes les entrées de la page juste avant d'utiliser jQuery pour soumettre le formulaire . J'ai donc modifié mon "désactiver chaque entrée, même les types" cachés "":

$(":input").attr("disabled","disabled"); 

pour "désactiver uniquement les entrées de type" bouton "":

$('input[type=button]').attr('disabled',true);

C'était ainsi que l'utilisateur ne pouvait pas appuyer accidentellement deux fois sur le bouton 'Go' et ouvrir notre base de données!!. Il semble que si vous mettez l'attribut 'désactivé' sur un masque de type 'masqué', leurs valeurs ne seront pas envoyé si le formulaire est soumis!

1
Josh P

Je viens de passer des heures à résoudre un problème similaire. Le problème dans mon cas était le

max_input_vars = "1000"

par défaut, dans le fichier php.ini. J'ai eu un formulaire vraiment énorme sans uploads. php.ini est défini sur upload_max_filesize = "100M" et post_max_size = "108M" et ce n'était sûrement pas le problème dans mon cas. Le comportement PHP est identique pour max_input_vars lorsqu'il dépasse 1 000 variables dans le formulaire. Il retourne et vide le tableau _POST. J'aurais aimé pouvoir le trouver il y a une heure et des heures.

0
user3242171

Je recevais l'erreur suivante de Mod Security:

Access denied with code 500 (phase 2). Pattern match "((select|grant|delete|insert|drop|alter|replace|truncate|update|create|rename|describe)[[:space:]]+[A-Z|a-z|0-9|\*| |\,]+[[:space:]]+(from|into|table|database|index|view)[[:space:]]+[A-Z|a-z|0-9|\*| |\,]|UNION SELECT.*\'.*\'.*,[0-9].*INTO.*FROM)" at REQUEST_BODY. [file "/usr/local/Apache/conf/modsec2.user.conf"] [line "345"] [id "300013"] [rev "1"] [msg "Generic SQL injection protection"] [severity "CRITICAL"]

Une fois que j'ai retiré ma configuration de sécurité de mod pour tester, tout a fonctionné comme prévu. Maintenant, j'ai juste besoin de modifier mes règles pour rester en sécurité mais suffisamment flexible pour mes besoins :)

0
Luke

En plus du message de MRMage:

J'ai dû définir cette variable pour résoudre le problème suivant: certaines variables $_POST (avec un grand tableau> 1000 éléments) ont disparu:

suhosin.request.max_vars = 2500

"request", pas "post" était la solution ...

0

Mon problème était que j'utilisais la balise HTML <base> pour modifier l'URL de base de mon site de test. Une fois que j'ai supprimé cette balise de l'en-tête, les données $_POST sont revenues.

0
Ben

C’est un peu comme ce que @icesar a dit .

Mais j'essayais de publier des éléments sur mon API, situés dans site/api/index.php, en ne postant que vers site/api car ils sont transmis à index.php par lui-même. Ceci, cependant, a apparemment pour effet de gâcher quelque chose, car mon $_POST s'est vidé à la volée. Poster simplement sur site/api/index.php directement à la place a résolu le problème.

0
Victor Häggqvist

Assurez-vous que vous utilisez name = " votre_nom_variable " dans la balise input.

J'utilise par erreur id = " votre_nom_variable ".

J'ai passé beaucoup de temps à attraper le virus.

0
Frank Hsieh

Je sais que c'est vieux, mais je voulais partager ma solution.

Dans mon cas, le problème se trouvait dans mon .htaccess, car j’avais ajouté des variables pour augmenter la limite maximale de chargement de mon PHP. Mon code était comme ça:

php_value post_max_size 50MB
php_value upload_max_filesize 50MB

Plus tard, je remarque que les valeurs doivent être xxM et non xxMB et quand je l’ai changé:

php_value post_max_size 50M
php_value upload_max_filesize 50M

maintenant, mon $ _POST a renvoyé les données comme d'habitude avant . J'espère que cela aidera quelqu'un dans le futur.

0
Walid Ajaj

Dans mon cas (page php sur le serveur OVH mutualisé) enctype="text/plain" ne fonctionne pas ($_POST et le $_REQUEST correspondant est vide), les autres exemples ci-dessous fonctionnent . `

<form action="?" method="post">
<!-- in this case, my google chrome 45.0.2454.101 uses -->
<!--     Content-Type:application/x-www-form-urlencoded -->
    <input name="say" value="Hi">
    <button>Send my greetings</button>
</form>

<form action="?" method="post" enctype="application/x-www-form-urlencoded">
    <input name="say" value="Hi">
    <button>Send my application/x-www-form-urlencoded greetings</button>
</form>

<form action="?" method="post"  enctype="multipart/form-data">
    <input name="say" value="Hi">
    <button>Send my multipart/form-data greetings</button>
</form>

<form action="?" method="post" enctype="text/plain"><!-- not working -->
    <input name="say" value="Hi">
    <button>Send my text/plain greetings</button>
</form>

`

Plus ici: method = "post" enctype = "text/plain" ne sont pas compatibles?

0
PaulH

Dans mon cas, lors de la publication de HTTP à HTTPS, le $ _POST est vide. Le problème était que le formulaire avait une action comme celle-ci //example.com Lorsque j'ai corrigé l'URL à https://example.com , le problème a disparu.

Ce n’est peut-être pas la solution la plus pratique, mais j’ai bien compris que si je définissais l’attribut form action sur le domaine racine, on pouvait accéder à index.php et obtenir les variables publiées. Cependant, si je définis une URL réécrite en tant qu'action, cela ne fonctionne pas.

0
Rápli András