Introducción
Un informe nuevo no debe impedir que el equipo lea sus datos anteriores. Configurarás el control de versiones, publicarás dos informes y distinguirás las lecturas históricas de las actuales antes de limpiar deliberadamente este almacén desechable.
Usa los conocimientos sobre variables, referencias a objetos y configuraciones raíz independientes del laboratorio anterior. Este entorno nuevo proporciona únicamente las herramientas, el acceso del proveedor y un informe de referencia ajeno.
Relación con las certificaciones
| Certificación | Tarea del examen | Práctica |
|---|---|---|
| Cloud Practitioner (CLF-C02) | Tarea 3.1 | Usar definiciones de infraestructura repetibles y consultas operativas de recursos. |
| Developer – Associate (DVA-C02) | Tarea 3.3, habilidad 3.3.4 | Práctica básica de despliegue de una definición de infraestructura. |
| DevOps Engineer – Professional (DOP-C02) | Tarea 2.1 | Práctica básica de gestión de recursos mediante una definición de IaC. |
| Solutions Architect – Associate (SAA-C03) | Tarea 1.3 | Práctica básica de conservación y lectura de datos históricos de S3 antes de una limpieza deliberada. |

Publica la primera versión
En este paso, gestionarás con Terraform la configuración de control de versiones del bucket antes de publicar su primer informe.
Las versiones de objetos de S3 son copias conservadas de los datos, cada una con un ID de versión. Son distintas de las revisiones de HCL en Git y del archivo de bloqueo del proveedor de Terraform. Terraform puede configurar el control de versiones; después, S3 conserva versiones de los objetos cuando se actualizan los datos. Un plan sin cambios no demuestra por sí solo que los datos históricos sean legibles.
Entra en la configuración raíz preparada y escribe la definición del almacenamiento:
cd /home/labex/project/report-history
cat > main.tf <<'EOF'
variable "report" { type = string }
resource "aws_s3_bucket" "reports" {
bucket = "terraform-history-reports"
}
resource "aws_s3_bucket_versioning" "reports" {
bucket = aws_s3_bucket.reports.id
versioning_configuration {
status = "Enabled"
}
}
resource "aws_s3_object" "report" {
bucket = aws_s3_bucket.reports.id
key = "reports/current.csv"
content = var.report
content_type = "text/csv"
depends_on = [aws_s3_bucket_versioning.reports]
}
EOF
Ahora hay tres recursos: un bucket, su configuración de control de versiones y un objeto. El objeto ya depende del bucket mediante su referencia al ID. La declaración explícita depends_on añade el orden que no puede deducirse de esa referencia: el control de versiones debe estar habilitado antes de la primera carga.
Escribe la entrada del primer informe e inicializa:
cat > release1.tfvars <<'EOF'
report = "orders,12\n"
EOF
terraform init
terraform validate
terraform plan -var-file=release1.tfvars
Deben añadirse tres recursos. Aplica los cambios e introduce yes:
terraform apply -var-file=release1.tfvars
Consulta la configuración real y la primera versión:
aws s3api \
get-bucket-versioning \
--bucket terraform-history-reports
aws s3api \
list-object-versions \
--bucket terraform-history-reports \
--query 'Versions[].{Key:Key,VersionId:VersionId,Current:IsLatest}'
El estado es Enabled. El informe tiene un ID de versión no nulo y Current: true. AWS View muestra el objeto que se puede leer actualmente; usa la consulta de versiones para inspeccionar el historial.

