Как выполняется HTTP-запрос POST в node.js?


946

Как я могу сделать исходящий HTTP-запрос POST с данными в node.js?


16
Как подсказано в ответе Джеда Уотсона , я настоятельно рекомендую использовать запрос, если вы не пишете низкоуровневый API.
namuol

4
Вы можете просто использовать, node-fetchкоторый является реализацией нативного fetchметода JavaScript, для выполнения HTTP-запросов.
Фес Враста

Этот пост описывает основные сценарии использования запроса. blog.modulus.io/node.js-tutorial-how-to-use-request-module
Шасват Рунгта

Ответы:


855

Вот пример использования node.js для выполнения запроса POST к API компилятора Google:

// We need this to build our post string
var querystring = require('querystring');
var http = require('http');
var fs = require('fs');

function PostCode(codestring) {
  // Build the post string from an object
  var post_data = querystring.stringify({
      'compilation_level' : 'ADVANCED_OPTIMIZATIONS',
      'output_format': 'json',
      'output_info': 'compiled_code',
        'warning_level' : 'QUIET',
        'js_code' : codestring
  });

  // An object of options to indicate where to post to
  var post_options = {
      host: 'closure-compiler.appspot.com',
      port: '80',
      path: '/compile',
      method: 'POST',
      headers: {
          'Content-Type': 'application/x-www-form-urlencoded',
          'Content-Length': Buffer.byteLength(post_data)
      }
  };

  // Set up the request
  var post_req = http.request(post_options, function(res) {
      res.setEncoding('utf8');
      res.on('data', function (chunk) {
          console.log('Response: ' + chunk);
      });
  });

  // post the data
  post_req.write(post_data);
  post_req.end();

}

// This is an async file read
fs.readFile('LinkedList.js', 'utf-8', function (err, data) {
  if (err) {
    // If this were just a small part of the application, you would
    // want to handle this differently, maybe throwing an exception
    // for the caller to handle. Since the file is absolutely essential
    // to the program's functionality, we're going to exit with a fatal
    // error instead.
    console.log("FATAL An error occurred trying to read in the file: " + err);
    process.exit(-2);
  }
  // Make sure there's data before we post it
  if(data) {
    PostCode(data);
  }
  else {
    console.log("No data to post");
    process.exit(-1);
  }
});

Я обновил код, чтобы показать, как публиковать данные из файла, вместо жестко закодированной строки. Для этого он использует команду async fs.readFile, публикуя реальный код после успешного чтения. Если есть ошибка, она выдается, и если нет данных, процесс завершается с отрицательным значением, указывающим на ошибку.


4
Правильно ли рассчитан заголовок длины содержимого? Предполагается, что это байты, верно?
Эрик

7
Обратите внимание, что querystring.stringify() не поддерживает вложенные объекты , поэтому вы можете использовать qs.stringify()вместо этого.
Johndodo

52
Content-Lengthэто байты и не обязательно длина строки (UTF-16 и т. д.). Использование Buffer.byteLength(data)всегда будет правильным.
Гринимпала

4
для отправки стандартных постданных объект querystring.stringifyдолжен быть вашим собственным объектом данных, а не мусором, который отображается в этом ответе (что может быть полезно для файловых объектов?). Я застрял на этом целую вечность ... stackoverflow.com/questions/9768192/… предоставил мое полное решение
RozzA

7
Понятно: если вы используете ssl-зашифрованный сайт, вам понадобится библиотека "https". Вы не можете просто изменить порт на 443.
Дейв Коллинз

1137

Это становится намного проще, если вы используете библиотеку запросов .

var request = require('request');

request.post(
    'http://www.yoursite.com/formpage',
    { json: { key: 'value' } },
    function (error, response, body) {
        if (!error && response.statusCode == 200) {
            console.log(body);
        }
    }
);

Помимо обеспечения хорошего синтаксиса, он упрощает запросы json, обрабатывает подписи oauth (для твиттера и т. Д.), Может создавать многоэлементные формы (например, для загрузки файлов) и потоковую передачу.

Для установки запроса используйте команду npm install request


153
{form: {key: 'value'}} следует заменить на {json: {key: 'value'}} (поскольку вопрос не относится к формам). Также нужно понимать, что «форма» и «json» - это ключевые слова библиотеки запросов, а не часть пользовательских данных (как бы ни был прост этот последний комментарий, мне потребовалось некоторое время, чтобы понять это ...)
blacelle

