Node js: How to set aws cloudwatch alarm state - alarm

Tried with below lambda function which will change the state of alarm "OnSNSFailureArm".
exports.handler = (event, context, callback) => {
var params = {
AlarmName: 'OnSNSFailureArm',
StateReason: 'Change Dynamically',
StateValue: "INSUFFICIENT_DATA"
};
cloudwatch.setAlarmState(params, function(err, data) {
if (err){
console.log(err, err.stack);
context.done();
}
else{
console.log(data);
context.done();
}
});
};

Related

Lambda not triggering codebuild to run?

I am trying to have lambda trigger a codebuild function when it hits the point within the lambda function, here is the current code im using for lamda:
console.log('Loading function');
const aws = require('aws-sdk');
const s3 = new aws.S3();
exports.handler = async (event, context) => {
const codebuild = new aws.CodeBuild();
let body = JSON.parse(event.body);
let key = body.model;
var getParams = {
Bucket: 'bucketname', // your bucket name,
Key: key + '/config/training_parameters.json' // path to the object you're looking for
}
if (key) {
const objects = await s3.listObjects({
Bucket: 'bucketname',
Prefix: key + "/data"
}).promise();
console.log(objects)
if (objects.Contents.length == 3) {
console.log("Pushing")
await s3.getObject(getParams, function(err, data) {
if (err)
console.log(err);
if (data) {
let objectData = JSON.parse(data.Body.toString('utf-8'));
const build = {
projectName: "projname",
environmentVariablesOverride: [
{
name: 'MODEL_NAME',
value: objectData.title,
type: 'PLAINTEXT',
},
]
};
console.log(objectData.title)
codebuild.startBuild(build,function(err, data){
if (err) {
console.log(err, err.stack);
}
else {
console.log(data);
}
});
console.log("Done with codebuild")
}
}).promise();
const message = {
'message': 'Execution started successfully!',
}
return {
'statusCode': 200,
'headers': {'Content-Type': 'application/json'},
'body': JSON.stringify(message)
};
}
}
};
Specifically this part should trigger it:
codebuild.startBuild(build,function(err, data){
if (err) {
console.log(err, err.stack);
}
else {
console.log(data);
}
});
But its not, it even outputs after the function? Im thinking its something to do with promises/await/async but cant find the right solution? Any help would be appreciated.
As you pointed out the problem is related to promises. Change your code like this:
const result = await codebuild.startBuild(build).promise();
And if you configured your lambda permissions for CodeBuild it should work.
You can change your s3.getObject the same way without the callback function:
const file = await s3.getObject(getParams).promise();
console.log(file.Body);

How to publish to AWS Shadow from lambda

This is the code Iam using,
var AWS = require('aws-sdk');
var iotdata = new AWS.IotData({
endpoint: '###########.iot.ap-south-1.amazonaws.com'
});
exports.handler = async (event) => {
var params = {
payload: Buffer.from('...') || 'STRING_VALUE'
encoded on your behalf */, /* required */
thingName: 'ESP32', /* required */
//shadowName: 'STRING_VALUE'
};
iotdata.updateThingShadow(params, function(err, data) {
if (err) console.log(err, err.stack); // an error occurred
else console.log(data); // successful response
});
};
I referred to this from the given link,
https://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/IotData.html#updateThingShadow-property
But I cant update my shadow.
I also dont understand in which format I should include the payload.
I am running this on AWS Lambda function in Nodejs 12.x environment. I also dont receive any errors in cloudwatch . Cloudwatch tells me execution result has succeeded? Can you help me?
I have already given permission for Lambda to updateShadow.
This the final correct code .....
var AWS = require('aws-sdk');
var iotdata = new AWS.IotData({
endpoint: '#######.iot.ap-south-1.amazonaws.com'
});
exports.handler = async (event) => {
var POST_DATA = JSON.stringify({"state":{"desired":{"state":10}}});
await new Promise((resolve, reject) => {
var params = {
payload:POST_DATA ,
thingName: 'ESP32', /* required */
//shadowName: 'STRING_VALUE'
};
iotdata.updateThingShadow(params, function(err, data) {
if (err) {
console.log(err, err.stack);
console.log("error................")// an error occurred
reject(err);
} else {
console.log(data); // successful response
resolve(data)
}
});
})
}
The issue here is that you are using the async Lambda handler. So while your updateThingShadow() call is in progress, the Lambda function completes and exits. You need to wait for that call to complete. There are two ways to do that -
Approach 1: (A simpler async-await syntax)
var AWS = require('aws-sdk');
var iotdata = new AWS.IotData({
endpoint: '###########.iot.ap-south-1.amazonaws.com'
});
exports.handler = async (event) => {
var params = {
// Define params
};
try {
const data = await iotdata.updateThingShadow(params).promise();
console.log(data);
} catch (err) {
console.log(err);
}
};
Approach 2: (If you prefer using the callback approach)
var AWS = require('aws-sdk');
var iotdata = new AWS.IotData({
endpoint: '###########.iot.ap-south-1.amazonaws.com'
});
exports.handler = async (event) => {
var params = {
// Define params
};
await new Promise((resolve, reject) => {
iotdata.updateThingShadow(params, function(err, data) {
if (err) {
console.log(err, err.stack); // an error occurred
reject(err); // End the promise with an error
} else {
console.log(data); // successful response
resolve(data); // End the promise with success
}
});
})
};