Actualiza el informe y lee su historial
En este paso, publicarás bytes diferentes, leerás explícitamente la versión anterior y demostrarás que leer el historial deja sin cambios el informe actual.
Crea un segundo archivo de entradas. Conservar ambos archivos facilita comparar las versiones de datos previstas; los archivos en sí no constituyen el historial almacenado.
cat > release2.tfvars <<'EOF'
report = "orders,25\n"
EOF
terraform plan -var-file=release2.tfvars -out=update.tfplan
terraform show update.tfplan
Debe actualizarse un objeto sin sustituir el bucket. -out guarda un artefacto de plan que incluye los valores de entrada seleccionados. Aplica ese artefacto revisado; este comando no solicita confirmación porque ya has seleccionado el plan guardado:
terraform apply update.tfplan
Vuelve a listar las versiones reales:
aws s3api \
list-object-versions \
--bucket terraform-history-reports \
--query 'Versions[].{Key:Key,VersionId:VersionId,Current:IsLatest}'
Las entradas anterior y actual tienen ID de versión diferentes. Selecciona el ID del informe anterior y muéstralo. La consulta filtra por la clave del informe y por IsLatest == false; [0] elige la primera entrada anterior coincidente en el historial de dos versiones de este laboratorio.
OLD_VERSION=$(aws s3api \
list-object-versions \
--bucket terraform-history-reports \
--query 'Versions[?Key==`reports/current.csv` && IsLatest==`false`].VersionId | [0]' \
--output text)
echo "$OLD_VERSION"
CURRENT_VERSION=$(aws s3api \
head-object \
--bucket terraform-history-reports \
--key reports/current.csv \
--query VersionId \
--output text)
echo "$CURRENT_VERSION"
Descarga la versión anterior por su ID y, después, descarga la versión actual sin indicar un ID de versión:
aws s3api \
get-object \
--bucket terraform-history-reports \
--key reports/current.csv \
--version-id "$OLD_VERSION" \
old-report.csv
cat old-report.csv
aws s3api \
get-object \
--bucket terraform-history-reports \
--key reports/current.csv \
current-report.csv
cat current-report.csv
Debes ver orders,12 en el archivo anterior y orders,25 en el archivo actual. Un GET de una versión concreta lee una versión existente; no la copia sobre el objeto actual. Consulta una vez más el ID actual y compáralo con el valor de CURRENT_VERSION mostrado:
aws s3api \
head-object \
--bucket terraform-history-reports \
--key reports/current.csv \
--query VersionId \
--output text
El ID no ha cambiado. Completa la comprobación de este paso antes de eliminar ninguna versión. La comprobación lee los bytes reales anteriores y actuales y conserva ambos. Consulta el control de versiones de S3 para conocer la diferencia entre la clave de un objeto, sus versiones y los marcadores de eliminación.
Elimina deliberadamente el historial gestionado
En este paso, harás un inventario y eliminarás todas las versiones de tu bucket de informes desechable antes de eliminar los recursos de su configuración de Terraform.
Destruir infraestructura y decidir descartar el historial de informes son acciones diferentes. Normalmente no se puede eliminar un bucket con control de versiones que no esté vacío. Eliminar un objeto actual sin indicar un ID de versión puede crear un marcador de eliminación, que oculta el objeto actual mientras las versiones anteriores permanecen. Aquí eliminarás explícitamente por ID las versiones del inventario, después de haber demostrado su conservación en el paso anterior.
Crea una solicitud de eliminación a partir del listado nativo de versiones. Este laboratorio solo tiene un pequeño conjunto de versiones de informes y ningún marcador de eliminación existente; todas las versiones listadas pertenecen a tu bucket. --query transforma cada entrada en los campos Key/VersionId que acepta delete-objects.
aws s3api \
list-object-versions \
--bucket terraform-history-reports \
--query '{Objects: Versions[].{Key:Key,VersionId:VersionId}}' \
> owned-versions.json
cat owned-versions.json
Revisa que el archivo contenga únicamente versiones de terraform-history-reports. Después, elimina exactamente esas versiones. file:// indica a la AWS CLI que lea una solicitud JSON del archivo local.
aws s3api \
delete-objects \
--bucket terraform-history-reports \
--delete file://owned-versions.json
aws s3api \
list-object-versions \
--bucket terraform-history-reports
El listado obtenido correctamente no contiene entradas Versions ni DeleteMarkers. Ahora destruye los recursos de esta configuración raíz e introduce yes:
terraform destroy -var-file=release2.tfvars
Terraform actualiza primero el estado y puede detectar que el objeto ya se ha eliminado. Después elimina la configuración de control de versiones restante y el bucket vacío. Por último, inspecciona la correspondencia y la referencia conservada:
terraform state list
aws s3api \
list-buckets \
--query 'Buckets[].Name'
aws s3api \
head-object \
--bucket team-reference-reports \
--key keep.txt \
--query ContentLength
La lista del estado está vacía y solo queda el bucket de referencia del equipo. No uses este procedimiento de descarte de datos en un almacén cuyo historial deba conservarse.
Resumen
Has distinguido los cambios de configuración de las versiones de datos, habilitado el control de versiones antes de la carga, leído bytes distintos de los informes anterior y actual sin sobrescribir la versión actual y elaborado explícitamente un inventario para descartar únicamente las versiones que gestionabas.



