Skip to content

~/nube/aws-s3 $ cat 05-sincronizacion.md

  • Introducción a la nube pública
  • AWS-S3

Sincronizar y recuperar una carpeta

Comprueba cambios, recupera una copia y observa una automatización opcional.

La asociación quiere copiar una carpeta con avisos, actualizar solo lo necesario y demostrar que puede recuperar un archivo. Vas a comparar una sincronización con una copia de seguridad y a comprobar los resultados, no solo la salida del comando.

Trabaja individualmente en Debian, como alumno, con AWS CLI 2. Conserva el perfil learnerlab que utilizaste en AWS CLI: desde esta página añadirás otro llamado default con las mismas credenciales para escribir órdenes más cortas.

Añadir el perfil predeterminado sin borrar learnerlab

Section titled “Añadir el perfil predeterminado sin borrar learnerlab”

Un perfil reúne credenciales y ajustes de AWS CLI. default es el que se utiliza cuando no escribes --profile. No es otra cuenta ni concede permisos nuevos: en nuestro caso será una segunda copia del mismo acceso temporal. El perfil learnerlab seguirá funcionando para repetir los comandos de 04.

Abre tu archivo privado dentro de Debian:

Terminal window
nano "$HOME/.aws/credentials"

Conserva el bloque [learnerlab] y añade un bloque [default]. Copia en ambos los mismos tres valores vigentes del laboratorio. El archivo tendrá esta estructura; los textos de ejemplo se sustituyen solo dentro del editor, nunca en comandos ni capturas:

[learnerlab]
aws_access_key_id = CLAVE_TEMPORAL
aws_secret_access_key = SECRETO_TEMPORAL
aws_session_token = TOKEN_TEMPORAL
[default]
aws_access_key_id = CLAVE_TEMPORAL
aws_secret_access_key = SECRETO_TEMPORAL
aws_session_token = TOKEN_TEMPORAL

Si ya existe [default], revisa y actualiza ese bloque: no añadas otra sección con el mismo nombre. Si retiraste las credenciales al terminar 04 o ya caducaron, toma un juego nuevo de tres valores desde AWS Details con Learner Lab activo y rellena ambos bloques. No mezcles valores de sesiones diferentes. Guarda y cierra el editor; conserva los permisos privados:

Terminal window
chmod 600 "$HOME/.aws/credentials"

Las copias no se actualizan entre sí. Cada vez que renueves las credenciales, actualiza las tres líneas de [default] y las tres de [learnerlab]. Si solo renuevas una sección, las órdenes que utilicen la otra pueden devolver ExpiredToken.

Retira selecciones de perfil y región de la sesión, y guarda estos ajustes para default:

Terminal window
unset AWS_PROFILE AWS_DEFAULT_PROFILE AWS_REGION AWS_DEFAULT_REGION
aws configure set region us-east-1
aws configure set output json
aws configure set cli_pager ""

set region fija la región predeterminada; set output el formato de respuesta; set cli_pager "" muestra la salida directamente sin abrir un visor. Se guardan en ~/.aws/config, no contienen credenciales y no modifican los ajustes de learnerlab. Por eso, a partir de 05 no repetiremos --profile, --region ni --no-cli-pager en cada orden. Mantén las variables de credenciales retiradas como se explicó en 04; no mezcles este archivo con credenciales exportadas en la shell.

Comprueba instalación, región e identidad:

Terminal window
aws --version
aws configure get region
aws sts get-caller-identity

La región debe ser us-east-1. Revisa la identidad localmente, sin capturar ni entregar la salida. Que STS responda no demuestra permisos de S3. Si falla, revisa que [default] tenga los tres valores vigentes antes de cambiar nada en el bucket.

No necesitas conservar el bucket de CLI. En la consola crea otro bucket privado, con prefijo aws-s3-sync- y ocho letras o números aleatorios propios, en us-east-1: General purpose, Shared global namespace si aparece, ACL deshabilitadas, cuatro BPA activas, SSE-S3, versionado y Object Lock deshabilitados. No publiques datos ni actives opciones adicionales. Comprueba inventario, saldo y nombre propio.

