Начиная с версии 59, Firefox имеет функцию под названием Race Cache With Network (RCWN). Если Firefox обнаружит, что диск работает медленно, он может решить начать сетевые запросы немедленно, не дожидаясь кэша. Это компромисс: если сетевые запросы выигрывают гонку, задержка улучшается; если выигрывает кэш, пропускная способность сети теряется.
Это полезная функция, но есть один сценарий, в котором она нежелательна. Предположим, WebExtension необходимо обновить ресурсы в фоновом режиме (например, один раз в час). Задержка здесь не важна, хотя правильное кэширование крайне важно, так как вам нужно платить за исходящий трафик c на стороне сервера.
Мой вопрос заключается в том, как отключить RCWN на уровне запроса. Как вы можете создать запрос (через fetch
или XMLHttpRequest
), который всегда будет сначала проверять кеш, а только потом выдавать сетевой запрос. Другими словами, никогда не гонитесь и никогда не обходите кеш.
Я знаю, что эту функцию можно отключить с помощью конфигураций (network.http.rcwn.enabled
), но это не решение. Во-первых, вам нужно убедить каждого пользователя изменить это предпочтение. Во-вторых, RCWN - полезная функция, которая обеспечивает ценность при обычном серфинге, где важна задержка. Если заставить пользователей отключить его, это приведет к неоптимальному просмотру.
Существует небольшая документация по RCWN, которая ожидает, что эти слайды , но я нашел ее реализацию в исходном коде Firefox :
nsresult nsHttpChannel::OpenCacheEntryInternal(...) {
...
if (sRCWNEnabled && maybeRCWN && !mApplicationCacheForWrite) {
bool hasAltData = false;
uint32_t sizeInKb = 0;
rv = cacheStorage->GetCacheIndexEntryAttrs(openURI, extension, &hasAltData,
&sizeInKb);
// We will attempt to race the network vs the cache if we've found
// this entry in the cache index, and it has appropriate attributes
// (doesn't have alt-data, and has a small size)
if (NS_SUCCEEDED(rv) && !hasAltData &&
sizeInKb < sRCWNSmallResourceSizeKB) {
MaybeRaceCacheWithNetwork();
}
}
...
}
Я пытался понять понятие «alt-data», но не смог найти никаких источников. Насколько я знаю, это означает альтернативные данные. Может ли это быть использовано (либо сервером, либо через запрос клиента), чтобы заставить кэшированные данные быть помеченными как alt-data, чтобы гонки не происходили?
Еще одна идея, которая у меня была: в выборке запрос, клиенты могут установить Cache-Control: only-if-cached
, но это меняет семантику c. Он должен остановить гонки, но если нет попадания, он вернет устаревший результат и не спросит сервер. Может быть, это можно было бы использовать, чтобы сначала попробовать такой запрос, и только потом сделать реальный сетевой запрос. Не очень элегантно, хотя. Есть ли лучшее решение этой проблемы?
Примечания: для получения дополнительной информации Firefox позволяет анализировать RCWN через about:networking#rcwn
, а кеш через about:cache
. Если вы проверите RCWN, вы увидите, что гонки не так уж редки, даже если у вас есть SSD. В сетевом мониторе обработанные запросы будут помечены в переданном столбце, например, как 100.86 KB (raced)
.