Sugerencias SQL

Las sugerencias SQL pueden forzar a una consulta a elegir un servidor específico de la agrupación de conexiones. Proporcionan al complemento una recomendación para utilizar un servidor indicado, lo que puede resolver problemas causados por intercambios de conexión y estados de conexión.

Las sugerencias SQL son comentarios que siguen el estándar. Ya que los comentarios SQL son ignorados por sistemas de procesamiento SQL, no interfieren con otros programas como el Servidor MySQL, el Proxy MySQL, o un cortafuegos.

El complemento admite tres sugerencias SQL: La sugerencia MYSQLND_MS_MASTER_SWITCH hace que el complemento ejecute una sentencia en el maestro, MYSQLND_MS_SLAVE_SWITCH fuerza el uso del esclavo, y MYSQLND_MS_LAST_USED_SWITCH ejecutará una sentencia en el mismo servidor que se utilizó con la sentencia anterior.

El complemento examina el comienzo de una sentencia para la existencia de una sugerencia SQL. Las sugerencias SQL solo son reconocidas si aparecen al comienzo de la sentencia.

Ejemplo #1 Configuración del complemento con un esclavo y un maestro

{
    "myapp": {
        "master": {
            "master_0": {
                "host": "localhost",
                "socket": "\/tmp\/mysql.sock"
            }
        },
        "slave": {
            "slave_0": {
                "host": "192.168.2.27",
                "port": "3306"
            }
        }
    }
}

Ejemplo #2 Sugerencias SQL para evitar el intercambio de conexión

<?php
$mysqli 
= new mysqli("myapp""nombre_usuario""contraseña""base_datos");
if (
mysqli_connect_errno()) {
  
/* Por supuesto, su manejo de errores es mejor... */
  
die(sprintf("[%d] %s\n"mysqli_connect_errno(), mysqli_connect_error()));
}

/* Conexión 1, la conexión vincula una variable SQL de usuario, no se ejecuta ningún SELECT en el maestro */
if (!$mysqli->query("SET @myrole='master'")) {
 
printf("[%d] %s\n"$mysqli->errno$mysqli->error);
}

/* Conexión 1, se ejecuta en el maestro debido a la sugerencia SQL */
if (!($res $mysqli->query(sprintf("/*%s*/SELECT @myrole AS _role"MYSQLND_MS_LAST_USED_SWITCH)))) {
 
printf("[%d] %s\n"$mysqli->errno$mysqli->error);
} else {
 
$fila $res->fetch_assoc();
 
$res->close();
 
printf("@myrole = '%s'\n"$fila['_role']);
}
$mysqli->close();
?>

El resultado del ejemplo sería:

@myrole = 'master'

En el ejemplo de arriba, el uso de MYSQLND_MS_LAST_USED_SWITCH evita el intercambio de sesión desde el maestro al esclavo al ejecutar la sentencia SELECT.

Las sugerencias SQL también se pueden usar para ejecutar sentencias SELECT en el servidor maestro de MySQL. Esto podría ser necesario si los servidores esclavos de MySQL están normalmente detrás del maestro, pero no se necesitan datos actuales del clúster.

En la versión 1.2.0, el concepto de nivel de servicio ha sido introducido para dirigir casos en los que no son necesarios datos actuales. El uso de un nivel de servicio requiere menos atención y elimina la necesidad de usar sugerencias SQL para este caso. Se puede encontrar más información más abajo en la sección de nivel de servicio y consistencia.

Ejemplo #3 Enfrentarse a la demora de replicación

<?php
$mysqli 
= new mysqli("myapp""nombre_usuario""contraseña""base_datos");
if (!
$mysqli) {
    
/* Por supuesto, su manejo de errores es mejor... */
    
die(sprintf("[%d] %s\n"mysqli_connect_errno(), mysqli_connect_error()));
}

/* Forzar el uso del maestro, el maestro siempre tiene datos recientes y actuales */
if (!$mysqli->query(sprintf("/*%s*/SELECT critical_data FROM important_table"MYSQLND_MS_MASTER_SWITCH))) {
    
printf("[%d] %s\n"$mysqli->errno$mysqli->error);
}
?>

Un caso de uso puede incluir la creación de tablas en un esclavo. Si no se proporciona una sugenrencia SQL, el complemento enviará las sentencias CREATE e INSERT al maestro. Utilice la sugerencia SQL MYSQLND_MS_SLAVE_SWITCH si quiere ejecutar tales sentencias en un esclavo, por ejemplo, para construir tablas de informes temporales.

Ejemplo #4 Creación de una tabla en un esclavo

<?php
$mysqli 
= new mysqli("myapp""nombre_usuario""contraseña""base_datos");
if (!
$mysqli) {
    
/* Por supuesto, su manejo de errores es mejor... */
    
die(sprintf("[%d] %s\n"mysqli_connect_errno(), mysqli_connect_error()));
}

/* Forzar el uso del esclavo */
if (!$mysqli->query(sprintf("/*%s*/CREATE TABLE informes_esclavo(id INT)"MYSQLND_MS_SLAVE_SWITCH))) {
    
printf("[%d] %s\n"$mysqli->errno$mysqli->error);
}
/* Continuar usando esta conexión esclava en particular */
if (!$mysqli->query(sprintf("/*%s*/INSERT INTO informes_esclavo(id) VALUES (1), (2), (3)"MYSQLND_MS_LAST_USED_SWITCH))) {
    
printf("[%d] %s\n"$mysqli->errno$mysqli->error);
}
/* ¡No usar MYSQLND_MS_SLAVE_SWITCH, ya que permitiría el intercambio con otro esclavo! */
if ($res $mysqli->query(sprintf("/*%s*/SELECT COUNT(*) AS _num FROM informes_esclavo"MYSQLND_MS_LAST_USED_SWITCH))) {
    
$fila $res->fetch_assoc();
    
$res->close();
    
printf("Hay %d filas en la tabla 'informes_esclavo'"$fila['_num']);
} else {
    
printf("[%d] %s\n"$mysqli->errno$mysqli->error);
}
$mysqli->close();
?>

La sugerencia SQL MYSQLND_MS_LAST_USED prohíbe el intercambio de una conexión, por lo que fuerza el uso de la conexión utilizada anteriormente.