Este será el árbol local de trabajo:

/optativa-nube/aws-s3/sync/
├── origen/
│ ├── aviso.txt
│ └── conservar.txt
├── restaurado/
├── registros/
├── scripts/
│ └── sincronizar-cron.sh (solo ampliación opcional)
└── bucket.txt (solo ampliación opcional)

Dentro de Debian crea las carpetas. Los archivos de ejemplo son ficticios y pequeños; no sincronices el directorio personal, todo el repositorio ni ~/.aws. Si ya hay trabajo de una ejecución anterior, revísalo antes de usar >, que sustituye el archivo:

Terminal window
mkdir -p /optativa-nube/aws-s3/sync/origen
mkdir -p /optativa-nube/aws-s3/sync/restaurado
mkdir -p /optativa-nube/aws-s3/sync/registros
mkdir -p /optativa-nube/aws-s3/sync/scripts
cd /optativa-nube/aws-s3/sync
printf 'Jornada de herramientas en la nube\nRevision: 1\n' > origen/aviso.txt
printf 'Documento ficticio para comprobar una recuperacion\n' > origen/conservar.txt
read -r -p 'Nombre exacto de tu bucket aws-s3-sync-: ' BUCKET
printf 'Comprueba tu destino en consola: %s\n' "$BUCKET"

Tienes también aviso.txt y conservar.txt. Antes de continuar, restaurado/ debe estar vacía y la variable debe identificar únicamente el bucket nuevo. La variable no se transmite automáticamente a otra terminal ni a cron.

sync compara origen y destino y aplica cambios en una dirección. Primero mostrarás lo previsto sin aplicarlo:

Terminal window
aws s3 sync origen/ "s3://$BUCKET/copias/" --no-follow-symlinks --dryrun

copias/ es el prefijo de los objetos de esta práctica. --no-follow-symlinks evita seguir enlaces simbólicos de la carpeta local hacia datos externos. --dryrun muestra las operaciones previstas y no carga ni borra, pero consulta AWS: necesita acceso y puede generar solicitudes con coste. No es una simulación totalmente local.

Reconoce los dos archivos antes de quitar --dryrun. No avances si aparecen archivos desconocidos o un destino diferente:

Terminal window
aws s3 sync origen/ "s3://$BUCKET/copias/" --no-follow-symlinks
aws s3 ls "s3://$BUCKET/copias/"

Comprueba en la consola las claves copias/aviso.txt y copias/conservar.txt y su clase Standard. El prefijo no cambia el nombre de tu carpeta local ni crea un disco remoto.

Repite la primera simulación sin modificar archivos. Lo esperado es que no proponga nuevas cargas. Si las propone, revisa qué cambió; no afirmes un resultado que no hayas observado.

Añade una línea al aviso; >> añade contenido y cambia su tamaño de forma deliberada:

Terminal window
printf 'Actualizacion ficticia para comprobar sync\n' >> origen/aviso.txt

Repite la simulación, identifica aviso.txt como cambio previsto y aplica la sincronización sin --dryrun. El archivo conservar.txt no ha cambiado.

sync utiliza existencia, tamaños y marcas temporales según el sentido de transferencia y las opciones. No es una comparación automática de todos los bytes. Por eso no basta con cambiar dos palabras de la misma longitud y suponer que cualquier fecha producirá el mismo resultado.

Para comprobar el contenido que acaba de guardarse, descárgalo a una copia separada:

Terminal window
aws s3 cp "s3://$BUCKET/copias/aviso.txt" restaurado/aviso.txt
diff origen/aviso.txt restaurado/aviso.txt

diff no debe mostrar diferencias. Si muestra cambios, comprueba las rutas y la descarga nueva antes de continuar.

