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

provider "aws" {
  region = var.aws_region

  default_tags {
    tags = module.default_tags.tags
  }
}

provider "aws" {
  alias  = "aws_us_east_1"
  region = "us-east-1"

  default_tags {
    tags = module.default_tags.tags
  }
}

provider "aws" {
  alias  = "aws_us_west_2"
  region = "us-west-2"

  default_tags {
    tags = module.default_tags.tags
  }
}

# Terraform backends cannot contain interpolations
terraform {
  backend "s3" {
    bucket  = "prod-royaltyshare-terraform-state"
    key     = "prod/gsirt-royaltyshare/terraform.tfstate"
    region  = "us-west-2"
    encrypt = "true"
  }
}

data "aws_caller_identity" "current" {}

data "aws_s3_bucket" "logging" {
  bucket = "prod-rs-s3-logs"
}

# Create the terraform state bucket
module "terraform_state_bucket" {
  source                = "git@github.com:theorchard/terraform-s3.git//modules/s3_bucket?ref=3.12.1"
  env                   = var.environment
  application_family    = var.application_family
  bucket_name           = "${var.application_family}-terraform-state"
  custom_logging_bucket = data.aws_s3_bucket.logging.bucket

  apply_server_side_encryption_by_default = {
    sse_algorithm = "AES256"
  }
}

data "aws_iam_policy_document" "gsirt_assume_role" {
  statement {
    actions = ["sts:AssumeRole"]

    principals {
      type = "AWS"
      identifiers = [
        "arn:aws:iam::797906716436:role/splunk_ec2_api_server_role",
      ]
    }
  }
}

data "aws_iam_policy_document" "gsirt_access_policy" {
  statement {
    effect = "Allow"

    actions = [
      "autoscaling:Describe*",
      "cloudfront:ListDistributions",
      "cloudwatch:Describe*",
      "cloudwatch:Get*",
      "cloudwatch:List*",
      "config:DeliverConfigSnapshot",
      "config:DescribeConfigRuleEvaluationStatus",
      "config:DescribeConfigRules",
      "config:GetComplianceDetailsByConfigRule",
      "config:GetComplianceSummaryByConfigRule",
      "ec2:DescribeAddresses",
      "ec2:DescribeImages",
      "ec2:DescribeInstances",
      "ec2:DescribeKeyPairs",
      "ec2:DescribeNetworkAcls",
      "ec2:DescribeRegions",
      "ec2:DescribeReservedInstances",
      "ec2:DescribeSecurityGroups",
      "ec2:DescribeSnapshots",
      "ec2:DescribeSubnets",
      "ec2:DescribeVolumes",
      "ec2:DescribeVpcs",
      "eks:DescribeAddon",
      "eks:DescribeAddonVersions",
      "eks:DescribeIdentityProviderConfig",
      "eks:DescribeUpdate",
      "eks:ListAddons",
      "eks:ListIdentityProviderConfigs",
      "eks:ListTagsForResource",
      "elasticloadbalancing:DescribeInstanceHealth",
      "elasticloadbalancing:DescribeListeners",
      "elasticloadbalancing:DescribeLoadBalancers",
      "elasticloadbalancing:DescribeTags",
      "elasticloadbalancing:DescribeTargetGroups",
      "elasticloadbalancing:DescribeTargetHealth",
      "iam:GetAccessKeyLastUsed",
      "iam:GetAccountPasswordPolicy",
      "iam:GetUser",
      "iam:ListAccessKeys",
      "iam:ListUsers",
      "inspector:Describe*",
      "inspector:List*",
      "kinesis:DescribeStream",
      "kinesis:ListStreams",
      "lambda:ListFunctions",
      "logs:DescribeLogGroups",
      "logs:DescribeLogStreams",
      "logs:GetLogDelivery",
      "logs:GetLogEvents",
      "logs:ListLogDeliveries",
      "network-firewall:ListTagsForResource",
      "rds:DescribeDBInstances",
      "s3:GetAccelerateConfiguration",
      "s3:GetBucketCORS",
      "s3:GetBucketLocation",
      "s3:GetBucketLogging",
      "s3:GetBucketTagging",
      "s3:GetLifecycleConfiguration",
      "s3:ListAllMyBuckets",
      "s3:ListBucket",
      "sns:Get*",
      "sns:List*",
      "sqs:GetQueueAttributes",
      "sqs:GetQueueUrl",
      "sqs:ListQueues",
    ]

    resources = [
      "*",
    ]
  }
}

