"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); Object.defineProperty(exports, "postProcessHTML", { enumerable: true, get: function() { return postProcessHTML; } }); const _constants = require("../shared/lib/constants"); const _nonnullable = require("../lib/non-nullable"); const middlewareRegistry = []; function registerPostProcessor(name, middleware, condition) { middlewareRegistry.push({ name, middleware, condition: condition || null }); } async function processHTML(html, data, options) { // Don't parse unless there's at least one processor middleware if (!middlewareRegistry[0]) { return html; } const { parse } = require("next/dist/compiled/node-html-parser"); const root = parse(html); let document = html; // Calls the middleware, with some instrumentation and logging async function callMiddleWare(middleware) { // let timer = Date.now() const inspectData = middleware.inspect(root, data); document = await middleware.mutate(document, inspectData, data); // timer = Date.now() - timer // if (timer > MIDDLEWARE_TIME_BUDGET) { // TODO: Identify a correct upper limit for the postprocess step // and add a warning to disable the optimization // } return; } for(let i = 0; i < middlewareRegistry.length; i++){ let middleware = middlewareRegistry[i]; if (!middleware.condition || middleware.condition(options)) { await callMiddleWare(middlewareRegistry[i].middleware); } } return document; } class FontOptimizerMiddleware { inspect(originalDom, options) { if (!options.getFontDefinition) { return; } const fontDefinitions = []; // collecting all the requested font definitions originalDom.querySelectorAll("link").filter((tag)=>tag.getAttribute("rel") === "stylesheet" && tag.hasAttribute("data-href") && _constants.OPTIMIZED_FONT_PROVIDERS.some(({ url })=>{ const dataHref = tag.getAttribute("data-href"); return dataHref ? dataHref.startsWith(url) : false; })).forEach((element)=>{ const url = element.getAttribute("data-href"); const nonce = element.getAttribute("nonce"); if (url) { fontDefinitions.push([ url, nonce ]); } }); return fontDefinitions; } constructor(){ this.mutate = async (markup, fontDefinitions, options)=>{ let result = markup; let preconnectUrls = new Set(); if (!options.getFontDefinition) { return markup; } fontDefinitions.forEach((fontDef)=>{ const [url, nonce] = fontDef; const fallBackLinkTag = ``; if (result.indexOf(``); // Remove inert font tag const escapedUrl = url.replace(/&/g, "&").replace(/[.*+?^${}()|[\]\\]/g, "\\$&"); const fontRegex = new RegExp(`]*data-href="${escapedUrl}"[^>]*/>`); result = result.replace(fontRegex, ""); const provider = _constants.OPTIMIZED_FONT_PROVIDERS.find((p)=>url.startsWith(p.url)); if (provider) { preconnectUrls.add(provider.preconnect); } } }); let preconnectTag = ""; preconnectUrls.forEach((url)=>{ preconnectTag += ``; }); result = result.replace('', preconnectTag); return result; }; } } async function postProcessHTML(pathname, content, renderOpts, { inAmpMode, hybridAmp }) { const postProcessors = [ process.env.NEXT_RUNTIME !== "edge" && inAmpMode ? async (html)=>{ const optimizeAmp = require("./optimize-amp").default; html = await optimizeAmp(html, renderOpts.ampOptimizerConfig); if (!renderOpts.ampSkipValidation && renderOpts.ampValidator) { await renderOpts.ampValidator(html, pathname); } return html; } : null, process.env.NEXT_RUNTIME !== "edge" && renderOpts.optimizeFonts ? async (html)=>{ const getFontDefinition = (url)=>{ if (renderOpts.fontManifest) { const { getFontDefinitionFromManifest } = require("./font-utils"); return getFontDefinitionFromManifest(url, renderOpts.fontManifest); } return ""; }; return await processHTML(html, { getFontDefinition }, { optimizeFonts: renderOpts.optimizeFonts }); } : null, process.env.NEXT_RUNTIME !== "edge" && renderOpts.optimizeCss ? async (html)=>{ // eslint-disable-next-line import/no-extraneous-dependencies const Critters = require("critters"); const cssOptimizer = new Critters({ ssrMode: true, reduceInlineStyles: false, path: renderOpts.distDir, publicPath: `${renderOpts.assetPrefix}/_next/`, preload: "media", fonts: false, ...renderOpts.optimizeCss }); return await cssOptimizer.process(html); } : null, inAmpMode || hybridAmp ? (html)=>{ return html.replace(/&amp=1/g, "&=1"); } : null ].filter(_nonnullable.nonNullable); for (const postProcessor of postProcessors){ if (postProcessor) { content = await postProcessor(content); } } return content; } // Initialization registerPostProcessor("Inline-Fonts", new FontOptimizerMiddleware(), // Using process.env because passing Experimental flag through loader is not possible. // @ts-ignore (options)=>options.optimizeFonts || process.env.__NEXT_OPTIMIZE_FONTS); //# sourceMappingURL=post-process.js.map