首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Node.js文件:无法读取未定义的属性‘TypeError’

Node.js文件:无法读取未定义的属性‘TypeError’
EN

Stack Overflow用户
提问于 2016-02-03 12:29:28
回答 3查看 22K关注 0票数 8

我刚开始学习node.js,很难用express和multer做一个简单的文件上传。

表单如下所示:

代码语言:javascript
复制
                                                             Upload Image    

在我的configure.js中,我有:

代码语言:javascript
复制
app.use(express.static(path.join(__dirname, 'public')));
app.use(multer({dest:'../public/upload/temp'}).single('file'));

image.js控制器:

代码语言:javascript
复制
create: function(req, res) {
        var saveImage = function() {
            console.log(req.body);
            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, //<line 55 error
                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();
    },

然而,当我尝试上传图片时,我得到了这个错误:

代码语言:javascript
复制
TypeError: Cannot read property 'file' of undefined
    at saveImage (/home/pc/node-dev/test-proj/controllers/image.js:55:37)
    at module.exports.create (/home/pc/node-dev/test-proj/controllers/image.js:76:9)
    at Layer.handle [as handle_request] (/home/pc/node-dev/test-proj/node_modules/express/lib/router/layer.js:95:5)
    at next (/home/pc/node-dev/test-proj/node_modules/express/lib/router/route.js:131:13)
    at Route.dispatch (/home/pc/node-dev/test-proj/node_modules/express/lib/router/route.js:112:3)
    at Layer.handle [as handle_request] (/home/pc/node-dev/test-proj/node_modules/express/lib/router/layer.js:95:5)
    at /home/pc/node-dev/test-proj/node_modules/express/lib/router/index.js:277:22
    at Function.process_params (/home/pc/node-dev/test-proj/node_modules/express/lib/router/index.js:330:12)
    at next (/home/pc/node-dev/test-proj/node_modules/express/lib/router/index.js:271:10)
    at urlencodedParser (/home/pc/node-dev/test-proj/node_modules/body-parser/lib/types/urlencoded.js:95:37)

当我记录req对象时,file不在那里:

代码语言:javascript
复制
{ title: 'myimage', description: 'something' }

实际上,这个代码片段只是我在this book中读到的一个稍微修改过的版本,它使用的是过时的express-3。所以基本上我只是用multer部件更新了它。

我想知道这里出了什么问题,以及如何修复它。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2016-02-03 12:45:14

您正在使用upload.single,您应该使用req.file而不是req.files。要上传多个文件,请使用upload.array

请注意,在req.file之后不需要另一个.file。如果您使用的是upload.single,则上传的文件为req.file

票数 12
EN

Stack Overflow用户

发布于 2020-05-08 07:21:26

通过上面提到的同一个book,在将req.files.file登录到控制台之后,我能够提出一个可行的解决方案,并且从控制台中的详细信息可以看出,path存在于file对象中,它是tempFilePath而不是path,因此实际路径应该是var tempPath = req.files.file.tempFilePath;。和完整的代码

代码语言:javascript
复制
create: function(req, res){
    var saveImage = function(){
      var possible = 'abcdefghijklmnopqrstuvwxyz0123456789';
      var imgUrl = '';

      for(var i=0; i<6; i++){
        imgUrl += possible.charAt(Math.floor(Math.random()*possible.length));
      }

     // if (!req.file) return console.log('Please upload a file')
     console.log(req.files.file)
     //
      var tempPath = req.files.file.tempFilePath;
      var ext = path.extname(req.files.file.name).toLowerCase();
      var 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();
  }

The details to the console after logging the req.files.file

票数 0
EN

Stack Overflow用户

发布于 2021-10-15 05:44:04

在上面提到的同一本书中,这是2021年,上面的所有代码都失败了,我已经和这个问题斗争了4天多,终于破解了它。我将multer中间件移到了routes模块中,以使其正常工作

将routes.js更新为

代码语言:javascript
复制
    var express = require('express'),
 path = require('path'),
 router = express.Router(),
 home = require('../controllers/home'),
 image = require('../controllers/image');
 const multer  = require('multer')
const upload = multer({ dest: path.join(__dirname,
    'public/upload/temp')});
module.exports = function(app) {
 router.get('/', home.index);
 router.get('/images/:image_id', image.index);
 router.post('/images',upload.single('image'), image.create);
 router.post('/images/:image_id/like', image.like);
 router.post('/images/:image_id/comment', image.comment);
 app.use(router);
};

将图像控制器中的create函数更新为

代码语言:javascript
复制
create: function (req, res) {
    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.file.path,
        ext = path.extname(req.file.originalname).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();
  }

从configure.js模块中注释掉或删除multer中间件

代码语言:javascript
复制
//app.use(multer({ dest: path.join(__dirname, 'public/upload/temp')}).single('image'));

确保index.handlebars中的表单与以下内容相对应

代码语言:javascript
复制
<form method="post" action="/images" enctype="multipart/form-data" >
        <div class="panel-body form-horizontal">
            <div class="form-group col-md-12">
                <label class="col-sm-2 control-label" for="file">Browse:</label>
                <div class="col-md-10">
                    <input class="form-control" type="file" name="image" id="file">
                </div>
            </div>
            <div class="form-group col-md-12">
                <label class="col-md-2 control-label" for="title">Title:</label>
                <div class="col-md-10">
                    <input class="form-control" type="text" name="title">
                </div>
            </div>
            <div class="form-group col-md-12">
                <label class="col-md-2 control-label" for="description">Description:</label>
                <div class="col-md-10">
                    <textarea class="form-control" name="description" rows="2"></textarea>
                </div>
            </div>
            <div class="form-group col-md-12">
                <div class="col-md-12 text-right">
                    <button type="submit" id="login-btn" class="btn btn-success" type="button">
                        <i class="fa fa-cloud-upload ">
                        </i> Upload Image</button>
                </div>
            </div>
        </div>
    </form>
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/35168541

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档