data "aws_iam_policy_document" "aws_waf_logs_rs_policy_document" {
  statement {
    sid    = ""
    effect = "Allow"

    resources = [
      "arn:aws:s3:::aws-waf-logs-prod-tf-rs-bucket/*",
      "arn:aws:s3:::aws-waf-logs-prod-tf-rs-bucket",
    ]

    actions = [
      "s3:ListBucket",
      "s3:GetObject",
      "s3:GetObjectVersion",
    ]
  }

  statement {
    sid       = ""
    effect    = "Allow"
    resources = ["arn:aws:sqs:us-west-2:290365479392:prod-rs-waf-logs-queue"]

    actions = [
      "sqs:ChangeMessageVisibility",
      "sqs:GetQueueUrl",
      "sqs:ListDeadLetterSourceQueues",
      "sqs:ReceiveMessage",
      "sqs:GetQueueAttributes",
      "sqs:ListQueueTags",
      "sqs:DeleteMessage",
    ]
  }

  statement {
    sid       = ""
    effect    = "Allow"
    resources = ["*"]
    actions   = ["sqs:ListQueues"]
  }

  statement {
    sid       = ""
    effect    = "Allow"
    resources = ["arn:aws:kms:us-west-2:290365479392:key/a3fd01ea-127e-4298-b01a-aebb66f7f764"]

    actions = [
      "kms:GenerateDataKey",
      "kms:Decrypt",
    ]
  }
}

# Create policy for GSIRT AWS WAF LOGS
resource "aws_iam_policy" "gsirt_waf_logs_access_policy" {
  name   = "${var.environment}-gsirt-waf-logs-access-policy"
  policy = data.aws_iam_policy_document.aws_waf_logs_rs_policy_document.json
}

resource "aws_iam_role_policy_attachment" "gsirt_waf_logs_access_policy_attachement" {
  role       = aws_iam_role.gsirt_access_role.id
  policy_arn = aws_iam_policy.gsirt_waf_logs_access_policy.arn
}

# Role used by GSIRT
resource "aws_iam_role" "gsirt_access_role" {
  name               = "GSIRT_AWS_Monitoring_Role"
  assume_role_policy = data.aws_iam_policy_document.gsirt_assume_role.json
}

# Create policy for GSIRT
resource "aws_iam_policy" "gsirt_access_policy" {
  name   = "${var.environment}-gsirt-access-policy"
  policy = data.aws_iam_policy_document.gsirt_access_policy.json
}

resource "aws_iam_role_policy_attachment" "gsirt_access_policy_attachement" {
  role       = aws_iam_role.gsirt_access_role.id
  policy_arn = aws_iam_policy.gsirt_access_policy.arn
}

resource "aws_iam_role_policy_attachment" "security_managed_policy_attachement" {
  role       = aws_iam_role.gsirt_access_role.id
  policy_arn = "arn:aws:iam::aws:policy/SecurityAudit"
}

resource "aws_iam_role_policy_attachment" "view_only_policy_attachment" {
  role       = aws_iam_role.gsirt_access_role.id
  policy_arn = "arn:aws:iam::aws:policy/job-function/ViewOnlyAccess"
}

module "aws_config" {
  source = "git@github.com:theorchard/terraform-gsirt.git//modules/config?ref=2.3.3"
  providers = {
    aws = aws.aws_us_west_2
  }

  environment                          = var.environment
  service_name                         = var.service_name
  custom_access_logging_bucket         = "prod-rs-s3-logs"
  notification_topic_arn               = "arn:aws:sns:us-west-2:797906716436:Config-US-West-2-sns"
  create_s3_bucket                     = true
  create_iam_role                      = true

  exclude_resource_types = [
    "AWS::Config::ResourceCompliance",
    "AWS::EC2::VPC",
    "AWS::EC2::NetworkInterface",
  ]

  recording_frequency_override_resource_types = [
    "AWS::ElasticLoadBalancingV2::TargetGroup",
    "AWS::EC2::SecurityGroup",
    "AWS::EC2::Subnet",
  ]
}

data "aws_canonical_user_id" "current" {}

data "aws_cloudfront_log_delivery_canonical_user_id" "cloudfront_logs_id" {}

module "cloudfront_access_logs" {
  source = "git@github.com:theorchard/terraform-gsirt.git//modules/access_logs?ref=2.3.2"

  environment                  = var.environment
  service_name                 = var.service_name
  access_log_type              = "cloudfront"
  custom_access_logging_bucket = "prod-rs-s3-logs"

  acl_policy_grants = [
    {
      id         = data.aws_canonical_user_id.current.id
      type       = "CanonicalUser"
      permission = "FULL_CONTROL"
    },
    {
      id         = data.aws_cloudfront_log_delivery_canonical_user_id.cloudfront_logs_id.id
      type       = "CanonicalUser"
      permission = "FULL_CONTROL"
    }
  ]
}

