17 puntos por GN⁺ 11 일 전 | 1 comentarios | Compartir por WhatsApp
  • Al mover una infraestructura de producción de $1,432 al mes a un servidor dedicado de $233 al mes, se mantuvo la continuidad del servicio sin tiempo de inactividad, incluso cambiando el sistema operativo
  • Se reprodujo la misma configuración de 30 bases de datos MySQL y 34 hosts virtuales de Nginx, además de GitLab EE, Neo4J, Supervisor y Gearman, y la migración se completó con replicación en tiempo real y sincronización incremental final
  • La clave de la migración de bases de datos fue la combinación de procesamiento paralelo con mydumper·myloader y replicación de MySQL; también se corrigieron problemas de esquema sys y permisos surgidos al pasar de MySQL 5.7 a 8.0
  • El cutover se realizó en este orden: reducción del TTL de DNS, cambio del Nginx del servidor antiguo a proxy inverso y modificación masiva de los registros A, de modo que las solicitudes al IP anterior durante la propagación de DNS se reenviaban al servidor nuevo
  • Como resultado, se logró un ahorro mensual de $1,199, un ahorro anual de $14,388, mejoras en CPU, memoria y almacenamiento, y 0 minutos de inactividad

Contexto de la migración

  • Al operar una empresa de software en Turquía, la inflación acelerada y la debilidad de la lira turca incrementaron fuertemente la carga de los costos de infraestructura en dólares
  • El costo del servidor existente en DigitalOcean era de $1,432 al mes, con una configuración de 192 GB de RAM, 32 vCPU, 600 GB SSD, 2 volúmenes de bloque de 1 TB y respaldos incluidos
  • El nuevo destino fue un servidor dedicado Hetzner AX162-R, con AMD EPYC 9454P de 48 núcleos y 96 hilos, 256 GB DDR5 y 1.92 TB NVMe Gen4 en RAID1
  • El costo mensual bajó a $233, con un ahorro mensual de $1,199 y un ahorro anual de $14,388
  • No había quejas sobre la confiabilidad del servidor anterior ni sobre la experiencia de desarrollo, pero para cargas steady-state la relación precio-rendimiento ya no resultaba razonable

Entorno operativo anterior

  • El stack operativo no era un entorno de prueba simple, sino una configuración real de producción
    • 30 bases de datos MySQL, con un total de 248 GB de datos
    • 34 hosts virtuales de Nginx distribuidos en varios dominios
    • GitLab EE con 42 GB de respaldos incluidos
    • Neo4J Graph DB operando con un volumen de 30 GB
    • Supervisor administrando decenas de workers en segundo plano
    • Uso de la cola de trabajos Gearman
    • Operación de apps móviles en vivo para cientos de miles de usuarios
  • El sistema operativo del servidor anterior era CentOS 7, ya fuera de soporte
  • El nuevo sistema operativo del servidor es AlmaLinux 9.7, una distribución compatible con RHEL 9 y una opción sucesora natural de CentOS
  • Esta migración no solo redujo costos, sino que también permitió salir de un sistema operativo que llevaba años sin actualizaciones de seguridad

