Назад | Перейти на главную страницу

Предиктивное кеширование HTTP

Немного предыстории

У меня есть ~ 150 скриптов, которые прямо или косвенно извлекают данные из экземпляра IBM Cognos, который я не контролирую. У меня нет доступа к Cognos API, поэтому возможный источник всех данных для этих сценариев - имитация входа в веб-браузер в качестве обычного пользователя для запуска и загрузки отчетов. Это медленно (от 5 до 90 секунд в зависимости от отчета). Раньше для этого использовался сценарий Perl, который дублировался каждый раз, когда кто-то хотел загрузить другой отчет. Это означало, что у нас был очень дублированный код, и часто отчеты по-прежнему загружались каждый день после того, как они больше не использовались. Я написал микросервис для загрузки произвольного отчета из Cognos, чтобы попытаться заменить все сценарии Perl. Вы отправляете HTTP-запрос GET на URL-адрес, указывающий на нужный отчет, микросервис имитирует загрузку отчета браузером, и вы получаете обратно файл CSV или JSON (в зависимости от того, что вы запросили). Это отлично подходит для уменьшения сложности, поскольку каждый сценарий может запрашивать данные из отчета в одной или двух строках прямо над тем местом, где они необходимы. Когда отчет больше не нужен, все, что нужно очистить, очевидно. Нам также больше не нужно синхронизировать расписания (например: Perl-скрипт для загрузки данных в 7:30, Python для их обработки в 7:35).

Конкретная проблема

Многие отчеты требуют больших вычислительных ресурсов, и недавно я получил массовое электронное письмо от администратора сервера Cognos, в котором в основном говорилось: «Перестаньте запускать одни и те же отчеты снова и снова и попробуйте запускать отчеты в нерабочее время». Для нас непиковые часы - это поздняя ночь. Многие скрипты делают то, что должно происходить, когда люди находятся в офисе (например, у нас есть скрипт, который отправляет телефонные звонки определенным людям), поэтому во многих случаях я не могу настроить время выполнения скриптов. Во всех случаях допустимы данные старше 24 часов.

Я думал, что, поскольку каждый отчет - это просто HTTP-запрос GET, я мог бы просто поставить кеш перед микросервисом. Проблема в том, что, хотя мы запускаем довольно много отчетов каждый день, большинство из них запускается только один раз в день. С большинством известных мне HTTP-кешей это приведет к тому, что каждый запрос будет пропуском кеша.

Вот что я хотел бы сделать: первый раз, когда поступает запрос на URL, происходит промах кеша. URL-адрес загружается из микросервиса и передается клиенту. Затем сервер знает, что он может ожидать снова увидеть запрос этого URL-адреса, поэтому в нерабочее время он обновляет кеш. На следующий день, когда сценарий запрашивает тот же URL-адрес, происходит попадание в кеш, и ответ возвращается немедленно. Если URL-адрес не обнаружен в течение некоторого периода времени, кеш удаляет его из списка URL-адресов, которые будут обновляться каждую ночь.

Общая проблема

В основном я ищу HTTP-кеш, который будет узнавать, какие URL-адреса будут попадать, и загружать их, прежде чем они будут запрошены. Такое уже существует или мне придется это написать?

Многие скрипты делают то, что должно происходить, когда люди находятся в офисе (например, у нас есть скрипт, который отправляет телефонные звонки определенным людям), поэтому во многих случаях я не могу настроить время выполнения скриптов. Во всех случаях допустимы данные старше 24 часов.

Отделите сбор данных от действия.

  • Получите данные в какое-то время ночи, например в 03:15. (Нечетное время не в час может быть менее загруженным.)
  • Обработка данных, создание отчетов или что-то еще.
  • Запланируйте любые отложенные действия, например, в 08:00. Если вы уже не делаете этого, то в системе UNIX или Linux рассмотрите at рабочие места.

Я думал, что, поскольку каждый отчет - это просто HTTP-запрос GET, я мог бы просто поставить кеш перед микросервисом. Проблема в том, что, хотя мы запускаем довольно много отчетов каждый день, большинство из них запускается только один раз в день. С большинством известных мне HTTP-кешей это приведет к тому, что каждый запрос будет пропущен из кеша.

Если вы настроили (ab) использование HTTP в качестве кеша, более внимательно изучите варианты программного обеспечения для кэширования. Например, Squid может принудительно переопределить время истечения срока действия, не соответствующее требованиям. Затем ваш скрипт может ПОЛУЧИТЬ данные с промахом в одночасье и ПОЛУЧИТЬ их снова с хитом, когда вы действительно этого захотите.

Сложность здесь заключается в том, чтобы установить время кеширования, в котором будут попадания и промахи там, где вы хотите. Лично мне кажется, что разделение сбора данных и расписания действий более чистое решение.