为什么我得到"名字未定义"当试图使用Express和Body Parser发布时

时间:2016-11-08 20:24:20

标签: node.js express postman

我正在尝试构建一个MEAN应用并尝试使用POSTMAN测试POSTing。当我这样做的时候,我一直都会遇到可怕的" TypeError:无法读取属性' name'未定义"。如果我输入一个简单的字符串,POST就会很好。但是当我使用" req.body.name"我收到了错误。我已经看过每个地方而且我没有看到我的错误。我甚至没有按照这个thread的建议。任何帮助或建议将不胜感激。

这是我目前在server.js文件中使用的代码:

    const express = require('express');
var bodyParser = require('body-parser');
var Bear = require('./models/bear')
var path = require('path');
var mongoose = require('mongoose');
var router = express.Router();

var app = express();


var staticAssets = __dirname + '/public';

    app.use(express.static(staticAssets));


    app.use('/api', router)
    app.use(bodyParser.json());
    app.use(bodyParser.urlencoded({extended: true}));


// Routes for my API
//===================================

// middleware to use for all requests
router.use(function(req,res,next){
    // logging happens here
    console.log('Something will happen.');
    next(); // Head to the next router...don't stop here
});

// Test router to make sure everything is working (accessed at GET http://localhost:3000/api)
router.get('/', function(req, res){
    res.json({message: 'hooray! welcome to our api!'})
})

//More routes will happen here with routes that end in "/bears"
router.route('/bears')
    //Create a bear (accessed at POST http://localhost:3000/api/bears)
    .post(function(req,res){
        var bear = new Bear(); // Create a new instance of the bear model
        console.log(req);
        bear.name = req.body.name; // set the bears name (comes from the request)

        //res.send(200, req.body);
        bear.save(function(err){
            if (err)
                res.send(err);
            res.json({message: 'Bear Created!!'});
        });
    });
//======================================

//var Products = require('./products.model.js');
var Product = require('./models/product.model');

var db = 'mongodb://localhost/27017';

mongoose.connect(db);







    var server = app.listen(3000);
console.log("App is listening on port 3000");

感谢。

另外,我试图在POSTMAN中使用的网址是http://localhost:3000/api/bears

1 个答案:

答案 0 :(得分:1)

快速处理请求自上而下,这意味着如果您需要通过中间件将所有功能应用于所有路由,则需要将中间件添加到您的应用之前任何需要它的路由。中间件通常就是这种情况,例如body-parser

使用路由器中间件时,通常不会将路由器构建在与将用作中间件的实际Express应用程序相同的文件中。相反,将其放在单独的文件和/或目录中以用于组织目的,这被认为是最佳实践。

Express Apps可以像这样构建

/lib
  /models
    bear.js
    product.js
/node_modules
/public
  /css    
/routes
  api.js
package.json
server.js

routes目录是放置任何适用的路由器中间件文件的位置,例如api路由器。 server.js是您的主要Express App,public是您的静态资产的存储位置。 lib是包含任何业务逻辑文件和模型的目录。

实际的Express应用程序和路由器文件看起来应该是这样的

server.js

'use strict';

const express = require('express');
const bodyParser = require('body-parser');
const path = require('path');

const apiRouter = require('./routes/api');

const app = express();

app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: true }));

app.use(express.static(path.join(__dirname, public)));

app.use(/api, apiRouter);

app.listen(port, () => {
    console.log(`Listening on port ${port});
});

module.exports = app; 

路由/ api.js

'use strict';

const router = require('express').Router();
const Bear = require('./lib/models/bear');

router.use((req, res, next) => {
    // logging happens here
    console.log('Something will happen.');
    next(); // Head to the next router...don't stop here
});

router.get('/', (req, res) => {
    return res.json({ message: 'hooray! welcome to our api!'})
});

router.route('/bears')
    //Create a bear (accessed at POST http://localhost:3000/api/bears)
    .post((req, res) => {
        var bear = new Bear(); // Create a new instance of the bear model

        console.log(req);
        bear.name = req.body.name; // set the bears name (comes from the request)

        //res.send(200, req.body);
        bear.save((err) => {
            if (err)
                return res.send(err);

            return res.json({message: 'Bear Created!!'});
        });
    });

module.exports = router;

要注意,您可以进一步分解API以增加解耦量。这方面的一个示例是将/api/bear路由移动到其自己的路由器中间件并移动到其自己的路由文件中。然后,只需将其作为中间件添加到routes/api.js路由器,就像在server.js中一样。如果您的应用程序具有合适大小的API,那么这将是最好的方法,因为它可以在将中间件应用于特定路由时提供最大的灵活性,并且可以使维护源变得更加容易。