Estrategia sin tiempo de inactividad

  • No se aceptó un método simple de cambiar DNS y reiniciar servicios; la migración sin downtime se realizó con un procedimiento de 6 etapas
  • Etapa 1: instalación de todo el stack en el servidor nuevo

    • Instalación de Nginx compilado desde código fuente con las mismas flags que en el servidor anterior
    • PHP se instaló mediante el repo de Remi y se aplicaron los mismos archivos de configuración .ini del servidor anterior
    • Instalación de MySQL 8.0, Neo4J Graph DB, GitLab EE, Node.js, Supervisor y Gearman, configurados para comportarse igual que antes
    • Antes de tocar los registros DNS, todos los servicios se dejaron funcionando igual que en el servidor anterior
    • Los certificados SSL se manejaron copiando por rsync todo el directorio /etc/letsencrypt/ del servidor anterior
    • Una vez que todo el tráfico se trasladó al nuevo servidor, se ejecutó certbot renew --force-renewal para renovar en lote los certificados de forma forzada
  • Etapa 2: replicación de archivos web con rsync

    • Se replicó por SSH todo el directorio /var/www/html, unos 65 GB y 1.5 millones de archivos, usando rsync
    • Se realizó verificación de integridad con la opción --checksum
    • Justo antes del cutover también se hizo una sincronización incremental final para reflejar los archivos modificados
  • Etapa 3: replicación maestro-esclavo de MySQL

    • En lugar de bajar las bases de datos para exportar y restaurar, se configuró replicación en tiempo real
    • El servidor anterior se dejó como maestro y el nuevo como esclavo de solo lectura
    • La carga inicial masiva se hizo con mydumper, y luego la replicación comenzó desde la posición exacta del binlog registrada en los metadatos del dump
    • Hasta el momento del cutover, ambas bases de datos se mantuvieron sincronizadas en tiempo real
  • Etapa 4: reducción del TTL de DNS

    • Se llamó por script a la API de DNS de DigitalOcean para reducir el TTL de todos los registros A/AAAA de 3600 segundos a 300 segundos
    • Los registros MX y TXT no se modificaron
    • Se excluyeron porque cambiar el TTL de registros de correo podía provocar problemas de entregabilidad
    • Después de esperar 1 hora para que el TTL anterior expirara globalmente, quedó todo listo para hacer el cutover dentro de 5 minutos
  • Etapa 5: convertir el Nginx del servidor anterior en proxy inverso

    • Un script en Python analizó los bloques server {} en las 34 configuraciones de sitios Nginx
    • La configuración anterior se respaldó y se reemplazó por configuración de proxy apuntando al servidor nuevo
    • Así, incluso durante la propagación de DNS, las solicitudes que llegaban al IP anterior se reenviaban silenciosamente al servidor nuevo
    • Desde la perspectiva del usuario, no hubo interrupción visible
  • Etapa 6: cutover de DNS y apagado del servidor anterior

    • Un script en Python llamó a la API de DigitalOcean para cambiar todos los registros A al nuevo IP en cuestión de segundos
    • El servidor anterior se mantuvo durante 1 semana como cold standby antes de apagarse
    • Durante todo el proceso, el servicio siguió respondiendo de forma directa o a través del proxy, por lo que no hubo un periodo sin disponibilidad

Migración de MySQL

  • La parte más compleja de todo el trabajo fue la migración de MySQL
  • Volcado de datos

    • Se usó mydumper en lugar de mysqldump
    • Aprovechando los 48 núcleos de CPU del nuevo servidor para exportación/importación paralela, un trabajo que con mysqldump de un solo hilo habría tomado días se redujo a unas horas
    • Entre las principales opciones utilizadas estaban --threads 32, --compress, --trx-consistency-only, --skip-definer, --chunk-filesize 256
    • El archivo metadata del dump principal registró la posición del binlog en el momento del snapshot
      • File: mysql-bin.000004
      • Position: 21834307
    • Esos valores se usaron después como punto inicial de la replicación
  • Transferencia del dump

    • Tras completar el dump, se transfirió al nuevo servidor mediante rsync sobre SSH
    • Se enviaron en total 248 GB de chunks comprimidos
    • La opción --compress de mydumper ayudó a mejorar la velocidad de transferencia por red
  • Carga de datos

    • Se usó myloader
    • Las opciones principales fueron --threads 32, --overwrite-tables, --ignore-errors 1062, --skip-definer
  • Problemas en el cambio de MySQL 5.7 a 8.0

    • Debido al entorno con CentOS 7, el servidor anterior seguía en MySQL 5.7
    • Antes de migrar, se verificó con mysqlcheck --check-upgrade que los datos fueran compatibles con MySQL 8.0, y el resultado fue sin problemas
    • En el nuevo servidor se instaló la versión más reciente de MySQL 8.0 Community
    • Los tiempos de ejecución de consultas se redujeron de forma significativa en todo el proyecto; en el texto original esto se atribuye al optimizador mejorado y las mejoras en InnoDB de MySQL 8.0
    • Aun así, surgieron problemas por el salto de versión
      • Después del import, la estructura de columnas de la tabla mysql.user tenía 45 columnas en vez de las 51 esperadas
      • Como resultado, faltaba mysql.infoschema y hubo fallas en la autenticación de usuarios
    • El primer intento de corrección usó los siguientes comandos
      • systemctl stop mysqld
      • mysqld --upgrade=FORCE --user=mysql &
    • El primer intento falló con el error ERROR: 'sys.innodb_buffer_stats_by_schema' is not VIEW
    • La causa fue que el esquema sys se había importado como tabla normal en lugar de vista
    • La solución fue ejecutar DROP DATABASE sys; y luego repetir la actualización
    • Después de eso, se completó con normalidad

