2015-11-27 2 views
0

Сегодня я добавлял возможность загружать фотографию в Facebook на сайт, над которым я работаю. Сайт построен в Express node.js, и я использую модуль запроса npm для загрузки.Node.js - разница между созданием формы для запроса и получением ее из request.post?

Я продолжал получать сообщение об ошибке: "(# 324) Требуется загрузить файл". Я думал, что это связано с файлом фотографии, который я пытался загрузить, поэтому я бы попробовал различные варианты преобразования его в base64, сменив заголовки, вручную создав запросы POST и т. Д.

Я в конечном итоге пробовал весь код от одного ответа, и, к моему удивлению, он работал, хотя данные изображения были только от fs.createReadStream(req.file.path), которые я пробовал много раз раньше.

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

request({ 
     url: 'https://graph.facebook.com/me/photos?access_token=' + req.user.facebook.token, 
     method: "POST", 
     form: { 
      source: fs.createReadStream(req.file.path), 
      message: req.body.message 
     } 
    }, function(error, response, body) { 
     var bodyJSON = JSON.parse(body); 
     if(bodyJSON.error) { 
      console.log(bodyJSON.error.message); 
     } 
    }); 

Это продолжало давать мне ошибку, о которой я упоминал ранее. Код, который я нашел, выглядит несколько иначе.

serverRequest = request.post('https://graph.facebook.com/me/photos?access_token=' + req.user.facebook.token, function(err, res, body) { 
    var bodyJSON = JSON.parse(body); 
    if(bodyJSON.error) { 
      console.log(bodyJSON.error.message); 
    } 
}); 

form = serverRequest.form() 
// append a normal literal text field ... 
form.append('message', req.body.message); 

// append a file field by streaming a file from disk ... 
form.append('source', fs.createReadStream(req.file.path)); 

Это работает. Поэтому я решил сравнить два разных объекта формы. Они довольно большие, поэтому я положил их на Пастбин. сначала можно увидеть here и второй here. Существуют огромные различия.

Теперь мне интересно, две вещи:

  1. Почему созданы два различных форм-Datas? В чем разница между двумя методами создания/добавления к ним?
  2. Как работает добавление формы из запроса в методе 1? Когда действительно возникает запрос на почту? Я бы предположил, что это делается на request.post (..), но затем я могу добавить материал в данные формы, прежде чем он будет опубликован.

Edit: Вопрос Ответил Ниже Вопрос ответил MSCDEX. Вот код, который я сейчас использую для запроса, на тот случай, если кому-то это понадобится.

request.post(
    { 
     url: 'https://graph.facebook.com/me/photos?access_token=' + authToken, 
     formData: { 
      message: message, 
      source: fs.createReadStream(imageFile.path) 
     } 
    }, function(err, res, body) { 
     var bodyJSON = JSON.parse(body); 
     if(bodyJSON.error) { 
      console.log(bodyJSON.error.message); 
     } 
    } 
); 

ответ

1

request documentation объясняет разницу. Первая форма предназначена для отправки запросов типа application/x-www-form-urlencoded, а вторая предназначена для отправки запросов типа multipart/form-data.

(Binary) файлы обычно не могут быть представлены с application/x-www-form-urlencoded запросами, поэтому multipart/form-data обычно используется вместо (хотя некоторые веб-сервисы могут позволить вам представить один файл через PUT запроса, где содержание запроса является исходным содержимое файла).

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

+0

Большое спасибо! Я прочитал документацию, но почему-то пропустил заголовки на частях формы. Я изменил свой код, чтобы перейти в 'multipart/form-data' вместо добавления его после.Спасибо также за объяснение процесса HTTP-запроса, что имеет большой смысл. –

+0

Я добавил новый, только что-быть безопасный код в исходный ответ. Я проверил, и он работает. –