Saludos amigos, hace apenas unos días Veeam anunciaba de manera oficial el soporte para MinIO Immutability de manera oficial en su HCL. Esto son maravillosas noticias para que podamos probar esta funcionalidad en nuestros labs, o en caso de que estemos usando almacenamiento Linux con MinIO para producción.
En esta entrada de Blog vamos a dar el salto a la piscina y veremos: cómo instalar y configurar MinIO con Erasure Coding Enabled, Immutability, Let’s Encrypt, y por último veremos cómo configurarlo en Veeam. Como se me ha ido de las manos, os dejo un menú para moveros más rápido:
- Requerimientos de Sistema para MinIO
- Desplegar y configurar MinIO, incluyendo Immutability y Let’s Encrypt
- Configuración de Veeam Backup & Replication con Immutability
Requerimientos de Sistema para MinIO
En esta guía no vamos a tratar de desplegar MinIO en producción, ya que suele requerir unos 96GB de RAM, determinados cores, etc. En mi caso estoy desplegando todo en 4vCPU y 16GB de RAM, ya que voy a tener solamente VBR enviando backups, con lo que nada serio.
Una de las cosas más importantes para poder ejecutar Immutability en MinIO, y que esté soportado por Veeam, es que necesitamos la versión de MinIO RELEASE.2020-07-12T19-14-17Z o superior, y además necesitamos que el server de MinIO esté ejecutándose con Erasure Coding.
¿Qué es MinIO Erasure Coding?
MinIO Erasure Coding es un algoritmo matemático para reconstruir datos perdidos o corruptos. MinIO usa el código Reed-Solomon para fragmentar objetos en datos variables y bloques de paridad. Por ejemplo, en una configuración de 12 unidades, un objeto puede ser dividido en un número variable de bloques de datos y paridad en todas las unidades – desde seis bloques de datos y seis de paridad hasta diez bloques de datos y dos de paridad.
De manera predeterminada, MinIO divide los objetos en unidades de datos y de paridad N/2. Sin embargo, puede usar clases de almacenamiento para usar una configuración personalizada. Recomendamos los bloques de datos y paridad N/2, ya que asegura la mejor protección contra las fallas de la unidad.
En el ejemplo de 12 unidades de disco arriba, con el servidor MinIO ejecutándose en la configuración predeterminada, puede perder cualquiera de las seis unidades y aún así reconstruir los datos de manera confiable a partir de las unidades restantes.
¿Por qué es útil MinIO Erasure Coding?
MinIO Erasure Coding protege los datos de fallos de múltiples unidades, a diferencia de RAID o replicación. Por ejemplo, RAID6 puede proteger contra el fallo de dos unidades, mientras que en el código de borrado de MinIO puede perder hasta la mitad de las unidades y aún así los datos permanecen seguros. Además, MinIO Erasure Coding está a nivel de objeto y puede recuperar un objeto a la vez. En el caso de RAID, la recuperación sólo puede hacerse a nivel de volumen, lo que se traduce en un alto tiempo de inactividad. Como MinIO codifica cada objeto individualmente, puede curar los objetos de forma incremental. Los servidores de almacenamiento, una vez desplegados, no deberían requerir reemplazo de discos o curación durante la vida del servidor. El backend de Erasure Coding de MinIO está diseñado para la eficiencia operativa y aprovecha al máximo la aceleración de hardware siempre que esté disponible.
Más información aquí – https://docs.min.io/docs/minio-erasure-code-quickstart-guide.html
Configuración de discos para usar con MinIO Erasure Coding
En este laboratorio voy a usar 4 discos para mi servidor de MinIO, de 100GB cada uno, usando por supuesto THIN en VMware, para no consumir todo el espacio de mi VSAN, la configuración de la VM se ve tal que así:
Una vez que tenemos todos los discos, tendremos que realizar los siguiente pasos por cada disco, os dejo los pasos con el sdb, pero tendréis que hacerlo con sdc, sdd, y sde:
Comenzaremos particionando el disco:
fdisk /dev/sdb
Tendremos que presionar n para crear una nueva, usando todo el espacio, y de tipo 8e, que es LVM para poder manejarlo mejor luego en caso que queramos crecer:
Welcome to fdisk (util-linux 2.31.1).
Changes will remain in memory only, until you decide to write them.
Be careful before using the write command.
Device does not contain a recognized partition table.
Created a new DOS disklabel with disk identifier 0xab657906.
Command (m for help): n
Partition type
p primary (0 primary, 0 extended, 4 free)
e extended (container for logical partitions)
Select (default p): p
Partition number (1-4, default 1):
First sector (2048-209715199, default 2048):
Last sector, +sectors or +size{K,M,G,T,P} (2048-209715199, default 209715199):
Created a new partition 1 of type 'Linux' and of size 100 GiB.
Command (m for help): t
Selected partition 1
Hex code (type L to list all codes): 8e
Changed type of partition 'Linux' to 'Linux LVM'.
Command (m for help): w
The partition table has been altered.
Calling ioctl() to re-read partition table.
Syncing disks.
Vamos a proceder ahora a crear el LVM, con toda su configuración, tal que así:
pvcreate /dev/sdb1 vgcreate vg_xfs_minio_1 /dev/sdb1 lvcreate -L +99G -n xfs_minio_1 vg_xfs_minio_1 mkfs.xfs /dev/vg_xfs_minio_1/xfs_minio_1
Acabaremos creando un nuevo directorio y montando esa nueva partición:
mkdir /root/xfs_minio_1 mount /dev/vg_xfs_minio_1/xfs_minio_1 /root/xfs_minio_1/
Si queremos comprobar que todo ha ido bien, con este comando podremos ver todo:
df -hT /root/xfs_minio/ Filesystem Type Size Used Avail Use% Mounted on /dev/mapper/vg_xfs_minio-xfs_minio_1 xfs 99G 134M 99G 1% /root/xfs_minio_1
Repetir esto por cada disco, os debería quedar algo así:
df -h Filesystem Size Used Avail Use% Mounted on udev 5.9G 0 5.9G 0% /dev tmpfs 1.2G 1.2M 1.2G 1% /run /dev/mapper/ubuntu--vg-ubuntu--lv 19G 4.9G 13G 28% / tmpfs 5.9G 0 5.9G 0% /dev/shm tmpfs 5.0M 0 5.0M 0% /run/lock tmpfs 5.9G 0 5.9G 0% /sys/fs/cgroup /dev/sda2 976M 145M 765M 16% /boot tmpfs 1.2G 0 1.2G 0% /run/user/1000 /dev/mapper/vg_xfs_minio_1-xfs_minio_1 99G 12G 88G 12% /root/xfs_minio_1 /dev/mapper/vg_xfs_minio_2-xfs_minio_2 99G 12G 88G 12% /root/xfs_minio_2 /dev/mapper/vg_xfs_minio_3-xfs_minio_3 99G 12G 88G 12% /root/xfs_minio_3 /dev/mapper/vg_xfs_minio_4-xfs_minio_4 99G 12G 88G 12% /root/xfs_minio_4
No os olvidéis de añadirlos al fstab, para ello sacar el UID con blkid /dev/mapper/vg_xfs_minio_3-xfs_minio_3, en mi caso por ejemplo:
echo 'UUID=155b62fb-e7cb-424f-91d7-3e09217d7e7f /root/xfs_minio_1 xfs defaults 1 1' >> /etc/fstab echo '85f1550b-5459-4427-8a45-8fe139cfaebe /root/xfs_minio_2 xfs defaults 1 1' >> /etc/fstab echo '0c47b7cd-edc3-4ef9-9b6a-0d3f2dc476db /root/xfs_minio_3 xfs defaults 1 1' >> /etc/fstab echo '2833348b-7053-49f1-a96d-d00ee8f071ed /root/xfs_minio_4 xfs defaults 1 1' >> /etc/fstab
Ya estamos listos para el siguiente paso.
Desplegar y configurar MinIO, incluyendo Immutability y Let’s Encrypt
Bueno, bueno, ya hemos llegado hasta esta parte, con lo que no nos demoramos más, vamos allá, instalaremos la última versión de MinIO usando el siguiente comando:
wget https://dl.min.io/server/minio/release/linux-amd64/minio chmod +x minio
Una vez tenemos todo descargado y preparado, podríamos lanzar una instancia sencilla de MinIO, para ver que funciona, sin ningún Erasure Coding, ni nada, solo por probar, así por ejemplo:
./minio server /home/oper/test Endpoint: http://192.168.1.185:9000 http://127.0.0.1:9000 AccessKey: minioadmin SecretKey: minioadmin Browser Access: http://192.168.1.185:9000 http://127.0.0.1:9000 Command-line Access: https://docs.min.io/docs/minio-client-quickstart-guide $ mc config host add myminio http://192.168.1.185:9000 minioadmin minioadmin Object API (Amazon S3 compatible): Go: https://docs.min.io/docs/golang-client-quickstart-guide Java: https://docs.min.io/docs/java-client-quickstart-guide Python: https://docs.min.io/docs/python-client-quickstart-guide JavaScript: https://docs.min.io/docs/javascript-client-quickstart-guide .NET: https://docs.min.io/docs/dotnet-client-quickstart-guide Detected default credentials 'minioadmin:minioadmin', please change the credentials immediately using 'MINIO_ACCESS_KEY' and 'MINIO_SECRET_KEY'
Si accedo a la IP y al puerto, veo que podemos entrar a una interfaz MinIO y todo funciona bien:
Una vez introduzco las credenciales, me aseguraré que tengo una versión moderna de MinIO, especialmente superior a la recomendada por Veeam en su HCL:
Vale, como todo me funciona bien, vamos a dar el paso y configurar todo de manera más segura y elegante usando Let’s Encrypt.
Configurar MinIO con Let’s Encrypt
Como siempre, haremos uso de certbot, que nos ayudará a generar todo el proceso, y la validación de nuestros certificados de Let’s Encrypt, actualizaremos el sistema e instalaremos certbot:
sudo apt-get install software-properties-common sudo add-apt-repository universe sudo add-apt-repository ppa:certbot/certbot sudo apt-get update sudo apt-get install certbot
Hay varios modos de validar nuestro dominio, yo encuentro el modo de DNS manual, en caso de no tener Cloudflare, etc, el más sencillo, con lo que lo haré así:
certbot --manual --preferred-challenges dns certonly -d minio.jorgedelacruz.es --staple-ocsp -m [email protected] --agree-tos
Esto lanzará el siguiente output, que tendremos que configurar en nuestro DNS público:
Saving debug log to /var/log/letsencrypt/letsencrypt.log Plugins selected: Authenticator manual, Installer None Obtaining a new certificate Performing the following challenges: dns-01 challenge for minio.jorgedelacruz.es - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - NOTE: The IP of this machine will be publicly logged as having requested this certificate. If you're running certbot in manual mode on a machine that is not your server, please ensure you're okay with that. Are you OK with your IP being logged? - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - (Y)es/(N)o: yes - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Please deploy a DNS TXT record under the name _acme-challenge.minio.jorgedelacruz.es with the following value: OIOLPq0SBAH41d5hKAEL08OueThzMyboRGduxdi5L3c Before continuing, verify the record is deployed. - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Press Enter to Continue
Una vez ponemos esta entrada .TXT en nuestro DNS público, hacemos click en Enter y si todo ha ido bien veremos lo siguiente:
Waiting for verification... Cleaning up challenges IMPORTANT NOTES: - Congratulations! Your certificate and chain have been saved at: /etc/letsencrypt/live/minio.jorgedelacruz.es/fullchain.pem Your key file has been saved at: /etc/letsencrypt/live/minio.jorgedelacruz.es/privkey.pem Your cert will expire on 2020-10-19. To obtain a new or tweaked version of this certificate in the future, simply run certbot again. To non-interactively renew *all* of your certificates, run "certbot renew" - If you like Certbot, please consider supporting our work by: Donating to ISRG / Let's Encrypt: https://letsencrypt.org/donate Donating to EFF: https://eff.org/donate-le
Si queremos comprobar los ficheros, etc, lo haremos así:
ls -l /etc/letsencrypt/live/minio.jorgedelacruz.es/ total 4 lrwxrwxrwx 1 root root 46 Jul 21 15:43 cert.pem -> ../../archive/minio.jorgedelacruz.es/cert1.pem lrwxrwxrwx 1 root root 47 Jul 21 15:43 chain.pem -> ../../archive/minio.jorgedelacruz.es/chain1.pem lrwxrwxrwx 1 root root 51 Jul 21 15:43 fullchain.pem -> ../../archive/minio.jorgedelacruz.es/fullchain1.pem lrwxrwxrwx 1 root root 49 Jul 21 15:43 privkey.pem -> ../../archive/minio.jorgedelacruz.es/privkey1.pem -rw-r--r-- 1 root root 692 Jul 21 15:43 README
Vamos a copiar estos ficheros a la carpeta de MinIO del usuario desde el que queremos ejecutar MinIO, en mi caso es root, para no complicarme, pero en vuestro caso securizarlo algo más:
cp /etc/letsencrypt/live/minio.jorgedelacruz.es/fullchain.pem /root/.minio/certs/public.crt cp /etc/letsencrypt/live/minio.jorgedelacruz.es/privkey.pem /root/.minio/certs/private.key
Arrancar MinIO con Erasure Coding
No tiene mucho misterio, ya que tenemos el certificado SSL, y tenemos también nuestras particiones y puntos de montaje listos, tendremos todo preparado para lanzar MinIO con Erasure Coding, lo que viene a ser con alta disponibilidad, etc. Claro es todo en un server, pero es para pruebas:
./minio server --address ":443" /root/xfs_minio_1/ /root/xfs_minio_2/ /root/xfs_minio_3/ /root/xfs_minio_4/
Formatting 1st zone, 1 set(s), 4 drives per set.
WARNING: Host local has more than 2 drives of set. A host failure will result in data becoming unavailable.
Status: 4 Online, 0 Offline.
Endpoint: https://192.168.1.185 https://127.0.0.1
AccessKey: minioadmin
SecretKey: minioadmin
Browser Access:
https://192.168.1.185 https://127.0.0.1
Command-line Access: https://docs.min.io/docs/minio-client-quickstart-guide
$ mc config host add myminio https://192.168.1.185 minioadmin minioadmin
Object API (Amazon S3 compatible):
Go: https://docs.min.io/docs/golang-client-quickstart-guide
Java: https://docs.min.io/docs/java-client-quickstart-guide
Python: https://docs.min.io/docs/python-client-quickstart-guide
JavaScript: https://docs.min.io/docs/javascript-client-quickstart-guide
.NET: https://docs.min.io/docs/dotnet-client-quickstart-guide
Certificate:
Signature Algorithm: SHA256-RSA
Issuer: C=US, O=Let's Encrypt, CN=Let's Encrypt Authority X3
Validity
Not Before: Tue, 21 Jul 2020 14:43:33 GMT
Not After : Mon, 19 Oct 2020 14:43:33 GMT
Certificate:
Signature Algorithm: SHA256-RSA
Issuer: O=Digital Signature Trust Co., CN=DST Root CA X3
Validity
Not Before: Thu, 17 Mar 2016 16:40:46 GMT
Not After : Wed, 17 Mar 2021 16:40:46 GMT
Detected default credentials 'minioadmin:minioadmin', please change the credentials immediately using 'MINIO_ACCESS_KEY' and 'MINIO_SECRET_KEY'
Estaría bien que cambiaráis el usuario y password para tener más seguridad también. Además, como os he dicho, MinIO nos dice que tenemos todo en el mismo servidor, con lo que no es realmente resistente a fallos físicos, pero vale. Si nos vamos por HTTPS, ya veremos buenas noticias:
Crear un nuevo Bucket en MinIO con el atributo de Immutability
Este comando os fallará si no estáis usando una versión moderna de MinIO, y si no estáis usando Erasure Coding, necesitamos minio-client, con lo que lo descargaremos de manera rápida:
wget https://dl.min.io/client/mc/release/linux-amd64/mc chmod +x mc
Lo configuraremos de manera rápida añadiendo un nuevo host, así:
./mc config host add minio-veeam https://minio.jorgedelacruz.es YOURS3ACCESSKEY YOURSECERTKEY --api S3v4
Ahora ya podremos lanzar el siguiente comando, que tiene el atributo -l (–with-lock)
./mc mb --debug -l minio-veeam/veeam-immutable
Y si todo ha ido bien veremos lo siguiente:
mc: <DEBUG> HTTP/1.1 200 OK Content-Length: 0 Accept-Ranges: bytes Content-Security-Policy: block-all-mixed-content Date: Tue, 21 Jul 2020 17:53:15 GMT Location: /veeamimmutable Server: MinIO/RELEASE.2020-07-20T02-25-16Z Vary: Origin X-Amz-Request-Id: 1623D601B41CBFAE X-Xss-Protection: 1; mode=block mc: <DEBUG> Response Time: 99.203176ms Bucket created successfully `minio-veeam/veeamimmutable`.
Y por supuesto por HTTPS, veremos lo siguiente en el cliente:
¡Felicidades! Ya tenemos todo listo, nuestro MinIO de manera particular, listo, con HTTPS y usando immutable Storage. Vamos al último paso, la configuración de Veeam Backup & Replication.
Configuración de Veeam Backup & Replication con Immutability
Creación de Backup Repository – Object Storage
Ya tenemos todo listo, tendremos que estar usando Veeam Backup & Replication v10 para poder hacer uso de MinIO con immutability, nos iremos a la parte de Backup Infrastructure – Repositories, y crearemos uno nuevo:
Seleccionaremos de tipo Object Storage:
Seleccionaremos de tipo S3-Compatible, y una vez dentro introduciremos un nombre y descripción para este nuevo Object Storage:
Seleccionaremos el servidor, que tenemos con HTTPS y un FQDN válido y las credenciales que tengamos:
Seleccionaremos el bucket, que en mi caso es el que hemos creado anteriormente como immutable, además de introducir una carpeta donde queremos guardar las copias, y el número de días que queremos hacer nuestros backups immutables:
Por último si estamos contentos con todo, haremos click en Finish:
Ya estamos listos para ir al siguiente paso.
Creación de Scale-out Backup Repository – con MinIO Immutable como Capacity Tier
Nos iremos hasta Scale-out Backup Repositories, y crearemos uno nuevo:
Introduciremos un nombre y descripción que queramos:
Como Performance Tier seleccionaremos un disco local donde tengamos ya copias, o donde queramos lanzar copias, ya sean diarias, o las GFS, etc:
En la parte de Capacity Tier, seleccionaremos el nuevo Object Storage a MinIO que ya tenía Immutable configurado, y seleccionaremos qué queremos mandar, en mi caso he seleccionado las copias, además de mover los backups que estén completos también, como son semanales, mensuales, etc:
Creación de Backup Copy Job que va a este nuevo SOBR con Immutability
Crearemos un nuevo trabajo de Backup Copy, prefiero pruning ya que nos da más reportes y visibilidad:
Seleccionaremos la VM, o el trabajo o trabajos que queremos hacer una copia a este repositorio de Object Storage con Immutability:
Seleccionaremos el Backup Repository, así como los puntos de restauración a guardar:
El trabajo de Backup Copy comenzará y seguirá lanzandose cada día para copiar los nuevos puntos de restauración de un lugar a otro: 
Eliminando puntos de restauración de un Object Storage con Immutability
Si nos vamos a nuestro Object Storage en Veeam, y queremos eliminar puntos de restauración que están en este Object Storage, esté es el error que obtendremos:
En grande:
Eso es todo amigos, espero que os haya gustado este blog post tan detallado y largo, más de 2000 palabras, espero os sirva.


Hola Jorge, Un post genial muchas gracias y felicidades, la funcionalidad de backup inmutable realmente es muy interesante, quería aplicar esta funcionalidad en un entorno onpremises. La idea es que alquien que se haga con el control del Veeam, no pueda eliminar los datos guardados con el “backup inmutable”.
Tengo algunas preguntas: Supongo que las credenciales para acceder al “Object storage” guardadas en Veeam, no podrían ser descrifradas de ninguna forma, no?
Al configurar el “Object storage” aparece: “Object storage must support S3 Object Lock feature” Además de un storage S3 en AWS y MinIO, hay otros tipos de storage compatibles hay con: S3 Object Lock feature”??