Я подготовил базовый c пример, чтобы продемонстрировать, чего я хочу достичь. Рассмотрим html ниже.
<html>
<head></head>
<body>
<header> </header>
<div class='container'></div>
<footer></footer>
</body>
</html>
Довольно базовый c. Все данные Dynami c отправляются в контейнер div. Отдых стоит c. Я использовал сервисных работников и модель оболочки приложения (вид), чтобы ускорить время загрузки. Я сделал что-то вроде этого
top-shell.html
- который заканчивается прямо перед контейнером. bottom-shell.html
- начинается с нижнего колонтитула. И сам контейнер.
<!-- top-shell.html -->
<html>
<head></head>
<body>
<header> </header>
<!-- bottm-shell.html -->
<footer></footer>
</body>
</html>
Контейнер содержит данные Dynami c. Так что мне придется загружать через запрос. Я пытался транслировать его вместе с остальными. Dev.to, статьи Google Developer очень помогли. Это код. Этот фрагмент не проверен
function pageStream(request) {
const stream = new ReadableStream({
start(controller) {
const fetchHeader = caches.match('/top-shell.html')
const fetchContainer = fetch('/container.html')
.then(response => response)
function push(stream) {
const reader = stream.getReader();
return reader.read().then(function process(result) {
if (result.done) return
controller.enqueue(result.value);
return reader.read().then(process);
});
}
fetchHeader.then(response => push(response.body))
.then(() => fetchContainer)
.then(response => push(response.body))
.then(() => controller.close())
}
});
return new Response(stream, {
headers: {
'Content-Type': 'text/html; charset=utf-8'
}
});
}
self.addEventListener('fetch', event => {
// Checks ... (assets excluded, only html)
event.respondWith(pageStream(event.request));
});
Я исключил некоторые части и нижнюю оболочку, чтобы разместить меньше кода. Он отлично работает.
Дело в том, что я не люблю делить теги html как это тело. Я хотел бы, чтобы тело и тег html заканчивались в этом файле. И затем укажите точку c, в которую будет вставлен контейнер во время потоковой передачи. Вот так
<html>
<body>
<header></header>
<!-- {{ container here }} -->
<!-- {{ footer here from cache }} -->
</body>
</html>
Итак, этот файл будет загружен из кеша. Затем контейнер начнет потоковую передачу и вставится в {{ container here }}
. Я могу написать простую систему шаблонов типа jinja2, которая сделает эту работу. Я хочу, чтобы все это произошло внутри работника службы. Я не хочу, чтобы пользователи видели эти фигурные скобки, конечно.
Я достиг точки, где я могу декодировать уже переданный поток, используя TextDecoder
, но не мог двигаться вперед, потому что весь файл, включая container
is streaming , я не могу полностью заменить фигурные скобки. Если я удаляю его, куда будет вставлен следующий кусок.
Простите за мои ошибки. Совершенно запутанный и не имеющий solid понимания определенных вещей, чтобы приблизиться к этому одному.
Кстати, кто-нибудь может добавить тег ReadableStream
. Интересно, почему это не доступно: /