Home > other >  Terraform AWS: SQS destination for Lambda doesn't get added
Terraform AWS: SQS destination for Lambda doesn't get added

Time:12-03

I have a working AWS project that I'm trying to implement in Terraform.

One of the steps requires a lambda function to query athena and return results to SQS (I am using this module for lambda instead of the original resource). Here is the code:


data "archive_file" "go_package" {
  type        = "zip"
  source_file = "./report_to_SQS_go/main"
  output_path = "./report_to_SQS_go/main.zip"
}


resource "aws_sqs_queue" "emails_queue" {
  name = "sendEmails_tf"
}

module "lambda_report_to_sqs" {
  source                 = "terraform-aws-modules/lambda/aws"
  function_name          = "report_to_SQS_Go_tf"
  handler                = "main"
  runtime                = "go1.x"
  create_package         = false
  local_existing_package = "./report_to_SQS_go/main.zip"
  attach_policy_json     = true
  policy_json = jsonencode({
    Version = "2012-10-17"
    Statement = [
      {
        Effect : "Allow"
        Action : [
          "dynamodb:*",
          "lambda:*",
          "logs:*",
          "athena:*",
          "cloudwatch:*",
          "s3:*",
          "sqs:*"
        ]
        Resource : ["*"]
      }
    ]
  })
  destination_on_success = aws_sqs_queue.emails_queue.arn
  timeout                = 200
  memory_size            = 1024
}

The code works fine and produces the desired output; however, the problem is, SQS doesn't show up as a destination (although the Queue shows up in SQS normally and can send/recieve messages).

I don't think permissions are the problem because I can add SQS destinations manually from the console successfully.

CodePudding user response:

The variable destination_on_success is only used if you also set create_async_event_config as true. Below is extracted from https://github.com/terraform-aws-modules/terraform-aws-lambda/blob/master

variables.tf

############################
# Lambda Async Event Config
############################

variable "create_async_event_config" {
  description = "Controls whether async event configuration for Lambda Function/Alias should be created"
  type        = bool
  default     = false
}

variable "create_current_version_async_event_config" {
  description = "Whether to allow async event configuration on current version of Lambda Function (this will revoke permissions from previous version because Terraform manages only current resources)"
  type        = bool
  default     = true
}

.....

variable "destination_on_failure" {
  description = "Amazon Resource Name (ARN) of the destination resource for failed asynchronous invocations"
  type        = string
  default     = null
}

variable "destination_on_success" {
  description = "Amazon Resource Name (ARN) of the destination resource for successful asynchronous invocations"
  type        = string
  default     = null
}

main.tf

resource "aws_lambda_function_event_invoke_config" "this" {
  for_each = { for k, v in local.qualifiers : k => v if v != null && local.create && var.create_function && !var.create_layer && var.create_async_event_config }

  function_name = aws_lambda_function.this[0].function_name
  qualifier     = each.key == "current_version" ? aws_lambda_function.this[0].version : null

  maximum_event_age_in_seconds = var.maximum_event_age_in_seconds
  maximum_retry_attempts       = var.maximum_retry_attempts

  dynamic "destination_config" {
    for_each = var.destination_on_failure != null || var.destination_on_success != null ? [true] : []
    content {
      dynamic "on_failure" {
        for_each = var.destination_on_failure != null ? [true] : []
        content {
          destination = var.destination_on_failure
        }
      }

      dynamic "on_success" {
        for_each = var.destination_on_success != null ? [true] : []
        content {
          destination = var.destination_on_success
        }
      }
    }
  }
}

So the destination_on_success is only used in this resource and this resources is only invoked if several conditions are met. The key one being var.create_async_event_config must be true.

You can see the example for this here https://github.com/terraform-aws-modules/terraform-aws-lambda/blob/be6cf9701071bf807cd7864fbcc751ed2552e434/examples/async/main.tf

module "lambda_function" {
  source = "../../"

  function_name = "${random_pet.this.id}-lambda-async"
  handler       = "index.lambda_handler"
  runtime       = "python3.8"
  architectures = ["arm64"]

  source_path = "${path.module}/../fixtures/python3.8-app1"

  create_async_event_config = true
  attach_async_event_policy = true

  maximum_event_age_in_seconds = 100
  maximum_retry_attempts       = 1

  destination_on_failure = aws_sns_topic.async.arn
  destination_on_success = aws_sqs_queue.async.arn
}
  • Related