7
Я продолжаю возвращаться к этому вопросу и ответу. Это действительно должен быть «ответ» на вопрос.
Спенсер Кормос

6
Вы заслуживаете золотой значок чисто для этого ответа. Это намного полезнее, чем принятый ... и он уже существовал в 2012 году? Ничего себе
Золтан Шмидт

3
вам может понадобиться добавить зависимость, выполнив эту команду 'npm install --save request'
Shady

18
Эта библиотека устарела.
Evorlor

138

Вы можете использовать библиотеку запросов. https://www.npmjs.com/package/request

var request = require('request');

Чтобы опубликовать данные JSON:

var myJSONObject = { ... };
request({
    url: "http://josiahchoi.com/myjson",
    method: "POST",
    json: true,   // <--Very important!!!
    body: myJSONObject
}, function (error, response, body){
    console.log(response);
});

Чтобы опубликовать данные XML:

var myXMLText = '<xml>...........</xml>'
request({
    url: "http://josiahchoi.com/myjson",
    method: "POST",
    headers: {
        "content-type": "application/xml",  // <--Very important!!!
    },
    body: myXMLText
}, function (error, response, body){
    console.log(response);
});

После просмотра в их документации. он утверждает следующее: json - устанавливает тело, но в JSON-представление значения и добавляет Content-type: application / json header. Кроме того, анализирует тело ответа как JSON. Это означает, что когда json = true, он установит заголовок, json и body. В противном случае заголовок не задан и разбирается как текст. (Как в приведенном выше примере XML). Это делает API запросов удобным и упрощенным, но на первый взгляд довольно сложным для понимания.
Джосия Чой

Это технически в их документах, но ни один из примеров не показывает это - только данные формы. Это иголка в стоге сена, и, как таковая, это огромное упущение, поскольку это второй по частоте способ использования ajax в JS, и, безусловно, один из самых распространенных в Интернете.
Кайл Бейкер

Использование request.post IMO несколько лучше, чем указание POST в качестве метода. Вот некоторые примеры из GitHub для использования request.POST
drorw

12
Эта библиотека устарела.
Evorlor

44

Я использую Restler и Needle для производственных целей. Они оба гораздо более мощные, чем родной httprequest. Можно запросить с базовой аутентификацией, специальной записью заголовка или даже загружать / скачивать файлы.

Что касается операции post / get, они также намного проще в использовании, чем необработанные вызовы ajax с использованием httprequest.

needle.post('https://my.app.com/endpoint', {foo:'bar'}, 
    function(err, resp, body){
        console.log(body);
});

Я попробовал запрос, данные формы узла и superagent перед иглой. игла была единственной, которая работала правильно для меня, когда я пытался сделать многочастную загрузку файла формы.
Пол Янг

35

Просто и без зависимостей. Использует обещание, чтобы вы могли дождаться результата. Возвращает тело ответа и не проверяет код состояния ответа.

const https = require('https');

function httpsPost({body, ...options}) {
    return new Promise((resolve,reject) => {
        const req = https.request({
            method: 'POST',
            ...options,
        }, res => {
            const chunks = [];
            res.on('data', data => chunks.push(data))
            res.on('end', () => {
                let body = Buffer.concat(chunks);
                switch(res.headers['content-type']) {
                    case 'application/json':
                        body = JSON.parse(body);
                        break;
                }
                resolve(body)
            })
        })
        req.on('error',reject);
        if(body) {
            req.write(body);
        }
        req.end();
    })
}

Применение:

const res = await httpsPost({
    hostname: 'sentry.io',
    path: `/api/0/organizations/org/releases/${changesetId}/deploys/`,
    headers: {
        'Authorization': `Bearer ${process.env.SENTRY_AUTH_TOKEN}`,
        'Content-Type': 'application/json',
    },
    body: JSON.stringify({
        environment: isLive ? 'production' : 'demo',
    })
})

Для чего используется writeметод req,write()?
Ари

@Ari, который пишет тело запроса ... nodejs.org/api/…
mpen

21

Вы также можете использовать Requestify , действительно классный и простой HTTP-клиент, который я написал для nodeJS +, он поддерживает кэширование.

Просто сделайте следующее:

    var requestify = require('requestify');

    requestify.post('http://example.com', {
        hello: 'world'
    })
    .then(function(response) {
        // Get the response body (JSON parsed or jQuery object for XMLs)
        response.getBody();
    });

