如何使用multer或body-parser上传文件

我是一个NodeJS初学者,跟着一本书“使用MongoDB和NodeJS进行Web开发”。 我在“第6章”中被卡住了。 当我使用Muller进行file upload时,服务器会引发以下错误:

/Users/fk / Documents / imageuploader / node_modules / express / lib / application.js: 209 throw new TypeError('app.use() requires middleware functions'); ^ TypeError: app.use() requires middleware functions 

但是当我用bodyParserreplace它时,服务器启动,但是当我点击上传button时,它给我在浏览器上的以下错误。

 500 TypeError: Cannot read property 'file' of undefined 

但是,它应该将我redirect到另一个页面,其中显示上传的文件。

这里是我的bodyParser代码,请看我是否正确使用它,因为它在服务器启动时给我“body-parser deprecated”。 我看过其他的问题,像我和我一样,但没有一个真正的工作。

 app.use(bodyParser.json()); app.use(bodyParser.urlencoded({ extended: true })); app.use(bodyParser({ uploadDir: path.join(__dirname, '../public/upload/temp') })); 

下面的代码显示了我如何使用Muller,以防万一如果有什么我不该做的,请让我知道。 在上传文件,body-parser或multer的情况下哪个更好?

 app.use(multer({ dest: path.join(__dirname, '../public/upload/temp') })); var saveImage = function() { var possible = 'abcdefghijklmnopqrstuvwxyz0123456789', imgUrl = ''; for (var i = 0; i < 6; i += 1) { imgUrl += possible.charAt(Math.floor(Math.random() * possible.length)); } var tempPath = req.files.file.path, ext = path.extname(req.files.file.name).toLowerCase(), targetPath = path.resolve('./public/upload/' + imgUrl + ext); if (ext === '.png' || ext === '.jpg' || ext === '.jpeg' || ext === '.gif') { fs.rename(tempPath, targetPath, function(err) { if (err) throw err; res.redirect('/images/' + imgUrl); }); } else { fs.unlink(tempPath, function() { if (err) throw err; res.json(500, { error: 'Only image files are allowed.' }); }); } }; saveImage(); 

前面的代码块是我用来上传文件的逻辑。 在这个错误中,它将'file'指向未定义,它位于saveImage函数的以下行中。 无法获取path,因此根据saveImage函数的else部分抛出错误500。 为什么'文件'在这里没有定义? 我不明白。

 var tempPath = req.files.file.path, 

multer()返回一个使用你指定的设置的中间件生成器,所以你不能直接把它的返回值传递给app.use() 。 您可以在文档中看到它可以生成的所有中间件types,但通常生成的中间件通常会在路由级别添加,而不是像其他身体parsing器那样全局添加。 这是因为您通常会传递您期望的文件字段的名称。

例如,这将接受其表单字段名称为foo的单个文件(以及任何非文件字段):

 var upload = multer({ dest: path.join(__dirname, '../public/upload/temp') }); // ... app.post('/upload', upload.single('foo'), function(req, res) { if (req.file) { console.dir(req.file); return res.end('Thank you for the file'); } res.end('Missing file'); }); 

此外, body-parser当前不会导出一个multipart/form-data -capable中间件,所以你不能使用该模块来处理上传的文件(很less,在application/x-www-form-urlencoded表单或其他东西,但效率要低得多)。

这里是MEANfile upload的基本代码,请查看

HTML

 <form id="frmDoc" name="frmDocument" ng-submit="upload()" class="form-horizontal form-bordered" enctype="multipart/form-data" > <fieldset> <div class="form-group"> <label class="col-md-4 control-label" for="val_email">Document<span class="text-danger">*</span></label> <div class="col-md-4"> <div class="input-group"> <input type="file" name="file" id='file' required="required" /> </div> </div> </div> </fieldset> <div class="form-group form-actions"> <div class="col-md-8 col-md-offset-4"> <button type="submit" class="btn btn-sm btn-primary"><i class="fa fa-upload"></i> submit</button> </div> </div> </form> 

客户端代码

 app.controller ('myctrl',function($scope,$http){ $scope.upload = function () { var file = angular.element(document.querySelector('#file')).prop("files")[0]; $scope.files = []; $scope.files.push(file); $http({ method: 'POST', url: '/users/upload', headers: { 'Content-Type': undefined }, transformRequest: function (data) { var formData = new FormData(); formData.append('model', angular.toJson(data.model)); formData.append('file', data.files[0]); return formData; }, data: { model: { title: 'hello'}, files: $scope.files } }).success(function (res) { console.log(res) }); } }); 

服务器端代码

 var multer = require('multer'); var mkdirp = require('mkdirp'); var storage = multer.diskStorage({ destination: function (req, file, cb) { //var code = JSON.parse(req.body.model).empCode; var dest = 'public/uploads/'; mkdirp(dest, function (err) { if (err) cb(err, dest); else cb(null, dest); }); }, filename: function (req, file, cb) { cb(null, Date.now()+'-'+file.originalname); } }); var upload = multer({ storage: storage }); router.post('/upload', upload.any(), function(req , res){ console.log(req.body); res.send(req.files); });