2015-09-23 22 views
6

我最近遵循了关于如何构建快速服务器(https://codeforgeek.com/2014/06/express-nodejs-tutorial/)的简单教程。快速服务器 - 无法开机自检/

我想扩展本教程中的代码,以便我可以回复发布请求。我想通过更新JSON文件来做到这一点(恰好是充满了“用户评论”,然后在“/”

./server.js重新描绘:

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

// routing configuration 
require('./router/main')(app); 

// ejs configuration 
app.set('views', __dirname + '/views'); 
app.set('view engine', 'ejs'); 
app.engine('html', require('ejs').renderFile); 

// run the server 
var server = app.listen(8080, function(){ 
    console.log('Express server listening on port 8080'); 
}); 

。 /router/main.js(路由器):

var fs = require('fs'); 
var ejs = require('ejs') 

module.exports = function(app){ 

    app.get('/', function(req, res){ 
    var comments = JSON.parse(fs.readFileSync(__dirname + '/../comments.json')); 
    res.render('index.ejs', comments); 
    }); 

    app.post('/', function(req, res){ 
    console.log('here in post'); 
    var name = req.body.name; 
    var message = req.body.message; 
    var newComment = {"name": name, "message": message}; 
    var comments = JSON.parse(fs.readFileSync(__dirname + '/../comments.json')); 
    comments.push(newComment); 
    fs.writeFileSync(__dirname + '/../comments.json', comments, 'utf8'); 
    //redirect to a 'get' on '/' 
    res.redirect('/'); 
    }); 

    app.get('/about', function(req, res){ 
    res.render('about.html') 
    }); 

} 

./views/index.ejs:

<div> 

    <div> 
    <h1> Joe's Forum </h1> 
    <a href='/about'> (about) </a> 
    </div> 

    <div> 
    <ul> 
    <% comments.forEach(function(comment){ %> 
     <li> 
     <%= comment.name %> : <%= comment.message %> 
     </li> 
    <% }); %> 
    </ul> 
    </div> 

    <h2> Enter a new comment </h2> 

    <form action='/' method="post"> 
    Enter your name: <input type='text' name='name'> <br><br> 
    Enter your message: <input type='textarea' name='message'> <br><br> 
    <input type='submit' value='Submit'> 
    <form> 

</div> 

./comments.json:

{ 
    "comments": [ 
    {"name":"Joe", "message" : "What advantages does Node.js afford the web developer?"}, 
    {"name": "John", "message": "Asynchronous IO helps us to keep our pages responsive even if the server is fetching data"} 
    ] 
} 

当我试图从我的形式提交新的评论,我看到的是这样的:

“不能发布/”

有人可以解释为什么我可能会得到这个错误吗?谢谢

+0

你正在做的真正禁忌的东西。你永远不应该使用nodeJS的'Sync' api,当然不能使用express服务器的响应。也没有错误检查任何地方,所以你的服务器将非常容易崩溃。你能显示“comments.json”的内容吗? – caasjj

+0

好吧。然而,我只是想“让它成为工作”,以此作为学习Express的练习。我知道这不是很棒的代码。一旦我收到“发布请求”,我打算将其清理干净(即订阅最佳做法)。按照要求,我会编辑包含comments.json。 –

+0

完全不是意味着批评 - 只是指出你可能会或可能没有意识到的东西。现在,我想我也明白为什么你的代码行为不当。你正在'Object'上做'comments.push',而不是'Array'。让我看看我能否为你解决一个明确的答案。 – caasjj

回答

3

实际上存在一些问题,但主要的问题是您没有body解析器 - 将POST中的节点流转换为req.body的模块。我目前只熟悉bodyParser,你应该研究一下。尽管它在Express 4.x文档中显示,但运行服务器时会收到弃用消息。

另一个问题是comments.push的问题。那应该是comments.comments.push。以下作品:

router.js:

var fs = require('fs'); 
var ejs = require('ejs') 

module.exports = function(app){ 

    app.get('/', function(req, res){ 
    var comments = JSON.parse(fs.readFileSync(__dirname + '/../comments.json')); 
    res.render('index.ejs', comments); 
    }); 

    app.post('/', function(req, res){ 
    console.log('here in post'); 
    console.log(req.body) 
    var name = req.body.name; 
    var message = req.body.message; 
    var newComment = {"name": name, "message": message}; 
    var comments = JSON.parse(fs.readFileSync(__dirname + '/../comments.json')); 
    comments.comments.push(newComment); 
    fs.writeFileSync(__dirname + '/../comments.json', JSON.stringify(comments), 'utf8'); 
    //redirect to a 'get' on '/' 
    res.redirect('/'); 
    }); 

    app.get('/about', function(req, res){ 
    res.render('about.html') 
    }); 

} 

和server.js:

var express = require('express'); 
var bodyParser = require('body-parser'); 
var app = express(); 

app.use(bodyParser.urlencoded()) 

// routing configuration 
require('./router/main')(app); 

// ejs configuration 
app.set('views', __dirname + '/views'); 
app.set('view engine', 'ejs'); 
app.engine('html', require('ejs').renderFile); 

// run the server 
var server = app.listen(8080, function(){ 
    console.log('Express server listening on port 8080'); 
}) 
+0

感谢您的回答。一旦我获得了15的声望,我就会赞扬它。 –

+0

欣赏!请仔细研究一下正文解析和中间件的问题,因为这将对Express的工作方式非常有益。 – caasjj