From 3c136de186b153a767d304d501b7da4183a87ede Mon Sep 17 00:00:00 2001
From: Adar Nimrod <nimrod@shore.co.il>
Date: Sat, 9 Apr 2022 19:45:00 +0300
Subject: [PATCH] Scaffolding for AWS infra.

---
 .gitignore                        |   3 +
 .gitlab-ci.yml                    |  25 +++++
 Terraform/AWS/.terraform.lock.hcl |  22 +++++
 Terraform/AWS/main.tf             | 152 ++++++++++++++++++++++++++++++
 4 files changed, 202 insertions(+)
 create mode 100644 Terraform/AWS/.terraform.lock.hcl
 create mode 100644 Terraform/AWS/main.tf

diff --git a/.gitignore b/.gitignore
index 8568394..3377d94 100644
--- a/.gitignore
+++ b/.gitignore
@@ -49,8 +49,11 @@ dist/
 *.env
 .bundle/
 !Pipfile.lock
+!pdm.lock
+!Gemfile.lock
 .terraform
 .terraform.*
+!.terraform.lock.hcl
 tfplan
 *.tfstate*
 *.venv
diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml
index 833e902..8d09add 100644
--- a/.gitlab-ci.yml
+++ b/.gitlab-ci.yml
@@ -2,3 +2,28 @@
 include:
   - project: shore/ci-stuff
     file: templates/pre-commit.yml
