php $ _POST масив порожній після надсилання форми


99

У мене є власна CMS, яку я створив, яка прекрасно працює на моїй розроблювальній коробці (Ubuntu / PHP5 + / MySQL5 +).

Я просто перемістив його до робочого вікна для мого клієнта, і тепер усі подані форми відображаються як порожні масиви $ _POST.

Я знайшов хитрість перевірити, чи дані фактично передаються за допомогою, file_get_contents('php://input');і там дані відображаються нормально - $_POST/ $_REQUESTмасиви завжди порожні.

Я також перевірив правильність заголовків типу вмісту через firebug ( application/x-www-form-urlencoded; charset=utf-8).

Ця проблема трапляється незалежно від того, подається форма через AJAX чи звичайна форма.

Будь-яка допомога дуже вдячна!

php  arrays  forms  post 

Перевірте post_max_size: значення має бути встановлено як 8М, а не 8МБ. В останньому випадку ви не побачите жодних помилок, але розмір $ _POST встановиться на 0
Сергій Карпов,

Відповіді:


186

Я знаю, що це питання стосувалося POST через форму, але прийшов сюди, шукаючи відповіді на подібну проблему, коли POSTing із контентом типу JSON. Знайшов відповідь і хотів поділитися нею, оскільки це коштувало мені багато часу.

Під час використання типу вмісту JSON масив $ _POST не заповнюватиметься (я вважаю лише багатоскладові форми)

Ось що вдалося виправити.

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

сподіваюся, що це комусь допоможе!


Цей спосіб має сенс - він виправив мій контролер пакетного оновлення :)
Martin Zeitler

2
Ще одна альтернатива - змінити Content-Typeзаголовок application/x-www-form-urlencodedі потім серіалізувати свої дані $.param(dataObject). Це має допомогти.
ŁukaszBachman

1
@ ŁukaszBachman Як це зробити, якщо DataObject що - щось на зразок ........ title=something&body=anything. Я хочу отримати назву титулу та тіла. $ dataobject ["title"] повертається порожнім. У моєму випадку $ _POST порожній. І єдиний спосіб отримати його за допомогою file_get_contents ("php: // input") ... за винятком того, що він не закодований json.
Хуршид Алам

Це дуже корисно. Дивна річ у тому, що у мене немає проблем з відправленням Json на мою розроблювальну машину, але робити на виробничій.
Simon H


86

Ось ще одна можлива причина - моя форма надсилалась на domain.com без WWW. і я створив автоматичне переспрямування, щоб додати "WWW". Масив $ _POST видалявся в процесі. Тож, щоб виправити це, все, що мені потрібно було, - подати на www.domain.com


24
Блін, переписування URL-адреси в моєму htaccessбуло причиною того, що POSTs не працювали. Я автоматично додавав скісну риску до всіх URL-адрес, але в коді як ACTION я використовував URL-адресу без скісної риски. Ваша відповідь допомогла, оскільки я ніколи не думав перевірити .htaccess. +1
бінар

У мене була переадресація домену (з маскуванням) за допомогою Godaddy, і це, здається, є джерелом проблеми. Дякую!
Кріс Принс

1
У мене також була подібна проблема, вона виходила з мого .htaccessфайлу. Це знімали .phpрозширення з URL-адреси, і моя форма була POSTспрямована на URL-адресу з розширенням.
Емануель Вінтілья

25

У мене була подібна проблема. Виявилося простим виправленням. У тому вигляді, який я мав

<form action = "directory" method = "post">

де каталог був назвою ... каталогу. Мій масив POST був порожнім. Коли я переглянув URL-адресу в своєму браузері, він відображався з нахилом вперед в кінці.

Додавання косої риски в кінці моєї дії зробило трюк -

<form action = "каталог /" метод = "повідомлення">

Мій масив $ _POST знову був повний!


1
Це не повинно бути виправленням, наприклад, на CakePHP, у якої є хороша система маршрутизації, у цьому не вдалося (я не маю на увазі Cake не вдалося), можливо, підхід до цієї проблеми не є рамками або файлами .php, але деякі налаштування апаші, я хотів би проаналізувати цю проблему. Це досить цікаво.
Джеймс

На аналогічній ноті у мене був той самий випуск, що і в OP, але лише якщо <form>тег не мав nameатрибута, і лише в IE.
jkt123

13