1
Это не работает для меня, смотрите проблему здесь: github.com/ranm8/requestify/issues/2
Эрл Сегал-Галеви

20

Обновление 2020:

Мне очень нравится phin - ультралегкий HTTP-клиент Node.js

Это может быть использовано двумя разными способами. Один с Обещаниями (Async / Await), а другой с традиционными стилями обратного вызова.

Установить через: npm i phin

Прямо из README с await:

const p = require('phin')

await p({
    url: 'https://ethanent.me',
    method: 'POST',
    data: {
        hey: 'hi'
    }
})


Непроизведенный (обратный вызов) стиль:

const p = require('phin').unpromisified

p('https://ethanent.me', (err, res) => {
    if (!err) console.log(res.body)
})

По состоянию на 2015 год в настоящее время существует множество различных библиотек, которые могут выполнить это с минимальным кодированием. Я очень предпочитаю элегантные легковесные библиотеки для HTTP-запросов, если вам абсолютно не нужен контроль над низкоуровневыми HTTP-компонентами.

Одна такая библиотека - Unirest

Чтобы установить его, используйте npm.
$ npm install unirest

И на Hello, World!примере, к которому все привыкли.

var unirest = require('unirest');

unirest.post('http://example.com/helloworld')
.header('Accept', 'application/json')
.send({ "Hello": "World!" })
.end(function (response) {
  console.log(response.body);
});


Дополнительно:
многие люди также предлагают использовать запрос [2]

Стоит отметить, что за кулисами Unirestиспользуется requestбиблиотека.

Unirest предоставляет методы для прямого доступа к объекту запроса.

Пример:

var Request = unirest.get('http://mockbin.com/request');

1
Еще один, который я нашел, который выглядит довольно хорошо, это github.com/request/request, который кажется немного более популярным, чем unirest, по крайней мере на момент написания этой статьи
Lochlan

Я могу засвидетельствовать запрос. Это очень хорошая библиотека. Я считаю, что запрос предоставляет более низкоуровневую функциональность, поэтому его целесообразно использовать для конкретных приложений. Когда меня не интересуют вещи низкого уровня, я считаю, что Unirest является адекватным.
Леви Робертс

Почему Unirest считается легким, когда это зависит от запроса? Сам запрос имеет 22 зависимости, я не вижу, как это
легко

@raphadko Я уверен, что за эти годы произошел вздор. Не забудьте проверить
Леви Робертс

17
var https = require('https');


/**
 * HOW TO Make an HTTP Call - POST
 */
// do a POST request
// create the JSON object
jsonObject = JSON.stringify({
    "message" : "The web of things is approaching, let do some tests to be ready!",
    "name" : "Test message posted with node.js",
    "caption" : "Some tests with node.js",
    "link" : "http://www.youscada.com",
    "description" : "this is a description",
    "picture" : "http://youscada.com/wp-content/uploads/2012/05/logo2.png",
    "actions" : [ {
        "name" : "youSCADA",
        "link" : "http://www.youscada.com"
    } ]
});

// prepare the header
var postheaders = {
    'Content-Type' : 'application/json',
    'Content-Length' : Buffer.byteLength(jsonObject, 'utf8')
};

// the post options
var optionspost = {
    host : 'graph.facebook.com',
    port : 443,
    path : '/youscada/feed?access_token=your_api_key',
    method : 'POST',
    headers : postheaders
};

console.info('Options prepared:');
console.info(optionspost);
console.info('Do the POST call');

// do the POST call
var reqPost = https.request(optionspost, function(res) {
    console.log("statusCode: ", res.statusCode);
    // uncomment it for header details
//  console.log("headers: ", res.headers);

    res.on('data', function(d) {
        console.info('POST result:\n');
        process.stdout.write(d);
        console.info('\n\nPOST completed');
    });
});

// write the json data
reqPost.write(jsonObject);
reqPost.end();
reqPost.on('error', function(e) {
    console.error(e);
});

Есть ли способ просмотреть тело сообщения о запросе или по запросу или ответу?
Якобаллвуд

17

Доступны десятки библиотек с открытым исходным кодом, которые вы можете использовать для выполнения HTTP-запроса POST в Node.

1. Аксиос (рекомендуется)

const axios = require('axios');

const data = {
    name: 'John Doe',
    job: 'Content Writer'
};

