¿Cómo optimizar la arquitectura de la base de datos para sitios de alto volumen?

28

La pregunta es menos sobre elementos de configuración específicos de Mysql, pero más sobre el manejo de múltiples bases de datos, división de lectura y escritura en múltiples servidores de bases de datos, maestro + maestro. ¿Maestro + esclavos múltiples?

¿Con qué ha tenido la mejor experiencia la gente? ¿Hay algún ejemplo de cómo lograrlo?

vaskoism
fuente

Respuestas:

18

Tenemos una experiencia bastante amplia de los clústeres de MySQL, y Percona ha trabajado con nosotros en varias ocasiones al superar los límites de las configuraciones complejas.

¿Puede Magento manejar de forma nativa esclavos de solo lectura?

Magento es capaz de dividir las lecturas / escrituras en diferentes servidores de bases de datos (con la excepción de algunas versiones rotas, por ejemplo, EE 1.11), lo que le permite compensar la selectcarga a un servidor (o más) adicional (es); y reenviar todas las update/writeconsultas a un solo maestro.

Cuando debo hacerlo

Esta es una pregunta más apropiada. Con los sistemas operativos Magento dedicados como MageStack , cada vez es más común que las técnicas avanzadas de almacenamiento en caché del lado del servidor estén disponibles y se utilicen fácilmente (como el almacenamiento en caché de Varnish y el almacenamiento en caché de Redis).

Históricamente, Magento nunca ha estado sujeto a MySQL, sino a PHP. Pero a medida que Varnish y el almacenamiento en caché de página completa (FPC) se usan con mayor frecuencia, la carga de las tareas repetidas (cargas de categoría / producto, búsquedas frecuentes) se absorbe repentinamente y PHP se convierte en una carga menor. De hecho, solo entra en juego para generar el contenido inicialmente o completar escenarios no almacenables en caché (agregar al carrito, completar pedidos, etc.); a efectos de explicación, estamos ignorando deliberadamente la carga administrativa .

Siempre hemos mantenido el hecho de que MySQL no es un área de preocupación para la mayoría de los minoristas, como se ve aquí y aquí . Pero si está en la región de procesamiento de cientos de pedidos por hora, no de uno o dos dígitos, pronto se convertirá en un área de optimización.

En última instancia, para tiendas más pequeñas (<25k visitantes únicos diarios)

Sus esfuerzos se centrarían mucho mejor en simplemente encontrar un host apropiado que pueda sugerir el hardware correcto desde el offset y que haya configurado la máquina de la manera más óptima para su tienda . No pierda su tiempo buscando configuraciones Master / Slave o Master / Master, lo que no generará ningún beneficio de rendimiento y, en última instancia, requerirá atención continua y conocimiento avanzado de MySQL.

En última instancia, el tamaño y la selección del hardware tendrán un papel más importante que la optimización de MySQL.

Pero para tiendas más grandes

A medida que su tienda comienza a crecer, la carga de conversión o transaccional se vuelve más una carga con la tarea repetida de completar complejos insertsy updates. La adición de cada nuevo pedido provocará la disminución del stock del catálogo, las devoluciones de llamada de las pasarelas de pago y las actualizaciones de los sistemas EPOS / ERP. Combine esto con la purga de caché asociada de los respectivos productos / categorías y pronto verá que la carga de MySQL aumenta desproporcionadamente.

Multi-master nunca es una solución que recomendamos o consideramos como una opción viable, pero Master / Slave puede generar beneficios (enfatizamos, en tiendas de tamaño Enterprise) al compensar la carga de lectura a los nodos secundarios / terciarios.

Pero todavía quiero hacerlo

Primero configura tus esclavos. Somos grandes defensores de las utilidades Percona y ramas de MySQL - tienen una herramienta ideal para tomar calientes copias de seguridad de su base de datos existente - innobackupex. Hay una buena escritura aquí .

En el maestro

Reemplace $ TIMESTAMP o pestaña completa.

mysql
> GRANT REPLICATION SLAVE ON *.*  TO 'repl'@'$slaveip' IDENTIFIED BY '$slavepass';
> quit;
innobackupex --user=username --password=password /path/to/backupdir
innobackupex --user=username --password=password /
       --apply-log /path/to/backupdir/$TIMESTAMP/

