对node.js中两个单独查询的结果进行计算
我几乎只使用Python编程,但我正在尝试学习Node。我的思维是如此的同步,以至于我在编单词,脑袋撞在墙上,试图找出回调。我意识到回调是传递给函数的函数?我已经成功地编写了非常简单的回调,但无法使此代码按我希望的方式工作 本质上,我需要将这两个查询的结果相乘,然后我将基于该数学编写一个if语句 希望有人能告诉我如何编写一个函数来调用这些函数,等待结果,将它们相乘,并包含一个if语句供我处理 这需要在node上完成,因为我正在将它添加到用node开发的聊天机器人中对node.js中两个单独查询的结果进行计算,node.js,asynchronous,callback,Node.js,Asynchronous,Callback,我几乎只使用Python编程,但我正在尝试学习Node。我的思维是如此的同步,以至于我在编单词,脑袋撞在墙上,试图找出回调。我意识到回调是传递给函数的函数?我已经成功地编写了非常简单的回调,但无法使此代码按我希望的方式工作 本质上,我需要将这两个查询的结果相乘,然后我将基于该数学编写一个if语句 希望有人能告诉我如何编写一个函数来调用这些函数,等待结果,将它们相乘,并包含一个if语句供我处理 这需要在node上完成,因为我正在将它添加到用node开发的聊天机器人中 var getSkuCount
var getSkuCount = function() {
pool.getConnection(function(err, connection) {
connection.query("select count(sku) from products_per_store where store_id = " + sID + " group by store_id", function (err, record) {
if (err) {
console.error('DATABASE ERROR:', err);
}
return record
connection.release();
});
});
};
var getAssetCount = function () {
console.log("getting total of scrapers attached to " + store_id);
pool.getConnection(function(err, connection) {
connection.query("SELECT count(*) FROM external_crawl_settings WHERE store_id = " + sID + " group by store_id", function (err, record) {
if (err) {
console.log(err);
return console.error('DATABASE ERROR:', err);
}
connection.release();
});
});
}
var skuCount = getSkuCount();
var assetCount = getAssetCount();
if skuCount * assetCount > 50000 {
do something
};
我已经消除了全局变量
assetCount
,skuCount
,并采用了不同的方法来解决您的所有问题。此解决方案需要2个不同的文件。1个用于管理连接,1个用于整合所有路由
您需要在应用程序的index.js
或类似的服务器启动脚本中包含此内容
app server.js//服务器启动文件
'use strict';
let express = require('express');
let connectionManager = require('./connection-manager');
//read from your config file
let config = {
port: 7007,
host: 'host',
user: 'user',
password: 'password',
database: 'database',
connectionLimit: 'limit'
};
function startServer(config) {
let application = require('../'); // your application with all the routes
server = http.createServer(application);
return new Promise((resolve, reject) => {
server.listen(config.port, ()=> {
return resolve();
}).on('error', (err)=> {
return reject(err);
});
});
}
connectionManager.init(config).then(()=> {
return startServer(config);
}).then(()=> {
console.log(`server is up at ${config.port}`);
}).catch((err) => {
console.log('err while starting server', err.stack);
});
连接管理器.js//连接管理器
'use strict';
let mysql = require('promise-mysql');
let connectionPool;
class Connections {
static init(config) {
return mysql.createPool({
host: config.host,
user: config.user,
password: config.password,
database: config.database,
connectionLimit: config.limit
}).getConnection().then((connection)=> {
connectionPool = connection;
});
}
static getConnection() {
// you can call this across your applications
return connectionPool;
}
static releaseConnection() {
//call this only if you want to shut the application
connectionPool.close(); // or equivalent method available
}
}
module.exports = Connections;
sample.js
'use strict';
let connection = require('./connection-manager').getConnection();
function compute(sid) {
let skuCount = connection.query('select count(sku) "cnt" from products_per_store where store_id = ' + sID + ' group by store_id');
let assetCount = connection.query('SELECT count(*) "cnt" FROM external_crawl_settings WHERE store_id = ' + sID + ' group by store_id');
return Promise.all([
skuCount,
assetCount
]).then((results)=> {
let skuCount = results[0];
let assetCount = results[1];
if (skuCount * assetCount > 50000) {
//do something
}
}).catch((err) => {
console.log('DATABASE ERROR:', err.stack);
});
}
此外,您可以拥有的开放连接数量是否有限制
由于连接池为您处理连接回收,这取决于您拥有的硬件资源。但我可以建议您从默认值开始,并不断增加,直到获得所需的性能
我的slack机器人随机崩溃,我无法找出原因
您是否使用类似的流程管理器。如果是这样,只有在看到它时,才能帮助您进一步调试它。Process manager会跟踪所有异常,这些异常是您在管理应用程序时可能遇到的错误
程序是否仅在出现未捕获错误时结束
对。如果您尚未处理process.on(uncaughtException)
,process.on(unhandledRejections)
。这是一个值得出租的地方
我的机器人是否会达到连接限制并崩溃 不能说。但是,通过检查
/var/log/mysql/error.log
、日志中的错误堆栈跟踪、pm2日志,您可以获得额外的线索
如何释放连接
如果您正在使用任何连接池,则不必这样做。这是哪个数据库?您可能希望在数据库中使用promise接口,然后当您从每个请求中获得承诺时,您可以使用
promise.all()
来了解两个查询何时完成,然后您可以对两个结果进行处理。还有其他(不太理想的)选择,比如将第二个查询嵌套在第一个查询中,这样当第二个查询完成时,您就可以访问这两个结果。或者编写代码,为每个查询保留一个计数器,并有一个填充结果的位置,以便您可以在两个完成中测试cnt,以了解何时完成这两个操作。去承诺。@jfriend00承诺会是什么样子?我在服务器上安装了bluebird和bot?我很早以前就有过承诺,但我已经忘了它是如何运作的。请举例说明代码的外观,好吗?即使只是展示如何嵌套查询也会很有帮助;你肯定需要使用承诺。查看[那里有一个示例。只需复制并粘贴。然后查看[。我希望它有帮助。1.您可以使用Promise.all()
运行connection=conn
下面的两个查询。通过这种方式,您可以减少。然后()
。这也将消除全局变量skuCount
,assetCount
。2.您可以使用和单个全局连接,而不是为每个db交互创建新连接并在完成后关闭object@Sridhar你能把这个写出来吗?我会投票给你的答案。还有,开放的数量有限制吗你可以拥有连接?我的slack机器人随机崩溃,我无法找出原因。程序是否只有在出现未捕获的错误时才会结束?我的机器人是否会达到连接限制并崩溃?你如何释放连接?我一直在尝试类似的方法。我释放连接时没有承诺,但似乎无法释放我已经尽可能地更新了我的答案,以解决你所有的问题questions@Sridhar我正在获取连接。查询不是函数吗?
pool.getConnection().then(function(connection) {
let skuCount = connection.query('select count(sku) "cnt" from products_per_store where store_id = ' + sID + ' group by store_id');
let assetCount = connection.query('SELECT count(*) "cnt" FROM external_crawl_settings WHERE store_id = ' + sID + ' group by store_id');
return Promise.all([
skuCount,
assetCount
]).then((results)=> {
let skuCount = parseInt(results[0][0].cnt);
let assetCount = parseInt(results[1][0].cnt);
if (skuCount * assetCount > 50000) {
console.log('Too many inputs to run without permission');
}
console.log(skuCount*assetCount);
}).catch((err) => {
console.log('DATABASE ERROR:', err.stack);
});
}).catch(function(err) {
console.log(err);
});