Add preload link headers for downstream Cloudflare early hints (#171)
Because it takes us at best several seconds to request information from a homeserver and then server-side render the page, the browser has to wait for the response before it can even try loading the necessary assets. With this change that facilitates early hints, the browser can preload all of the assets necessary before we are done generating the response and will be ready to go by the time we're all done on the server. Fix https://github.com/matrix-org/matrix-public-archive/issues/32 Part of https://github.com/matrix-org/matrix-public-archive/issues/132 See https://developers.cloudflare.com/cache/about/early-hints/ for information on enabling in Cloudflare
This commit is contained in:
parent
321c6a4f26
commit
17a39ab8db
|
@ -0,0 +1,29 @@
|
|||
'use strict';
|
||||
|
||||
const assert = require('assert');
|
||||
|
||||
// Set some preload link headers which we can use with Cloudflare to turn into 103 early
|
||||
// hints, https://developers.cloudflare.com/cache/about/early-hints/
|
||||
//
|
||||
// This will turn into a nice speed-up since the server side render can take some time
|
||||
// while we fetch all the information from the homeserver and the page can have all of
|
||||
// the assets loaded and ready to go by that time. This way there is no extra delay
|
||||
// after the page gets served.
|
||||
function setHeadersToPreloadAssets(res, pageOptions) {
|
||||
assert(res);
|
||||
assert(pageOptions);
|
||||
|
||||
const { styles, scripts } = pageOptions;
|
||||
|
||||
const styleLinks = styles.map((styleUrl) => {
|
||||
return `<${styleUrl}>; rel=preload; as=style`;
|
||||
});
|
||||
|
||||
const scriptLinks = scripts.map((scriptUrl) => {
|
||||
return `<${scriptUrl}>; rel=preload; as=script`;
|
||||
});
|
||||
|
||||
res.append('Link', [].concat(styleLinks, scriptLinks).join(', '));
|
||||
}
|
||||
|
||||
module.exports = setHeadersToPreloadAssets;
|
|
@ -8,6 +8,7 @@ const asyncHandler = require('../lib/express-async-handler');
|
|||
|
||||
const fetchPublicRooms = require('../lib/matrix-utils/fetch-public-rooms');
|
||||
const renderHydrogenVmRenderScriptToPageHtml = require('../hydrogen-render/render-hydrogen-vm-render-script-to-page-html');
|
||||
const setHeadersToPreloadAssets = require('../lib/set-headers-to-preload-assets');
|
||||
|
||||
const config = require('../lib/config');
|
||||
const basePath = config.get('basePath');
|
||||
|
@ -65,15 +66,16 @@ router.get(
|
|||
const roomDirectoryStylesUrl = urlJoin(basePath, '/css/room-directory.css');
|
||||
const jsBundleUrl = urlJoin(basePath, '/js/entry-client-room-directory.es.js');
|
||||
|
||||
const pageHtml = await renderHydrogenVmRenderScriptToPageHtml({
|
||||
pageOptions: {
|
||||
const pageOptions = {
|
||||
title: `Matrix Public Archive`,
|
||||
styles: [hydrogenStylesUrl, stylesUrl, roomDirectoryStylesUrl],
|
||||
scripts: [jsBundleUrl],
|
||||
locationHref: urlJoin(basePath, req.originalUrl),
|
||||
shouldIndex,
|
||||
cspNonce: res.locals.cspNonce,
|
||||
},
|
||||
};
|
||||
const pageHtml = await renderHydrogenVmRenderScriptToPageHtml({
|
||||
pageOptions,
|
||||
vmRenderScriptFilePath: path.resolve(
|
||||
__dirname,
|
||||
'../../shared/room-directory-vm-render-script.js'
|
||||
|
@ -102,6 +104,8 @@ router.get(
|
|||
},
|
||||
});
|
||||
|
||||
setHeadersToPreloadAssets(res, pageOptions);
|
||||
|
||||
res.set('Content-Type', 'text/html');
|
||||
res.send(pageHtml);
|
||||
})
|
||||
|
|
|
@ -23,6 +23,7 @@ const timestampToEvent = require('../lib/matrix-utils/timestamp-to-event');
|
|||
const { removeMe_fetchRoomCreateEventId } = require('../lib/matrix-utils/fetch-room-data');
|
||||
const getMessagesResponseFromEventId = require('../lib/matrix-utils/get-messages-response-from-event-id');
|
||||
const renderHydrogenVmRenderScriptToPageHtml = require('../hydrogen-render/render-hydrogen-vm-render-script-to-page-html');
|
||||
const setHeadersToPreloadAssets = require('../lib/set-headers-to-preload-assets');
|
||||
const MatrixPublicArchiveURLCreator = require('matrix-public-archive-shared/lib/url-creator');
|
||||
const {
|
||||
MS_LOOKUP,
|
||||
|
@ -868,15 +869,16 @@ router.get(
|
|||
const stylesUrl = urlJoin(basePath, '/css/styles.css');
|
||||
const jsBundleUrl = urlJoin(basePath, '/js/entry-client-hydrogen.es.js');
|
||||
|
||||
const pageHtml = await renderHydrogenVmRenderScriptToPageHtml({
|
||||
pageOptions: {
|
||||
const pageOptions = {
|
||||
title: `${roomData.name} - Matrix Public Archive`,
|
||||
styles: [hydrogenStylesUrl, stylesUrl],
|
||||
scripts: [jsBundleUrl],
|
||||
locationHref: urlJoin(basePath, req.originalUrl),
|
||||
shouldIndex,
|
||||
cspNonce: res.locals.cspNonce,
|
||||
},
|
||||
};
|
||||
const pageHtml = await renderHydrogenVmRenderScriptToPageHtml({
|
||||
pageOptions,
|
||||
vmRenderScriptFilePath: path.resolve(__dirname, '../../shared/hydrogen-vm-render-script.js'),
|
||||
vmRenderContext: {
|
||||
toTimestamp,
|
||||
|
@ -900,6 +902,8 @@ router.get(
|
|||
},
|
||||
});
|
||||
|
||||
setHeadersToPreloadAssets(res, pageOptions);
|
||||
|
||||
res.set('Content-Type', 'text/html');
|
||||
res.send(pageHtml);
|
||||
})
|
||||
|
|
Loading…
Reference in New Issue