rsync -avprP -e ssh /path/to/backupdir/$TIMESTAMP TheSlave:/path/to/mysql/
scp /etc/mysql/my.cnf TheSlave:/etc/mysql/my.cnf

En el esclavo

/etc/init.d/mysql stop
mv /path/to/mysql/datadir /path/to/mysql/datadir_bak
mv /path/to/mysql/$TIMESTAMP /path/to/mysql/datadir
chown -R mysql:mysql /path/to/mysql/datadir
sed -i 's#server-id=1#server-id=2#g' /etc/mysql/my.cnf
/etc/init.d/mysql start
cat /var/lib/mysql/xtrabackup_binlog_info
> TheMaster-bin.000001     481

mysql
> CHANGE MASTER TO MASTER_HOST='$masterip', MASTER_USER='repl', MASTER_PASSWORD='$slavepass', MASTER_LOG_FILE='TheMaster-bin.000001', MASTER_LOG_POS=481;
> START SLAVE;

Luego, una vez que su esclavo esté operativo, en la práctica, solo se necesitan unas pocas líneas de código adicionales para lograrlo.

En ./app/etc/local.xml

<default_read>
  <connection>
    <use/>
    <host><![CDATA[host]]></host>
    <username><![CDATA[username]]></username>
    <password><![CDATA[password]]></password>
    <dbname><![CDATA[dbname]]></dbname>
    <type>pdo_mysql</type>
    <model>mysql4</model>
    <initStatements>SET NAMES utf8</initStatements>
    <active>1</active>
  </connection>
</default_read>

Fuentes

Ben Lessani - Sonassi
fuente
"Históricamente, Magento nunca ha estado sujeto a MySQL, sino a PHP". No estoy seguro de qué Magento hablas, pero EAV siempre ha sido un problema de rendimiento. :)
B00MER
1
Bueno, me refiero a los más de 400 servidores Magento que administramos ... como regla general, hay muchos otros cuellos de botella antes de que MySQL sea una consideración. De hecho, un excelente ejemplo es uno de nuestros clientes durante diciembre. Con 15k visitantes únicos por hora, procesando 200 pedidos por hora en un solo servidor configurado (32 núcleos, 64GB de RAM). Para el lector típico de esta pregunta, es extremadamente improbable que esté haciendo incluso este volumen. Entonces, en los niveles de tráfico y transacciones que encontrarán, MySQL no es el cuello de botella.
Ben Lessani - Sonassi
1
@Brandon. Solo quiero decir agregar. No niego que ajustar MySQL no sea un requisito, obviamente lo es. Pero no es necesario configurar una configuración Maestro / Maestro o Maestro / Esclavo para mejorar el rendimiento hasta que realmente llegue a un cierto punto de inflexión, y eso es bastante alto. Además, es mucho más posible causar un cuello de botella en el rendimiento o arriesgar la integridad de los datos, al intentar hacer tal cosa.
Ben Lessani - Sonassi
5

En general, Magento está vinculado a la CPU, no a la base de datos, y la mayor parte de la actividad de la CPU se puede almacenar en caché, por lo que encontrará tantos tutoriales sobre configuraciones de barniz / nginx. También puede mover su administrador a un nodo web separado como se detalla aquí .

Para mayor robustez general, la mejor inversión absoluta será un servicio MySQL administrado.

Solo tengo experiencia con Amazon RDS, pero automatizan la conmutación por error, las copias de seguridad, las actualizaciones, la ampliación / reducción, así como la creación de réplicas de lectura. Por lo tanto, puede tener un nodo maestro de alta disponibilidad que tenga conmutación por error automática: Amazon utiliza una replicación de registro binaria personalizada para mantener al esclavo sincronizado, la conmutación por error generalmente toma menos de 2 minutos y luego puede crear tantas réplicas de lectura como desee. necesita escalar para sus necesidades de informes / integración.

Busqué dividir lecturas / escrituras que es muy factible con la arquitectura de Magento, pero la base de datos no es un cuello de botella en mi caso de uso. Recomiendo utilizar perfiles como xhprof / xhgui en lugar de adivinar lo que necesita ser optimizado. La primera regla del perfil es medir.