axios.post('https://reqres.in/api/users', data)
    .then((res) => {
        console.log(`Status: ${res.status}`);
        console.log('Body: ', res.data);
    }).catch((err) => {
        console.error(err);
    });

2. Игла

const needle = require('needle');

const data = {
    name: 'John Doe',
    job: 'Content Writer'
};

needle('post', 'https://reqres.in/api/users', data, {json: true})
    .then((res) => {
        console.log(`Status: ${res.statusCode}`);
        console.log('Body: ', res.body);
    }).catch((err) => {
        console.error(err);
    });

3. Запрос

const request = require('request');

const options = {
    url: 'https://reqres.in/api/users',
    json: true,
    body: {
        name: 'John Doe',
        job: 'Content Writer'
    }
};

request.post(options, (err, res, body) => {
    if (err) {
        return console.log(err);
    }
    console.log(`Status: ${res.statusCode}`);
    console.log(body);
});

4. Собственный модуль HTTPS

const https = require('https');

const data = JSON.stringify({
    name: 'John Doe',
    job: 'Content Writer'
});

const options = {
    hostname: 'reqres.in',
    path: '/api/users',
    method: 'POST',
    headers: {
        'Content-Type': 'application/json',
        'Content-Length': data.length
    }
};


const req = https.request(options, (res) => {
    let data = '';

    console.log('Status Code:', res.statusCode);

    res.on('data', (chunk) => {
        data += chunk;
    });

    res.on('end', () => {
        console.log('Body: ', JSON.parse(data));
    });

}).on("error", (err) => {
    console.log("Error: ", err.message);
});

req.write(data);
req.end();

Для деталей, проверьте эту статью .


14

Это самый простой способ, которым я пользуюсь, чтобы сделать запрос: используя модуль запроса.

Команда для установки модуля запроса:

$ npm install request

Пример кода:

var request = require('request')

var options = {
  method: 'post',
  body: postData, // Javascript object
  json: true, // Use,If you are sending JSON data
  url: url,
  headers: {
    // Specify headers, If any
  }
}

request(options, function (err, res, body) {
  if (err) {
    console.log('Error :', err)
    return
  }
  console.log(' Body :', body)

});

Вы также можете использовать встроенный модуль http для Node.js, чтобы сделать запрос.


1
Эта библиотека устарела.
Юрий Ткаченко

12