Переконайтеся, що в php.ini:

  • track_vars (доступно лише для дуже старих версій PHP) встановлено на On
  • variables_order містить лист P
  • post_max_size встановлено на розумне значення (наприклад, 8 МБ)
  • (якщо використовується сухозин-пластир) suhosin.post.max_varsі suhosin.request.max_varsдосить великі.

Я думаю, що друга моя пропозиція вирішить вашу проблему.


1
Дякуємо MrMage, вдячні за вашу розуміння та перевіримо ці налаштування ini та повідомимо, чи це зробило трюк. Дякую!

1
Налаштування "post_max_size" - це мій шоустоппер. Під час надсилання форми я завантажував великий файл, і цей параметр містив менше значення. Тому я отримую порожній масив публікацій, коли я надсилаю форму.
shasi kanth

9

Я виявив, що при публікації з HTTP на HTTPS $_POSTприходить порожній. Це сталося під час тестування форми, але у мене пішло час, поки я цього не усвідомив.


5

Я зіткнувся з подібною, але дещо іншою проблемою, і на її вивчення пішло 2 дні.

  • У моєму випадку також масив POST був порожнім.

  • Потім перевіряється за допомогою file_get_contents ('php: // input'); і це також було порожнім.

Пізніше я виявив, що браузер не запитував підтвердження повторного надсилання даних форми після того, як якщо я оновлю сторінку, завантажену після подання POST. Це була безпосередньо освіжаюча сторінка. Але коли я змінив URL-адресу форми на іншу, вона передала POST належним чином і попросила повторно надіслати дані при спробі оновити сторінку.

Потім я перевірив, що не так із фактичною URL-адресою. З URL-адресою не було помилок, однак вона вказувала на папку без index.php в URL-адресі, і я перевіряв POST на index.php.

Тут я сумнівався, що перенаправлення з / на /index.php призводить до втрати даних POST і перевіряється URL із додаванням index.php до URL.

Це спрацювало.

Опублікував його тут, щоб хтось знайшов це корисним.


1
У мене була така ж проблема, без '/' наприкінці URL-адреси, у $ _REQUEST нічого не існує, але з '/' або '/index.php', усі опубліковані дані існують у $ _REQUEST. Це можуть бути мої налаштування nginx чи щось інше!
MohaMad

4

На даний момент у вас немає елегантного рішення, але я хотів би поділитися своїми висновками для подальшого використання іншими, хто стикається з цією проблемою. Джерелом проблеми було 2 переосмислені значення php у файлі .htaccess. Я просто додав ці 2 значення, щоб збільшити обмеження розміру файлів для завантаження файлів із 8 МБ за замовчуванням на щось більше - я помітив, що просто наявність цих 2 значень у файлі htaccess взагалі, більших чи менших, ніж за замовчуванням, спричинило проблему .

php_value post_max_size xxMB
php_value upload_max_filesize xxMB

Я додав додаткові змінні, щоб, сподіваємось, підняти межі для всіх suhosin.post.xxx/suhosin.upload.xxx змін, але вони, на жаль, ніяк не вплинули на цю проблему.

Підсумовуючи це, я не можу реально пояснити "чому" тут, але визначив першопричину. Я відчуваю, що це, зрештою, проблема suhosin / htaccess, але, на жаль, та, яку я не зміг вирішити, крім як видалити 2 перевизначені значення php вище.

Сподіваюсь, це допоможе комусь у майбутньому, оскільки я вбив кілька годин, розбираючись у цьому. Дякую всім, хто знайшов час, щоб допомогти мені в цьому (MrMage, Andrew)


Це питання може бути варто задати на Serverfault, особливо якщо проблема полягає в налаштуваннях сервера / htaccess.
Девід каже повернути Моніку

5
Якщо я не помиляюся, розмір повинен бути вказаний як "xxM", а не "xxMB", тож мені цікаво, чи може це щось із цим робити ...
JC Inacio

4

Я міг би вирішити проблему, використовуючи enctype = "application / x-www-form-urlencoded", оскільки за замовчуванням є "text / plain". Якщо ви зареєструєтесь у $ DATA, сеператор - це пробіл для "текст / звичайний" та спеціальний символ для "коду урленкоду".

Ласкаво з повагою до Френка


4

Вимкнення цього enable_post_data_readingпараметра призведе до цього. Відповідно до документації:

enable_post_data_reading