Ralph Tice
fuente
Por favor, no estamos aquí para construir un sitio web de marcadores donde las preguntas se respondan con enlaces. Incluya las partes esenciales de la respuesta aquí y proporcione el enlace para referencia.
j0k
@ j0k Los enlaces se proporcionan como referencia y la respuesta es independiente; si no está de acuerdo, sea más específico.
Ralph Tice el
Sí, al menos, tu respuesta es mejor que la otra. Lo que quiero decir es que OP podría necesitar más información técnica sobre qué configurar, por qué no un esquema de arquitectura, etc. ¡Incluso si tu experiencia es excelente!
j0k
5

No he tenido experiencia en producción con esto, pero después de investigar un poco, he encontrado este artículo. En este artículo, alguien explica cómo configurar la replicación maestro-esclavo para Magento, por lo que podría serle útil.

Bit más importante:

/app/etc/local.xml

<default_setup>
    <connection>
        <host><![CDATA[Master-host]]></host>
        <username><![CDATA[user]]></username>
        <password><![CDATA[pass]]></password>
        <dbname><![CDATA[magentodb]]></dbname>
        <active>1</active>
    </connection>
</default_setup>
<default_read>
    <connection>
        <use/>
        <host><![CDATA[Slave-host]]></host>
        <username><![CDATA[user]]></username>
        <password><![CDATA[pass]]></password>
        <dbname><![CDATA[magento]]></dbname>
        <type>pdo_mysql</type>
        <model>mysql4</model>
        <initStatements>SET NAMES utf8</initStatements>
        <active>1</active>
    </connection>
</default_read> 

La configuración para el servidor maestro MySQL (/etc/mysql/my.cnf) agrega el siguiente contenido en el archivo:

[mysqld]
server-id       = 1
log_bin         = /var/log/mysql/mysql-bin.log
expire_logs_days    = 10
max_binlog_size     = 100M
binlog_do_db        = magento_demo
binlog_ignore_db    = mysql 

La configuración para el servidor esclavo MySQL (/etc/mysql/my.cnf) agrega el contenido siguiente en el archivo:

[mysqld]
server-id=2
log-bin=mysql-bin
master-host=192.168.1.2
master-user=username
master-password=111111
master-port=3306
replicate-do-db=magento_demo
replicate-ignore-db=mysql
master-connect-retry=60 

Reinicie ambos servidores MySQL luego

Kenny
fuente
1
El enlace solitario se considera una respuesta pobre ya que no tiene sentido por sí mismo y no se garantiza que el recurso objetivo esté vivo en el futuro . Sería preferible incluir aquí las partes esenciales de la respuesta y proporcionar el enlace para referencia.
j0k
@ j0k, hecho según lo solicitado;)
Kenny
3

Una idea es que puede dividir las lecturas de su catálogo en servidores esclavos utilizando dns round-robin .

Por lo tanto, configure la replicación normal maestro -> esclavo (s) en MySQL.

Luego, en su configuración de Magento, puede configurar su catálogo para que realice lecturas desde su host DNS configurado para round-robin. Las escrituras permanecerán en su base de datos maestra.

Puedes hacer esto en app/etc/local.xml

<catalog_read_setup>
   <connection>
      <host><![CDATA[round.robbin.dns.host]]></host>
      <username><![CDATA[USERNAME]]></username>
      <password><![CDATA[password]]></password>
      <dbname><![CDATA[DATABASE]]></dbname>
      <initStatements><![CDATA[SET NAMES utf8]]></initStatements>
      <model><![CDATA[mysql4]]></model>
      <type><![CDATA[pdo_mysql]]></type>
      <pdoType><![CDATA[]]></pdoType>
      <active>1</active>
   </connection>
</catalog_read_setup>
<catalog_read>
   <connection>
     <use>catalog_read_setup</use>
   </connection>
 </catalog_read>

Puede redirigir cualquier módulo central (y de terceros) para usar una instancia de MySQL diferente de la misma manera.

ProxiBlue
fuente
1
DNS round robin no es una solución de ningún tipo. El proxy MySQL o HAProxy son soluciones mucho más sofisticadas para equilibrar la carga de lectura de MySQL.
Ben Lessani - Sonassi