From 9f67207cca08cd1dee024810b2c41c1f54f66d42 Mon Sep 17 00:00:00 2001 From: Michal Piechowiak Date: Wed, 10 Jun 2020 11:47:36 +0200 Subject: [PATCH] implement `getModule`, load needed modules for a page in browser and for SSR --- .../gatsby/cache-dir/gatsby-browser-entry.js | 2 ++ packages/gatsby/cache-dir/loader.js | 23 +++++++++++++++++-- packages/gatsby/cache-dir/modules.js | 9 ++++++++ packages/gatsby/cache-dir/static-entry.js | 17 ++++++++++++-- 4 files changed, 47 insertions(+), 4 deletions(-) create mode 100644 packages/gatsby/cache-dir/modules.js diff --git a/packages/gatsby/cache-dir/gatsby-browser-entry.js b/packages/gatsby/cache-dir/gatsby-browser-entry.js index 63fbe06f81eda..612381f1465d6 100644 --- a/packages/gatsby/cache-dir/gatsby-browser-entry.js +++ b/packages/gatsby/cache-dir/gatsby-browser-entry.js @@ -115,3 +115,5 @@ export { useStaticQuery, prefetchPathname, } + +export { getModule } from "./modules" diff --git a/packages/gatsby/cache-dir/loader.js b/packages/gatsby/cache-dir/loader.js index bfc8a67aa8919..f0920d0640c2c 100644 --- a/packages/gatsby/cache-dir/loader.js +++ b/packages/gatsby/cache-dir/loader.js @@ -1,6 +1,7 @@ import prefetchHelper from "./prefetch" import emitter from "./emitter" import { setMatchPaths, findPath, findMatchPath } from "./find-path" +import { addModule, getModule } from "./modules" /** * Available resource loading statuses @@ -199,8 +200,12 @@ export class BaseLoader { } let pageData = result.payload - const { componentChunkName } = pageData - return this.loadComponent(componentChunkName).then(component => { + const { componentChunkName, moduleDependencies = [] } = pageData + + return Promise.all([ + this.loadComponent(componentChunkName), + this.fetchModuleDependencies(moduleDependencies), + ]).then(([component]) => { const finalResult = { createdAt: new Date() } let pageResources if (!component) { @@ -351,6 +356,20 @@ export class BaseLoader { return appData }) } + + fetchModuleDependencies(moduleDependencies) { + return Promise.all( + moduleDependencies.map(moduleId => { + if (getModule(moduleId)) { + return Promise.resolve() + } + + return this.loadComponent(moduleId, `modules`).then(module => { + addModule(moduleId, module) + }) + }) + ) + } } const createComponentUrls = componentChunkName => diff --git a/packages/gatsby/cache-dir/modules.js b/packages/gatsby/cache-dir/modules.js new file mode 100644 index 0000000000000..abe00b464d6b6 --- /dev/null +++ b/packages/gatsby/cache-dir/modules.js @@ -0,0 +1,9 @@ +const modules = new Map() + +export function addModule(moduleId, module) { + modules.set(moduleId, module) +} + +export function getModule(moduleId) { + return modules.get(moduleId) +} diff --git a/packages/gatsby/cache-dir/static-entry.js b/packages/gatsby/cache-dir/static-entry.js index 33d923ab6fc10..5adf5f474cf8a 100644 --- a/packages/gatsby/cache-dir/static-entry.js +++ b/packages/gatsby/cache-dir/static-entry.js @@ -18,6 +18,7 @@ const { const { RouteAnnouncerProps } = require(`./route-announcer-props`) const apiRunner = require(`./api-runner-ssr`) const syncRequires = require(`$virtual/sync-requires`) +const { addModule, getModule } = require(`./modules`) const { version: gatsbyVersion } = require(`gatsby/package.json`) const stats = JSON.parse( @@ -201,7 +202,19 @@ export default (pagePath, callback) => { const appDataUrl = getAppDataUrl() - const { componentChunkName } = pageData + const { componentChunkName, moduleDependencies } = pageData + + // make sure needed modules for the page are loaded in modules provider + if (moduleDependencies) { + moduleDependencies.forEach(moduleId => { + if (getModule(moduleId)) { + return + } + + const module = syncRequires.modules[moduleId] + addModule(moduleId, module) + }) + } class RouteHandler extends React.Component { render() { @@ -274,7 +287,7 @@ export default (pagePath, callback) => { // Create paths to scripts let scriptsAndStyles = flatten( - [`app`, componentChunkName].map(s => { + [`app`, componentChunkName, ...(moduleDependencies || [])].map(s => { const fetchKey = `assetsByChunkName[${s}]` let chunks = get(stats, fetchKey)