Configuración de replicación de MySQL

  • Una vez terminada la carga del dump en ambos servidores, el nuevo servidor se configuró como réplica del anterior
  • En la sentencia CHANGE MASTER TO se especificaron el IP del servidor anterior, el usuario de replicación, el puerto 3306, MASTER_LOG_FILE='mysql-bin.000004' y MASTER_LOG_POS=21834307
  • Después se ejecutó START SLAVE;
  • Casi de inmediato la replicación se detuvo por error 1062 Duplicate Key
  • La causa fue que el dump se hizo en dos partes y, entre una y otra, hubo escrituras en algunas tablas; así, el dump importado y la reproducción del binlog intentaban insertar duplicadamente la misma fila
  • Para resolverlo, se aplicó esta configuración
    • SET GLOBAL slave_exec_mode = 'IDEMPOTENT';
    • START SLAVE;
  • El modo IDEMPOTENT omite silenciosamente errores de clave duplicada y de fila faltante
  • Todas las bases de datos críticas se sincronizaron sin errores, y en pocos minutos Seconds_Behind_Master bajó a 0

Verificación previa al cutover

  • Antes de tocar los registros DNS, era necesario verificar que todos los servicios funcionaran correctamente en el nuevo servidor
  • El método de validación consistió en modificar temporalmente el archivo /etc/hosts de la máquina local para mapear los dominios al IP del nuevo servidor
  • Así, el navegador y Postman enviaban solicitudes al servidor nuevo, mientras que los usuarios externos seguían conectándose al servidor anterior
  • Se revisaron los endpoints de API, el panel de administración y el estado de respuesta de cada servicio
  • Tras confirmar todo, se procedió al cutover real

Problema con el privilegio SUPER

  • Después de que la replicación maestro-esclavo quedó completamente sincronizada, se confirmó que en el nuevo servidor las sentencias INSERT tenían éxito aunque read_only = 1
  • La causa fue que todos los usuarios PHP de las aplicaciones tenían asignado el privilegio SUPER
  • En MySQL, el privilegio SUPER omite read_only
  • En el resultado de SHOW GRANTS FOR 'some_db_user'@'localhost'; se confirmó que el privilegio SUPER estaba incluido
  • Se ejecutó repetidamente REVOKE SUPER ON *.* FROM 'some_db_user'@'localhost'; sobre un total de 24 usuarios de aplicación
  • Después se ejecutó FLUSH PRIVILEGES;
  • A partir de ese momento, read_only = 1 bloqueó correctamente las escrituras de los usuarios de aplicación mientras la replicación siguió funcionando

