Как отправить тревогу Cloudwatch в SNS на основе фильтра метрик журнала Cloudwatch с помощью Terraform - PullRequest
0 голосов
/ 27 марта 2019

Я тестирую фильтр сигналов тревоги в облачном хранилище (точнее, проверяю, не исчерпана ли лямбда в памяти) для отправки в SNS, который затем отправляется в очередь SQS. Однако я не вижу фильтра, появившегося в логах. Настройка cloudwatch (filtered alarm) -> SNS -> SQS ->splunk

Что у меня так далеко:

resource "aws_cloudwatch_metric_alarm" "general_lambda_error" {
    depends_on = [
      "aws_cloudwatch_log_metric_filter.max_memory_time_out",
    ]   
    alarm_name                = "general_lambda_error"
    comparison_operator       = "GreaterThanOrEqualToThreshold" 
    evaluation_periods        = "1" 
    metric_name               = "Errors" 
    namespace                 = "AWS/Lambda" 
    period                    = "60" 
    statistic                 = "SampleCount" 
    threshold                 = "2"
    alarm_description         = "This metric monitors Lambda Memory Max Usage and other Errors: threshold=2"
    alarm_actions             = [ "some-arn" ]
    dimensions {
      FunctionName = "lambda-test"
      Resource = "lambda-test"
    }
}
resource "aws_cloudwatch_log_metric_filter" "max_memory_time_out" {
    name                      = "max_memory_time_out"
    pattern                   = "[report_name=\"REPORT\", 
  request_id_name=\"RequestId:\", request_id_value, duration_name=\"Duration:\", duration_value, duration_unit=\"ms\", billed_duration_name_1=\"Billed\", bill_duration_name_2=\"Duration:\", billed_duration_value, billed_duration_unit=\"ms\", memory_size_name_1=\"Memory\", memory_size_name_2=\"Size:\", memory_size_value, memory_size_unit=\"MB\", max_memory_used_name_1=\"Max\", max_memory_used_name_2=\"Memory\", max_memory_used_name_3=\"Used:\", max_memory_used_value, max_memory_used_unit=\"MB\"]"
    log_group_name            = "/aws/lambda/lambda-test"
    metric_transformation {
      name      = "SampleCount"
      namespace = "cloudwatch_filter"
      value     = "1"
    }
}

Как я могу отправить отфильтрованное сообщение? Я нашел эту ссылку , которая описывает аналогичную проблему, но решение состоит в создании лямбда-функции. Могу ли я сделать это без создания лямбда-функции?

1 Ответ

0 голосов
/ 29 марта 2019

Вот код для получения журналов Cloudwatch на S3:

resource "aws_iam_role" "cloudwatchToFirehose" {
  name               = "${var.env}-${var.name}FirehoseCWL-Role"

  assume_role_policy = <<JSON
{
  "Version": "2012-10-17",
  "Statement": [{
      "Action": "sts:AssumeRole",
      "Principal": { "Service": "logs.${var.region}.amazonaws.com"},
      "Effect": "Allow"
  }]
}
JSON
}

resource "aws_iam_policy" "cloudwatchToFirehose" {
  name   = "${var.env}-${var.name}FirehoseCWL-Policy"

  policy = <<JSON
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect":"Allow",
      "Action": [
                "firehose:DeleteDeliveryStream",
                "firehose:PutRecord",
                "firehose:PutRecordBatch",
                "firehose:UpdateDestination"
      ],
      "Resource": ["${aws_kinesis_firehose_delivery_stream.firehoseToS3.arn}"]
    }
  ]
}
JSON
}

resource "aws_iam_role_policy_attachment" "cloudwatchToFirehose" {
  role       = "${aws_iam_role.cloudwatchToFirehose.name}"
  policy_arn = "${aws_iam_policy.cloudwatchToFirehose.arn}"
}

resource "aws_iam_role" "firehoseToS3" {
  name               = "${var.env}-${var.name}FirehoseS3-Role"
  assume_role_policy = <<JSON
{
  "Version": "2012-10-17",
  "Statement": [{
      "Action": "sts:AssumeRole",
      "Principal": { "Service": "firehose.amazonaws.com"},
      "Effect": "Allow"
  }]
}
JSON

  lifecycle {
    create_before_destroy = true
  }
}

resource "aws_iam_policy" "firehoseToS3" {
  name   = "${var.env}-${var.name}FirehoseS3-Policy"
  policy = <<JSON
{
  "Version": "2012-10-17",
  "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "s3:AbortMultipartUpload",
                "s3:GetBucketLocation",
                "s3:GetObject",
                "s3:ListBucket",
                "s3:ListBucketMultipartUploads",
                "s3:PutObject",
                "s3:PutObjectAcl"
            ],
            "Resource": [
                "arn:aws:s3:::${var.logs_bucket}",
                "arn:aws:s3:::${var.logs_bucket}/*"
            ]
        },
        {
            "Effect": "Allow",
            "Action": [
                "kinesis:DescribeStream",
                "kinesis:GetShardIterator",
                "kinesis:GetRecords"
            ],
            "Resource": "${aws_kinesis_firehose_delivery_stream.firehoseToS3.arn}"
        },
        {
           "Effect": "Allow",
           "Action": [
               "kms:Decrypt",
               "kms:GenerateDataKey"
           ],
           "Resource": [
               "${var.kms_general_key}"
           ]
        },
        {
           "Effect": "Allow",
           "Action": [
               "logs:PutLogEvents"
           ],
           "Resource": [
               "arn:aws:logs:*:*:log-group:${var.org}-${var.group}-${var.environment}/Firehose:*"
           ]
        },
        {
           "Effect": "Allow",
           "Action": [
               "lambda:InvokeFunction",
               "lambda:GetFunctionConfiguration"
           ],
           "Resource": [
               "arn:aws:lambda:*:*:function:*:*"
           ]
        }
  ]
}
JSON

  lifecycle {
    create_before_destroy = true
  }
}

resource "aws_iam_role_policy_attachment" "firehoseToS3" {
  role       = "${aws_iam_role.firehoseToS3.name}"
  policy_arn = "${aws_iam_policy.firehoseToS3.arn}"
  lifecycle {
    create_before_destroy = true
  }
}

resource "aws_kinesis_firehose_delivery_stream" "firehoseToS3" {
  name        = "${var.env}-${var.name}Firehose-Stream"
  destination = "s3"

  s3_configuration {
    role_arn        = "${aws_iam_role.firehoseToS3.arn}"
    bucket_arn      = "arn:aws:s3:::${var.logs_bucket}"
    buffer_interval = "300"
    buffer_size     = "10"
    prefix          = "${var.name}"
  }
}

resource "aws_cloudwatch_log_subscription_filter" "cloudwatchToFirehose" {
  count           = "1"
  name            = "${var.env}-${var.name}Filter-Subscription"
  role_arn        = "${aws_iam_role.cloudwatchToFirehose.arn}"
  log_group_name  = "${element(var.log_groups, count.index)}"
  filter_pattern  = ""
  destination_arn = "${aws_kinesis_firehose_delivery_stream.firehoseToS3.arn}"
}
...