resource "aws_iam_role_policy_attachment" "gsirt_cloudfront_access_policy_attachement" {
  role       = aws_iam_role.gsirt_access_role.id
  policy_arn = module.cloudfront_access_logs.access_logs_policy_arn
}

data "aws_iam_policy_document" "s3_access_logs_bucket_policy" {
  statement {
    sid    = "S3ServerAccessLogsPolicy"
    effect = "Allow"
    actions = [
      "s3:PutObject",
    ]

    resources = [
      "${module.s3_access_logs.access_logs_bucket_arn}/*"
    ]

    principals {
      type = "Service"
      identifiers = [
        "logging.s3.amazonaws.com"
      ]
    }

    condition {
      test     = "StringEquals"
      variable = "aws:SourceAccount"
      values = [
        data.aws_caller_identity.current.account_id
      ]
    }
  }
}

module "s3_access_logs" {
  source = "git@github.com:theorchard/terraform-gsirt.git//modules/access_logs?ref=2.3.2"

  environment             = var.environment
  service_name            = var.service_name
  access_log_type         = "s3"
  bucket_policy_overrides = [data.aws_iam_policy_document.s3_access_logs_bucket_policy.json]
}

resource "aws_iam_role_policy_attachment" "gsirt_s3_access_policy_attachement" {
  role       = aws_iam_role.gsirt_access_role.id
  policy_arn = module.s3_access_logs.access_logs_policy_arn
}

# LB logs
data "aws_elb_service_account" "current" {}

module "lb_access_logs" {
  source = "git@github.com:theorchard/terraform-gsirt.git//modules/access_logs?ref=2.3.2"

  environment                  = var.environment
  service_name                 = var.service_name
  access_log_type              = "lb"
  custom_access_logging_bucket = "prod-rs-s3-logs"
  bucket_policy_overrides      = [data.aws_iam_policy_document.lb_logs_bucket_policy_document.json]
}

data "aws_iam_policy_document" "lb_logs_bucket_policy_document" {
  statement {
    sid       = "AllowElbServiceAccount"
    effect    = "Allow"
    resources = ["${module.lb_access_logs.access_logs_bucket_arn}/*"]
    actions = [
      "s3:PutObject",
    ]

    principals {
      type = "AWS"
      identifiers = [
        data.aws_elb_service_account.current.arn,
      ]
    }
  }

  statement {
    sid       = "AWSLogDeliveryAclCheck"
    effect    = "Allow"
    resources = [module.lb_access_logs.access_logs_bucket_arn]
    actions   = ["s3:GetBucketAcl"]

    principals {
      type        = "Service"
      identifiers = ["delivery.logs.amazonaws.com"]
    }

    condition {
      test     = "StringEquals"
      variable = "aws:SourceAccount"
      values   = [data.aws_caller_identity.current.account_id]
    }

    condition {
      test     = "ArnLike"
      variable = "aws:SourceArn"
      values   = ["arn:aws:logs:*:${data.aws_caller_identity.current.account_id}:*"]
    }
  }

  statement {
    sid       = "AWSLogDeliveryWrite"
    effect    = "Allow"
    resources = ["${module.lb_access_logs.access_logs_bucket_arn}/*"]
    actions   = ["s3:PutObject"]

    principals {
      type        = "Service"
      identifiers = ["delivery.logs.amazonaws.com"]
    }

    condition {
      test     = "StringEquals"
      variable = "aws:SourceAccount"
      values   = [data.aws_caller_identity.current.account_id]
    }

    condition {
      test     = "ArnLike"
      variable = "aws:SourceArn"
      values   = ["arn:aws:logs:*:${data.aws_caller_identity.current.account_id}:*"]
    }

    condition {
      test     = "StringEquals"
      variable = "s3:x-amz-acl"
      values   = ["bucket-owner-full-control"]
    }
  }
}

resource "aws_iam_role_policy_attachment" "gsirt_lb_access_policy_attachement" {
  role       = aws_iam_role.gsirt_access_role.id
  policy_arn = module.lb_access_logs.access_logs_policy_arn
}

resource "aws_iam_role_policy_attachment" "gsirt_guardduty_access_policy_attachement" {
  role       = aws_iam_role.gsirt_access_role.id
  policy_arn = "arn:aws:iam::${data.aws_caller_identity.current.account_id}:policy/prod-rs-guardduty-access-policy"
}

module "datatheorem" {
  source = "git@github.com:theorchard/terraform-gsirt.git//modules/datatheorem?ref=2.3.2"

  environment                 = var.environment
  service_name                = "datatheorem"
  datatheorem_aws_external_id = "d+0NFcHUoNYFVL4YNs6G32Vq0Je2"
}

removed {
  from = module.sme_cloud_compliance
  lifecycle {
    destroy = false
  }
}

