【发布时间】:2015-08-24 17:43:49
【问题描述】:
我有以下 Lambda 函数代码:
console.log('Loading function');
var aws = require('aws-sdk');
var ddb = new aws.DynamoDB();
function getUser(userid) {
var q = ddb.getItem({
TableName: "Users",
Key: {
userID: { S: userid } }
}, function(err, data) {
if (err) {
console.log(err);
return err;
}
else {
console.log(data);
}
});
console.log(q);
}
exports.handler = function(event, context) {
console.log('Received event');
getUser('user1');
console.log("called DynamoDB");
context.succeed();
};
我有一个这样定义的 [Users] 表:
{
"cognitoID": { "S": "token" },
"email": { "S": "user1@domain.com" },
"password": { "S": "somepassword" },
"tos_aggreement": { "BOOL": true },
"userID": { "S": "user1" }
}
当我(从 AWS 控制台或 CLI)调用函数时,我可以在日志中看到消息,但从未调用 getItem() 的回调。
我尝试在没有回调的情况下执行 getItem(params),然后定义了完成、成功和失败的回调,但是当我执行 send() 时,甚至也不调用完整的回调。
我知道调用是异步的,我想也许 lambda 函数在查询完成之前就完成了,因此不会调用回调,但是,我在函数末尾添加了一个简单的愚蠢循环,并且调用在 3 秒后超时,根本没有调用回调。
我尝试了不同的函数 batchGetItem、getItem、listTables 和扫描。结果是一样的,没有错误,但是回调函数永远不会被调用。
我敢打赌,如果我在不使用 Lambda 的情况下查询 dynamoDB,它会得到结果,所以我真的想知道为什么这里什么都没有发生。
我为该函数创建了一个角色,并创建了一个策略,允许访问 dynamoDB 中我需要但无济于事的功能。
政策如下所示:
{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": [ "lambda:InvokeFunction" ], "Resource": "arn:aws:lambda:*:*:*" }, { "Effect": "Allow", "Action": [ "dynamodb:GetItem", "dynamodb:BatchGetItem", "dynamodb:Scan", "dynamodb:PutItem", "dynamodb:Query", "dynamodb:GetRecords", "dynamodb:ListTables" ], "Resource": "arn:aws:dynamodb:*:*:*" }, { "Action": [ "logs:*" ], "Effect": "Allow", "Resource": "*" } ] }
我在模拟器中运行了该策略,它按我想的那样工作。 有什么建议吗?
【问题讨论】:
-
您是否收到消息说进程在完成请求之前已退出?
-
不,因为我在那里有一个 context.done() 或 context.succeed() 调用。问题是 JSNode 脚本是异步的,当您调用 dynamoDB 时,由于 lambda 函数终止,它的回调可能永远不会被调用。事实上,dynamoDB 操作甚至没有时间开始。
标签: javascript node.js callback amazon-dynamodb aws-lambda