我遇到了node.js的问题,每次运行查询时,它都会重新运行以前运行的所有查询以及新查询。
更具体地说:我有一个包含三个字段的表单:名字,姓氏,电子邮件。当我提交该表格时,我想: - 检查用户是否已存在于数据库中(我使用电子邮件地址上的SQL查询执行此操作)。 - 如果客户端存在,则在表单上显示无法添加客户端的消息。 - 如果用户不存在,请将客户端添加到数据库并显示“已成功添加的客户端”#39;表格上留言。
看起来很简单,对吧?
发生的事情是,对于我添加的第一个新用户,一切都很好。然后我添加了第二个新用户,但数据库中发生的是它添加了两个条目:它重新添加第一个新用户,第二个也是。如果我尝试添加第三个用户,它最终会运行3' INSERT INTO'查询,再次添加第一个用户(第三次)和第二个用户,然后是第三个用户。等等...
就像某个地方有一些存储空间,我没有在表单提交之间清除 - 但我没有在这里使用会话,所以我不知道这个表单数据在哪里持续!
有什么想法?我对node.js很新,我认为我必须遗漏一些非常基本的东西,但我无法看到它。
以下是我的' index.html'中的javascript和表单。文件:
<script type="text/javascript">
$(document).ready(function(){
$("#new_client").submit(function(){
var form = $(this);
//remove previous message section
form.siblings('p').remove();
$.getJSON(
form.attr('action'),
form.serialize(),
function (result){
if (result.success == true){
$(form).before("<p>Success: "+result.message+"</p>");
}
else if (result.success == false){
var html = "";
for (var i = 0; i < result.message.length; i++){
html += "<p>Failed: "+result.message[i]+"</p>";
}
$(form).before(html);
}
}); //end $.getJSON
return false;
});
});
</script>
<body>
<form id="new_client" action="/add_client" method="get">
<!-- NOTE: we need to use method="get" for getJSON -->
<input type="text" name="first_name" placeholder="Client first name">
<input type="text" name="last_name" placeholder="Client last name">
<input type="text" name="email" placeholder="Client email">
<button type="submit">Add Client</button>
</form>
</body>
以下是我的nodejs代码(server.js)的一部分:
var http = require('http');
var url = require('url');
var path = require('path');
var fs = require('fs');
var querystring = require('querystring');
var mysql = require('mysql');
var events = require('events');
var Validator = require('validator').Validator;
var eventEmitter = new events.EventEmitter();
var db = mysql.createConnection({
//host:'localhost',
port: 8889,
user: 'root',
password: 'root',
database: 'test_database'
});
server = http.createServer(function (request, response){
var pageUrl = url.parse(request.url).pathname;
if(pageUrl === '/add_client'){
var dataQuery = url.parse(request.url).query;
var formData = querystring.parse(dataQuery);
//set up event listener for 'add client result'
eventEmitter.on('addClientResult', function (result){
response.end(JSON.stringify(result));
});
//set up listener for existing client check
eventEmitter.on('clientIsNewResult', function (result){
if (result.success === false){
response.end(JSON.stringify(result));
}
else {
//this will trigger the 'addClientResult' event
addClient(db, formData.first_name, formData.last_name, formData.email);
}
});
//set up event listener for validated data
eventEmitter.on('validateDataResult', function (result){
if (result.success === false)
response.end(JSON.stringify(result));
else{
//trigger 'clientIsNewResult' event
clientIsNew(db, formData.email);
}
});
// trigger the validateDataResult event
validateData(formData.first_name, formData.last_name, formData.email);
} //end 'add_client'
else { ... code for other actions and where we start the response object... }
}); //end of server object
server.listen(8080);
function clientIsNew(db, email){
db.query('SELECT * FROM clients WHERE email=?', [email],
function (errors, results, fields) {
if (errors) throw errors;
//console.log(this.sql);
if (results.length > 0){
query_result = {
'success': false,
'message': ['There is already a client with this email address!']
}
}
else {
query_result = {
'success': true,
'message': 'This is a unique user'
};
}
eventEmitter.emit('clientIsNewResult', query_result);
});
}
function addClient(db, first_name, last_name, email){
//the only time we should get here is when we want to create a new user
//so we should only get here when 'clientIsNewResult' is triggered and gets
// a result of true... at least that is the intention!
db.query('INSERT INTO clients SET first_name=?, last_name=?, email=?, created_at=NOW();',
[first_name, last_name, email],
function (errors, results, fields) {
if (errors) throw errors;
//console.log(this.sql);
insert_result = {
'success': true,
'message': 'Client is added'
}
eventEmitter.emit('addClientResult', insert_result);
}
);
}
function validateData(first_name, last_name, email){
... validates info, no problems with this ...
eventEmitter.emit('validateDataResult', result);
}
console.log('Server running at http://localhost:8080/');
好的,我希望这不是太多,我删除了很多评论和其他的console.log行。
如果我需要发布更多或更少的内容,或者我忘记了某些内容,请告诉我。
提前感谢您的帮助!
答案 0 :(得分:0)
将事件发射器移动到http请求
内移动
var eventEmitter = new events.EventEmitter();
到
server = http.createServer(function (request, response){
var pageUrl = url.parse(request.url).pathname;
var eventEmitter = new events.EventEmitter();
答案 1 :(得分:0)
最后得到导师的一些指导。我的问题是每次我向服务器发送数据时,我都在创建另一个事件监听器,但之前的事件监听器仍然存在。所以我第二次提交表单时,同一事件中有两个事件监听器;第三次,有三个......等。
解决方案:代码的主要重构,不要使用这么多。另请:将eventEmitter.on()
更改为eventEmitter.once()
以获取addClientResult事件,这是唯一的事件侦听器。毕竟,我只想在每次向服务器提交数据时添加一个客户端。