задний план
Поскольку существуют пакетные операции с данными в кеше Redis, такие как прогрев данных кеша или получение данных кеша пакетами на странице списка, после использования транзакции отправки нескольких пакетов обнаруживается, что давление Redis остается высоким. , но после использования трубопровода давление упало до нормы. , а также из-за этого случая напишу здесь анализ и заметки.
multi
Введение
Отмечает начало блока транзакции. Несколько команд в блоке транзакций будут помещены в очередь по порядку и, наконец, выполнены атомарно с помощью команды EXEC.
Принцип реализации
Я использую расширение php, чтобы вызвать службу Redis и выполнить ее Код выглядит следующим образом:
$redis = new redis();
$redis->connect('127.0.0.1',6379);
$handle = $redis->multi();
$handle->incr('a');
$handle->incr('b');
$handle->exec();
Чтобы просмотреть конкретный процесс подключения в течение этого периода, используйте wireshark для мониторинга порта 6379 петлевого адреса, а запрос захвата пакета показан на следующем рисунке:
После того, как клиент Redis устанавливает соединение с сервером, запускается транзакция с несколькими отметками, и каждый раз, когда она выполняется, сервер возвращает флаг поставленной в очередь очереди. Просмотрите исходный файл Redis src/multi.c:
void queueMultiCommand(client *c) {
multiCmd *mc;
int j;
c->mstate.commands = zrealloc(c->mstate.commands,
sizeof(multiCmd)*(c->mstate.count+1));
mc = c->mstate.commands+c->mstate.count;
mc->cmd = c->cmd;
mc->argc = c->argc;
mc->argv = zmalloc(sizeof(robj*)*c->argc);
memcpy(mc->argv,c->argv,sizeof(robj*)*c->argc);
for (j = 0; j < c->argc; j++)
incrRefCount(mc->argv[j]);
c->mstate.count++;
}
В приведенном выше исходном коде вы можете видеть, что сервер Redis каждый раз сохраняет команды в блоке транзакций в память.В приведенном выше введении объясняется, что в конечном итоге он выполняется командой exec.Посмотрите на результат возврата в следующем примере изображение, чтобы понять сервер Redis один раз.Возвращает все результаты выполнения команды.
pipeline
Введение
Клиент записывает выполненную команду в буфер, и, наконец, команда exec отправляет ее в redis для выполнения за один раз и возвращается.
Принцип реализации
Точно так же используйте соответствующий код для вызова Redis для захвата пакетов;
$redis = new redis();
$redis->connect('127.0.0.1',6379);
$handle = $redis->pipeline();
$handle->incr('a');
$handle->incr('b');
$handle->exec();
Продолжайте использовать wireshark для захвата пакетов, как показано ниже.
- Пример схемы пакета запросов клиента конвейера
- Пример схемы возврата пакета конвейерного сервера
Кратко проанализирован приведенный выше рисунок. Работа конвейера требует поддержки клиента и сервера. Клиент записывает команду в буфер и, наконец, отправляет ее на сервер с помощью команды exec. Сервер разделяет команду и возвращает результаты. по одному.
Разница между двумя
Из приведенных выше запросов также видно, что наиболее очевидная разница между ними заключается в том, что клиент отправляет запросы по-разному.Конкретные различия заключаются в следующем:
- конвейер выбирает буферизацию на стороне клиента, а множественный выбор буферизации на стороне сервера;
- Количество запросов непостоянно.Мульти требует, чтобы каждая команда была отправлена на сервер один раз, и конвейер отправляется на сервер одновременно.Количество запросов меньше по сравнению с мульти.
- multi/exec может гарантировать атомарность, в то время как конвейер не гарантирует атомарность
Адрес личного блога:blog.walkerx.cn