带有 Lambda 的蓝鸟不返回数据
Bluebird with Lambda not returning data
我们有一个简单的查询,可以使用部署在 nodejs 上的无服务器应用程序从我们的数据库中获取信息。不幸的是,我无法从 Bluebird promise 那里得到任何回应——回应总是超时,我不确定是什么导致了这个问题。以下是我的文件:
serverless.yml:
service: myAuth0
provider:
name: aws
iamRoleARN: arn:aws:iam::XXXXXXXXX:role/test-role
runtime: nodejs4.3
stage: production
region: us-us-1
iamRoleStatements:
- Effect: "Allow"
Action:
- "ec2:CreateNetworkInterface"
- "ec2:DescribeNetworkInterfaces"
- "ec2:DeleteNetworkInterface"
Resource: "*"
vpc:
securityGroupIds:
- ${self:custom.${opt:stage, self:provider.stage}.${opt:region, self:provider.region}.vpc.securitygroup}
subnetIds:
- ${self:custom.${opt:stage, self:provider.stage}.${opt:region, self:provider.region}.vpc.subnet1}
- ${self:custom.${opt:stage, self:provider.stage}.${opt:region, self:provider.region}.vpc.subnet2}
custom:
production:
us-east-1:
vpc:
subnet1: subnet-11111111
subnet2: subnet-22222222
securitygroup: sg-33333333
functions:
getUserRoles:
handler: app/handler.handle
events:
- http:
method: get
path: userstest/roles
handler.js:
'use strict';
require('dotenv').config();
var Promise = require('bluebird');
var getConn = require('./dbConn');
module.exports.handle = (event, context, callback) => {
Promise.using(getConn(), function(conn){
return conn.query('select ert.name from emp_roles ert order by ert.name').then(function(rows){
let roles = [];
rows.forEach(function(row){
roles.push(row.name);
});
return roles;
}).catch(function(err){
console.log(error);
});
}).then(function(roles){
console.log("found roles: " + roles);
callback(null, {roles: roles});
});
};
dbConn.js:
var mysql = require('promise-mysql');
var pool = mysql.createPool({
connectionLimit: 10,
host : process.env.MYSQL_HOST,
user : process.env.MYSQL_USER,
password : process.env.MYSQL_PW,
database : process.env.MYSQL_DB
});
function getConn() {
return pool.getConnection().disposer(function(connection) {
pool.releaseConnection(connection);
});
}
module.exports = getConn;
我添加了控制台日志条目,我可以看到它完成了它们...但是它没有 return 任何东西,我最终遇到连接错误。我看到数据已获取,Lambda 只是坐在那里 6 秒,没有 returning 任何东西。以下是来自云观察的最新条目:
18:15:01 START RequestId: 195a7218-a516-11e6-b52d-5f028bb2bdf6
Version: $LATEST 18:15:01 2016-11-07T18:15:01.820Z
195a7218-a516-11e6-b52d-5f028bb2bdf6 found roles: 9 18:15:07 END
RequestId: 195a7218-a516-11e6-b52d-5f028bb2bdf6 18:15:07 REPORT
RequestId: 195a7218-a516-11e6-b52d-5f028bb2bdf6 Duration: 6002.14 ms
Billed Duration: 6000 ms Memory Size: 1024 MB Max Memory Used: 18 MB
18:15:07 2016-11-07T18:15:07.468Z 195a7218-a516-11e6-b52d-5f028bb2bdf6
Task timed out after 6.00 seconds
将 Bluebird 与 Lambda 结合使用时是否出现问题?
Bluebird 绝对有效。
我认为使用处理器结束连接可能有问题。我使用 postgresql promise 库所以不能真正尝试使用 mysql 但我重写它以使用处理器并且我得到相同的超时。
尝试在 finally 块中结束连接。
db.getConnection()
.then(doMyQuery)
.catch(catchErrors)
.finally(db.disposeConnection)
编辑:好的,实际上释放连接在 lambda 中是不好的,你应该结束它们。 mysqljs 文档说:
When you are done with a connection, just call connection.release()
and the connection will return to the pool, ready to be used again by
someone else.
你真的不想要那个。这就是你超时的原因。当您的承诺链结束时,连接 returns 到池和 WAITS 将再次使用,因此 lambda 超时,因为它永远不会结束。
使用connection.end() 或connection.destroy()
关于已接受答案的注释:
不建议使用 finally 块释放数据库连接。如果 promise 链的生命周期出现问题,可能 finally
不会被调用,从而导致资源泄漏。这记录在蓝鸟文档中:http://bluebirdjs.com/docs/api/resource-management.html
我们有一个简单的查询,可以使用部署在 nodejs 上的无服务器应用程序从我们的数据库中获取信息。不幸的是,我无法从 Bluebird promise 那里得到任何回应——回应总是超时,我不确定是什么导致了这个问题。以下是我的文件:
serverless.yml:
service: myAuth0
provider:
name: aws
iamRoleARN: arn:aws:iam::XXXXXXXXX:role/test-role
runtime: nodejs4.3
stage: production
region: us-us-1
iamRoleStatements:
- Effect: "Allow"
Action:
- "ec2:CreateNetworkInterface"
- "ec2:DescribeNetworkInterfaces"
- "ec2:DeleteNetworkInterface"
Resource: "*"
vpc:
securityGroupIds:
- ${self:custom.${opt:stage, self:provider.stage}.${opt:region, self:provider.region}.vpc.securitygroup}
subnetIds:
- ${self:custom.${opt:stage, self:provider.stage}.${opt:region, self:provider.region}.vpc.subnet1}
- ${self:custom.${opt:stage, self:provider.stage}.${opt:region, self:provider.region}.vpc.subnet2}
custom:
production:
us-east-1:
vpc:
subnet1: subnet-11111111
subnet2: subnet-22222222
securitygroup: sg-33333333
functions:
getUserRoles:
handler: app/handler.handle
events:
- http:
method: get
path: userstest/roles
handler.js:
'use strict';
require('dotenv').config();
var Promise = require('bluebird');
var getConn = require('./dbConn');
module.exports.handle = (event, context, callback) => {
Promise.using(getConn(), function(conn){
return conn.query('select ert.name from emp_roles ert order by ert.name').then(function(rows){
let roles = [];
rows.forEach(function(row){
roles.push(row.name);
});
return roles;
}).catch(function(err){
console.log(error);
});
}).then(function(roles){
console.log("found roles: " + roles);
callback(null, {roles: roles});
});
};
dbConn.js:
var mysql = require('promise-mysql');
var pool = mysql.createPool({
connectionLimit: 10,
host : process.env.MYSQL_HOST,
user : process.env.MYSQL_USER,
password : process.env.MYSQL_PW,
database : process.env.MYSQL_DB
});
function getConn() {
return pool.getConnection().disposer(function(connection) {
pool.releaseConnection(connection);
});
}
module.exports = getConn;
我添加了控制台日志条目,我可以看到它完成了它们...但是它没有 return 任何东西,我最终遇到连接错误。我看到数据已获取,Lambda 只是坐在那里 6 秒,没有 returning 任何东西。以下是来自云观察的最新条目:
18:15:01 START RequestId: 195a7218-a516-11e6-b52d-5f028bb2bdf6 Version: $LATEST 18:15:01 2016-11-07T18:15:01.820Z 195a7218-a516-11e6-b52d-5f028bb2bdf6 found roles: 9 18:15:07 END RequestId: 195a7218-a516-11e6-b52d-5f028bb2bdf6 18:15:07 REPORT RequestId: 195a7218-a516-11e6-b52d-5f028bb2bdf6 Duration: 6002.14 ms Billed Duration: 6000 ms Memory Size: 1024 MB Max Memory Used: 18 MB 18:15:07 2016-11-07T18:15:07.468Z 195a7218-a516-11e6-b52d-5f028bb2bdf6 Task timed out after 6.00 seconds
将 Bluebird 与 Lambda 结合使用时是否出现问题?
Bluebird 绝对有效。
我认为使用处理器结束连接可能有问题。我使用 postgresql promise 库所以不能真正尝试使用 mysql 但我重写它以使用处理器并且我得到相同的超时。
尝试在 finally 块中结束连接。
db.getConnection()
.then(doMyQuery)
.catch(catchErrors)
.finally(db.disposeConnection)
编辑:好的,实际上释放连接在 lambda 中是不好的,你应该结束它们。 mysqljs 文档说:
When you are done with a connection, just call connection.release() and the connection will return to the pool, ready to be used again by someone else.
你真的不想要那个。这就是你超时的原因。当您的承诺链结束时,连接 returns 到池和 WAITS 将再次使用,因此 lambda 超时,因为它永远不会结束。
使用connection.end() 或connection.destroy()
关于已接受答案的注释:
不建议使用 finally 块释放数据库连接。如果 promise 链的生命周期出现问题,可能 finally
不会被调用,从而导致资源泄漏。这记录在蓝鸟文档中:http://bluebirdjs.com/docs/api/resource-management.html