How to scan the dynamodb table form the AWS Lambda function

I am trying to scan the Dynamodb table form my following code, can anyone please guide me what is wrong here.
const AWS = require("aws-sdk");
const dynamodb = new AWS.DynamoDB({
region: "eu-west-1",
apiVersion: "2012-08-10"
});
exports.handler = async (event, callback) => {
const params = {
TableName: "job_Status"
};
dynamodb.scan(params, (err, data) => {
if (err) {
console.log(err);
callback(err);
} else {
console.log(data);
callback(null, data);
}
});
};
I have given full dynamodb access role to the function but still it gives me the null response. Any idea what can be wrong here?
Response:
I tried with dynaomClient which not working too.
const AWS = require("aws-sdk");
const db = new AWS.DynamoDB.DocumentClient({
region : 'eu-west-1'
});
exports.handler = async (event, callback) => {
const params = {
TableName: "job_Status"
};
db.scan(params, (err, data) => {
if (err) {
console.log(err);
callback(err);
} else {
console.log(data);
callback(null, data);
}
});
};
Your Lambda function is async but your code uses callbacks. By the time the callback is reached, your function has already been terminated because it ran asynchronously. I'd speculate that the null output you see is the return value from the Lambda function, not your console.log.
Replace your call to scan with the following:
try{
let results = await db.scan(params).promise()
console.log(results);
} catch(err){
console.log(err)
}
For more info, check out the AWS documentation about working with promises.

Adding CloudWatchEvents to AWS lambda function

I have 2 AWS lambda functions belonging to the same account producer and consumer function. I want the producer to schedule the consumer to run at a specified time. When I check under CloudWatch Events the events are being created but the consumer is not being triggered. I am using this link
Producer Code
var AWS = require('aws-sdk');
var cwevents = new AWS.CloudWatchEvents({apiVersion: '2015-10-07'});
var params_for_rule = {
Name: 'DEMO_EVENT',
ScheduleExpression: 'cron(0/3 * * * ? *)',
State: 'ENABLED'
};
var params_for_target = {
Rule: 'DEMO_EVENT',
Targets: [
{
Arn: 'consumer',
Id: 'default',
}
]
};
exports.handler = async (event, context, callback) => {
const response = {
statusCode: 200,
body: JSON.stringify('Hello from Lambda!'),
};
cwevents.putRule(params_for_rule, function(err, data){
if(err){
console.log("Not Working");
}
else{
console.log("Working");
cwevents.putTargets(params_for_target, function(err, data){
if(err){
console.log("Not Working");
}
else{
console.log("Working");
}
});
}
});
};
You are calling callback before the function putTargets will return.
Your callback code should be done after putTargets returns with success.
cwevents.putRule(params_for_rule, function(err, data){
if(err){
console.log("Not Working");
}
else{
console.log("Working");
cwevents.putTargets(params_for_target, function(err, data){
if(err){
console.log("Not Working");
callback(err, null);
}
else{
console.log("Working");
callback(null, response);
}
});
}
});
For the cloud Watch event to be added we need to add certain permissions using the addPermission method. Here is the
document.
Here is the sample code.
cwevents.putRule(params_for_rule, function(err, data){
if(err){
console.log("Not Working",data);
}
else{
console.log("Working",data);
lambda.addPermission(lambdaPermission, function(err, data){
if(err){
console.log(err);
}
else{
console.log(data);
cwevents.putTargets(params_for_target, function(err, data){
if(err){
console.log("Not Working",data);
}
else{
console.log("Working",data);
}
});
}
});
}
});

Calling AWSCognito signup from lambda function

I am trying to create a lambda function to create a user whenever there is an update in one of the tables of dynamo db.
I have created a dynamodb table with a trigger. I get "adminCreateUser not a function" error when i run the below code in lambda.
lambda function:
exports.handler = function(event, context) {
// TODO implement
cognitoidentityserviceprovider.adminCreateUser(params, function(err, data) {
if (err) console.log(err, err.stack); // an error occurred
else console.log(data); // successful response
});
context.done(null, 'Hello from Lambda');
};
It should be just the code below. Maybe make sure adminCreateUser is in your main AWS SDK, it was only introduced pretty recently.
const AWS = require('aws-sdk');
exports.handler = (event, context, callback) => {
AWS.config.apiVersions = {
cognitoidentityserviceprovider: '2016-04-18'
};
AWS.config.update({accessKeyId: 'akid', secretAccessKey: 'secret'});
var cognito = new AWS.CognitoIdentityServiceProvider({
region: 'us-east-1'
});
params = {};
cognito.adminCreateUser(params, function(err, data) {
if (err) console.log(err, err.stack); // an error occurred
else
console.log(data); // successful response
});
context.done(null, 'Hello from Lambda');
};