[JS][Chrome] Ре-энтерабельность сообщений
От: EugenePerfect  
Дата: 14.08.19 18:05
Оценка:
Суть вопроса. У меня есть наколенкенаписанное расширение для хрома.

Предназначено оно для упрощения работы на одном сайте, состоящем из страниц/публикаций, однозначно идентифицируемых целым номером, объединяемых в каталоги.

В этих каталогах, к сожалению, при просмотре показываются не все интересующие меня детали — но при вхождении в саму публикацию, естественно, все парсится "на раз".

Поэтому возникла (и реализована) идея при заходе в публикацию, все интересующие меня тэги сохранять в массиве через chrome.storage.local

Как было сделано ранее?

1) Скриптом в content_scripts при открытии каждой публикации массив тэгов считывается через chrome.storage.local.get

2) Парсятся тэги со страницы

3) Проверяем наличие тэгов по номеру публикации в массиве

4) Если их еще нет, добавляем в массив и сохраняем через chrome.storage.local.set

И все было бы хорошо, если бы не возможность перезатирания информации одновременно открытыми в нескольких вкладках публикациями.

Как показал опыт, сайт очень тормозной, и его скрипты "подвешивает" вкладки, так что между п. 1 и п. 4 проходит так много времени, что другие вклади успевают уже успевают записать информацию в массив, но "подвисшая" вкладка ее затирает, и все пропадает, кроме последнего элемента этого своеобразного "кэша".

И это нехорошо.

Для предупреждения этой фигни, я попытался сделать процесс более атомарным: то есть пункты 1), 2), 3) оставил как есть, но 4) вынес виде обработчика сообщения в background script, типа такого (максимально упрощенно):

chrome.extension.onMessage.addListener(function(request, sender, callback) {
  switch (request.type) {
  case "add":
      chrome.storage.local.get('tags_array', function(item) {
        item = item.tags_array || new Array();

        var found = false;

        for(var i = 0; i < item.length; i++){
          var a = item[i].split(",");
          if(a[0] == request.pubnumber){ 
            found = true;
            break;
          }
        }

        if(!found){
          item.push(request.pubnumber + "," + request.tags);
          chrome.storage.local.set({ tags_array : item });
        }
      });
  }
}


И вот, внимание, вопрос. Может ли быть такое, что фоновый скрипт обрабатывает одновременно несколько сообщений от страниц? Нужно ли дополнительно плодить триггеры и задержки типа такого:

var busy = false;

chrome.extension.onMessage.addListener(function(request, sender, callback) {
  switch (request.type) {
  case "add":
      for(;busy;)
        ;

      chrome.storage.local.get('tags_array', function(item) {
        busy = true;

        item = item.tags_array || new Array();

        var found = false;

        for(var i = 0; i < item.length; i++){
          var a = item[i].split(",");
          if(a[0] == request.pubnumber){ 
            found = true;
            break;
          }
        }

        if(!found){
          item.push(request.pubnumber + "," + request.tags);
          chrome.storage.local.set({ tags_array : item });
        }

        busy = false;
      });
  }
}


И имеет ли это вообще смысл, или нет гарантии что на момент выполнения строки
busy = false;

chrome.storage.local.set полностью сохранит массив?
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.