Preparación de DNS

  • Todos los dominios se administraban con DigitalOcean DNS, con los nameservers conectados desde GoDaddy
  • La reducción del TTL se automatizó con scripts contra la API de DigitalOcean
  • El cambio se limitó solo a los registros A y AAAA
  • Los registros MX y TXT no se tocaron
    • Se excluyó el cambio de TTL de registros relacionados con correo por posibles problemas de entregabilidad con Google Workspace
  • Tras esperar 1 hora para la expiración del TTL anterior, quedó todo listo para el cutover

Conversión del Nginx del servidor anterior a proxy inverso

  • En lugar de editar manualmente 34 archivos de configuración, se hizo una conversión automática con un script en Python
  • El script analizó los bloques server {} de todos los archivos de configuración y reemplazó el bloque principal de contenido por configuración de proxy
  • Las configuraciones originales se respaldaron como archivos .backup
  • En el ejemplo de configuración se aplicaron proxy_pass https://NEW_SERVER_IP;, proxy_set_header Host $host;, proxy_set_header X-Real-IP $remote_addr;, proxy_read_timeout 150;
  • La opción clave fue proxy_ssl_verify off
    • Porque el certificado SSL del servidor nuevo era válido para el dominio, pero no para la dirección IP
    • Como ambos extremos estaban bajo control, aquí se consideró aceptable desactivar la verificación

Procedimiento de cutover

  • Justo antes del cutover, la condición era tener el retraso de replicación en Seconds_Behind_Master: 0 y el proxy inverso listo
  • La secuencia de ejecución fue la siguiente
    • En el servidor nuevo: STOP SLAVE;
    • En el servidor nuevo: SET GLOBAL read_only = 0;
    • En el servidor nuevo: RESET SLAVE ALL;
    • En el servidor nuevo: supervisorctl start all
    • En el servidor anterior: nginx -t && systemctl reload nginx para activar el proxy
    • En el servidor anterior: supervisorctl stop all
    • En la Mac local: python3 do_cutover.py para cambiar todos los registros A del DNS al IP del nuevo servidor
    • Espera de propagación de aproximadamente 5 minutos
    • En el servidor anterior: comentar todas las entradas de crontab
  • El script de cutover de DNS llamaba a la API de DigitalOcean para cambiar todos los registros A en unos 10 segundos

Trabajo adicional después del cutover

  • Tras completar la migración, se detectó que varios webhooks de proyectos de GitLab seguían apuntando al IP del servidor anterior
  • Se escribió y aplicó un script que recorría todos los proyectos mediante la API de GitLab y actualizaba en lote los webhooks

Resultado final

  • El costo mensual bajó de $1,432 a $233
  • El ahorro anual fue de $14,388
  • También se consiguió un servidor más potente en rendimiento
    • La CPU pasó de 32 vCPU a 96 CPU lógicas
    • La RAM pasó de 192 GB a 256 GB DDR5
    • El almacenamiento cambió de una configuración mixta de ~2.6 TB a 2 TB NVMe RAID1
    • El tiempo de inactividad fue de 0 minutos
  • El tiempo total de toda la migración fue de aproximadamente 24 horas
  • No hubo impacto para los usuarios

Lecciones clave

  • La replicación de MySQL es la herramienta clave para migraciones sin downtime
    • La idea es configurarla temprano, dejar que alcance el ritmo y luego hacer el cutover
  • Es indispensable revisar los permisos de usuarios MySQL antes de migrar
    • Si existe el privilegio SUPER, se puede omitir read_only y el esclavo deja de ser realmente de solo lectura
  • Es importante automatizar con scripts las actualizaciones de DNS, cambios de configuración de Nginx y correcciones de webhooks
    • Manejar manualmente más de 34 sitios toma mucho tiempo y aumenta la posibilidad de errores
  • La combinación mydumper + myloader es mucho más rápida que mysqldump en datasets grandes
    • Con dump y restauración paralelos de 32 hilos, un trabajo de varios días se redujo a unas horas
  • En cargas steady-state, un proveedor cloud puede resultar caro, y un servidor dedicado puede ofrecer mayor rendimiento a menor costo

