¿Cómo configurar el equilibrio de carga global utilizando Digital Ocean DNS y Nginx?


ACTUALIZACIÓN: Vea la respuesta que he proporcionado a continuación para la solución que finalmente configuré en AWS.

Actualmente estoy experimentando con metodologías sobre la mejor manera de implementar una capa global de equilibrio de carga para mis servidores de aplicaciones en Digital Ocean y hay algunas piezas que aún tengo que armar.

El Objetivo

Ofrecer un servicio de alta disponibilidad a mis usuarios enrutando todas las conexiones al 'clúster' de servidores más cercano en SFO, NYC, LON, y eventualmente Singapur.

Además, eventualmente me gustaría automatizar el mantenimiento de esto escribiendo un demonio que pueda monitorear, escalar y curar cualquiera de los servidores en el sistema. O combinaré varios servicios para lograr los mismos objetivos de automatización. Primero tengo que averiguar cómo hacerlo manualmente.

La Pila

  1. Ubuntu 14.04
  2. Nginx 1.4.6
  3. nodo.js
  4. MongoDB de Compose.io (anteriormente MongoHQ)

Desglose Global de dominios

Una vez que arregle todo, mi dominio se vería algo como esto:{[28]]}

**GLOBAL**
global-balancing-1.myapp.com
global-balancing-2.myapp.com
global-balancing-3.myapp.com

**NYC**
nyc-load-balancing-1.myapp.com
nyc-load-balancing-2.myapp.com
nyc-load-balancing-3.myapp.com

nyc-app-1.myapp.com
nyc-app-2.myapp.com
nyc-app-3.myapp.com

nyc-api-1.myapp.com
nyc-api-2.myapp.com
nyc-api-3.myapp.com

**SFO**
sfo-load-balancing-1.myapp.com
sfo-load-balancing-2.myapp.com
sfo-load-balancing-3.myapp.com

sfo-app-1.myapp.com
sfo-app-2.myapp.com
sfo-app-3.myapp.com

sfo-api-1.myapp.com
sfo-api-2.myapp.com
sfo-api-3.myapp.com

**LON**
lon-load-balancing-1.myapp.com
lon-load-balancing-2.myapp.com
lon-load-balancing-3.myapp.com

lon-app-1.myapp.com
lon-app-2.myapp.com
lon-app-3.myapp.com

lon-api-1.myapp.com
lon-api-2.myapp.com
lon-api-3.myapp.com