Якщо вимкнути цю опцію, $ _POST і $ _FILES не будуть заповнені. Єдиним способом читання публікацій буде через прошивку вхідного потоку php: //. Це може бути корисно для запитів проксі-серверів або для обробки даних POST у ефективній пам'яті.


4

Якщо ви публікуєте файл index.php у каталозі, наприклад /api/index.php, переконайтеся, що у своїй формі ви вказали повний каталог для файлу, наприклад

Це

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

АБО

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

працює.

Але це не вдається

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

Я насправді маю прямо протилежне. Я виявив, що /my_uriце спрацює, але ні /my_uri/.
Посилання14,

мала таку ж проблему. здається, apache або nginx додають переспрямування з / api на / api /
Джон Сміт,

4
<form action="test.php" method="post">
                        ^^^^^^^^^^^^^

Гаразд, це було дурним, і я буду засмучувати себе публічно, але я збив невеликий тестовий скрипт на щось у PHP, і коли мій $_POSTмасив був порожнім, StackOverflow - це перше місце, яке я подивився, і я не знайшов потрібної відповіді .

Я лише писав

<form action="test.php">

і забув вказати метод як такий POST!

Я впевнений, що хтось буде нюхати, але якщо це допоможе комусь, хто робить те саме, я не заперечую! Всі ми робимо це час від часу!


Не можу повірити, що я також забув! Я просто пробую новий сервер, і відчув, що це було щось через конфігурацію ... все одно, дякую за нагадування!
Самуель Айала Феррейра

4

У моєму випадку, коли ви публікуєте повідомлення з HTTP на HTTPS, $ _POST залишається порожнім. Проблема полягала в тому, що форма мала таку дію, як це //example.com. Коли я зафіксував URL-адресу на https://example.com , проблема зникла.


1
Я думаю, це щось пов’язане з тим, як налаштовано сервер. У мене виникають ті самі проблеми з використанням GoDaddy як хоста. Це рішення не вирішило проблему.
acarlstein

Це рішення вирішило моє питання. У мене був гарний головний голова.
gokaysatir

3

тут же питання!

я намагався підключитися до мого локального коду сервера через поштовий запит у листоноші, і ця проблема витрачала багато часу!

для всіх, хто використовує локальний проект (наприклад, листоноша): використовуйте свою IPv4-адресу (введіть ipconfig в cmd) замість ключового слова "localhost". у моєму випадку:

до:

localhost/app/login

після:

192.168.1.101/app/login

Листоноша видав мені кілька питань зі скребленими значеннями json, які мають лапки або пробіли. Він очікує певного формату.
Том Андерсон

2

ДОВІДКА: http://www.openjs.com/articles/ajax_xmlhttp_using_post.php

Метод POST

Ми збираємось внести деякі зміни, щоб метод POST буде використаний при надсиланні запиту ...

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);

Деякі заголовки http мають бути встановлені разом із будь-яким запитом POST. Тож ми встановили їх у ці рядки ...

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);
  }
}

Ми встановлюємо обробник для події зміни стану готовності. Це той самий обробник, який ми використовували для методу GET. Тут ви можете скористатись http.responseText - вставити в div, використовуючи innerHTML (AHAH), eval (JSON) або будь-що інше.

http.send(params);

Нарешті, ми надсилаємо параметри із запитом. Дана URL-адреса завантажується лише після виклику цього рядка. У методі GET параметром буде нульове значення. Але в методі POST дані, що надсилаються, будуть надсилатися як аргумент функції send. Змінна params була оголошена у другому рядку як lorem=ipsum&name=binny- тому ми надсилаємо два параметри - 'lorem' та 'name' зі значеннями 'ipsum' та 'binny' відповідно.


1

У моєму випадку це було тому, що я використовував jQuery, щоб відключити всі входи на сторінці безпосередньо перед тим, як використовувати jQuery для подання форми. Тож я змінив свій "вимкнути кожен вхід, навіть" приховані "типи":

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

щоб "вимкнути лише введення" кнопки ":

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

Це було так, що користувач не міг випадково натиснути кнопку 'go' двічі та втрутити наш БД! Здається, що якщо ви введете атрибут 'disabled' на тип "прихованого" типу, їх значення не будуть пересилатися, якщо форма подана!


1

Для мене .htaccess переспрямовувався, коли mod_rewrite не був встановлений. Встановіть mod_rewite і все в порядку.

Конкретно:

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

виконував.


1

Я просто витратив години на вирішення подібної проблеми. Проблема в моєму випадку полягала в тому, що