Scripts en GitHub

  • Todos los scripts en Python usados en la migración se publicaron en GitHub
  • Lista de scripts incluidos
    • do_list_domains_ttl.py
      • Consulta los registros A, el IP y el TTL de todos los dominios en DigitalOcean
    • do_ttl_update.py
      • Reduce en lote el TTL de todos los registros A/AAAA a 300 segundos
    • do_to_hetzner_bulk_dns_records_import.py
      • Migra todas las zonas DNS de DigitalOcean a Hetzner DNS
    • do_cutover_to_new_ip.py
      • Cambia todos los registros A del IP del servidor anterior al del nuevo servidor
    • nginx_reverse_proxy_update.py
      • Convierte toda la configuración de sitios nginx a configuración de proxy inverso
    • mysql_compare.py
      • Compara el conteo de filas de todas las tablas entre dos servidores MySQL
    • final_gitlab_webhook_update.py
      • Actualiza todos los webhooks de proyectos GitLab al IP del nuevo servidor
    • mydumper
      • Biblioteca de mydumper
  • Todos los scripts admiten el modo DRY_RUN = True para previsualizar con seguridad antes de aplicar cambios reales

1 comentarios

 
GN⁺ 11 일 전
Comentarios en Hacker News
  • Hace unos meses moví dos servidores de Linode y DO a Hetzner, y logré una gran reducción de costos sin cambiar demasiado. Lo más impresionante fue que era un stack caótico con decenas de sitios, distintos lenguajes, librerías antiguas, MySQL y Redis todo mezclado. Pero Claude Code migró todo, y cuando faltaban librerías incluso reescribió parte del código para resolverlo. Ahora este tipo de migraciones complejas son mucho más fáciles, así que creo que en el futuro habrá mucha más movilidad entre proveedores

    • Creo que la gente no pagaba por cómputo mágico, sino por no tener que tocar 10 años de glue code pegado con cinta. Pero si los agentes empiezan a devorarse ese glue, el moat de los proveedores existentes se va a adelgazar rápido
    • Sinceramente, esto se siente como un anuncio de Claude dentro de otro anuncio de Hetzner. Ya me pregunto hasta dónde llega el nivel de anidación
    • Siento que no hace falta llevar absolutamente toda conversación a ser sobre IA
    • Yo también voy a irme de Linode en los próximos meses. Lo usé por más de 10 años y hasta les referí muchos clientes, pero siguieron subiendo precios y ahora en lugares como Hetzner puedes conseguir 8 veces más memoria, NVMe dedicado y CPU dedicada por menos dinero. Pierdes un poco ventajas como la facilidad de mover servidores virtuales, pero incluso cuando hay incidentes, el soporte de Hetzner siempre me ha parecido rápido y competente
    • Yo también estoy usando cada vez más a Claude para DevOps. Corro VMs sobre Proxmox en bare metal propio, y Claude me optimiza y configura redes nuevas entre varias máquinas con una velocidad brutal; casi se siente como un colega o un sysadmin muy bien pagado
  • Estoy planeando una migración de AWS a Hetzner. Amazon a veces cobra 20 veces más que la competencia, te empuja a compromisos a largo plazo para conseguir precios medio decentes, y además hace que sacar datos sea carísimo, lo cual me parece muy hostil hacia el cliente. Uno pensaría que las tarifas de egress están para encerrarte, pero en realidad terminan presionando para que, si mueves una parte a la competencia, acabes moviendo todo. Aun así, en mi caso la migración es un poco más fácil porque no construí la plataforma encima de servicios exclusivos de Amazon

    • Eso era cierto antes, pero en enero de 2024 GCP cambió el panorama con su política de exención de costos de egress, y AWS unos meses después sacó una política parecida. No lo digo para convencerte de quedarte, solo para comentar que técnicamente sí se puede pedir un waiver. Yo tampoco tengo claro hasta dónde aplica en la práctica, y por cómo lo redactó AWS parecía que también había influencia del EU Data Act
  • Cada vez que veo publicaciones así, me llama la atención que casi nadie hable de redundancia o balanceadores de carga. Si se cae un solo servidor, pueden caerse varios servicios al mismo tiempo, y me pregunto si de verdad les parece aceptable. Puede que ahorren dinero, pero quizá terminen gastando más en tiempo de mantenimiento y futuros dolores de cabeza

    • Creo que depende del tipo de servicio y de qué tan crítico sea. Si un servidor puede funcionar 10 años y en todo ese tiempo sumar entre 1 semana y 1 mes de caída, en muchos casos eso es perfectamente aceptable. Para pequeños negocios, sitios hobby, foros o blogs donde el sitio web no es la operación principal, un downtime corto quizá no sea un gran problema. De hecho, esa larga cola de sitios de bajo tráfico podría ser la mayoría de la web. No todo necesita alta disponibilidad, y si la quieres, estos proveedores también ofrecen cosas como load balancers
    • Creo que la razón por la que estas publicaciones se vuelven populares es que muchas veces exponen un desajuste entre requisitos y solución. Si era un hobby project o un negocio pequeño sobrediseñado con arquitectura enterprise, y que se caiga un día de vez en cuando no importa tanto, entonces quizá no necesitas el stack completo estilo cloud. Pero en este caso fue curioso que el artículo enfatizara la migración sin downtime y luego la arquitectura de llegada no pareciera especialmente tolerante a fallos. Con un poco más de estructura del lado de Hetzner probablemente habría mejorado bastante
    • Para muchas cargas de trabajo no hace falta ese nivel de preparación. Y no hay que subestimar la confiabilidad de la simplicidad. Trabajé muchos años como Linux sysadmin y vi mucho más downtime en sistemas complejos que en sistemas simples. En algún punto entre la teoría y la realidad, me quedó la impresión de que la opción simple aguanta mejor en la mayoría de los casos
    • Siendo justos, ya estaban usando una VM única en DigitalOcean, así que tampoco estaban aprovechando tanto las ventajas de un proveedor cloud. Normalmente estas historias caen en dos grupos: casos donde la gente se fue al cloud por razones equivocadas y en realidad le conviene más algo físico, y casos donde hacer ese cambio sería un desastre. Este parece más cercano al primero. Si ya funcionaba bien en DO, en Hetzner también debería estar bien con una política de DR razonable
    • Puede que esta decisión venga de no haber vivido realmente mucho tiempo el infierno de mantenimiento ni los dolores de cabeza futuros
  • En lithus.eu hemos migrado clientes con frecuencia desde varias nubes hacia Hetzner. Normalmente armamos configuraciones multiservidor, a veces multi-AZ, y distribuimos cargas con Kubernetes para dar HA. En un solo nodo Kubernetes puede ser demasiado, pero con varios nodos ya tiene mucho más sentido. Para backups usamos Velero junto con respaldos a nivel aplicación; por ejemplo, en Postgres hacemos backup de WAL para tener PITR. Los datos con estado se dejan al menos en dos nodos para garantizar HA. En rendimiento también suele ir mejor bare metal, y muchas veces vimos latencias a la mitad frente a AWS. Creo que la causa no es tanto la virtualización en sí, sino factores alrededor como NVMe, menor latencia de red y menos cache contention. Dejé más detalles en un post anterior de HN

    • Yo también lo medí por mi cuenta hace algunos años, y desde entonces no volví a mirar servidores virtuales. El tiempo de CPU no se reserva como la RAM, así que el rendimiento frente al hardware real era realmente malo. También me pareció útil esta medición
    • Un despliegue en k8s se deja mover muy bien. Tiene mucho menos lock-in que los servicios administrados de varios clouds. Mi stack también es más o menos k8s, Postgres hosted y almacenamiento tipo s3, así que siempre podría autoalojar Postgres y al final lo central sería k8s y s3. Creo que Hetzner también tiene algo parecido a s3, aunque no lo he revisado, y mover 100 TB sí suena como un trabajo grande
    • Por cierto, HA significa high availability
    • El artículo era razonable, pero al final dejar el correo sí se sintió un poco como copy promocional
  • Este artículo fue bastante duro de leer. Se sentía como si Claude hubiera hecho la migración y luego yo estuviera leyendo un reporte escrito por Claude. Si realmente ahorraron así gracias a un LLM, genial, pero si lo vas a publicar, mínimo debería estar editado para quitar repeticiones y esa forma de escribir de LLM

    • Ya sé que mucha gente no lee el original, pero esta vez de verdad fue doloroso de leer
  • Creo que hay que tener cuidado con Hetzner. Antes me gustaba mucho, pero hace poco me fui. Nos apagaron unas 30 VM que usábamos en nuestro pipeline de CI/CD por una sola disputa de cobro de 36 dólares. Les mandamos comprobantes de pago completo, incluso registros del banco, y ni así quisieron revisarlo. Mientras tratábamos de contactarlos con urgencia, igual terminaron bloqueando todo acceso. Ahora nos movimos a Scaleway

    • Su atención al cliente me pareció sorprendentemente hostil. Aun así, todavía lo uso para cosas no críticas
    • El manejo de cobros en Hetzner está bastante automatizado, pero por lo general, incluso si falla el cobro de la tarjeta, suelen dar como un mes de margen antes de cortar
  • Hace unos meses, cuando buscaba una alternativa a AWS para un pequeño SaaS side project, al principio consideré seriamente Hetzner por el ahorro de costos y por apoyar cloud europeo. Estaba dispuesto a aceptar tener que hacer más cosas manualmente, pero al final lo que me frenó fue la reputación de IP. Una de las reglas del firewall administrado de AWS que usamos en la empresa bloqueaba muchas IP de Hetzner, quizá incluso todas, y en mi laptop de trabajo tampoco podía abrir sitios alojados en IP de Hetzner por políticas de TI. Puede que usando algo como Cloudflare eso pese menos, pero también vi comentarios de que la protección DDoS es floja. Al final elegí DO App Platform en región de la UE, y la opción de base de datos administrada también fue una gran ventaja

    • Si Amazon bloquea a la competencia de esa forma, desde su punto de vista suena bastante conveniente
    • No sé a qué regla de firewall te refieres, pero sí me sorprende bastante que DO sea visto como más confiable que Hetzner. Cuando veo scrapers o hackers, el ASN de DO también aparece seguido, así que siento que ellos también podrían terminar bloqueados algún día
    • En mi experiencia, las IP de DO eran peores. De hecho, justo por eso me fui de DO
    • Yo mencioné este tema antes en un hilo sobre Tor. Supuse que Hetzner, por ser amigable con Tor, podía verse afectado en reputación de IP, aunque en ese momento también hubo respuestas diciendo que no había problemas de reputación. Pero viendo material del Tor Project, parece que Hetzner representa alrededor del 7% de la red Tor, así que el asunto no parece tan simple
    • Irónicamente, yo resolví el 99% de mis problemas de bots solo con bloquear AWS y Azure. No hubo cero daño para usuarios reales, y hasta estoy pensando si vender eso como servicio
  • Compartir este tipo de experiencia de migración me pareció bastante útil, y se agradece. Yo veo la comparación entre DO y Hetzner como el trade-off entre abrir DoorDash o UberEats y cocinar la cena tú mismo. Incluso la proporción de costos se siente parecida. Yo trabajo con las tres grandes nubes y con on-prem, pero para tareas pequeñas o pruebas de PoC todavía sigo yendo a la consola de DigitalOcean. Esa comodidad de tener un servidor o bucket listo con unos cuantos clics, defaults sensatos y backups con una sola casilla sí tiene valor cuando consideras el costo del tiempo

    • No estoy totalmente seguro de qué quieres decir, pero siento que la consola de Hetzner funciona de manera parecida
    • Lo interesante del artículo para mí fueron dos cosas. Una fue el propio procedimiento de migración sin downtime, que sí sirve como referencia general. La otra fue la decisión de cambiar instancias cloud por bare metal, donde el ahorro de costos también implica pagar con conmutación rápida ante fallos y con pérdida de backups. Si yo lo hiciera, probablemente gastaría unos 200 dólares más para tener un hot spare e ir alternando primario/secundario cada ciertos días para validar que ambos sigan funcionando bien. Con un costo relativamente bajo puedes reducir mucho el riesgo de una falla grave
    • Lo que acabas de describir es prácticamente la misma experiencia que Hetzner Cloud lleva ofreciendo desde hace años. Y además tienen la Hetzner Cloud API, así que puedes montar todo con IaC sin siquiera hacer clic en botones
    • En mi caso, sobre servidores de Hetzner levanto Coolify y con eso consigo una experiencia casi de servicio one-click
    • Al ver esta situación, lo único en lo que pensé fue en este xkcd
  • Me quedé con la duda de cómo hacen los backups de la DB. Quería saber si tienen replica o standby, o si solo hacen backups por hora. En una configuración de servidor único como esa, una falla de hardware como un SSD puede parar la app de inmediato, y especialmente si muere el SSD, imagino que podrían pasar horas o días antes de volver a levantar todo

    • Hetzner normalmente anuncia sus servidores de hardware con 2x 1TB SSD, y recomienda bastante armar SW RAID1 para tener 1 TB útil. El instalador de imágenes incluso va por ahí por defecto. Si años después muere el primer SSD, mientras el monitoreo lo detecte puedes migrarte a otra máquina, usar una solución intermedia o réplica, o aguantar sobre el otro disco mientras te hacen el hot-swap. Claro, al irte a servidores físicos pierdes parte de la redundancia del cloud, así que eso hay que meterlo en el modelo de riesgo junto con el ahorro. Y como mínimo, no tener ni siquiera backups diarios hacia almacenamiento remoto sí me parecería temerario. Eso también aplica en cloud, solo que configurarlo es más fácil
    • Puede que a nadie le importe demasiado aunque esté caído tanto tiempo. Por ejemplo, si la app móvil de mi HOA estuviera caída una semana, a mí me daría bastante igual. No todo necesita estar siempre activo
    • Yo tuve la misma preocupación. El artículo me dio la impresión de que el autor estaba priorizando recortes agresivos de costos sin pensarlo del todo. La VM de DigitalOcean probablemente sí soportaba live migration y snapshots, mientras que en Hetzner eso solo lo tienes en el producto cloud. En Hetzner bare metal, si muere un disco o una pieza, se murió, y aunque te cambien el disco, la recuperación la haces tú desde cero. Hetzner deja eso bastante claro en varios lugares
    • Lo más fácil que he hecho fue con MongoDB: replication, sharding y failover eran muy sencillos. Más recientemente, en PostgreSQL también armé un setup con pg_auto_failover usando 1 monitor, 1 primary y 1 replica, y una vez que le agarras la mano a la configuración y a las trampas, también resulta bastante fácil. En mi experiencia, incluso se puede hacer una migración sin downtime
    • Si ellos decidieron aceptar esos trade-offs, no creo que podamos decir automáticamente que está mal. No todas las apps necesitan disponibilidad 24/7, y a la mayoría de los sitios web unas cuantas horas de downtime no los destruyen. Si el ahorro supera el riesgo, puede ser una decisión de negocio totalmente razonable. Lo que sí me da curiosidad es qué estrategia tienen para backup y recuperación, y qué cambió en eso al pasar a Hetzner
  • La imagen meme del encabezado la había hecho yo. La había puesto en este artículo, y me dio gusto verla usada dos veces