我编写了一个node.js lambda函数,当新记录插入特定表时,该函数根据dynamodb流触发。
该函数仅接收新事件,插入记录的过滤器,然后对于每个记录,使用几个字段从其他表中检索数据。使用该组合数据,组成消息并通过SNS发送到特定目标ARN。
该功能正常运行。检索所有相关数据,并发送推送通知。
但是,由于某种原因,该函数似乎被多次调用同一个流,并多次处理新插入的记录。结果是目标设备多次接收相同的推送通知。
我应该将回调放在不同的地方,还是我没有正确地调用上下文?
这是功能:
'use strict';
var AWS = require("aws-sdk");
var dynamodb = new AWS.DynamoDB();
var sns = new AWS.SNS();
console.log('Loading function');
exports.handler = (event, context, callback) => {
console.log('Received event:', JSON.stringify(event, null, 2));
event.Records.forEach((record) => {
console.log(record.eventID);
console.log(record.eventName);
console.log('DynamoDB Record: %j', record.dynamodb);
if (record.eventName == 'INSERT') {
var matchId = record.dynamodb.NewImage.eventId.S;
var match_params = {
Key: {
"eventId": {
S: matchId
}
},
TableName: "xxxxxxxxxxx-mobilehub-xxxxxxx-Event"
};
//retrieve the match information from Event table
dynamodb.getItem(match_params, function(err, data) {
var match_description = "";
if (err) {
console.log(err, err.stack);
context.fail('No match event record found in Event table');
} else {
match_description = data.Item.description.S;
var uId = record.dynamodb.NewImage.participantUserId.S; //participantUserId
var user_params = {
Key: {
"userId": {
S: uId
}
},
TableName: "xxxxxxxxxxx-mobilehub-xxxxxxxxx-User"
};
//retrieve the user record from User table
dynamodb.getItem(user_params, function(err, data) {
if (err) {
console.log(err, err.stack); // an error occurred
context.fail('Error occurred. See log.');
} else {
console.log(data); // successful response
if (data.length === 0) {
console.log("No User Record Found.");
context.fail('No user found for participantUserId.');
} else {
var deviceARN = data.Item.device_arn.S;
if (deviceARN <= 1) {
console.log("User has not registered their device for push notifications.");
context.fail('User has not registered for notifications');
} else {
var json_message = JSON.stringify({
APNS_SANDBOX: JSON.stringify({
aps: {
alert: "You are playing in an upcoming match " + match_description,
badge: 1,
sound: 'default'
}
})
});
var snsparams = {
Message: json_message,
MessageStructure: 'json',
TargetArn: deviceARN
};
sns.publish(snsparams, function(err, data) {
if (err) {
console.log(err); // an error occurred
context.fail('SNS send failed. See log.');
} else {
console.log(data); // successful response
context.success('Push notification sent to user.');
}
});
}
}
}
});
}
});
}
});
callback(null, `Successfully processed ${event.Records.length} records.`);
};
答案 0 :(得分:0)
就我而言,我多次添加了相同的事件源。
与AWS支持工程师的对话中的报价:
使用我的内部工具,我注意到Lambda函数xxxxxx具有 事件来源: arn:aws:events:my_region:my_acct_id:rule / my_event_target 配置两次作为推送事件源。这意味着这可能是原因 为什么每分钟都会看到两次调用。你能不能 在您这边确认是否为$ LATEST配置了两次此事件 版本的lambda,并确认是否符合要求?
我希望这可以节省一些时间:)
答案 1 :(得分:0)
在底部的lambda页面中,尝试将“并发”未保留的帐户并发调整为1,将“异步调用”重试尝试调整为0。作为测试,请尝试这些并观察其行为。可能会有帮助。