Tenemos una base de datos a nivel empresarial de gran escala. Como parte de nuestro modelo de negocio, todos los usuarios web acceden a nuestros servidores web al mismo tiempo cada mes, lo que a su vez afecta nuestro cuadro sql. El tráfico es muy pesado y continúa creciendo a medida que crece la empresa. Se ha realizado la optimización del proceso sql y el hardware ya se ha ampliado a un nivel muy alto.
Estamos buscando fragmentar la base de datos ahora para garantizar que podamos manejar el crecimiento de la empresa y las cargas futuras.
Hemos decidido qué datos particulares se deben fragmentar. Es un subconjunto de nuestra base de datos que es altamente utilizado.
Sin embargo, mi pregunta es sobre los datos no fragmentados que son comunes / universales. Un ejemplo de datos como este puede ser una tabla de inventario, por ejemplo, o posiblemente una tabla de empleados, una tabla de usuarios, etc.
Veo dos opciones para manejar estos datos comunes / universales:
1) diseño 1 - Coloque los datos comunes / universales en una base de datos externa. Todas las escrituras ocurrirán aquí. Estos datos luego se replicarán en cada fragmento permitiendo que cada fragmento lea estos datos y se unan internamente a estos datos en procesos t-sql.
2) diseño 2: dé a cada fragmento su propia copia de todos los datos comunes / universales. Deje que cada fragmento escriba localmente en estas tablas y utilice la replicación de combinación sql para actualizar / sincronizar estos datos en todos los demás fragmentos.
preocupaciones sobre el diseño # 1
1) Problemas transaccionales: si tiene una situación en la que debe escribir o actualizar datos en un fragmento y luego escribir / actualizar una tabla común / universal en 1 proceso almacenado, por ejemplo, ya no podrá hacerlo fácilmente. Los datos ahora existen en instancias y bases de datos SQL separadas. Es posible que necesite involucrar a MS DTS para ver si puede ajustar estas escrituras en una transacción, ya que están en una base de datos separada. El rendimiento es una preocupación aquí y las posibles reescrituras pueden estar involucradas para procesos que escriben en datos fragmentados y comunes.
2) una pérdida de integridad referencial. No es posible hacer integridad referencial cruzada de bases de datos.
3) Recodificar grandes áreas del sistema para que sepa escribir datos comunes en la nueva base de datos universal pero lea datos comunes de los fragmentos.
4) aumento de los viajes a la base de datos. Al igual que en el punto 1 anterior, cuando se encuentra con una situación en la que debe actualizar datos fragmentados y datos comunes, realizará múltiples viajes de ida y vuelta para lograr esto, ya que los datos ahora están en bases de datos separadas. Aquí hay latencia de red, pero no estoy tan preocupado por este problema como los 3 anteriores.
preocupaciones sobre el diseño # 2
En el diseño # 2, cada fragmento obtiene su propia instancia de todos los datos comunes / universales. Esto significa que todo el código que se une o actualiza datos comunes continúa funcionando / ejecutándose tal como lo hace hoy. Se necesita muy poca grabación / reescritura del equipo de desarrollo. Sin embargo, este diseño depende completamente de la replicación de fusión para mantener los datos sincronizados en todos los fragmentos. los dbas son altamente calificados y están muy preocupados de que la replicación de fusión no sea capaz de manejar esto y si falla la replicación de fusión, la recuperación de esta falla no es excelente y podría impactarnos muy negativamente.
Tengo curiosidad por saber si alguien se ha ido con la opción de diseño # 2. También tengo curiosidad por saber si estoy pasando por alto una tercera o cuarta opción de diseño que no veo.
gracias de antemano.
fuente
Respuestas:
Su pregunta se centró en esto:
Cuando está haciendo sharding, y tiene datos que todos los fragmentos necesitan ver, debe clasificar esos datos con algunos atributos:
¿Cambia con frecuencia? En sus ejemplos, enumeró Inventario, Empleado y Usuario. Por lo general, el inventario cambia muy rápido, pero los registros de Empleados solo cambian periódicamente (por ejemplo, unos cientos de actualizaciones por día).
¿Cuánto retraso puede tolerar cada fragmento?Aunque el inventario puede estar cambiando constantemente, normalmente puede tolerar una gran cantidad de retraso (minutos o incluso horas) en una mesa como esa. Si está vendiendo artículos únicos con una cantidad muy limitada que nunca puede reponer (piense en obras de arte originales), entonces no comparte esos datos en absoluto, solo consulta la base de datos original. Sin embargo, en la mayoría de las tiendas en línea, no está vendiendo todos los artículos todos los días, y de todos modos va a reabastecer las cosas rápidamente, por lo que realmente no necesita recuentos de inventario de hasta milisegundos. De hecho, en la mayoría de los casos, solo necesita un indicador En stock que sea 0 o 1, y un proceso central actualiza ese indicador. De esa manera, no tiene que empujar cada golpe de subida / bajada del recuento de elementos a cada fragmento. Datos de empleados o usuarios, por otro lado,
¿Te unirás de las tablas fragmentadas a las no fragmentadas? Idealmente, la respuesta aquí es no: debe hacer dos consultas separadas para obtener los datos y luego unirlas en el lado de la aplicación. Esto se vuelve mucho más difícil desde la perspectiva de una aplicación, pero le brinda la capacidad de obtener los datos más recientes de cada fuente.
¿Son estos datos originales o copiados?Otra forma de pensar en esta pregunta: ¿qué necesita hacer una copia de seguridad y con qué frecuencia? Por lo general, en un entorno de fragmentación de alto volumen, desea que las copias de seguridad sean lo más rápidas y lo más pequeñas posible. (Después de todo, debe proteger cada nodo y desea que todos los fragmentos se conmuten por error a DR en el mismo momento, no tener algunos fragmentos con datos más nuevos que otros). Esto significa que los datos fragmentados y los no Los datos fragmentados deben estar en bases de datos completamente separadas, incluso si están en el mismo servidor. Es posible que necesite copias de seguridad constantes del registro de transacciones de mis datos fragmentados (originales), pero es posible que no necesite hacer una copia de seguridad de los datos no fragmentados. Probablemente sea más fácil para mí simplemente actualizar mi tabla de Empleados o Usuarios desde la única fuente de verdad en lugar de hacer una copia de seguridad en cada fragmento. Sin embargo, si todos mis datos están en una sola base de datos,
Ahora, sobre sus preocupaciones:
"Problemas transaccionales ... ya no podrá hacer esto fácilmente". Correcto. En escenarios fragmentados, arroje el concepto de una transacción por la ventana. También empeora: para los datos fragmentados, puede tener uno fragmentado y en línea, y otro fragmentado temporalmente debido a una conmutación por error o reinicio de la instancia del clúster. Debe planificar la falla de cualquier parte del sistema, en cualquier momento.
"No es posible hacer integridad referencial cruzada de bases de datos". Correcto. Cuando divide una sola tabla en varios servidores, se pone el pantalón grande y le dice al servidor de la base de datos que se está haciendo cargo de tareas difíciles como copias de seguridad en un momento determinado, relaciones entre tablas y combinación de datos de múltiples fuentes. Está en ti y en tu código ahora.
"Recodificar grandes áreas del sistema para que sepa escribir datos comunes en la nueva base de datos universal pero lea datos comunes de los fragmentos". Corregir aquí también. No hay un botón fácil para esto, pero una vez que haya incorporado esto en la aplicación, podrá escalar como loco. Yo diría que la forma más fácil de hacer esto es dividir las conexiones de la aplicación por lecturas .
"aumento de los viajes a la base de datos". - Sí, si divide los datos en varios servidores, la aplicación tendrá que llegar más a la red. La clave es implementar también el almacenamiento en caché para que algunos de estos datos puedan almacenarse en sistemas de bajo costo, mayor rendimiento y sin bloqueo. La consulta más rápida es la que nunca haces.
También he presentado más ventajas y desventajas para dividir las bases de datos de múltiples inquilinos aquí , como el ajuste del rendimiento en fragmentos individuales, diferentes estrategias de copia de seguridad / recuperación por fragmento y desafíos de implementación de esquemas.
fuente
En un nivel alto, la forma típica de fragmentar (o particionar horizontalmente) datos es fragmentar las tablas transaccionales y replicar las tablas de nivel maestro. Como la mayoría de las soluciones tecnológicas, esto, por supuesto, resuelve un conjunto de problemas y crea un conjunto completamente nuevo de problemas ... pero ya estamos acostumbrados a eso, ¿no? ;-)
Sin embargo, me preguntaría si SQLServer es su mejor solución para esto. ¿La carga de trabajo se parece más a OLTP o más a DW / BI?
Saludos, Dave Sisk
fuente
Una posible tercera opción. Con el uso de fragmentos relacionales (en lugar del cuadro negro), debería poder fragmentar y distribuir toda su base de datos. Debido a que se basa en un modelo tradicional de datos relacionales, la base de datos sabe qué datos están almacenados en qué servidores y, por lo tanto, dónde encontrarlos, por lo que todos sus datos pueden considerarse 'comunes / universales'. Eche un vistazo a dbShards como una posibilidad para facilitar todo el proceso de fragmentación.
fuente