2015-12-17 4 views
0

Наш API должен отправить данные в Zapier, если некоторые конкретные данные были изменены в нашей БД.Доступ к тому же экземпляру setTimeout() из нескольких экземпляров Node.js

К примеру, у нас есть компании таблицу и если имя или адрес поле было изменено, мы вызываем крючок Zapier.

Иногда наш API принимает множество запросов на изменение в течение нескольких минут, но мы не хотим, чтобы вызвать Zapier крючок несколько раз (так как это довольно дорого), поэтому мы называем setTimeout() (и перезаписывает существующие setTimeout) на каждый запрос на изменение, с задержкой 5000ms.

Он отлично работает, и нет нескольких вызовов крюка Zapier, даже если мы получим много запросов на изменение от клиента в этом периоде 5000ms.

Теперь, поскольку наш трафик растет, мы хотели бы установить несколько экземпляров node.js за некоторым балансировщиком нагрузки.

Но в этом случае разные экземпляры Node.js не могут использовать - и перезаписать - тот же самый экземпляр setTimeout, что вызовет много бесполезных вызовов Zapier.

Не могли бы вы помочь нам, как решить эту проблему - оставаясь масштабируемым?

ответ

1

Если вы хотите сохранить состояние между отдельными экземплярами, вам следует рассмотреть с точки зрения инфраструктуры некоторый механизм блокировки, такой как Redis. Всякий раз, когда вы хотите запустить вызов Zapier, если блокировка не активна, вы устанавливаете его на Redis, все остальные вызовы не будут запускаться, поскольку он заблокирован, всякий раз, когда выполняется обратный вызов setTimeout, вы отключите блокировку. Остерегайтесь того, что Redis может стать SPOF, я не знаю, где вы размещаете свои услуги, но это может быть важным моментом для рассмотрения.

Edit:

Замок на Redis может иметь ссылку на последнюю часть информации, которую необходимо обновить. Таким образом, по первому запросу вы устанавливаете данные для сохранения в Redis, подождите 5 секунд и обновляете. Если в этот временной интервал были внесены какие-либо изменения, он будет сохранен на Redis, таким образом, вы будете обновляться только с интервалом в 5 секунд, вам нужно добавить дополнительную логику. Пример:

function zapierUpdate(data) { 

    if (isLocked()) { 

    // Locked! We will update the data that needs to be saved on the 
    // next setTimeout callback 
    updateLockData(data); 

    } else { 

    // First lock and save data. 
    lock(data); 
    // and update in 5 seconds 
    setTimeout(function(){ 
     // getLockData fetches the data on Redis and releases the lock 
     var newData = getLockData(); 
     // Update the latest data that might have been updated. 
     callZapierNow(newData); 
    },5000); 

    } 

} 
+0

Я добавил небольшой пример. –

Смежные вопросы