terraform {
  backend "s3" {
    bucket                  = "prod-dna-tfstate"
    key                     = "Apollo/Production/deploy.tfstate"
    region                  = "us-east-1"
    shared_credentials_file = "~/.aws/credentials"
    profile                 = "gdb-delphi-prod"
    dynamodb_table          = "terraform-state-lock-dynamodb"
  }
}

provider "aws" {
  profile = var.aws_profile
  region  = var.aws_region_id

  default_tags {
    tags = {
      platform           = var.platform.name
      environment        = var.platform.environment
      platform_with_env  = "${var.platform.name} ${var.platform.environment}"
      managed_by         = "Terraform"
      application_family = "apollo"
    }
  }
}

provider "aws" {
  alias   = "gdb-apollo-dev"
  profile = "gdb-apollo-dev"
  region  = var.aws_region_id

  default_tags {
    tags = {
      platform           = var.platform.name
      environment        = var.platform.environment
      platform_with_env  = "${var.platform.name} ${var.platform.environment}"
      managed_by         = "Terraform"
      application_family = "apollo"
    }
  }
}

provider "aws" {
  alias   = "gdb-apollo-prod"
  profile = "gdb-apollo-prod"
  region  = var.aws_region_id

  default_tags {
    tags = {
      platform           = var.platform.name
      environment        = var.platform.environment
      platform_with_env  = "${var.platform.name} ${var.platform.environment}"
      managed_by         = "Terraform"
      application_family = "apollo"
    }
  }
}

provider "aws" {
  alias   = "gdb-delphi-dev"
  profile = "gdb-delphi-dev"
  region  = var.aws_region_id

  default_tags {
    tags = {
      platform           = var.platform.name
      environment        = var.platform.environment
      platform_with_env  = "${var.platform.name} ${var.platform.environment}"
      managed_by         = "Terraform"
      application_family = "apollo"
    }
  }
}

locals {
  env_prefix          = lower(var.platform.prefix)
  project_group       = lower(var.platform.name)
  name_prefix         = "${local.env_prefix}-${local.project_group}"
  account_id          = data.aws_caller_identity.current.account_id
  account_alias       = data.aws_iam_account_alias.current.account_alias
  policy_base_arn     = "arn:aws:iam::${local.account_id}:policy/${local.name_prefix}"
  environment         = lower(var.platform["environment"])
  secrets_name_prefix = "${local.project_group}/${local.env_prefix}"
  aggregated_tag      = "${var.platform.short_platform_name}_${upper(var.platform.prefix)}"

  docker_image_env_tag = {
    dev   = "develop",
    qa    = "qa",
    stage = "release",
    uat   = "uat",
    prod  = "master",
  }

  common_tags = {}
}

# The attribute `${data.aws_caller_identity.current.account_id}` will be current account number.
data "aws_caller_identity" "current" {}

data "aws_iam_account_alias" "current" {}

data "aws_vpc" "main" {
  tags = {
    Name = "${local.name_prefix}-vpc"
  }
}

data "aws_subnets" "public_subnets" {
  filter {
    name   = "vpc-id"
    values = [data.aws_vpc.main.id]
  }

  tags = {
    Name = "${local.name_prefix}-subnet-public-0*"
  }
}

data "aws_subnets" "private_subnets" {
  filter {
    name   = "vpc-id"
    values = [data.aws_vpc.main.id]
  }

  tags = {
    Name = "${local.name_prefix}-subnet-private-0*"
  }
}

data "aws_subnets" "private_db_subnets" {
  filter {
    name   = "vpc-id"
    values = [data.aws_vpc.main.id]
  }

  tags = {
    Name = "${local.name_prefix}-subnet-private-db-0*"
  }
}

data "aws_security_group" "main" {
  tags = {
    Name = "${local.name_prefix}-sg-ecs"
  }
}

data "aws_iam_role" "standard_exec" {
  name = "${local.name_prefix}-ecs_task_execution_role"
}

data "aws_ecs_cluster" "main" {
  cluster_name = "${local.name_prefix}-clu"
}

# Load balancers
data "aws_lb" "external_alb" {
  name = "${local.name_prefix}-alb-external"
}