+  - project: shore/ci-stuff
+    file: templates/terraform.yml
+
+default:
+  before_script:
+    - apt-get update
+    - apt-get install -y terraform
+
+AWS Terraform plan:
+  extends: .tf_plan
+  stage: test
+  #rules: &aws_tf_rules
+  #  - changes:
+  #      - ${TF_ROOT}/
+  variables: &aws_tf_vars
+    TF_ROOT: Terraform/AWS
+
+AWS Terraform apply:
+  extends: .tf_apply
+  stage: deploy
+  #rules: *aws_tf_rules
+  needs:
+    - job: AWS Terraform plan
+      artifacts: true
+  variables: *aws_tf_vars
diff --git a/Terraform/AWS/.terraform.lock.hcl b/Terraform/AWS/.terraform.lock.hcl
new file mode 100644
index 0000000..c6c8a13
--- /dev/null
+++ b/Terraform/AWS/.terraform.lock.hcl
@@ -0,0 +1,22 @@
+# This file is maintained automatically by "terraform init".
+# Manual edits may be lost in future updates.
+
+provider "registry.terraform.io/hashicorp/aws" {
+  version     = "4.9.0"
+  constraints = "~> 4.0"
+  hashes = [
+    "h1:GtmIOZMkKmr9tMLWouHWiGXmKEL/diOTNar5XfOVLjs=",
+    "zh:084b83aef3335ad4f5e4b8323c6fe43c1ff55e17a7647c6a5cad6af519f72b42",
+    "zh:132e47ce69f14de4523b84b213cedf7173398acda14245b1ffe7747aac50f050",
+    "zh:2068baef7dfce3613f3b4f27314175e971f8db68d9cde9ec30b5659f80c68c6c",
+    "zh:63c6f489683d5f1ac55e82a0df387143ed22701d5f22c109a4d5c9924dd4e437",
+    "zh:8115fd21965954fa4568c09331e05bb29da967fab8d077419aed09954378e216",
+    "zh:8efdc95fde108f777ed9c79ae25dc17aea9771903250f5c5c8a4c726b90a345f",
+    "zh:9b12af85486a96aedd8d7984b0ff811a4b42e3d88dad1a3fb4c0b580d04fa425",
+    "zh:9d42a7bc34d84b70c1d1bcc215cabd63abbcbd0352b70bd84da6c3916634932f",
+    "zh:aacbcceb241aa475888c0869e87593182edeced3170c76a0c960dd9c905df449",
+    "zh:c7fe7904511052e4102870256819a1917177572cf684f0611ebf767f9c1fbaa8",
+    "zh:c8e07c3424663d1d0e7e32f4ade8099c19f6326d37c6da98104d90c986ff66fc",
+    "zh:e47cafbd38b56ef14fd8d727b4ffea847c166b1c684f585ee5fb78983b537248",
+  ]
+}
diff --git a/Terraform/AWS/main.tf b/Terraform/AWS/main.tf
new file mode 100644
index 0000000..128ca23
--- /dev/null
+++ b/Terraform/AWS/main.tf
@@ -0,0 +1,152 @@
+terraform {
+  backend "http" {}
+  required_providers {
+    aws = {
+      source  = "hashicorp/aws"
+      version = "~> 4.0"
+    }
+  }
+}
+
+locals {
+  env     = terraform.workspace == "default" ? "prod" : terraform.workspace
+  module  = basename(abspath(path.root))
+  name    = "${local.project}-${local.module}-${local.env}"
+  project = "homelab"
+  common_tags = {
+    Environment = local.env
+    Module      = local.module
+    Name        = local.name
+    Project     = local.project
+  }
+}
+
+output "env" {
+  description = "Environment (prod/dev etc.)."
+  value       = local.env
+}
+
+output "module" {
+  description = "The name of the Terraform module, used to tagging resources."
+  value       = local.module
+}
+
+output "project" {
+  description = "The name of the Git project, used to tagging resources."
+  value       = local.project
+}
+
+variable "region" {
+  default     = "us-east-1"
+  description = "AWS region."
+  type        = string
+}
+
+output "region" {
+  description = "AWS region."
+  value       = var.region
+}
+
+provider "aws" {
+  region = var.region
+  default_tags {
+    tags = local.common_tags
+  }
+}
+
+data "aws_caller_identity" "current" {}
+
+locals {
+  account_id = data.aws_caller_identity.current.account_id
+}
+
+output "account_id" {
+  description = "The AWS account ID."
+  value       = local.account_id
+}
+
+data "aws_iam_policy_document" "ec2_assume_policy" {
+  statement {
+    effect  = "Allow"
+    actions = ["sts:AssumeRole"]
+
+    principals {
+      type        = "Service"
+      identifiers = ["ec2.amazonaws.com"]
+    }
+  }
+}
+
+locals {
+  ec2_assume_policy = data.aws_iam_policy_document.ec2_assume_policy.json
+}
+
+output "ec2_assume_policy" {
+  value       = local.ec2_assume_policy
+  description = "IAM policy document for EC2 instance assuming a role."
+}
+
+data "aws_iam_policy_document" "task_assume_policy" {
+  statement {
+    effect  = "Allow"
+    actions = ["sts:AssumeRole"]
+
+    principals {
+      type        = "Service"
+      identifiers = ["ecs-tasks.amazonaws.com"]
+    }
+  }
+}
+
+locals {
+  task_assume_policy = data.aws_iam_policy_document.task_assume_policy.json
+}
+
+output "task_assume_policy" {
+  description = "IAM policy document for ECS tasks assuming a role."
+  value       = local.task_assume_policy
+}
+
+locals {
+  resource_group_query = {
+    ResourceTypeFilters = [
+      "AWS::AllSupported",
+    ]
+    TagFilters = [
+      {
+        Key    = "Environment"
+        Values = [local.env, ]
+      },
+      {
+        Key    = "Module"
+        Values = [local.module, ]
+      },
+      {
+        Key    = "Project"
+        Values = [local.project, ]
+      },
+    ]
+  }
+}
+
+resource "aws_resourcegroups_group" "group" {
+  name = local.name
+  resource_query {
+    query = jsonencode(local.resource_group_query)
+  }
+}
+
+locals {
+  resource_group_arn  = aws_resourcegroups_group.group.arn
+  resource_group_name = aws_resourcegroups_group.group.name
+}
+
+output "resource_group_arn" {
+  description = "ARN of the resource group."
+  value       = local.resource_group_arn
+}
+
+output "resource_group_name" {
+  description = "Name of the resource group."
+  value       = local.resource_group_name
+}
-- 
GitLab