Ya has comprobado que ambos archivos existen en S3. Retira solo el archivo local ficticio conservar.txt, que recuperarás después desde la copia remota:

Terminal window
rm -- origen/conservar.txt

Ejecuta primero la simulación normal: no debería proponer la eliminación del objeto remoto. Compárala con esta segunda simulación:

Terminal window
aws s3 sync origen/ "s3://$BUCKET/copias/" --no-follow-symlinks --delete --dryrun

--delete propone eliminar del destino lo que no existe en el origen. En esta actividad permanece unido a --dryrun: no ejecutes el borrado real. El objeto remoto conserva ahora la copia necesaria para la recuperación.

Un espejo puede propagar una eliminación; no demuestra un respaldo histórico. Esta práctica tampoco conserva automáticamente las revisiones anteriores del aviso, porque el bucket no tiene versionado.

Sin borrar ni sobrescribir el origen, sincroniza ahora en el sentido S3 → local:

Terminal window
aws s3 sync "s3://$BUCKET/copias/" restaurado/
diff origen/aviso.txt restaurado/aviso.txt
cat restaurado/conservar.txt

Debe recuperarse el aviso actualizado sin diferencias y aparecer de nuevo conservar.txt con su texto ficticio. Has probado una recuperación de la copia actual; no has demostrado recuperación ante todas las incidencias ni creado una política completa de respaldo.

Crea origen/nuevo-aviso.txt con una línea ficticia distinta. Simula y aplica su subida, recupéralo en restaurado/ y comprueba el contenido. Después explica qué dirección usarías para recuperar toda la carpeta si desapareciera el origen local. No borres toda la carpeta para demostrarlo y no utilices --delete real.

Ampliación opcional: una ejecución con cron

Section titled “Ampliación opcional: una ejecución con cron”

Si has completado la sincronización manual, puedes observar una tarea programada durante la sesión activa. Esta ampliación es opcional; no requiere mantener el equipo encendido de madrugada. Un contenedor detenido no ejecuta cron y una credencial copiada que caduca no se renueva sola.

Descarga sincronizar-cron.sh y guárdalo en optativa-nube/aws-s3/sync/scripts/ desde el anfitrión. El navegador y el explorador del anfitrión permiten hacerlo tanto en Windows como en Linux. Se verá en Debian en la ruta del árbol anterior. Si trabajas sin acceso al descargable, crea ese archivo con nano scripts/sincronizar-cron.sh y copia el código completo que sigue.

El script obtiene su carpeta a partir de su propia ubicación y solo acepta la estructura aws-s3/sync/scripts/, una carpeta origen real y un bucket con el prefijo de esta práctica. Usa el perfil predeterminado del usuario, comprueba que su región sea us-east-1, verifica autenticación y región del bucket y se detiene antes de escribir si fallan. No contiene secretos ni renueva credenciales. No ejecuta --delete y no sigue enlaces simbólicos.

