module "default_tags" {
  source             = "git@github.com:theorchard/terraform-default-tags.git//?ref=2.0.0"
  environment        = var.environment
  application_family = var.application_family
  service_name       = var.service_name
  team_name          = var.team_name
}

provider "aws" {
  region = var.aws_region

  default_tags {
    tags = module.default_tags.tags
  }
}

provider "aws" {
  region  = var.aws_region
  alias   = "networking"
  profile = "networking"

  default_tags {
    tags = module.default_tags.tags
  }
}

# Terraform backends cannot contain interpolations
terraform {
  backend "s3" {
    bucket  = "prod-amp-terraform-state"
    key     = "prod/fivetran-proxy/terraform.tfstate"
    region  = "us-east-1"
    encrypt = "true"
  }
}

data "aws_caller_identity" "current" {}

data "aws_vpc" "vpc" {
  tags = {
    Name = "AMP-AAS-P2"
  }
}

data "aws_subnets" "fargate_service_subnets" {
  filter {
    name   = "vpc-id"
    values = [data.aws_vpc.vpc.id]
  }
  filter {
    name = "tag:Name"
    values = [
      "AMP-AAS-P2-IAPP-1A",
      "AMP-AAS-P2-IAPP-1B",
    ]
  }
}

data "aws_subnets" "lb_subnets" {
  filter {
    name   = "vpc-id"
    values = [data.aws_vpc.vpc.id]
  }
  filter {
    name = "tag:Name"
    values = [
      "AMP-AAS-P2-XDMZ-1A",
      "AMP-AAS-P2-XDMZ-1B",
    ]
  }
}

module "fargate_environment" {
  source = "git@github.com:theorchard/terraform-fargate.git//?ref=6.4.3"

  providers = {
    aws.dns = aws.networking
  }

  environment                     = var.environment
  service_name                    = var.service_name
  application_family              = var.application_family
  secrets_manager_service_name    = var.service_name
  non_ecr_image                   = "086679231553.dkr.ecr.us-east-1.amazonaws.com/docker-ssh-proxy:latest"
  datadog_custom_image            = "086679231553.dkr.ecr.us-east-1.amazonaws.com/orchard-datadog-agent:latest"
  fluentbit_custom_image          = "086679231553.dkr.ecr.us-east-1.amazonaws.com/orchard-fluent-bit:latest"
  aws_region                      = var.aws_region
  commit_sha                      = "latest"
  container_port                  = "2222"
  task_type                       = "worker"
  health_check_command            = "echo 'fivetran proxy'"
  desired_task_count              = 2
  task_cpu                        = 1024
  task_memory                     = 2048
  maximum_capacity                = 2
  minimum_capacity                = 2
  vpc_id                          = data.aws_vpc.vpc.id
  additional_lb_target_group_arns = [aws_lb_target_group.fivetran_proxy_ecs_nlb_tg.arn]
  splitio_enabled                 = false
  ows_machine_to_machine_enabled  = false

  fargate_service_subnets = data.aws_subnets.fargate_service_subnets.ids

  environment_variables = [
    {
      Environment = var.environment
    },
    {
      SERVICE_NAME = var.service_name
    },
    {
      PERMIT_DB_HOST = join(" ", var.permit_db_hosts)
    },
    {
      PROXY_USER = "fivetran"
    },
  ]
}

resource "aws_security_group" "fivetran_proxy_ecs_nlb_sg" {
  name        = "fivetran-proxy-ecs-nlb-sg"
  description = "Security group for Fivetran Proxy ECS NLB"
  vpc_id      = data.aws_vpc.vpc.id

  ingress {
    description = "Allow all inbound traffic from the VPC"
    from_port   = 2222
    to_port     = 2222
    protocol    = "tcp"
    cidr_blocks = [
      "3.67.81.32/29", # Fivetran AWS eu-central-1 Block
    ]
  }

  egress {
    description = "Allow outbound traffic"
    from_port   = 2222
    to_port     = 2222
    protocol    = "tcp"
    cidr_blocks = [
      "0.0.0.0/0",
    ]
  }
}

resource "aws_security_group_rule" "fivetran_proxy_task_allow_inbound_from_nlb" {
  type                     = "ingress"
  from_port                = 2222
  to_port                  = 2222
  protocol                 = "tcp"
  source_security_group_id = aws_security_group.fivetran_proxy_ecs_nlb_sg.id
  security_group_id        = module.fargate_environment.fargate_security_group_id
}

resource "aws_lb" "fivetran_proxy_ecs_nlb" {
  name               = "fivetran-proxy"
  internal           = false
  load_balancer_type = "network"
  security_groups    = [aws_security_group.fivetran_proxy_ecs_nlb_sg.id]
  subnets            = data.aws_subnets.lb_subnets.ids

  enable_cross_zone_load_balancing = true

  access_logs {
    enabled = true
    bucket  = "shared-orcd-lb-logs-${var.aws_region}"
    prefix  = "${data.aws_caller_identity.current.account_id}/${var.environment}-${var.service_name}"
  }

  tags = local.tags
}

resource "aws_lb_listener" "fivetran_proxy_ecs_nlb_listener" {
  load_balancer_arn = aws_lb.fivetran_proxy_ecs_nlb.arn
  port              = 2222
  protocol          = "TCP"

  default_action {
    type             = "forward"
    target_group_arn = aws_lb_target_group.fivetran_proxy_ecs_nlb_tg.arn
  }

  tags = local.tags
}

resource "aws_lb_target_group" "fivetran_proxy_ecs_nlb_tg" {
  name        = "fivetran-proxy"
  port        = 2222
  protocol    = "TCP"
  vpc_id      = data.aws_vpc.vpc.id
  target_type = "ip"

  health_check {
    healthy_threshold   = 3
    unhealthy_threshold = 3
    interval            = 10
    port                = "traffic-port"
    protocol            = "TCP"
  }

  deregistration_delay = "300"

  tags = local.tags
}

module "fargate_service_dashboard" {
  source                            = "git@github.com:theorchard/terraform-datadog.git//modules/service?ref=6.15.3"
  environment                       = var.environment
  environment_type                  = "fargate"
  service_name                      = var.service_name
  application_family                = var.application_family
  service_4xx_monitor_enabled       = false
  service_5xx_monitor_enabled       = false
  notification_endpoints            = "@slack-devops-internal-alerts"
  escalation_notification_endpoints = "@slack-devops-internal-alerts"
}

module "fivetran_proxy_secrets_manager" {
  source   = "git@github.com:theorchard/terraform-secrets-manager.git//?ref=1.5.1"
  for_each = toset(var.sshd_host_fingerprints_secret_names)

  application_family = var.application_family
  environment        = var.environment
  service_name       = var.service_name
  secret_name        = each.value
}
