Тема: Content-Type: application, multipart

Я виріши не користуватися application/x-www-form-urlencoded коли відправляю на сервер запити за допомогою технології ajax, я хочу використовувати JSON.
Я зробив простий проект що легко було розбиратися. (калькулятор на дію додавання)

Як мені так відправити запит, щоб не використовувати application/x-www-form-urlencoded ?
Коли я пишу

xhttp.setRequestHeader("Content-type", "application/json; charset=utf-8");

масив POST пустий. Як отримати дані з змінних num1 і num2 ?

Це робоча версія, але з application/x-www-form-urlencoded
HTML + JS + AJAX

<html>
    <head>
        <title>Non</title>
    </head>
<body>
    <table>
        <tr>
            <td colspan="2"><input type="number" id="num1"></td>
        </tr>
        <tr>
            <td colspan="2"><input type="number" id="num2"></td>
        </tr>
        <tr>
            <td colspan="2">
                <input type="number" id="answer" style="background-color: white;" value="0" disabled>
            </td>
        </tr>
        <tr>
            <td colspan="2"><button type="button" onclick="loadCalc()">Send</button></td>
        </tr>
        <tr>
            <td><p>Condition:</p></td>
            <td><p id="condition">ready</p></td>          
        </tr>
    </table>
    
    <script>
        function loadCalc() 
        {
            var xhttp = new XMLHttpRequest();
            xhttp.onreadystatechange = function() 
            {
                if (this.readyState == 0) 
                {
                    document.getElementById('condition').innerHTML = 
                    'request not initialized';
                }
                else if (this.readyState == 1) 
                {
                    document.getElementById('condition').innerHTML = 
                    'server connection established';
                }
                else if (this.readyState == 2) 
                {
                    document.getElementById('condition').innerHTML = 
                    'request received';
                }
                else if (this.readyState == 3) 
                {
                    document.getElementById('condition').innerHTML = 
                    'processing request';
                }
                else if (this.readyState == 4 && this.status == 200) 
                {
                    document.getElementById('condition').innerHTML = 
                    'ready';
                    document.getElementById('answer').value = 
                    Number(this.responseText);
                }
            };
            var num1 = document.getElementById('num1').value;
            var num2 = document.getElementById('num2').value;
            var request = JSON.stringify({
                "num1": num1,
                "num2": num2
            });
            xhttp.open('POST', 'calculator.php', true);
            xhttp.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
            xhttp.send('request=' + request); 
        }
    </script>
</body>
</html>

PHP

<?php
header('Content-Type: application/json; charset=utf-8');
$jd = json_decode($_POST['request']);
echo $jd->{'num1'} + $jd->{'num2'};
?>

Ще в мене питання про бінарні файли, я читав що бінарні файли відправляються за допомогою MIME типу multipart/form-data, але коли я почитав як складно це все робиться, то в мене виникло питання: "чи це й досі використовується ?" Як відправлять на сервер бінарні файли ?
Можна використовувати наприклад JSON ( Якщо так то як ? ) ?

{ "filename": file.jpg }
Подякували: 221VOLT1

2 Востаннє редагувалося truesupport (22.01.2017 04:32:23)

Re: Content-Type: application, multipart

69 рядок

xhttp.send('request=' + request);

замініть на

xhttp.send(request);

ну і не забудьте поміняти 68 рядок і я думаю мало би запрацювати я не піднімав ніякого бекенду для тесту і PHP в мене немає тим більше.

На рахунок файлів я не знаю як найкраще, напевно так як ще робиться нативно через форму і <input type="file" /> я знаю що дехто бере читає картинку як текст ( напевно супер неправильне технічне визначення але супер зрозуміле для початківців) перетворює цей текст в формат base64 і відправляє. Щось по типу цього

function sendImageSomewhere() {

var image = grabImageFromSomewhere();
var convertedImage = convertStringToBase64(image);
var request = { imageToSend: convertedImage, fiename: 'lalka.jpg', other_data_that_you_need: 'lskdfjsdjfl' };
sendRequestToServer(request);

}