Y luego si hay alguna tensión en cualquier capa dada, en cualquier región dada, puedo simplemente girar una nueva gotita para ayudar: nyc-app-4.myapp.com, lon-load-balancing-5.myapp.com, etc {

Metodología de Trabajo Actual

  • Un trío (mínimo) de servidores global-balancing recibe todo el tráfico. Estos servidores están DNS Round-Robin equilibrados como se ilustra en este (francamente confuso) artículo: Cómo Configurar la Carga DNS Round-Robin Balancing .

  • Usando el Nginx GeoIP Módulo y MaxMind GeoIP Data el origen de una solicitud determinada se determina en función de la $geoip_city_continent_code.

  • La capa global-balancing luego enruta la solicitud al servidorleast connected en la capa load-balancing del servidor apropiado cluster: nyc-load-balancing-1, sfo-load-balancing-3, lon-load-balancing-2, etc.. Esta capa es también un trío (mínimo) de gota.

  • Las regional load-balancing luego enruta la solicitud a la least connected servidor en la capa app o api: nyc-app-2, sfo-api-1, lon-api-3, etc...

Los detalles del kung-fu Nginx se pueden encontrar en este tutorial: Villiage Idiot: Configurar Nginx con GSLB / Proxy inverso en AWS . Más información general sobre Nginx load-balancing está disponible aquí y aquí.

Preguntas

¿Dónde pongo el global-balancing los servidores?

Me parece extraño que los pusiera todos en un solo lugar, o que extendiera esa capa por todo el mundo. Digamos, por ejemplo, que los puse a todos en Nueva York. Entonces alguien de Francia golpea mi dominio. La solicitud iría desde Francia, a Nueva York, y luego sería enrutada de regreso a LON. O si pongo uno de cada uno en SFO, NYC y LON, entonces no es posible que un usuario de Toronto (Parkdale, represent) pueda enviar una solicitud que termina yendo a LON solo para ser enrutado de nuevo a ¿NYC?

¿Las solicitudes posteriores se enrutan a la misma IP?

Como en, si un usuario de Toronto envía una solicitud que la capa global-balancing determina que debe ir a NYC, hace la siguiente solicitud de ese origen ir directamente a NYC, o es todavía suerte del sorteo que llegará al servidor global-balancing más cercano (NYC en este caso).

¿Y las sesiones?

He configurado Nginx para usar la directiva ip_hash; para que dirija la user to the same app or api endpoint (a node process, in my case) but how will global balancing affect this, if at all?

¿Algún Ejemplo De DNS?

No soy exactamente un experto en DNS (actualmente estoy tratando de averiguar por qué mis registros CNAME no se resuelven), pero soy un estudio rápido cuando se me proporciona un ejemplo sólido. ¿Alguien ha pasado por este proceso antes y puede proporcionar una muestra de cómo se ven los registros DNS para una configuración exitosa?

Qué acerca de SSL / TLS?

¿Necesitaría un certificado para cada servidor, o solo para los tres servidores global-balancing ya que es la única puerta de enlace pública?

Si lees todo esto entonces recompénsate con un cupcake. Gracias de antemano por cualquier ayuda.

Author: AJB, 2014-09-05

4 answers

El Objetivo: Ofrecer un servicio altamente disponible a mis usuarios enrutando todas las conexiones al 'clúster' de servidores más cercano en SFO, NYC, LON y, finalmente, Singapur.

La capa de equilibrio global luego enruta la solicitud a theleast servidor conectado...

Si estoy leyendo su configuración correctamente, en realidad está proxy de sus equilibradores globales a los equilibradores en cada región. Esto no cumple con su objetivo de enrutar a los usuarios a la regi.

Hay tres maneras que conozco de conseguir lo que estás buscando:

  1. Redireccionamiento 30x
    Sus balanceadores globales reciben la solicitud HTTP y luego la redirigen a un grupo de servidores en o cerca de la región de la que cree que proviene la solicitud, en función de la dirección IP. Esto suena como lo que estabas tratando de arreglar. Este método tiene efectos secundarios para algunas aplicaciones, y también aumenta el tiempo que tarda un usuario en obtener datos, ya que está agregando una tonelada de gastos generales. Esto solo tiene sentido si los recursos a los que está redirigiendo son muy grandes, y el clúster regional local podrá servir de manera mucho más eficiente.

  2. Anycast (aprovechando el enrutamiento BGP)
    Esto es lo que los grandes jugadores como Akamai utilizan para su CDN. Básicamente, hay varios servidores en Internet con la misma dirección IP enrutable. Supongamos que tengo servidores en varias regiones, y tienen la dirección IP de 192.0.2.1. Si estoy en los EE.UU. y tratar de conectarse a 192.0.2.1, y alguien está en Europa que intenta conectarse a 192.0.2.1, es probable que vamos a ser enrutado al servidor más cercano. Esto utiliza el propio enrutamiento de Internet para encontrar la mejor ruta (basada en las condiciones de la red) para el tráfico. Desafortunadamente, no puedes simplemente usar este método. Usted necesita su propio número COMO, y hardware físico. Si encuentras un proveedor de VPS que te permite tener una parte de su bloque Anycast, déjame ¡saber!

  3. Geo-DNS
    Hay algunos proveedores de DNS que proporcionan un servicio a menudo comercializado como"Geo-DNS". Tienen un montón de servidores DNS alojados en direcciones anycast que pueden enrutar el tráfico a sus servidores más cercanos. Si un cliente consulta un servidor DNS europeo, debe devolver la dirección de los servidores de su región europea, frente a algunos de otras regiones. Hay muchas variaciones en los servicios de Geo DNS. Otros simplemente mantienen una base de datos geo-IP y devuelven el servidor para la región que creen que está más cerca, al igual que el método de redirección, pero para DNS antes de que se realice la solicitud HTTP. Esta es generalmente la buena opción, por precio y facilidad de uso.

¿Las solicitudes posteriores se enrutan a la misma IP?

Muchos balanceadores de carga tienen una opción "stickiness" que dice que las solicitudes de la misma dirección de red deben ser enrutadas al mismo servidor final (siempre que el servidor final todavía esté en funcionamiento).

¿Qué pasa con las sesiones?

Esta es exactamente la razón por la que querrías esa pegajosidad. Cuando se trata de datos de sesión, tendrá que encontrar una manera de mantener todos sus servidores actualizados. Siendo realistas, esto no siempre está garantizado. Cómo manejarlo depende de su aplicación. ¿Puede mantener una instancia de Redis o lo que sea para que todos sus servidores ataquen de manera confiable desde todo el mundo? ¿Realmente necesita esos datos de sesión en cada región? O puede tener sus servidores de aplicaciones principales tratar con los datos de la sesión en una ubicación?

¿Algún Ejemplo de DNS?

Publique preguntas separadas para estos. La "configuración exitosa" de todos se ve diferente.

¿Qué pasa con SSL / TLS?

Si está proxy de datos, solo sus balanceadores globales necesitan manejar HTTPS. Si está redirigiendo, entonces todos los servidores deben manejarlo.

 18
Author: Brad,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-09-05 03:25:43

Una Solución De Trabajo

He tenido un viaje salvaje en los últimos meses averiguando toda la configuración Global-HA. Toneladas de diversión y finalmente me he establecido con un equipo que funciona muy bien, y no es nada como el descrito en la pregunta anterior.

Todavía planeo escribir esto en forma de tutorial, pero el tiempo es escaso mientras me dirijo al sprint final para lanzar mi aplicación a principios del próximo año, así que aquí hay un breve resumen de la plataforma de trabajo que terminé con.


Descripción general

Terminé trasladando toda mi implementación a AWS. Me encanta Digital Ocean, pero la realidad es que AWS está a años luz de ellos (y de todos, en realidad) cuando se trata de los servicios ofrecidos bajo un mismo techo. Mis gastos mensuales subieron ligeramente, pero una vez que terminé de retocar y simplificar terminé con una solución que cuesta alrededor de 7 75/mes por región para la implementación más básica (2 instancias detrás de un ELB). Y un nuevo la región se puede girar y desplegar en aproximadamente 30 minutos.


Equilibrio global

Rápidamente descubrí (gracias a la respuesta de @Brad anterior) que tratar de girar mi propia capa de DNS de equilibrio global es una locura. Fue un infierno de un montón de diversión averiguar cómo funciona una capa como esta, pero a falta de conseguir en un avión y raspar mis nudillos instalar millones de dólares en equipos en todo el mundo, no iba a ser posible rodar mi propio.

Cuando finalmente descubrí lo que estaba buscando, encontré a mi nuevo mejor amigo: AWS Route 53. Ofrece una red DNS robusta con alrededor de 50 nodos a nivel mundial y la capacidad de hacer algunos trucos de enrutamiento realmente geniales, como enrutamiento basado en la ubicación, enrutamiento basado en latencia (que es un poco impresionante) y registros de AWS Alias que enrutan 'automáticamente' el tráfico a otros servicios de AWS que usará (como ELB para el equilibrio de carga).

Terminé usando basado en latencia enrutamiento que dirige el tráfico global al Equilibrador de carga Elástico regional más cercano, que tiene un Grupo de Escalado automático conectado en cualquier región determinada.

Dejaré que usted haga su tarea sobre los otros proveedores: www.f5.com, www.dyn.com, www.akamai.com, www.dnsmadeeasy.com . Dependiendo de sus necesidades, puede haber una mejor solución para usted, pero esto funciona muy bien para mí.


Entrega De Contenido Red

Route 53 se integra muy bien con AWS Cloudfront. Configuro un bucket S3 que estoy usando para almacenar todos los archivos multimedia estáticos que mis usuarios subirán, y he configurado una distribución de Cloudfront a la fuente desde mi bucket S3 media.myapp.com. Hay otros proveedores de CDN, así que haga sus compras. Pero Cloudfront recibe muy buenas críticas y es muy fácil de configurar.


Equilibrio de carga y terminación SSL

Actualmente estoy usando AWS Elastic Load Balancer para equilibrar la carga entre las instancias de mi aplicación, que viven en un Grupo de escalado automático . La solicitud es recibida por primera vez por ELB, momento en el que se termina SSL y la solicitud se pasa a través de una instancia en el Grupo Auto-Scaling.

NOTA: Una advertencia gigante para ELB es que, irónicamente, no maneja muy bien los picos masivos. Un ELB puede tardar hasta 15 minutos en desencadenar un evento de ampliación por sí mismo, creando 500 / timeouts mientras tanto. Un aumento constante y constante en el tráfico supuestamente se maneja bastante bien, pero si te golpean con un pico, puede fallarte. Si sabes que vas a ser golpeado, puedes 'llamar con anticipación' y AWS calentará tu ELB para ti, lo cual es bastante ridículo y anti-patrón a la esencia de AWS, pero me imaginando que están trabajando en ello, o ignorándolo porque no es realmente un gran problema. Siempre puede girar su propio HAProxy o Nginx capa de equilibrio de carga si ELB no funciona para usted.


Grupo de autoescalado

Cada región tiene un ASG que está programado para escalar cuando la carga pasa una métrica determinada:

IF CPU > 90% FOR 5 MINUTES: SCALEUP
IF CPU < 70% FOR 5 MINUTES: SCALEDN

Todavía no he puesto a prueba el combo ELB/ASG. Eso es un poco por debajo de mi lista de tareas pendientes, pero sé que hay muchos otros que utilizan esta configuración y no parece tener ningún problema de rendimiento importante.

La configuración para un Auto-Scaling Group es un poco complicado en mi opinión. En realidad es un proceso de tres pasos:

  1. Cree una AMI configurada a su gusto.
  2. Cree una configuración de lanzamiento que use la AMI que ha creado.
  3. Cree un Grupo de Escalado automático que utilice la Configuración de lanzamiento que ha creado para determinar qué tipo de AMI y de instancia lanzar para cualquier evento de ESCALADO dado.

Para gestionar la configuración y la implementación de aplicaciones cuando se inicia una instancia, se utiliza el campo"Datos de usuario" para introducir un script que se ejecutará una vez que se inicie una instancia determinada. Esta es posiblemente la peor nomenclatura en la historia del tiempo. Cómo" Datos de usuario " describe un script de inicio que solo conoce el autor. De todos modos, ahí es donde pegas el script que maneja todos tus apt-gets, mkdirs, clones de git, etc.


Instancias y Equilibrio interno

También he agregado una 'capa de equilibrio interno' adicional usando Nginx que me permite 'flat-pack" todo mi Nodo.aplicaciones js (app.myapp.com, api.myapp.com, mobile.myapp.com, www.myapp.com, etc.myapp.com) en todos los casos. Cuando una instancia recibe una solicitud que se le pasa de ELB, Nginx gestiona el enrutamiento de la solicitud al nodo correcto.puerto js para cualquier aplicación dada. Algo así como una contenedorización de pobres. Esto tiene el beneficio adicional de que cada vez que una de mis aplicaciones necesita hablar con la otra (como cuando app. necesita enviar una solicitud a api.) se hace a través de localhost:XXXX en lugar de tener que salga a través de la red de AWS o del propio Internet.

Esta configuración también maximiza el uso de mis recursos al eliminar cualquier infraestructura inactiva si la capa de aplicación que aloja recibe tráfico ligero. También elimina la necesidad de tener y ELB / ASG combo para cada aplicación, ahorrando más dinero.

No hay trampas o advertencias que me he encontrado usando este tipo de configuración, pero hay una solución que debe estar en su lugar con respecto a la comprobación de salud (ver debajo).

También hay una buena ventaja en que todas las instancias tienen un rol de IAM, lo que significa que sus credenciales de AWS se 'cuecen' en cada instancia al nacer y son accesibles a través de sus ENV vars. Y AWS rota automáticamente sus credenciales por usted. Muy seguro, muy genial.


Controles de salud

Si vas por la ruta de la configuración anterior, empaquetando todas tus aplicaciones en una caja y ejecutando un equilibrador de carga interno, entonces necesitas crear un poca utilidad para manejar las comprobaciones de salud de ELB. Lo que hice fue crear una aplicación adicional llamada ping.myapp.com. Y luego configuré mis comprobaciones de estado de ELB para enviar cualquier comprobación de estado al puerto en el que se está ejecutando mi aplicación ping, así:

Ping Protocol: HTTP
Ping Port:     XXXX
Ping Path:     /ping

Esto envía todas las comprobaciones de estado a mi pequeño ayudante ping, que a su vez golpea localhost:XXXX/ping en todas las aplicaciones que residen en la instancia. Si todos devuelven una respuesta de 200, mi aplicación ping devuelve una respuesta de 200 a la comprobación de estado del ELB y instances puede vivir otros 30 segundos.

NOTA: No utilice Comprobaciones de estado de Escalado automático si está utilizando un ELB. Utilice los controles de salud del ELB. Es un poco confuso, pensé que eran lo mismo, no lo son. Tiene la opción de habilitar uno u otro. Ve con ELB.


La Capa De Datos

Una cosa que está claramente ausente de mi configuración es la capa de datos. Yo uso Compose.io como mi proveedor de capa de datos administrada y me despliego en AWS, por lo que obtengo una latencia muy baja entre mis capas de aplicaciones y mi capa de datos. He hecho una investigación preliminar sobre cómo desplegaría mi capa de datos a nivel mundial y descubrí que es muy compleja y muy costosa, por lo que la he eliminado de mi lista como un problema que aún no necesita resolverse. El peor de los casos es que voy a ejecutar mi capa de datos en US-East solamente y reforzar el hardware. Esto no es lo peor del mundo ya que mi API es estrictamente datos JSON en el cable por lo que el la respuesta promedio es relativamente pequeña. Pero puedo ver que esto se convierte en un cuello de botella a gran escala, a escala global - si alguna vez llego allí. Si alguien tiene alguna entrada en esta capa me encantaría escuchar lo que tienes que decir.


Ta-Da!

Alta Disponibilidad Global Con Un Presupuesto De Cerveza. Sólo me llevó 6 meses averiguarlo.

Me encanta escuchar cualquier comentario o idea de cualquiera que le lea esto.

 12
Author: AJB,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-12-23 04:17:16

Puede utilizar Anycast para su servicio web de forma gratuita si utiliza el plan gratuito de Cloudflare.

 2
Author: miolini,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-12-23 14:32:19

Digital Ocean ahora admite el equilibrio de carga de los propios servidores. Es extremadamente fácil de configurar y funciona muy bien! Le ahorra tener que agregar componentes innecesarios como nginx (si solo desea usar para el equilibrio de carga).

Estábamos teniendo problemas al usar cargas de archivos SSL con nginx en un servidor digital Ocean, sin embargo, desde la actualización Digital Ocean, hemos eliminado nginx y ahora usamos la función de equilibrio de carga de Digital Ocean y funciona como lo necesitamos.

 0
Author: Sean _space,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-03-01 11:46:45