Мне нравится простота суперагента ( https://github.com/visionmedia/superagent ). Один и тот же API на узле и в браузере.

;(async function() {
  var response = await superagent.post('http://127.0.0.1:8125/', {age: 2})
  console.log(response)
})

Существует также извлечение узла ( https://www.npmjs.com/package/node-fetch ), в котором есть API, соответствующий fetchбраузерам - однако для этого требуется ручное кодирование строки запроса, автоматическая обработка типов содержимого не выполняется или так что любая другая работа superagent делает.


1
И в отличие от иглы, unirest и co, она обеспечивает легкий вес (суперагент: 16k, unirest: 1M, игла: 530K)
Lars

9

Если вы ищете HTTP-запросы на основе обещаний, axios прекрасно справляется со своей задачей.

  const axios = require('axios');

  axios.post('/user', {firstName: 'Fred',lastName: 'Flintstone'})
      .then((response) => console.log(response))
      .catch((error) => console.log(error));

ИЛИ

await axios.post('/user', {firstName: 'Fred',lastName: 'Flintstone'})

6

Чтобы
отправить запрос Rest / JSON Мы можем просто использовать пакет запроса и сохранить значения, которые мы должны отправить, в переменной Json.

Сначала установите пакет require в вашей консоли с помощью npm install request --save

var request = require('request');

    var options={
                'key':'28',
                'key1':'value',
                'key2':'value'
                }

    request({
             url:"http://dev.api.ean.com/ean-services/rs/hotel/v3/ping?                      
                 minorRev="+options.key+
                 "&cid="+options.key1+
                 "&apiKey="+options.key2,
             method:"POST",
             json:true},function(error,response,body){
                     console.log(body)
               }
    );

2
Никогда не создавайте свою собственную строку запроса. Вы пренебрегаете, чтобы правильно кодировать свои значения. Node.js имеет библиотеку для этой цели: nodejs.org/api/querystring.html
Брэд,

Эта библиотека устарела.
Юрий Ткаченко

4

Я нашел видео, которое объясняет, как этого добиться: https://www.youtube.com/watch?v=nuw48-u3Yrg

Он использует модуль http по умолчанию вместе с модулями querystring и stringbuilder. Приложение берет два числа (используя два текстовых поля) с веб-страницы и после отправки возвращает сумму этих двух (вместе с сохранением значений в текстовых полях). Это лучший пример, который я мог найти где-либо еще.

var http = require("http");
var qs = require("querystring");
var StringBuilder = require("stringbuilder");

var port = 9000;

function getCalcHtml(req, resp, data) {
    var sb = new StringBuilder({ newline: "\r\n" });
    sb.appendLine("<html>");
    sb.appendLine(" <body>");
    sb.appendLine("     <form method='post'>");
    sb.appendLine("         <table>");
    sb.appendLine("             <tr>");
    sb.appendLine("                 <td>Enter First No: </td>");

    if (data && data.txtFirstNo) {
        sb.appendLine("                 <td><input type='text' id='txtFirstNo' name='txtFirstNo' value='{0}'/></td>", data.txtFirstNo);
    }
    else {
        sb.appendLine("                 <td><input type='text' id='txtFirstNo' name='txtFirstNo' /></td>");
    }

    sb.appendLine("             </tr>");
    sb.appendLine("             <tr>");
    sb.appendLine("                 <td>Enter Second No: </td>");

    if (data && data.txtSecondNo) {
        sb.appendLine("                 <td><input type='text' id='txtSecondNo' name='txtSecondNo' value='{0}'/></td>", data.txtSecondNo);
    }
    else {
        sb.appendLine("                 <td><input type='text' id='txtSecondNo' name='txtSecondNo' /></td>");
    }

    sb.appendLine("             </tr>");
    sb.appendLine("             <tr>");
    sb.appendLine("                 <td><input type='submit' value='Calculate' /></td>");
    sb.appendLine("             </tr>");

    if (data && data.txtFirstNo && data.txtSecondNo) {
        var sum = parseInt(data.txtFirstNo) + parseInt(data.txtSecondNo);
        sb.appendLine("             <tr>");
        sb.appendLine("                 <td>Sum: {0}</td>", sum);
        sb.appendLine("             </tr>");
    }

    sb.appendLine("         </table>");
    sb.appendLine("     </form>")
    sb.appendLine(" </body>");
    sb.appendLine("</html>");
    sb.build(function (err, result) {
        resp.write(result);
        resp.end();
    });
}

function getCalcForm(req, resp, data) {
    resp.writeHead(200, { "Content-Type": "text/html" });
    getCalcHtml(req, resp, data);
}

function getHome(req, resp) {
    resp.writeHead(200, { "Content-Type": "text/html" });
    resp.write("<html><html><head><title>Home</title></head><body>Want to some calculation? Click <a href='/calc'>here</a></body></html>");
    resp.end();
}

function get404(req, resp) {
    resp.writeHead(404, "Resource Not Found", { "Content-Type": "text/html" });
    resp.write("<html><html><head><title>404</title></head><body>404: Resource not found. Go to <a href='/'>Home</a></body></html>");
    resp.end();
}

function get405(req, resp) {
    resp.writeHead(405, "Method not supported", { "Content-Type": "text/html" });
    resp.write("<html><html><head><title>405</title></head><body>405: Method not supported</body></html>");
    resp.end();
}

http.createServer(function (req, resp) {
    switch (req.method) {
        case "GET":
            if (req.url === "/") {
                getHome(req, resp);
            }
            else if (req.url === "/calc") {
                getCalcForm(req, resp);
            }
            else {
                get404(req, resp);
            }
            break;
        case "POST":
            if (req.url === "/calc") {
                var reqBody = '';
                req.on('data', function (data) {
                    reqBody += data;
                    if (reqBody.length > 1e7) { //10MB
                        resp.writeHead(413, 'Request Entity Too Large', { 'Content-Type': 'text/html' });
                        resp.end('<!doctype html><html><head><title>413</title></head><body>413: Request Entity Too Large</body></html>');
                    }
                });
                req.on('end', function () {
                    var formData = qs.parse(reqBody);
                    getCalcForm(req, resp, formData);
                });
            }
            else {
                get404(req, resp);
            }
            break;
        default:
            get405(req, resp);
            break;
    }
}).listen(port);

4

Это мое решение для POSTа GET.

О Postметоде:

Если тело является объектом JSON, поэтому важно десериализовать его JSON.stringifyи, возможно, установить соответствующий Content-Lenghtзаголовок:

      var bodyString=JSON.stringify(body)
      var _headers = {
        'Content-Length': Buffer.byteLength(bodyString)
      };

перед тем как написать это на запрос:

request.write( bodyString );

Об обоих Getи Postметодах:

Это timeoutможет произойти как socketразъединение, поэтому вы должны зарегистрировать его обработчик следующим образом:

request.on('socket', function (socket) {
        socket.setTimeout( self.timeout );
        socket.on('timeout', function() {
            request.abort();
            if(timeout) return timeout( new Error('request timed out') );
        });
    });

в то время как requestобработчик

       request.on('timeout', function () {
          // Timeout happend. Server received request, but not handled it
          // (i.e. doesn't send any response or it took to long).
          // You don't know what happend.
          // It will emit 'error' message as well (with ECONNRESET code).
          req.abort();
          if(timeout) return timeout( new Error('request timed out') );
        });

Я настоятельно рекомендую зарегистрировать оба обработчика.

Тело ответа разбито на куски, поэтому вы должны соединить куски в dataобработчике:

      var body = '';
      response.on('data', function(d) {
          body += d;
      });

На будет содержать все тело ответа:endbody

      response.on('end', function() {
        try {
            var jsonResponse=JSON.parse(body);
            if(success) return success( jsonResponse );
        } catch(ex) { // bad json
          if(error) return error(ex.toString());
        }
      });

Это безопасно , чтобы обернуть с try... уловом theJSON.parse` , так как вы не можете быть уверены , что это хорошо отформатированный JSON на самом деле и нет никакого способа , чтобы быть уверенным в нем в то время , что вы делаете запрос.

Модуль: SimpleAPI

/**
 * Simple POST and GET
 * @author Loreto Parisi (loretoparisi at gmail dot com)
*/
(function() {

  var SimpleAPI;

  SimpleAPI = (function() {

    var qs = require('querystring');

    /**
     * API Object model
     * @author Loreto Parisi (loretoparisi at gmail dot com)
     */
    function SimpleAPI(host,port,timeout,ssl,debug,json) {

      this.host=host;
      this.port=port;
      this.timeout=timeout;
      /** true to use ssl - defaults to true */
      this.ssl=ssl || true;
      /** true to console log */
      this.debug=debug;
      /** true to parse response as json - defaults to true */
      this.json= (typeof(json)!='undefined')?json:true;
      this.requestUrl='';
      if(ssl) { // use ssl
          this.http = require('https');
      } else { // go unsafe, debug only please
          this.http = require('http');
      }
    }

    /**
     * HTTP GET
     * @author Loreto Parisi (loretoparisi at gmail dot com)
     */
    SimpleAPI.prototype.Get = function(path, headers, params, success, error, timeout) {

      var self=this;
      if(params) {
        var queryString=qs.stringify(params);
        if( queryString ) {
          path+="?"+queryString;
        }
      }
      var options = {
        headers : headers,
        hostname: this.host,
        path: path,
        method: 'GET'
      };
      if(this.port && this.port!='80') { // port only if ! 80
        options['port']=this.port;
      }
      if(self.debug) {
        console.log( "SimpleAPI.Get", headers, params, options );
      }
      var request=this.http.get(options, function(response) {

          if(self.debug) { // debug
            console.log( JSON.stringify(response.headers) );
          }

          // Continuously update stream with data
          var body = '';
          response.on('data', function(d) {
              body += d;
          });
          response.on('end', function() {
            try {
              if(self.json) {
                var jsonResponse=JSON.parse(body);
                if(success) return success( jsonResponse );
              }
              else {
                if(success) return success( body );
              }
            } catch(ex) { // bad json
              if(error) return error( ex.toString() );
            }
          });
        });
        request.on('socket', function (socket) {
            socket.setTimeout( self.timeout );
            socket.on('timeout', function() {
                request.abort();
                if(timeout) return timeout( new Error('request timed out') );
            });
        });
        request.on('error', function (e) {
          // General error, i.e.
          //  - ECONNRESET - server closed the socket unexpectedly
          //  - ECONNREFUSED - server did not listen
          //  - HPE_INVALID_VERSION
          //  - HPE_INVALID_STATUS
          //  - ... (other HPE_* codes) - server returned garbage
          console.log(e);
          if(error) return error(e);
        });
        request.on('timeout', function () {
          // Timeout happend. Server received request, but not handled it
          // (i.e. doesn't send any response or it took to long).
          // You don't know what happend.
          // It will emit 'error' message as well (with ECONNRESET code).
          req.abort();
          if(timeout) return timeout( new Error('request timed out') );
        });

        self.requestUrl = (this.ssl?'https':'http') + '://' + request._headers['host'] + request.path;
        if(self.debug) {
          console.log("SimpleAPI.Post",self.requestUrl);
        }
        request.end();
    } //RequestGet

    /**
     * HTTP POST
     * @author Loreto Parisi (loretoparisi at gmail dot com)
     */
    SimpleAPI.prototype.Post = function(path, headers, params, body, success, error, timeout) {
      var self=this;

      if(params) {
        var queryString=qs.stringify(params);
        if( queryString ) {
          path+="?"+queryString;
        }
      }
      var bodyString=JSON.stringify(body)
      var _headers = {
        'Content-Length': Buffer.byteLength(bodyString)
      };
      for (var attrname in headers) { _headers[attrname] = headers[attrname]; }

      var options = {
        headers : _headers,
        hostname: this.host,
        path: path,
        method: 'POST',
        qs : qs.stringify(params)
      };
      if(this.port && this.port!='80') { // port only if ! 80
        options['port']=this.port;
      }
      if(self.debug) {
        console.log( "SimpleAPI.Post\n%s\n%s", JSON.stringify(_headers,null,2), JSON.stringify(options,null,2) );
      }
      if(self.debug) {
        console.log("SimpleAPI.Post body\n%s", JSON.stringify(body,null,2) );
      }
      var request=this.http.request(options, function(response) {

          if(self.debug) { // debug
            console.log( JSON.stringify(response.headers) );
          }

          // Continuously update stream with data
          var body = '';
          response.on('data', function(d) {
              body += d;
          });
          response.on('end', function() {
            try {
                console.log("END", body);
                var jsonResponse=JSON.parse(body);
                if(success) return success( jsonResponse );
            } catch(ex) { // bad json
              if(error) return error(ex.toString());
            }
          });

        });

        request.on('socket', function (socket) {
            socket.setTimeout( self.timeout );
            socket.on('timeout', function() {
                request.abort();
                if(timeout) return timeout( new Error('request timed out') );
            });
        });
        request.on('error', function (e) {
          // General error, i.e.
          //  - ECONNRESET - server closed the socket unexpectedly
          //  - ECONNREFUSED - server did not listen
          //  - HPE_INVALID_VERSION
          //  - HPE_INVALID_STATUS
          //  - ... (other HPE_* codes) - server returned garbage
          console.log(e);
          if(error) return error(e);
        });
        request.on('timeout', function () {
          // Timeout happend. Server received request, but not handled it
          // (i.e. doesn't send any response or it took to long).
          // You don't know what happend.
          // It will emit 'error' message as well (with ECONNRESET code).
          req.abort();
          if(timeout) return timeout( new Error('request timed out') );
        });

        self.requestUrl = (this.ssl?'https':'http') + '://' + request._headers['host'] + request.path;
        if(self.debug) {
          console.log("SimpleAPI.Post",self.requestUrl);
        }

        request.write( bodyString );
        request.end();

    } //RequestPost

    return SimpleAPI;

  })();

  module.exports = SimpleAPI

}).call(this);

Применение:

// Parameters
// domain: example.com
// ssl:true, port:80
// timeout: 30 secs
// debug: true
// json response:true
var api = new SimpleAPI('posttestserver.com', 80, 1000 * 10, true, true, true); 

var headers = {
    'Content-Type' : 'application/json',
    'Accept' : 'application/json' 
};
var params = {
  "dir" : "post-test"
};
var method = 'post.php';

api.Post(method, headers, params, body
    , function(response) { // success
       console.log( response );
    }
    , function(error) { // error
      console.log( error.toString() );
    }
    , function(error) { // timeout
       console.log( new Error('timeout error') );
    });

4

После долгих попыток создания низкоуровневой утилиты для обработки сообщений и получения запросов для моего проекта, я решил опубликовать свои усилия здесь. В основном в строках принятого ответа приведен фрагмент для выполнения запросов http и https POST для отправки данных JSON.

const http = require("http")
const https = require("https")

// Request handler function
let postJSON = (options, postData, callback) => {

    // Serializing JSON
    post_data = JSON.stringify(postData)

    let port = options.port == 443 ? https : http

    // Callback function for the request
    let req = port.request(options, (res) => {
        let output = ''
        res.setEncoding('utf8')

        // Listener to receive data
        res.on('data', (chunk) => {
            output += chunk
        });

        // Listener for intializing callback after receiving complete response
        res.on('end', () => {
            let obj = JSON.parse(output)
            callback(res.statusCode, obj)
        });
    });

   // Handle any errors occurred while making request
    req.on('error', (err) => {
        //res.send('error: ' + err.message)
    });

    // Request is made here, with data as string or buffer
    req.write(post_data)
    // Ending the request
    req.end()
};

let callPost = () => {

    let data = {
        'name': 'Jon',
        'message': 'hello, world'
    }

    let options = {
        host: 'domain.name',       // Your domain name
        port: 443,                 // 443 for https and 80 for http
        path: '/path/to/resource', // Path for the request
        method: 'POST',            
        headers: {
            'Content-Type': 'application/json',
            'Content-Length': Buffer.byteLength(data)
        }
    }

    postJSON(options, data, (statusCode, result) => {
        // Handle response
        // Process the received data
    });

}

2
Вы никогда не используете сериализованные post_data? запись в виде объекта js конвертируется в буфер по умолчанию?
ThatBrianDude

3
let request = require('request');
let jsonObj = {};
request({
    url: "https://myapii.com/sendJsonData",
    method: "POST",
    json: true,
    body: jsonObj
    }, function (error, resp, body){
       console.log(resp);
});

Или вы можете использовать эту библиотеку:

let axios = require("axios");
let jsonObj = {};

const myJsonAPI = axios.create({
   baseURL: 'https://myapii.com',
   timeout: 120*1000
});

let response = await myJsonAPI.post("sendJsonData",jsonobj).catch(e=>{
    res.json(e);
});
console.log(response);

requestбиблиотека устарела.
Юрий Ткаченко

3

Axios - это основанный на обещаниях HTTP-клиент для браузера и Node.js. Axios упрощает отправку асинхронных HTTP-запросов на конечные точки REST и выполнение операций CRUD. Его можно использовать в простом JavaScript или с такой библиотекой, как Vue или React.

const axios = require('axios');

        var dataToPost = {
          email: "your email",
          password: "your password"
        };

        let axiosConfiguration = {
          headers: {
              'Content-Type': 'application/json;charset=UTF-8',
              "Access-Control-Allow-Origin": "*",
          }
        };

        axios.post('endpoint or url', dataToPost, axiosConfiguration)
        .then((res) => {
          console.log("Response: ", res);
        })
        .catch((err) => {
          console.log("error: ", err);
        })

2

Публикация другого примера axios запроса axios.post, в котором используются дополнительные параметры конфигурации и пользовательские заголовки.

var postData = {
  email: "test@test.com",
  password: "password"
};

let axiosConfig = {
  headers: {
      'Content-Type': 'application/json;charset=UTF-8',
      "Access-Control-Allow-Origin": "*",
  }
};

axios.post('http://<host>:<port>/<path>', postData, axiosConfig)
.then((res) => {
  console.log("RESPONSE RECEIVED: ", res);
})
.catch((err) => {
  console.log("AXIOS ERROR: ", err);
})


0

Используя запрос зависимости.

Простое решение:

 import request from 'request'
 var data = {
        "host":"127.1.1.1",
        "port":9008
    }

request.post( baseUrl + '/peers/connect',
        {
            json: data,  // your payload data placed here
            headers: {
                'X-Api-Key': 'dajzmj6gfuzmbfnhamsbuxivc', // if authentication needed
                'Content-Type': 'application/json' 
            }
        }, function (error, response, body) {
            if (error) {
                callback(error, null)
            } else {
                callback(error, response.body)
            }
        });

3
откуда requestвзялась?
CodyBugstein

Эта библиотека устарела.
Юрий Ткаченко

0

Request-PromiseОбеспечивает ответ на основе обещания. Коды ответа http, отличные от 2xx, приведут к отклонению обещания. Это может быть перезаписано установкой options.simple = false

var options = {
  method: 'POST',
  uri: 'http://api.posttestserver.com/post',
  body: {
  some: 'payload'
 },
  json: true // Automatically stringifies the body to JSON
};

rp(options)
.then(function (parsedBody) {
    // POST succeeded...
})
.catch(function (err) {
    // POST failed...
});
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.