node.js + mysql:“在已经将握手排队之后无法将握手排队。”

Tra*_*vis 0 javascript mysql runtime-error node.js

我正在尝试创建两个函数,一个从 SQL 数据库检索对象,另一个将对象保存到同一个 SQL 数据库。我正在使用node.jsmysql执行此操作。我有两个函数fetchEmployeeEmployee.save,分别获取和保存员工。然而,当我调用fetchEmployee,并且回调包含 时Employee.save,我收到错误Cannot enqueue Handshake after already enqueuing a Handshake.更奇怪的是,Employee.save似乎在引发错误之前运行。

编辑employee.save似乎运行是异步的症状,因为console.log("Saved!")在回调函数传递给之前调用,SQL.parse这意味着错误出现在parse. 另外,如果console.log("connection created");在 后面添加了inside parse con.connect,并且console.log("Made it out.");在 的末尾添加了con.connect,那么在调用 时Employee.save,控制台会输出> "connection created",然后抛出错误,这意味着保存查询永远不会完成,但错误会在之后抛出con.connect

Employee 类由以下定义

function Employee(obj) {
    /** Defines the Employee class
     * @arg obj.id : an integer; the employee's id
     * @arg obj.name : A string; the employee's name
     * @arg obj.position : A string; the employee's positions split by commas
     */

    this.id = obj.id;
    this.name = obj.name;
    this.position = obj.position;

    this.save = function() {
        SQL.parse({
            sql : `UPDATE EMPLOYEES
                SET id=?, name=?, position=?
                WHERE id=?`,
                replace_ : [this.id, this.name, this.position, this.id],
                result : false
        });
        console.log("Saved!");
    }
}
Run Code Online (Sandbox Code Playgroud)

请注意console.log("Saved!");,因为稍后会出现

fetchEmployee由该函数定义:

function fetchEmployee(id, callback) {
    /** Fetch an employee from the employee table
     * @arg id : An integer; the id of the employee to fetch
     * @arg callback : A callback function to pass the employee to
     */

     SQL.parse({ // Perform the parse, define the sql, replace, and result
        sql : "SELECT * FROM employees WHERE id=?",
        replace_ : [id],
        result : true
     },

     function(err, data) {
         if(err) { // Pass an error if there's an error
             callback(err, null);
             throw err;
         }
         // Pass the employee to the callback as an employee object if there's no errors
         callback(null, new Employee({  // data is passed as a list from the sql table, so take only the object we need through [0]
                id : data[0].id,
                name : data[0].name,
                position : data[0].position
             })
         );
     });
}
Run Code Online (Sandbox Code Playgroud)

最后,在该文件中定义了 SQL.parse:

var mySQL = require("mysql");

var con = mySQL.createConnection({ //Create connection
    host : "localhost",
    database : "testdb1",
    user : "root",
    password : "***************" 
});

function parse(obj, callback) {
    /** Parses an sql query. 
     * @arg callback : A callback function, will be passed the data
     * @arg obj.sql : an sql query
     * @arg obj.replace_ : A list of replacements for ?s in sql
     * @arg obj.result : a boolean indicating whether a result should be returned
     */

     //Assign meaningfull values
     obj.replace_ = obj.replace_ || [];
     callback = callback || function() {};

    con.connect(function(err) {
        if(err) throw err;

        //Connect and pass the sql command to the server
        con.query(obj.sql, obj.replace_, function(err, data) {
            if(err) { //Pass the err to the callback if there is an err
                callback(err, null);
                throw err;
            }
            else if(obj.result) { // Pass the data to the callback if result is true
                callback(null, data)
            }
        });
    });
}

module.exports = {
    parse : parse
};
Run Code Online (Sandbox Code Playgroud)

当我调用这段代码时

fetchEmployee(985, function(err, data) {
    if(err) throw err;
    console.log(data);
    data.save();
});
Run Code Online (Sandbox Code Playgroud)

控制台输出

Employee {
  id: 985,
  name: 'Skidd',
  position: 'Dishwasher, Busser',
  save: [Function] }
Saved!
Error: Cannot enqueue Handshake after already enqueuing a Handshake. [...]
Run Code Online (Sandbox Code Playgroud)

在我看来,它运行正确fetchEmployee,因为数据与员工的数据一起正确记录到控制台。然后它记录Saved!,似乎表明Employee.save运行正确,然后在完成所有代码后,抛出错误。我一生都无法弄清楚为什么会发生这种情况,在这里或在谷歌上或通过测试。

我尝试添加到incon.end的末尾,这将错误更改为parsesql.jsCannot enqueue Handshake after invoking quit

Tra*_*vis 6

我能够通过放置来解决这个问题

var con = mySQL.createConnection({ //Create connection
    host : "localhost",
    database : "testdb1",
    user : "root",
    password : "***************" 
});
Run Code Online (Sandbox Code Playgroud)

在函数内部parse,尽管我不能 100% 确定为什么会这样。