data "aws_lb_listener" "external_https_listener" {
  load_balancer_arn = data.aws_lb.external_alb.arn
  port              = 443
}

data "aws_lb_listener" "external_http_listener" {
  load_balancer_arn = data.aws_lb.external_alb.arn
  port              = 80
}

data "aws_route53_zone" "apollo_stream_zone" {
  provider     = aws.gdb-delphi-dev
  name         = "apollo.stream."
  private_zone = false
}

data "aws_s3_bucket" "logs" {
  bucket = "security-${local.account_id}-logs"
}

data "aws_iam_policy" "secrets-services-ro" {
  arn = "${local.policy_base_arn}-secrets-services-ro"
}

data "aws_iam_policy" "scheduling_policy" {
  arn = "${local.policy_base_arn}-scheduling"
}

data "aws_iam_policy" "logging_policy" {
  arn = "${local.policy_base_arn}-logging"
}

data "aws_iam_policy" "push_notifications_consumer_policy" {
  arn = "${local.policy_base_arn}-push-notifications-consumer"
}

data "aws_iam_policy" "push_notifications_producer_policy" {
  arn = "${local.policy_base_arn}-push-notifications-producer"
}

data "aws_iam_policy" "track_visit_consumer_policy" {
  arn = "${local.policy_base_arn}-track-visit-consumer"
}

data "aws_iam_policy" "track_visit_producer_policy" {
  arn = "${local.policy_base_arn}-track-visit-producer"
}

data "aws_iam_policy" "auth0_log_ids_bucket_rw_policy" {
  arn = "${local.policy_base_arn}-auth0-log-ids-rw"
}

data "aws_iam_policy" "hot_hits_history_rw" {
  arn = "${local.policy_base_arn}-hot_hits_history_rw"
}

resource "aws_cloudwatch_log_group" "datadog-agent" {
  name = "/ecs/${local.name_prefix}-datadog-agent"
  tags = merge(
    local.common_tags,
    {
      project                  = "Infrastructure",
      service                  = "ECS",
      plat_env_project_service = "${local.aggregated_tag}_INFRA_ECS"
    }
  )
}

data "aws_iam_policy_document" "run_ecs_task" {
  statement {
    actions   = ["iam:PassRole"]
    effect    = "Allow"
    resources = ["*"]
    condition {
      test     = "StringEquals"
      variable = "iam:PassedToService"
      values = [
        "ec2.amazonaws.com",
        "ecs-tasks.amazonaws.com"
      ]
    }
  }
  statement {
    actions   = ["ecs:RunTask"]
    effect    = "Allow"
    resources = ["arn:aws:ecs:*:${local.account_id}:task-definition/${local.name_prefix}*:*"]
    condition {
      test     = "ArnLike"
      variable = "ecs:cluster"
      values   = ["arn:aws:ecs:${var.aws_region_id}:${local.account_id}:cluster/${local.name_prefix}-clu"]
    }
  }
  statement {
    actions   = ["ecs:ListTasks"]
    effect    = "Allow"
    resources = ["*"]
    condition {
      test     = "ArnLike"
      variable = "ecs:cluster"
      values   = ["arn:aws:ecs:${var.aws_region_id}:${local.account_id}:cluster/${local.name_prefix}-clu"]
    }
  }
}

resource "aws_iam_policy" "run_ecs_task" {
  name        = "${local.name_prefix}-run_ecs_tasks"
  description = "Allows to run and list ECS tasks in ${local.name_prefix}-clu ECS cluster."
  policy      = data.aws_iam_policy_document.run_ecs_task.json
}

module "ecs_scheduler_role" {
  source      = "../../../modules/iam/roles/cloudwatch_role"
  name_prefix = local.name_prefix
  name        = "ecs_scheduler_role"
  common_tags = local.common_tags
  policies_list = [
    aws_iam_policy.run_ecs_task.arn
  ]
}

data "aws_kms_key" "secrets_general_key" {
  key_id = "alias/${local.env_prefix}/${local.project_group}/secrets_general"
}

data "aws_elasticache_cluster" "main" {
  cluster_id = "${local.name_prefix}-api"

  provider = aws.gdb-apollo-prod
}

module "domains" {
  source = "../../../modules/domains/apollo"
}
