Задний план:
Следующий код AJAX работает успешно (ReactJS + JQuery frontend, PHP backend).
const data = {request_type:"load_data", start:1, end:50};
$.ajax({
type: "POST",
url: "http://localhost/site/server.php",
data: data,
dataType: "json",
success: (JSobject) => {
this.setState({arr: JSobject.arr});
}
});
В Chrome Dev Tools заголовки server.php отображаются как «Form Data», например:
На бэкэнде PHP-сервера есть такая строка кода:
$request_type = $_POST["request_type"];
Пытаясь научиться делать Fetch (до сих пор я избегал этого в основном потому, что у меня был шаблон AJAX, который работал хорошо), я экспериментировал с попытками создать заменяющую замену для приведенного выше кода.
Я пробовал это:
const data = {request_type:"load_data", start:1, end:50};
fetch("http://localhost/site/server.php", {
method: "POST",
body: data
})
.then((JSobject) => {
this.setState({arr: JSobject.arr});
});
Но я получаю эту ошибку PHP:
Notice: Undefined index: request_type in .....server.php
А в Chrome Dev Tools заголовки server.php выглядят так:
Итак, я попытался изменить данные на JSON.stringify (data) вот так:
const data = {request_type:"load_data", start:1, end:50};
fetch("http://localhost/site/server.php", {
method: "POST",
body: JSON.stringify(data)
})
.then((JSobject) => {
this.setState({arr: JSobject.arr});
});
Но я все еще получаю ту же ошибку PHP:
Notice: Undefined index: request_type in .....server.php
А в Chrome Dev Tools заголовки server.php выглядят так:
Из-за общего разочарования (хотя это бессмысленно, потому что я все еще буду использовать JQuery), я подумал, что буду использовать JQuery $.param(), и это определенно сработает.
Итак, я попробовал это:
const data = $.param({request_type:"load_data", start:1, end:50});
fetch("http://localhost/site/server.php", {
method: "POST",
body: data
})
.then((JSobject) => {
this.setState({arr: JSobject.arr});
});
По-прежнему получаю ту же ошибку PHP
Notice: Undefined index: request_type in .....server.php
А в Chrome Dev Tools заголовки server.php выглядят так:
Мой вопрос: как мне изменить приведенный выше код Fetch, чтобы он стал заменой для кода AJAX вверху.
Я понимаю, что использование горизонтальных линий для некоторых может быть неприятным. Вы можете позволить себе поверить, что это действительно помогает многим из нас, обычных людей, следить за тем, что происходит в вопросе.





Отвечая на свой вопрос для других, кто может столкнуться с этой проблемой в будущем (а также для моей справки). Разобрался с ответом через эта ссылка и эта ссылка. Следующий код работал:
fetch("http://localhost/site/server.php", {
method: "POST",
body: JSON.stringify(data)
}).then(response => {
return response.json();
}).then((JSobject) => {
this.setState({arr: JSobject.arr});
});
Мне пришлось изменить код PHP на сервере. Первоначальный код "привратника" был:
$_POST = array_map("trim", $_POST);
$request_type = $_POST["request_type"];
Это нужно было закомментировать:
$_POST = array_map("trim", $_POST); //this had to be commented out
И вместо этого пришлось добавить:
$content = trim(file_get_contents("php://input"));
$_POST = json_decode($content, true);
А в Chrome Dev Tools заголовки server.php отображаются как «Request Payload»:
Я также видел несколько предложений по добавлению ключа "headers", например:
fetch("http://localhost/site/server.php", {
method: "POST",
headers: {"Content-Type": "application/x-www-form-urlencoded",},
body: JSON.stringify(data)
}).then(response => {
return response.json();
}).then((JSobject) => {
this.setState({arr: JSobject.arr});
});
Это тоже сработало, но в Chrome Dev Tools заголовки server.php отображаются как "Form Data":
Другой способ сделать это - обернуть объект (который должен быть отправлен) в JQuery $.param() (меня это интересовало, потому что я часто использую $.param() для добавления ключей и значений в form.serialize() на стороне клиента перед отправкой на PHP на сервере)
const data = $.param({request_type:"load_data", start:1, end:50});
fetch("http://localhost/site/server.php", {
method: "POST",
headers: {"Content-Type": "application/x-www-form-urlencoded",},
body: data
}).then(response => {
return response.json();
}).then((JSobject) => {
this.setState({arr: JSobject.arr});
});
Преимущество такого подхода состояло в том, что не требовалось никаких изменений в коде на стороне сервера.
В Chrome Dev Tools заголовки server.php отображаются как «Form Data»:
Без использования JQuery:
Re: предыдущий метод (с использованием $.param()), можно сделать это полностью без JQuery, но тогда потребуется некоторая функция для связывания пар ключ-значение объекта javascript при правильном кодировании специальных символов как x-www-form-urlencoded (эта ссылка объясняет, как это сделать).
Например, вместо этого:
const data = $.param({request_type:"load_data", start:1, end:50});
...
body: data
Можно было бы сделать это:
const data = {request_type:"load_data", start:1, end:50};
...
...
body: "request_type=load_data&start=1&end=50"