#!/usr/bin/env bash
# Ejecuta con Bash; no contiene ni renueva credenciales.
set -euo pipefail
umask 077
log() {
printf '%s %s\n' "$(date -u '+%Y-%m-%dT%H:%M:%SZ')" "$1"
}
fail() {
log "ERROR: $1" >&2
exit "$2"
}
# La copia del script vive en aws-s3/sync/scripts/.
BASE_DIR="$(cd -- "$(dirname -- "${BASH_SOURCE[0]}")/.." && pwd -P)"
[[ "${BASE_DIR##*/}" == sync && "${BASE_DIR%/sync}" == */aws-s3 ]] \
|| fail 'Ubicacion del laboratorio no valida.' 2
[[ -n "${HOME:-}" && -d "$HOME/.aws" ]] \
|| fail 'Falta el directorio privado de configuracion AWS.' 2
[[ -f "$BASE_DIR/bucket.txt" && ! -L "$BASE_DIR/bucket.txt" ]] \
|| fail 'Falta bucket.txt regular dentro del laboratorio.' 2
BUCKET="$(< "$BASE_DIR/bucket.txt")"
[[ "$BUCKET" =~ ^aws-s3-sync-[a-z0-9][a-z0-9-]*[a-z0-9]$ && ${#BUCKET} -le 63 ]] \
|| fail 'Destino no permitido: debe ser el bucket propio aws-s3-sync-.' 2
[[ -d "$BASE_DIR/origen" && ! -L "$BASE_DIR/origen" ]] \
|| fail 'Falta la carpeta origen o es un enlace simbolico.' 2
AWS_BIN="$(command -v aws)" || fail 'No se encuentra AWS CLI.' 2
[[ "$AWS_BIN" == /* && -x "$AWS_BIN" ]] || fail 'AWS CLI no es un ejecutable valido.' 2
# Evita mezclar las credenciales del perfil con exports de otra practica.
unset AWS_ACCESS_KEY_ID AWS_SECRET_ACCESS_KEY AWS_SESSION_TOKEN AWS_SECURITY_TOKEN
unset AWS_PROFILE AWS_DEFAULT_PROFILE AWS_CONFIG_FILE AWS_SHARED_CREDENTIALS_FILE
unset AWS_ENDPOINT_URL AWS_ENDPOINT_URL_S3 AWS_ENDPOINT_URL_STS
unset AWS_REGION AWS_DEFAULT_REGION
export AWS_PAGER="" AWS_EC2_METADATA_DISABLED=true
REGION_CONFIGURADA="$("$AWS_BIN" configure get region 2>/dev/null)" \
|| fail 'Falta la region predeterminada de AWS CLI.' 4
[[ "$REGION_CONFIGURADA" == us-east-1 ]] || fail 'La region predeterminada debe ser us-east-1.' 4
log 'Inicio de la comprobacion y sincronizacion.'
if ! "$AWS_BIN" sts get-caller-identity >/dev/null 2>&1; then
fail 'No hay autenticacion valida; no se ha sincronizado.' 3
fi
LOCATION="$("$AWS_BIN" s3api get-bucket-location --bucket "$BUCKET" \
--query LocationConstraint --output text 2>/dev/null)" \
|| fail 'No se puede comprobar la region del destino.' 4
[[ "$LOCATION" == None ]] || fail 'El destino no es us-east-1.' 4
if ! "$AWS_BIN" s3 sync "$BASE_DIR/origen/" "s3://$BUCKET/copias/" \
--no-follow-symlinks --only-show-errors >/dev/null 2>&1; then
fail 'La sincronizacion ha fallado; revisa la orden manual.' 5
fi
log 'Sincronizacion completada sin borrado remoto.'

Prepara su configuración con el nombre propio que ya has comprobado. bucket.txt contiene un nombre de recurso, no credenciales; no lo confundas con el archivo privado del perfil:

Terminal window
cd /optativa-nube/aws-s3/sync
printf '%s\n' "$BUCKET" > bucket.txt
chmod 600 bucket.txt
bash -n scripts/sincronizar-cron.sh
bash scripts/sincronizar-cron.sh

bash -n revisa la sintaxis, no ejecuta las operaciones ni acredita acceso. La segunda orden ejecuta el script: espera los mensajes de inicio y final correcto y confirma en S3 un cambio pequeño que hayas preparado en origen. Si falla, revisa la orden manual; no programes una tarea que ya falla.

La comprobación de ubicación devuelve None para us-east-1; el script acepta ese resultado únicamente después de una consulta correcta. Rechaza otras regiones y denegaciones. El prefijo del nombre y estas guardas no sustituyen tu comprobación de que el recurso es propio.

Dentro de Debian, instala cron si falta y comprueba su servicio. No se presupone que haya systemctl en el contenedor:

Terminal window
sudo apt-get install --yes --no-install-recommends cron
sudo service cron status

Si el servicio no estaba activo, inícialo y compruébalo de nuevo:

Terminal window
sudo service cron start
sudo service cron status

Recuerda si ya estaba activo antes de la práctica. Comprueba también que eres alumno: el crontab será de ese usuario, no de root.

Terminal window
whoami
crontab -e

Si pregunta por editor, elige nano. Conserva las entradas que ya existan y añade estas dos líneas al final, en una sola línea de comando después del comentario:

# AWS-S3-PRUEBA: retirar antes de limpiar el bucket
*/5 * * * * HOME=/home/alumno PATH=/usr/local/bin:/usr/bin:/bin /bin/bash /optativa-nube/aws-s3/sync/scripts/sincronizar-cron.sh >> /optativa-nube/aws-s3/sync/registros/cron.log 2>&1

*/5 programa los minutos divisibles por cinco, no exactamente cinco minutos después de guardar. El HOME y PATH se fijan solo para esa orden y las rutas son absolutas. >> añade al registro y 2>&1 reúne salida y errores. Cron no hereda tus variables interactivas; el script lee bucket.txt y el perfil [default] privado del usuario; no depende de una variable de perfil de la sesión interactiva.

Modifica con una línea ficticia uno de los archivos de origen. Espera una ejecución y consulta el registro:

Terminal window
tail -n 10 /optativa-nube/aws-s3/sync/registros/cron.log

Sus marcas terminadas en Z están en UTC. Comprueba en S3 que el contenido se ha actualizado; un log creado sin operación correcta no demuestra sincronización. Si las credenciales vencieron, el script registra el fallo y no intenta renovarlas ni abrir Learner Lab.

Vuelve a crontab -e y elimina únicamente el comentario y la línea de AWS-S3-PRUEBA. Guarda y consulta crontab -l para comprobarlo sin modificar las demás tareas. No uses crontab -r. Antes de limpiar el bucket, comprueba que no queda la entrada ni una ejecución en curso; espera a que termine cualquier ejecución iniciada. Si arrancaste cron solo para esta prueba y no había otras tareas, puedes detener su servicio con sudo service cron stop. No pares un servicio preexistente utilizado por otros trabajos.

  1. Si hiciste cron, retira y comprueba la entrada antes de borrar datos; no dejes una tarea apuntando a un bucket que vas a eliminar.
  2. En la consola, identifica tu bucket aws-s3-sync-, vacía sus objetos, comprueba el resultado y elimínalo. No hay versiones previstas: si aparecen, revisa el procedimiento específico. Confirma su ausencia al actualizar el inventario.
  3. Retira las credenciales temporales de ambos bloques, [default] y [learnerlab], cuando termines de utilizarlas; conserva otros perfiles ajenos y los ajustes no secretos. Registra saldo o actualización pendiente y finaliza Learner Lab si termina la sesión. Sustituye el contenido del portapapeles.
  4. Conserva los textos ficticios y las comprobaciones locales si los necesitas. Sal de Debian con exit; desde el anfitrión ejecuta docker stop p00-lab y comprueba docker ps -a --filter 'name=^/p00-lab$'. Debe aparecer detenido, sin eliminarlo ni borrar la carpeta compartida.

En la bitácora común entrega esta tabla, el resultado del reto y la limpieza. Si no hiciste cron, escribe «ampliación no realizada»; no es un requisito oculto del núcleo. No adjuntes logs completos con datos ajenos ni archivos de credenciales.

Comprobación Resultado real
Primera simulación y primera carga
Simulación sin cambios
Actualización de aviso.txt y comparación descargada
Diferencia entre simulación normal y con –delete
Recuperación de conservar.txt
Reto nuevo-aviso.txt
Cron opcional: ejecución observada y entrada retirada, o no realizado
Bucket ausente y cierre

Si algo falla, distingue autenticación, permiso, ruta local y destino; no lo soluciones abriendo el bucket al público. --dryrun también puede fallar por red o permisos. Una recuperación incompleta se registra como pendiente y se repite después de resolver la causa.

Fuentes: sync, perfiles temporales, GetBucketLocation y crontab de Debian.