Reputation: 2137
I am trying to create the cloudwatch ALARM if the average performance exceeds 5 milliseconds. I have configured an Amazon CloudWatch alarm to check the average value. But, the alarm is going into ALARM if just one data point breaches the threshold.
public static void main(String[] args) {
AWSExample aws = new AWSExample();
aws.testMethod();
}
Here is the testMethod.
public void testMethod() {
Instant start = Instant.now();
try {
try {
long myValue = (long) ((Math.random())*10000);
if(myValue>8000){
myValue = myValue - 3000;
}
Thread.sleep(myValue);
} catch(InterruptedException ex) {
Thread.currentThread().interrupt();
}
} catch (Throwable t) {
t.printStackTrace();
} finally {
Instant end = Instant.now();
Duration nano = Duration.between(start, end);
long endTime = nano.toMillis();
createMetricData(endTime);
createAnAlarm();
}
}
Method to create metric data
public void createMetricData(Long metricValue) {
final AmazonCloudWatch cw = getAmazonCloudWatch();
Dimension dimension = new Dimension().withName("UNIQUE_METHOD").withValue("testMethod");
MetricDatum datum = new MetricDatum()
.withMetricName("Method Execution Performance")
.withUnit(StandardUnit.Milliseconds).withValue(metricValue.doubleValue())
.withDimensions(dimension)
.withTimestamp(new Date());
PutMetricDataRequest metricDataRequest = new PutMetricDataRequest()
.withNamespace("METHOD/TRAFFIC").withMetricData(datum);
PutMetricDataResult response = cw.putMetricData(metricDataRequest);
System.out.println(response);
System.out.printf("Successfully put data point %f", metricValue.doubleValue());
}
Here is the method which creates the alarm.
private void createAnAlarm(){
final AmazonCloudWatch cw = getAmazonCloudWatch();
PutMetricAlarmRequest putMetricAlarmRequest = new PutMetricAlarmRequest()
.withPeriod(120)// The period, in seconds, over which the specified statistic is applied. Valid values are 10, 30, and any multiple of 60.
.withMetricName("Method Execution Performance")// The name for // the metric // associated // with the // alarm.
.withNamespace("METHOD/TRAFFIC")// The namespace for the metric // associated with the alarm. // https://docs.aws.amazon.com/AmazonCloudWatch/latest/monitoring/aws-namespaces.html
.withAlarmName("aws-Method-Performance")// The name for the alarm. // This name must be unique // within the AWS account.
.withEvaluationPeriods(1)// The number of periods over which // data is compared to the specified // threshold. An alarm's total // current evaluation period can be // no longer than one day, so this
// number multiplied by period cannot be more than 86,400 seconds.
.withActionsEnabled(true)// Indicates whether actions should be executed during any changes to
// the alarm state.
.withStatistic(Statistic.Average)// The statistic for the metric associated with the alarm, other than percentile
.withThreshold(5.0)// The value against which the specified statistic is compared.
.withComparisonOperator(ComparisonOperator.GreaterThanThreshold)
.withAlarmDescription("Alarm when method execution time exceeds 5 milliseconds")
.withAlarmActions("arn:aws:sns:eu-west-1:***********")//The actions to
//execute when this alarm transitions to the ALARM state from
// any other state. Each action is specified as an Amazon
// Resource Name (ARN).
.withUnit(StandardUnit.Milliseconds)// The unit of measure for
// the statistic
.withDimensions(new Dimension().withName("UNIQUE_METHOD").withValue("testMethod"));
PutMetricAlarmResult result = cw.putMetricAlarm(putMetricAlarmRequest);
System.out.println(result);
}
I want the average performance of the method exceeds 5 milliseconds. What is the issue here and how do I solve it?
Upvotes: 1
Views: 1535
Reputation: 12099
So the question is why is the alarm going into ALARM state if just one data point breaches the threshold? That's because you have this line in alarm creation:
.withEvaluationPeriods(1)
Also, you are calling createAnAlarm();
every time you publish a datapoint. There is no need to do that, you can create the alarm once and it will keep monitoring your metric.
As discussed in the comments, actual reason for this alarm firing is the fact that the threshold was set at 5 milliseconds but the expected execution time of the method is in the seconds range. Correct threshold to set in this case is 5 seconds:
.withThreshold(5000.0)
Upvotes: 2