Мне было приказано использовать метод php://input
вместо того, чтобы $_POST
взаимодействовать с Ajax-запросами из JQuery. То, что я не понимаю, это преимущества использования этого по сравнению с глобальным методом $_POST
или $_GET
.
243
Ответы:
Причина в том, что
php://input
возвращает все необработанные данные после HTTP-заголовков запроса, независимо от типа контента.PHP суперглобальный
$_POST
, только предполагается, что обернуть данные, которые либоapplication/x-www-form-urlencoded
(стандартный тип контента для простых форм-постов) илиmultipart/form-data
(в основном используется для загрузки файлов)Это потому, что это единственные типы контента, которые должны поддерживаться пользовательскими агентами. . Таким образом, сервер и PHP традиционно не ожидают получения какого-либо другого типа контента (что не означает, что они не могли).
Итак, если вы просто поместите старый добрый HTML
form
, запрос будет выглядеть примерно так:Но если вы много работаете с Ajax, эта проба также включает в себя обмен более сложными данными с типами (string, int, bool) и структурами (массивами, объектами), поэтому в большинстве случаев JSON является лучшим выбором. Но запрос с JSON-полезной нагрузкой будет выглядеть примерно так:
Теперь контент будет
application/json
(или, по крайней мере, ни один из вышеупомянутых), поэтому PHP$_POST
-wrapper не знает, как с этим справиться (пока).Данные все еще там, вы просто не можете получить к ним доступ через обертку. Так что вам нужно получить его самостоятельно в необработанном формате
file_get_contents('php://input')
( если он неmultipart/form-data
закодирован ).Это также, как вы бы получили доступ к XML-данным или любому другому нестандартному типу контента.
источник
application/json
как действительный источник данных для$_POST
массива. И есть даже опубликованные запросы специально для этой поддержки.php://input
может дать вам необработанные байты данных. Это полезно, если данные POST представляют собой структуру в кодировке JSON, что часто имеет место для запроса AJAX POST.Вот функция для этого:
$_POST
Массив является более полезным , когда вы обработки данных ключ-значение из формы, представленной традиционным POST. Это работает только в том случае, если POST-данные обычно имеют распознанный форматapplication/x-www-form-urlencoded
(подробнее см. Http://www.w3.org/TR/html4/interact/forms.html#h-17.13.4 ).источник
true
в качестве второго параметраjson_decode
, он вернет ассоциативный массив.Если данные поста искажены, $ _POST ничего не будет содержать. Тем не менее, php: // input будет иметь некорректную строку.
Например, есть некоторые ajax-приложения, которые не формируют правильную последовательность ключ-значение поста для загрузки файла, а просто выгружают весь файл как данные поста, без имен переменных или чего-либо еще. $ _POST будет пустым, $ _FILES также пустым, а вход php: // будет содержать точный файл, записанный в виде строки.
источник
Во-первых, основная истина о PHP.
PHP не был разработан для того, чтобы явно предоставлять вам чистый интерфейс типа REST (GET, POST, PUT, PATCH, DELETE) для обработки HTTP-запросов .
Однако
$_POST
,$_GET
и$_FILES
Суперглобальные , а функцияfilter_input_array()
очень полезны для нужд среднего человека / непрофессионала.Скрытое преимущество номер один
$_POST
(и$_GET
) заключается в том, что ваши входные данные автоматически кодируются PHP . Вы даже не задумываетесь об этом, особенно для параметров строки запроса в стандартном запросе GET.Тем не менее, тогда вы узнаете больше ...
При этом, когда вы продвигаетесь в своих знаниях по программированию и хотите использовать
XmlHttpRequest
объект JavaScript (для некоторых jQuery), вы видите ограничение этой схемы.$_POST
ограничивает вас использованием двух типов медиа вContent-Type
заголовке HTTP :application/x-www-form-urlencoded
, иmultipart/form-data
Таким образом, если вы хотите отправить значения данных в PHP на сервере и показать их в
$_POST
суперглобальном коде , то вы должны urlencode их на стороне клиента и отправить эти данные в виде пар ключ / значение - неудобный шаг для новичков (особенно при попытке выяснить, требуются ли разные части URL-адреса для разных форм кодирования: обычный, необработанный и т. д.).Для всех пользователей jQuery этот
$.ajax()
метод преобразует ваш JSON в пары ключ / значение, закодированные в URL, перед их передачей на сервер. Вы можете изменить это поведение, установивprocessData: false
. Просто прочитайте документацию $ .ajax () и не забудьте отправить правильный тип носителя в заголовке Content-Type.Кодировка URL? Какого черта!!!???
Как правило, если вы выполняете обычные синхронные (когда перерисовывается вся страница) HTTP-запросы с HTML-формой, пользовательский агент (веб-браузер) будет кодировать данные вашей формы для вас. Если вы хотите выполнять асинхронные HTTP-запросы с использованием
XmlHttpRequest
объекта, вы должны сформировать строку с кодировкой urlen и отправить ее, если хотите, чтобы эти данные отображались в$_POST
суперглобальном элементе .Как вы общаетесь с JavaScript? :-)
Преобразование из массива или объекта JavaScript в строку с кодировкой urlen беспокоит многих разработчиков (даже с такими новыми API, как Form Data ). Они бы предпочли просто отправить JSON, и для клиентского кода это было бы более эффективно .
Помните (подмигивание, подмигивание), обычный веб-разработчик не учится использовать
XmlHttpRequest
объект напрямую, глобальные функции, строковые функции, функции массива и регулярные выражения, такие как вы и я ;-). Урленкодинг для них - это кошмар. ;-)PHP, что дает?
Отсутствие в PHP интуитивной обработки XML и JSON отвлекает многих людей. Вы могли бы подумать, что это будет частью PHP сейчас (вздох).
Так много типов медиа (MIME-типы в прошлом)
XML, JSON и YAML имеют типы мультимедиа, которые можно поместить в
Content-Type
заголовок HTTP .Посмотрите, сколько медиа-типов (ранее MIME-типов) определены IANA.
Посмотрите, сколько там HTTP-заголовков .
php: // вход или перебор
Использование
php://input
потока позволяет вам обойти уровень абстракции для сидения / удерживания ребенка, который PHP навязал миру. :-) С большой властью приходит большая ответственность!Теперь, прежде чем иметь дело со значениями потоковых данных
php://input
, вы должны / должны сделать несколько вещей.Как насчет кодировки символов?
Ах, ха! Да, вы можете захотеть, чтобы поток данных, отправляемый в ваше приложение, был в кодировке UTF-8, но как узнать, так ли это?
Две критические проблемы.
php://input
.Собираетесь ли вы пытаться обрабатывать потоковые данные, не зная, сколько их сначала? Это ужасная идея . Вы не можете полагаться исключительно на
Content-Length
заголовок HTTP для указания размера входного потока, поскольку он может быть подделан.Вам понадобится:
Собираетесь ли вы попытаться преобразовать потоковые данные в UTF-8, не зная текущей кодировки потока? Как? Фильтр потока iconv ( пример фильтра потока iconv ), кажется, хочет начальную и конечную кодировку, как это.
Таким образом, если вы добросовестны, вам понадобится:
( Обновление :
'convert.iconv.UTF-8/UTF-8'
все будет принудительно переведено в UTF-8, но вам все равно придется учитывать символы, которые библиотека iconv может не знать, как переводить. Другими словами, вам нужно как-то определить, какое действие предпринять, когда символ не может быть переведен : 1) Вставьте фиктивный символ, 2) Fail / throw и исключения).Вы не можете полагаться исключительно на
Content-Encoding
заголовок HTTP , так как это может указывать на что-то вроде сжатия, как показано ниже. Это не то, что вы хотите принять решение в отношении iconv.Поэтому общие шаги могут быть ...
Часть I: HTTP-запрос, связанный
Часть II: Потоковые данные, связанные
Часть III: Тип данных, связанных
(Помните, что данные все еще могут быть строкой в кодировке URL, которую затем необходимо проанализировать и декодировать URL).
Часть IV: Значение данных, связанных
Фильтровать входные данные.
Проверьте входные данные.
Теперь ты видишь?
$_POST
Суперглобальный, наряду с php.ini настройки для ограничения на вход, проще для обывателя. Однако работа с кодировкой символов намного более интуитивна и эффективна при использовании потоков, потому что нет необходимости циклически перебирать суперглобальные переменные (или вообще массивы), чтобы проверять входные значения для правильного кодирования.источник
Поэтому я написал функцию, которая будет получать данные POST из потока ввода php: // .
Таким образом, проблема здесь заключалась в том, чтобы переключиться на метод запроса PUT, DELETE OR PATCH и по-прежнему получать данные почты, отправленные с этим запросом.
Я делюсь этим, может быть, для кого-то с похожим вызовом. Приведенная ниже функция - это то, что я придумал, и она работает. Я надеюсь, что это помогает!
источник
Простой пример того, как его использовать
источник