Мы реализовали retry_strategy, которая выдает ошибку после определенного количества повторных попыток. Затем он перейдет к обработчику Redis («ошибка»), который будет зарегистрирован и выйдет из приложения. При обновлении нашей библиотеки redis с 2.4.2
до 2.6.2
мы заметили, что это поведение уже не то же самое.
Репродукция:
const redis = require('redis');
const MAX_ATTEMPTS = 10;
var client = redis.createClient(port, host, {
retry_strategy: redisRetryStrategy
});
client.on('error', onError);
function OnError(err) {
console.log(err);
throw new Error('SHUTDOWN THE APP, REDIS IS NOT RESPONDING??');
}
function redisRetryStrategy(host, options) {
if (options.attempt >= MAX_ATTEMPTS) {
// Stop reconnecting after reaching the maximum number of attempts
return new Error('Maximum redis reconnect attempts reached');
}
return 1000; // Schedule next reconnection attempt after 1 sec.
}
На самом деле это было сделано специально. Причина в том, что у вас уже есть информация о сбое клиента, поэтому ее больше не нужно отправлять. Это действительно плохое изменение в поддержании semver в рабочем состоянии: / Мне очень жаль.
Я хотел бы провести небольшой опрос, чтобы узнать, что думают другие люди. Пинг @ NodeRedis / участники @dirkbonhomme
Да: передать ошибку в прослушиватель ошибок
Нет: сохранить текущее решение
Чтобы предложить вариант использования в пользу первого, connect-redis предоставляет параметр logErrors
который становится ( неочевидно ) взаимоисключающим с retry_strategy
если ошибки не всплывают.
new RedisStore({
logErrors: (err) => console.error, // does nothing
retry_strategy: (options) => {
if (options.error.code === 'ECONNREFUSED' || options.error.code === 'ENOTFOUND') {
return new Error('The server could not be found or refused the connection');
}
return 1000;
}
})
@tj
Я думаю, что текущая функциональность в порядке, если она указана в документации, а это не так. Я думаю, что было бы также приемлемо добавить параметр, который по-прежнему будет выдавать ошибки, возвращаемые стратегией повтора.
Бывший.:
redis.createClient({
retry_strategy: ...,
retry_strategy_bubble_up: true or false (default to false to keep existing functionality)
});
Просто потратил последний день, пытаясь выяснить, почему не регистрируются ошибки. Теперь, когда ведение журнала находится в обратном вызове retry_strategy, в моем приложении все работает так, как я хочу.
Вместо того, чтобы выдавать ошибку, я вручную генерирую событие ошибки, которое может быть перехвачено обработчиком ошибок:
retry_strategy: function(options) {
logger.debug('Retry redis connection: ', options.attempt);
// 5 mins
if (options.total_retry_time > 1000 * 60 * 5) {
// End reconnecting after a specific timeout and flush all commands with a individual error
return logger.error('Redis: maximum retry time exhausted');
}
if (options.attempt > 5) {
// End reconnecting with built in error
logger.error('Redis: maximum connection retry reached');
return client.emit('error', 'maximum retry');
}
return 1000 * 2;
},
Пузыриться ! (или что-то другое)
Пользовательский эмиттер ошибок, такой как @alannesta, написал беспорядочно, retry_strategy
- один из параметров конструктора, он не должен обращаться к объекту, находящемуся вне функции.
NodeRedis
уже есть система событий, просто используйте ее!
Поскольку end
занят, и это означает «соединение закрыто», мы можем добавить новое событие (назовем его сейчас просто «выключение»), которое указывает, что «мы сделали все, что могли, это соединение мертво. , впредь мы ничего не предпринимаем, вам лучше заняться уборкой ».
Мне действительно нужно это изменение.
Что-нибудь случилось с этой проблемой?
Есть ли причина, по которой это не закреплено или это просто приоритет? В чем преимущество отсутствия генерации события? При использовании retry_strategy
не существует очевидного способа закрыть службу без более работающего соединения redis, и это должен быть довольно простой вариант использования. Лучшим решением, вероятно, было бы отдельное мероприятие, как предложил @AaronJan ..
Я выпустил v3.0.0 , которые сейчас пузырь любых возвращаемых retry_strategy
ошибок вплоть до error
прослушивателя событий.
Самый полезный комментарий
Да: передать ошибку в прослушиватель ошибок