9

I try to create a server, which can receive a file from an HTTP request. I use Postman as user agent and I add a file to the request. This is the request:

POST /getfile HTTP/1.1
Host: localhost:3000
Content-Type: multipart/form-data; boundary=----WebKitFormBoundary7MA4YWxkTrZu0gW
Cache-Control: no-cache
Postman-Token: 9476dbcc-988d-c9bd-0f49-b5a3ceb95b85

------WebKitFormBoundary7MA4YWxkTrZu0gW
Content-Disposition: form-data; name="file"; filename="test.xls"
Content-Type: application/vnd.ms-excel


------WebKitFormBoundary7MA4YWxkTrZu0gW--

But when the request reaches the server I can not find the file in it (I mean in the request). I tried to receive it from the body part of the request, but it returned > {} <. I tried to figure out, how can I refer to the name of the file, but unfortunately I can not find any reference in the request header for the name of the file...

Can anybody help me to find out, what should I do?

Mahmoud
  • 456
  • 3
  • 13
HowToTellAChild
  • 623
  • 1
  • 9
  • 21
  • 2
    Do you use register a middleware like multer? https://www.npmjs.com/package/multer – Stavros Zavrakas Oct 27 '17 at 10:12
  • 2
    Can you show your server code? – Héctor Oct 27 '17 at 10:14
  • So this is http post of form data? Maybe use busboy from npm. See https://www.npmjs.com/package/busboy – teroi Oct 27 '17 at 10:26
  • @stavros.zavrakas multer seems easy to use and good to solve my problem. If you add this comment to answer section, I can accept it. Héctor: the problem solve, thanks your response! teroi: busboy seemed to me a little complex to multer. but thank your response! – HowToTellAChild Oct 30 '17 at 11:37
  • There is a good and easy option by suing express-fileupload https://www.npmjs.com/package/express-fileupload – Bharat May 18 '18 at 07:36

3 Answers3

9

As a follow up to my comment, you can use the multer module achieve the thing that you want: https://www.npmjs.com/package/multer

const express = require('express');
const multer = require('multer');

const app = express();
const upload = multer();

app.post('/profile', upload.array(), function (req, res, next) {
  // req.body contains the text fields 
});
Stavros Zavrakas
  • 3,045
  • 1
  • 17
  • 30
8

var app = require('express')();
var multer = require('multer');
var upload = multer();

app.post('/your_path', upload.array(), function (req, res, next) {
  // req.files is array of uploaded files
  // req.body will contain the text fields, if there were any
});
Adrian Zhang
  • 126
  • 3
5

You need to parse the form data from the request. There are a few packages that solves this problem, notably formidable, busboy (or busboy-connect), parted and flow.

Here's a solution using formidable, it is my preferred solution for things like image uploads because it saves to disk. If you just want to read the file, you can use one of the other packages above.

Install formidable

npm install formidable --save

Then, in your server, you will have to parse the data from the client:

// Somewhere at the start of your file
var IncomingForm = require('formidable').IncomingForm

// ...

// Then in your request handler
var form = new IncomingForm()
form.uploadDir = 'uploads'
form.parse(request, function(err, fields, files) {
  if (err) {
    console.log('some error', err)
  } else if (!files.file) {
    console.log('no file received')
  } else {
    var file = files.file
    console.log('saved file to', file.path)
    console.log('original name', file.name)
    console.log('type', file.type)
    console.log('size', file.size)

  }
})

A few things to note:

  • formidable saves files with new names, you can use fs to rename or move them
  • you can set form.keepExtensions = true if you want saved files to keep their extensions
Sunspots
  • 59
  • 2
  • thanks your response! I tried out your solution and worked good, but need too much coding for me. The multon module gives me an easier way to handle my issue. – HowToTellAChild Oct 30 '17 at 12:32