поняття не маю як реалізувати grabImageFromSomewhere() функцію, ще колись я використовував щось тааке але уже забув https://www.html5rocks.com/ru/tutorials/file/dndfiles/ Можливо по цьому посиланні знайдете щось корисне.

І ви походу неправильно читаєте дані на бекенді, треба якось так
https://backendcoder.com/how-to-get-jso … ata-in-php

Подякували: Betterthanyou, 221VOLT2

3

Re: Content-Type: application, multipart

truesupport Дякую, допомогли. Я справді не правильно на сервері приймав запит, з файлом теж вже розібрався.

truesupport написав:

PHP в мене немає тим більше.

Ну так прогрес не стоїть на місці, я вже давно перейшов на онлайн сервіси, досить зручно, ще й проекти завжди доступний на будь якій платформі. https://c9.io

4

Re: Content-Type: application, multipart

наступним кроком розвитку після ajax йде websockets
https://learn.javascript.ru/websockets
(як на php працювати з ними - без поняття, працюю з erlang/elixir)

Подякували: Betterthanyou1

5

Re: Content-Type: application, multipart

221VOLT написав:

наступним кроком розвитку після ajax йде websockets
https://learn.javascript.ru/websockets
(як на php працювати з ними - без поняття, працюю з erlang/elixir)

Дякую! Цього навіть не знав.

Подякували: 221VOLT1

6

Re: Content-Type: application, multipart

Прийшлося мені відмовитися все ж таки від application/json, тому що з ним складно (а можливо й не можливо) працювати у wordpress.

Зараз я відсилаю JSON так

var xhttp = new XMLHttpRequest;
...
xhttp.setRequestHeader('Content-type', 'application/x-www-form-urlencoded');
xhttp.send('action=showPosts&reqJSON=' + request);

А створюю JSON так

var request = JSON.stringify({
            'afterDate': { 'year': afterDate[0], 'month': afterDate[1], 'day': afterDate[2]},
            'beforeDate': { 'year': beforeDate[0], 'month': beforeDate[1], 'day': beforeDate[2]},
            'categoryName': '<?=$atts['category']?>'
        });

В мене виникла проблема, я відправляю таке

{
"afterDate":{"year":"2017","month":"01","day":"23"},
"beforeDate":{"year":"2017","month":"01","day":"26"},
"categoryName":"myCategory"
}

а отримую таке

{
\"afterDate\":{\"year\":\"2017\",\"month\":\"01\",\"day\":\"23\"},
\"beforeDate\":{\"year\":\"2017\",\"month\":\"01\",\"day\":\"26\"},
\"categoryName\":\"myCategory\"
}

тобто перед кожною лапкою вставляється слеш, чому так відбувається ? Як можна цього уникнути ?

(за допомогою заміни str_replace('\\', '', $_POST['reqJSON']) я вирішив цю проблему, але можливо можна налаштувати так відправлення і прийом щоб не потрібно було писати str_replace ?)

Подякували: 221VOLT1

7 Востаннє редагувалося 221VOLT (27.01.2017 07:23:21)

Re: Content-Type: application, multipart

тому що лапки екрануються?
https://developer.mozilla.org/uk/docs/W … /stringify

JSON.stringify({ x: 5 });
// '{"x":5}'
JSON.stringify({ x: 5, y: 'gg' });
//"{"x":5,"y":"gg"}"
Подякували: Betterthanyou1

8

Re: Content-Type: application, multipart

221VOLT написав:

тому що лапки екрануються?
https://developer.mozilla.org/uk/docs/W … /stringify

JSON.stringify({ x: 5 });
// '{"x":5}'
JSON.stringify({ x: 5, y: 'gg' });
//"{"x":5,"y":"gg"}"

Цілу ніч намагався виправити цю незрозумілу помилку, поки мені не прийшла ідея створити це все окремо від wordpress, як виявляється окремо все працює. Видно це wordpress псує запит, поки що обійдуся replaceом, а потім буду з'ясовувати далі причини.

Подякували: 221VOLT1