Приём и обработка POST-данных в PHP скрипте
Обработка POST запросов в PHP
Основной и наиболее эффективный способ обработки POST запросов в PHP заключается в использовании суперглобального массива $_POST. Этот массив автоматически заполняется данными, отправленными методом POST с типом содержимого application/x-www-form-urlencoded или multipart/form-data. Перед использованием данных необходимо проверить, что запрос действительно был отправлен методом POST, и выполнить базовую валидацию и фильтрацию.
<?php
if ($_SERVER['REQUEST_METHOD'] === 'POST') {
// Проверка существования поля
if (isset($_POST['name'])) {
$name = htmlspecialchars($_POST['name'], ENT_QUOTES, 'UTF-8');
// Дальнейшая обработка
}
}
?>Такой подход подходит для стандартных HTML форм, отправляющих данные в кодировке application/x-www-form-urlencoded. Важно помнить, что $_POST не содержит данные, отправленные с типом application/json или другими типами. Для них требуется другой метод.
Типичные ошибки: обращение к несуществующему ключу массива (вызывает предупреждение) и отсутствие проверки метода запроса (можно обработать GET данные как POST). Решение: использовать isset() или filter_input().
Как обработать POST запрос с JSON данными?
Если клиент отправляет данные в формате JSON (Content-Type: application/json), $_POST будет пустым. Необходимо прочитать сырое тело запроса через php://input и декодировать JSON.
<?php
$json = file_get_contents('php://input');
$data = json_decode($json, true);
if ($data !== null) {
// Обработка
}
?>Проблема: если данные приходят в неправильном формате, json_decode вернёт null. Рекомендуется проверять json_last_error(). Также php://input можно прочитать только один раз.
Как безопасно получить отдельное поле POST запроса?
Использование функции filter_input() с соответствующим фильтром позволяет сразу получить отфильтрованное значение и избежать ошибок.
<?php
$email = filter_input(INPUT_POST, 'email', FILTER_VALIDATE_EMAIL);
if ($email === false) {
// Невалидный email
}
?>Проблема: filter_input() не подходит для массивов (например, name[]). Для массивов нужно использовать filter_input_array() с правильной настройкой.
Как обработать множество однотипных полей (массив данных)?
Если форма содержит поля с именами вида tags[], PHP автоматически преобразует их в массив $_POST['tags']. Обработка массива должна включать проверку, что это действительно массив.
<?php
if (isset($_POST['tags']) && is_array($_POST['tags'])) {
foreach ($_POST['tags'] as $tag) {
$cleanTag = htmlspecialchars($tag, ENT_QUOTES, 'UTF-8');
// Обработка
}
}
?>Проблема: если ожидается массив, а приходит строка (например, если забыли добавить скобки в имени поля), возникнет ошибка. Нужна проверка is_array().
Как обработать файлы, отправленные через POST?
Загрузка файлов использует $_FILES при условии enctype="multipart/form-data". Важно проверять код ошибки загрузки.
<?php
if ($_SERVER['REQUEST_METHOD'] === 'POST' && isset($_FILES['file'])) {
if ($_FILES['file']['error'] === UPLOAD_ERR_OK) {
$tmpName = $_FILES['file']['tmp_name'];
// Перемещение файла
move_uploaded_file($tmpName, 'uploads/' . basename($_FILES['file']['name']));
}
}
?>Проблема: большие файлы могут превысить лимиты upload_max_filesize и post_max_size. Необходимо проверять размер и тип файла перед сохранением.
Расширенные примеры обработки POST запросов
Пример 1: Валидация всех полей формы с использованием фильтров
<?php
if ($_SERVER['REQUEST_METHOD'] === 'POST') {
$fields = [
'name' => FILTER_SANITIZE_STRING,
'email' => FILTER_VALIDATE_EMAIL,
'age' => ['filter' => FILTER_VALIDATE_INT, 'options' => ['min_range' => 0, 'max_range' => 120]]
];
$result = filter_input_array(INPUT_POST, $fields);
if ($result['name'] === false || $result['name'] === null) {
// Ошибка имени
}
if ($result['email'] === false) {
// Ошибка email
}
if ($result['age'] === false) {
// Ошибка возраста
}
}
?>Результат: массив $result содержит отфильтрованные значения или false/null при ошибке.
Пример 2: Обработка JSON запроса с проверкой корректности
<?php
$input = file_get_contents('php://input');
$data = json_decode($input, true);
if (json_last_error() !== JSON_ERROR_NONE) {
http_response_code(400);
echo json_encode(['error' => 'Invalid JSON']);
exit;
}
// Проверка обязательных ключей
$required = ['username', 'password'];
foreach ($required as $key) {
if (!isset($data[$key])) {
http_response_code(400);
echo json_encode(['error' => "Missing $key"]);
exit;
}
}
// Дальнейшая обработка
?>Результат: если JSON некорректен или отсутствуют поля, возвращается ошибка 400 с JSON.
Пример 3: Обработка массовой отправки данных (массив объектов)
<form method="post">
<input type="text" name="items[0][title]">
<input type="number" name="items[0][price]">
<input type="text" name="items[1][title]">
<input type="number" name="items[1][price]">
<button type="submit">Отправить</button>
</form>
<?php
if ($_SERVER['REQUEST_METHOD'] === 'POST' && isset($_POST['items'])) {
$items = $_POST['items'];
foreach ($items as $index => $item) {
if (!isset($item['title'], $item['price'])) {
// Пропустить или сообщить об ошибке
continue;
}
$title = htmlspecialchars($item['title'], ENT_QUOTES, 'UTF-8');
$price = floatval($item['price']);
// Сохранение
}
}
?>Результат: обрабатывается каждый элемент массива items.
Пример 4: Чтение сырых POST данных другого формата (например, XML)
<?php
$xmlString = file_get_contents('php://input');
$xml = simplexml_load_string($xmlString);
if ($xml === false) {
http_response_code(400);
exit('Invalid XML');
}
// Доступ к данным через $xml->element
?>Результат: объект SimpleXMLElement для работы с XML.
Пример 5: Проверка метода и отправка ответа в зависимости от типа запроса
<?php
header('Content-Type: application/json');
if ($_SERVER['REQUEST_METHOD'] !== 'POST') {
http_response_code(405);
echo json_encode(['error' => 'Method Not Allowed']);
exit;
}
$action = $_GET['action'] ?? 'default';
// Обработка в зависимости от параметра
?>Результат: если запрос не POST, возвращается ошибка 405.