понедельник, 8 октября 2012 г.

PHP расширение mysqli - множественные запросы



Помимо выполнения одного запроса за раз, MySQL и расширение mysqli предоставляет возможность выполнения множества запросов одной строкой. При этом можно получить выгоду в скорости за счёт передачи данных.

Для реализации этой возможности mysqli предоставляет метод multi_query(), который в качестве параметра принимает строку запросов, разделённых символом «;». Длинна строки ограничена количеством байт указанными директивой MySQL max_allowed_packet.

mysql> SHOW VARIABLES LIKE 'max_allowed_packet';
+--------------------+---------+
| Variable_name      | Value   |
+--------------------+---------+
| max_allowed_packet | 1048576 |
+--------------------+---------+
1 row in set (0.13 sec)

После отправки запроса, необходимо выбрать все результаты (даже если запросы не возвращают результатов). В противном случае при новых запросах получим ошибку «Error: Commands out of sync; you can't run this command now». При этом результат первого запроса выбирается автоматически.

Для выборки результатов можно использовать, например, следующий код:
do
{
    $result = $mysqli->store_result();
 
    if (is_object($result))
    {
        while ($row = $result->fetch_assoc())
        {
            print_r($row);
            echo '<br />';
        }
 
        $result->free();
    }
 
    echo '----<br />';
    break;
}
while ($mysqli->more_results() AND $mysqli->next_result());
В отличии от метода query(), метод для множественных запросов multi_query() подвержен SQL-инъекциям. Поэтому применять его нужно с осторожностью.

Метод next_result() возвращает false в случае, когда закончились результаты и когда запрос вернул ошибку. Поэтому на ошибку нужно проверять и после оконачания цикла выборки.
$mysqli = new mysqli('localhost', 'user', 'pass', 'test');
 
$mysqli->multi_query('  SELECT * FROM `test`;
    INSERT INT `test` (`value`) VALUES ("value");') OR
    exit('Error: (' . $mysqli->errno . ') ' . $mysqli->error);
 
do
{
    $result = $mysqli->store_result();
 
    if (is_object($result))
    {
        while ($row = $result->fetch_assoc())
        {
            print_r($row);
            echo '<br />';
        }
 
        $result->free();
    }
 
    echo '----<br />';
    break;
}
while ($mysqli->more_results() AND $mysqli->next_result());
 
if ($mysqli->errno)
{
    exit('Error: (' . $mysqli->errno . ') ' . $mysqli->error);
}
 
$mysqli->close();

Комментариев нет:

Отправить комментарий