Una vista rápida de los módulos de Terraform

Introducción

Los módulos en Terraform son una colección de recursos que se pueden vincular o simplemente crear individualmente. Cuando llamamos a un módulo, estamos llamando a un archivo con una serie de recursos y algunos parámetros, los cuales necesitamos especificar o bien en el propio recurso o en otro archivo que almacene nuestras variables.

¿Por qué usar Terraform?

  • Es una herramienta muy útil para desarrollar, cambiar y tener un versioning de nuestra infraestructura de manera eficiente y segura.
  • Es una herramienta que permite definir infraestructura como código y habilita cambiar y hacer un seguimiento de la infraestructura con facilidad.
  • Es independiente de la plataforma o ‘cloud agnostic’ y permite trabajar con múltiples proveedores cloud.

¿Qué necesitamos para este lab?

  • Terraform instalado. En este caso, ejecutamos la v.0.12.7.
  • En nuestro caso, utilizamos AWS como nuestro proveedor de servicios en la nube, por lo que necesitamos un usuario con acceso mediante programación. También necesitamos dar acceso a este usuario con la Política de IAM adecuada.
  • Tu editor de código preferido.

¡Empecemos!

Por lo general, primero deberíamos configurar un módulo Terraform con nuestros parámetros requeridos o simplemente obtener algún módulo oficial de la red. En nuestro caso, estamos usando un módulo propio con un Bucket S3 y su propia política y, por lo tanto, especificamos qué parámetros queremos en nuestro módulo.

resource "aws_s3_bucket" "this" {
  bucket            = var.bucket_name
  acl               = var.type_acl
  force_destroy     = var.destroy

  tags = {
    Name            = var.tag_name
  }
  versioning {
    enabled         = var.versioning
  } 
}

resource "aws_s3_bucket_policy" "this" {
  bucket = var.bucket_name
  policy = templatefile("${path.module}/templates/s3_origin_access_identity.json", {
    origin_access_identity_arn         = aws_cloudfront_origin_access_identity.this.iam_arn,
    origin_access_identity_bucket_name = var.bucket_name
  })
}

Como veis, hay algunos valores que los introducimos con variables por lo tanto, necesitaremos un fichero llamado «variables.tf» en el cuál introduciremos los valores.

En la misma carpeta que tenemos nuestro archivo “main.tf”, creamos nuestro fichero “variables.tf”:

### S3 VARIABLES

variable "bucket_name"      { }
variable "tag_name"         { }
variable "type_acl"         { }
variable "versioning"       { }
variable "destroy"          { }
variable "aliases"          { }
variable "certificate_arn"  { }

En este caso particular, puede que os preguntéis por qué estas variables no tienen ningún valor almacenado. Y la respuesta es que estamos usando un archivo principal llamado «terragrunt.hcl» el cuál almacenará todos nuestros valores cuando llamemos al módulo.

Otra cosa que puede resultar confusa es cómo especificar la política del Bucket. Podemos especificarla o bien con un archivo heredoc (EOF) o directamente con una función de Terraform llamada «templatefile».

El primer ejemplo está en la documentación oficial de Terraform, una web que os sugiero visitar para entender el verdadero poder de los módulos y sus recursos.

En nuestro caso usamos el segundo ejemplo y necesitamos que en la misma carpeta, haya otra llamada «templates» y dentro de ella, la política del Bucket como un archivo JSON.

{
    "Version": "2012-10-17",
    "Id": "PolicyForCloudFrontPrivateS3Content",
    "Statement": [
        {
            "Effect": "Allow",
            "Principal": {
                "AWS": "${origin_access_identity_arn}"
            },
            "Action": "s3:GetObject",
            "Resource": "arn:aws:s3:::${origin_access_identity_bucket_name}/*"
        }
    ]
  }

Como seguramente os habréis dado cuenta, hemos introducido varias variables ${origin_access_identity_arn} y ${origin_access_identity_bucket_name} y eso es porque así, introduciremos los valores desde fuera de esa política, desde el propio archivo ‘main.tf».

policy = templatefile("${path.module}/templates/s3_origin_access_identity.json", {
    origin_access_identity_arn         = aws_cloudfront_origin_access_identity.this.iam_arn,
    origin_access_identity_bucket_name = var.bucket_name
  })

Así, introducimos el arn llamando a otro recurso llamado «aws_cloudfront_origin_access_identity» y el nombre del bucket lo introducimos como hemos visto antes con nuestro archivo de variables.

Ahora solo necesitamos especificar el proveedor de Terraform y llamar al módulo con otro archivo que llamaremos «provider.tf» con los valores que hemos especificado:

provider "aws" {
  region     = var.region
  version    = "~> 2.0"
}

provider "aws" {
  alias  = "aws_us_east_1"
  region = "us-east-1"
}
module "s3" {
    source               = "../../../../../../modules/s3-cloudfront/"
    bucket_name          = var.bucket_name
    tag_name             = var.tag_name
    type_acl             = var.type_acl
    versioning           = var.versioning
    destroy              = var.destroy
    aliases              = var.aliases
    certificate_arn      = var.certificate_arn    
}

Y por último, desplegar nuestro módulo con los comandos terraform init, terraform plan y terraform apply.

Conclusión

En este post, hemos visto como desplegar un Bucket S3 con su respectiva política con Terraform. Os sugiero que visitéis la documentación oficial de Terraform para seguir aprendiendo sobre los módulos, recursos y sus parámetros.

También os invito a contactar con nosotros en caos de que necesitéis información acerca del mundo DevOps y no dudéis en seguir nuestro blog para descubrir otros posts útiles.

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *