sql >> Base de Datos >  >> NoSQL >> MongoDB

Problemas de conexión de MongoDB en Azure

Unos pocos miles de solicitudes por minuto es un gran load, y la única forma de hacerlo bien es controlando y limitando el número máximo de subprocesos que se pueden ejecutar en un momento dado.

Como no hay mucha información publicada sobre cómo ha implementado esto. Voy a cubrir algunas posibles circunstancias.

Es hora de experimentar...

Las constantes:

  • Elementos a procesar:
    • 50 por segundo , o en otras palabras...
    • 3000 por minuto , y una forma más de verlo...
    • 180.000 por hora

Las variables:

  • Tasas de transferencia de datos:

    • La cantidad de datos que puede transferir por segundo jugará un papel sin importar lo que hagamos, y esto variará a lo largo del día dependiendo de la hora del día.

      Lo único que podemos hacer es enviar más solicitudes desde diferentes CPU para distribuir el peso del tráfico que estamos enviando de un lado a otro.

  • Potencia de procesamiento:

    • Supongo que tienes esto en un WebJob en lugar de tener esto codificado dentro del sitio MVC en sí mismo. Es altamente ineficiente y no se ajusta al propósito que está tratando de lograr. Mediante el uso de un WebJob podemos poner en cola elementos de trabajo para ser procesados ​​por otros WebJobs . La cola en cuestión es Azure Queue Almacenamiento .

Los problemas:

  • Estamos intentando completar 50 transacciones por segundo, por lo que cada transacción debería realizarse en menos de 1 segundo si usáramos 50 subprocesos. Nuestro tiempo muerto de 45 segundos no sirve para nada en este momento.
  • Esperamos que se ejecuten 50 subprocesos simultáneamente y que se completen en menos de un segundo, cada segundo, en una sola CPU. (Estoy exagerando un punto aquí, solo para aclarar un punto... pero imagine descargar 50 archivos de texto cada segundo. Procesándolo, luego tratando de enviarlo a un colega con la esperanza de que incluso esté listo para atraparlo)
  • Necesitamos tener una lógica de reintento, si después de 3 intentos el elemento no se procesa, debe volver a colocarse en la cola. Idealmente, deberíamos proporcionar más tiempo al servidor para responder que solo un segundo con cada falla, digamos que le dimos un descanso de 2 segundos en la primera falla, luego 4 segundos, luego 10, esto aumentará en gran medida las probabilidades de que persistamos. / recuperando los datos que necesitábamos.
  • Estamos suponiendo que nuestro MongoDb puede manejar este número de solicitudes por segundo. Si aún no lo ha hecho, comience a buscar formas de escalarlo, el problema no es el hecho de que sea un MongoDb, la capa de datos podría haber sido cualquier cosa, es el hecho de que estamos haciendo esta cantidad de solicitudes de una sola fuente que será la causa más probable de sus problemas.

La solución:

  1. Configurar un WebJob y asígnele el nombre EnqueueJob . Este WebJob tendrá un único propósito, poner en cola elementos de trabajo para ser procesados ​​en el Queue Storage .
  2. Cree un Queue Storage Container llamado WorkItemQueue , esta cola actuará como desencadenante del siguiente paso y dará inicio a nuestras operaciones de escalamiento horizontal.
  3. Crear otro WebJob llamado DequeueJob . Este WebJob también tendrá un único propósito, sacar de la cola los elementos de trabajo de WorkItemQueue y envíe las solicitudes a su almacén de datos.
  4. Configurar DequeueJob para girar una vez que se ha colocado un elemento dentro de WorkItemQueue , inicie 5 subprocesos separados en cada uno y mientras la cola no esté vacía, elimine elementos de trabajo para cada subproceso e intente ejecutar el trabajo eliminado.
    1. Intento 1, si falla, espere y vuelva a intentarlo.
    2. Intento 2, si falla, espere y vuelva a intentarlo.
    3. Intento 3, si falla, vuelva a poner el elemento en cola en WorkItemQueue
  5. Configure su sitio web para escalar automáticamente a x cantidad de CPU (tenga en cuenta que su sitio web y los trabajos web comparten los mismos recursos)

Aquí hay un breve video de 10 minutos que brinda una descripción general sobre cómo utilizar los almacenamientos en cola y los trabajos web.

Editar:

Otra razón por la que puede estar recibiendo esos errores podría deberse también a otros dos factores, nuevamente causados ​​por estar en una aplicación MVC...

Si está compilando la aplicación con DEBUG atributo aplicado pero empujando el RELEASE versión en su lugar, podría tener problemas debido a la configuración en su web.config , sin el DEBUG atributo, una aplicación web ASP.NET ejecutará una solicitud durante un máximo de 90 segundos; si la solicitud tarda más, la eliminará.

Para aumentar el tiempo de espera a más de 90 segundos deberá cambiar el [httpRuntime][3] propiedad en su web.config ...

<!-- Increase timeout to five minutes -->
<httpRuntime executionTimeout="300" />

La otra cosa que debe tener en cuenta es la configuración de tiempo de espera de solicitud de su navegador> aplicación web, diría que si insiste en mantener el código en MVC en lugar de extraerlo y ponerlo en un WebJob, entonces usted puede usar el siguiente código para enviar una solicitud a su aplicación web y compensar el tiempo de espera de la solicitud.

string html = string.Empty;
string uri = "http://google.com";
HttpWebRequest request = (HttpWebRequest)WebRequest.Create(uri);
request.Timeout = TimeSpan.FromMinutes(5);

using (HttpWebResponse response = (HttpWebResonse)request.GetResponse())
using (Stream stream = response.GetResponseStream())
using (StreamReader reader = new StreamReader(stream))
{
    html = reader.ReadToEnd();
}