max_input_vars = "1000"

за замовчуванням у php.ini. У мене була справді величезна форма без завантажень. php.ini встановлений для upload_max_filesize = "100М" та post_max_size = "108М", і це, безумовно, не було проблемою в моєму випадку. Поведінка PHP однакова для max_input_vars, коли вона перевищує 1000 змінних у формі. Він повертає та порожній масив _POST. Мені б хотілося, щоб я міг знайти це одну годину та години тому.


1

Я знаю, що це старе, але хотів поділитися своїм рішенням.

У моєму випадку проблема була в моєму .htaccess, оскільки я додав змінні, щоб підвищити максимальний ліміт завантаження PHP. Мій код був таким:

php_value post_max_size 50MB
php_value upload_max_filesize 50MB

Пізніше я помічаю, що значення повинні подобатися xxM, а не xxMB, і коли я змінив його на:

php_value post_max_size 50M
php_value upload_max_filesize 50M

тепер мій $ _POST повертав дані як раніше. Сподіваюся, це допоможе комусь у майбутньому.


0

На додаток до повідомлення MRMage:

Мені довелося встановити цю змінну, щоб вирішити проблему, що деякі $_POSTзмінні (з великим масивом> 1000 елементів) зникли:

suhosin.request.max_vars = 2500

" request", а не " post" було рішенням ...


0

Мабуть, не найзручніше рішення, але я зрозумів, що якщо я встановити actionатрибут форми для кореневого домену, то до нього можна отримати доступ до index.php і отримає розміщені змінні. Однак якщо я встановив переписану URL-адресу як дію, вона не працює.


0

Це схоже на те, що сказав @icesar .

Але я намагався розмістити речі на своєму api, розташованому в site/api/index.php, лише розміщуючи повідомлення, site/apiоскільки він передається index.phpсам по собі. Це, однак, очевидно, змушує щось заплутатися, оскільки моє $_POSTспорожніло з льоту. Просто надсилаючи повідомлення site/api/index.phpбезпосередньо, а не вирішуючи це.


0

Моя проблема полягала в тому, що я використовував <base>тег HTML для зміни базової URL-адреси мого тестового сайту. Щойно я видалив цей тег із заголовка, $_POSTдані повернулися.


0

У моєму випадку (php-сторінка на сервері OVH взаємного переходу) enctype="text/plain"не працює ( $_POSTа відповідна $_REQUESTпорожня), інші приклади нижче працюють. `

<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>

`

Більше тут: method = "post" enctype = "text / plain" не сумісні?


0

Я отримував таку помилку від 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"]

Після того, як я вилучив конфігурацію безпеки мода для тестування, все працювало, як очікувалося. Тепер мені просто потрібно змінити свої правила, щоб залишатися в безпеці, але досить гнучким для своїх потреб :)


0

Обов’язково використовуйте name = " your_variable_name " у тезі вводу.

Я помилково використовую id = " your_variable_name ".

Я витратив багато часу, щоб зловити клопа.


0

Переконайтеся, що визначено nameвластивість кожного поля.

Це створить порожній POST на PHP

<input type="text" id="Phone">

Але це спрацює

<input type="text" name="Phone" id="Phone">

Я думаю, це щось пов’язане з тим, як налаштовано сервер. У мене виникають ті самі проблеми з використанням GoDaddy як хоста. Це рішення не вирішило проблему.
acarlstein

-1

Гаразд, я подумав, що я повинен поставити свою справу тут .... Я отримував масив публікацій порожнім у конкретних випадках .. Форма працює добре, але іноді користувачі скаржаться, що натискають кнопку подання, і нічого не відбувається .... Після деякого копання я виявив, що моя хостинг-компанія має модуль захисту, який перевіряє введення користувачів та очищує весь масив повідомлень (не тільки шкідливі дані), якщо він виявляє це. У моєму прикладі вчитель математики намагався ввести рівняння: dy + dx + 0 = 0; і дані були повністю стерті.

Щоб це виправити, я просто раджу йому зараз ввести дані в текстовій області як dy + dx + 0 = нуль, і тепер це працює .... Це може заощадити комусь час ..


5
Попросити користувачів дозволити помилковий код не можна.
freeworlder

Це насправді не несправний код, але ви можете розглянути нового провайдера хостингу. Або опублікуйте введення в іншій формі, наприклад, кодування URL-адреси HTML.
Том Андерсон
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.