UNPKG

17.3 kBSource Map (JSON)View Raw
1{"version":3,"sources":["../../server/on-demand-entry-handler.ts"],"names":["ADDED","Symbol","BUILDING","BUILT","entries","onDemandEntryHandler","watcher","multiCompiler","pagesDir","pageExtensions","maxInactiveAge","pagesBufferLength","compilers","invalidator","Invalidator","lastAccessPages","doneCallbacks","EventEmitter","compiler","hooks","make","tap","_compilation","startBuilding","getPagePathsFromEntrypoints","entrypoints","pagePaths","entrypoint","values","page","name","push","done","multiStats","clientStats","serverStats","stats","Set","compilation","entry","status","lastActiveTime","Date","now","emit","doneBuilding","disposeHandler","setInterval","disposeInactiveEntries","unref","handlePing","pg","entryInfo","toSend","invalid","success","includes","unshift","length","pop","ensurePage","normalizedPagePath","err","console","error","pagePath","pageUrl","replace","RegExp","join","bundleFile","serverBundlePath","posix","clientBundlePath","absolutePagePath","startsWith","require","resolve","normalize","Promise","reject","normalizedPage","once","handleCallback","Log","event","invalidate","middleware","req","res","next","url","query","runPing","data","write","JSON","stringify","pingInterval","on","clearInterval","disposingPages","Object","keys","forEach","constructor","building","rebuildAgain","isWebpack5","call"],"mappings":"8IAAA,8BAEA,0BACA,wBACA,2DACA,gEACA,4EAIA,sDACA,kDACA,+G,w4BAEO,KAAMA,CAAAA,KAAK,CAAGC,MAAM,CAAC,OAAD,CAApB,C,oBACA,KAAMC,CAAAA,QAAQ,CAAGD,MAAM,CAAC,UAAD,CAAvB,C,0BACA,KAAME,CAAAA,KAAK,CAAGF,MAAM,CAAC,OAAD,CAApB,C,oBAEA,GAAIG,CAAAA,OAQV,CAAG,EARG,C,wBAUQ,QAASC,CAAAA,oBAAT,CACbC,OADa,CAEbC,aAFa,CAGb,CACEC,QADF,CAEEC,cAFF,CAGEC,cAHF,CAIEC,iBAJF,CAHa,CAcb,CACA,KAAM,CAAEC,SAAF,EAAgBL,aAAtB,CACA,KAAMM,CAAAA,WAAW,CAAG,GAAIC,CAAAA,WAAJ,CAAgBR,OAAhB,CAAyBC,aAAzB,CAApB,CAEA,GAAIQ,CAAAA,eAAe,CAAG,CAAC,EAAD,CAAtB,CACA,GAAIC,CAAAA,aAAkC,CAAG,GAAIC,qBAAJ,EAAzC,CAEA,IAAK,KAAMC,CAAAA,QAAX,GAAuBN,CAAAA,SAAvB,CAAkC,CAChCM,QAAQ,CAACC,KAAT,CAAeC,IAAf,CAAoBC,GAApB,CACE,uBADF,CAEGC,YAAD,EAAmD,CACjDT,WAAW,CAACU,aAAZ,GACD,CAJH,EAMD,CAED,QAASC,CAAAA,2BAAT,CAAqCC,WAArC,CAAiE,CAC/D,KAAMC,CAAAA,SAAS,CAAG,EAAlB,CACA,IAAK,KAAMC,CAAAA,UAAX,GAAyBF,CAAAA,WAAW,CAACG,MAAZ,EAAzB,CAA+C,CAC7C,KAAMC,CAAAA,IAAI,CAAG,oCAAuBF,UAAU,CAACG,IAAlC,CAAb,CACA,GAAID,IAAJ,CAAU,CACRH,SAAS,CAACK,IAAV,CAAeF,IAAf,EACD,CACF,CAED,MAAOH,CAAAA,SAAP,CACD,CAEDnB,aAAa,CAACY,KAAd,CAAoBa,IAApB,CAAyBX,GAAzB,CAA6B,uBAA7B,CAAuDY,UAAD,EAAgB,CACpE,KAAM,CAACC,WAAD,CAAcC,WAAd,EAA6BF,UAAU,CAACG,KAA9C,CACA,KAAMV,CAAAA,SAAS,CAAG,GAAIW,CAAAA,GAAJ,CAAQ,CACxB,GAAGb,2BAA2B,CAACU,WAAW,CAACI,WAAZ,CAAwBb,WAAzB,CADN,CAExB,GAAGD,2BAA2B,CAACW,WAAW,CAACG,WAAZ,CAAwBb,WAAzB,CAFN,CAAR,CAAlB,CAKA,IAAK,KAAMI,CAAAA,IAAX,GAAmBH,CAAAA,SAAnB,CAA8B,CAC5B,KAAMa,CAAAA,KAAK,CAAGnC,OAAO,CAACyB,IAAD,CAArB,CACA,GAAI,CAACU,KAAL,CAAY,CACV,SACD,CAED,GAAIA,KAAK,CAACC,MAAN,GAAiBtC,QAArB,CAA+B,CAC7B,SACD,CAEDqC,KAAK,CAACC,MAAN,CAAerC,KAAf,CACAoC,KAAK,CAACE,cAAN,CAAuBC,IAAI,CAACC,GAAL,EAAvB,CACA3B,aAAa,CAAE4B,IAAf,CAAoBf,IAApB,EACD,CAEDhB,WAAW,CAACgC,YAAZ,GACD,CAvBD,EAyBA,KAAMC,CAAAA,cAAc,CAAGC,WAAW,CAAC,UAAY,CAC7CC,sBAAsB,CAAC1C,OAAD,CAAUS,eAAV,CAA2BL,cAA3B,CAAtB,CACD,CAFiC,CAE/B,IAF+B,CAAlC,CAIAoC,cAAc,CAACG,KAAf,GAEA,QAASC,CAAAA,UAAT,CAAoBC,EAApB,CAAgC,CAC9B,KAAMtB,CAAAA,IAAI,CAAG,wCAAiBsB,EAAjB,CAAb,CACA,KAAMC,CAAAA,SAAS,CAAGhD,OAAO,CAACyB,IAAD,CAAzB,CACA,GAAIwB,CAAAA,MAAJ,CAEA;AACA,GAAI,CAACD,SAAL,CAAgB,CACd;AACA,MAAO,CAAEE,OAAO,CAAE,IAAX,CAAP,CACD,CAED;AACA,GAAIzB,IAAI,GAAK,SAAb,CAAwB,CACtBwB,MAAM,CAAG,CAAEC,OAAO,CAAE,IAAX,CAAT,CACD,CAFD,IAEO,CACLD,MAAM,CAAG,CAAEE,OAAO,CAAE,IAAX,CAAT,CACD,CAED;AACA,GAAIH,SAAS,CAACZ,MAAV,GAAqBrC,KAAzB,CAAgC,OAEhC;AACA,GAAI,CAACY,eAAe,CAACyC,QAAhB,CAAyB3B,IAAzB,CAAL,CAAqC,CACnCd,eAAe,CAAC0C,OAAhB,CAAwB5B,IAAxB,EAEA;AACA,GAAId,eAAe,CAAC2C,MAAhB,CAAyB/C,iBAA7B,CAAgD,CAC9CI,eAAe,CAAC4C,GAAhB,GACD,CACF,CACDP,SAAS,CAACX,cAAV,CAA2BC,IAAI,CAACC,GAAL,EAA3B,CACA,MAAOU,CAAAA,MAAP,CACD,CAED,MAAO,CACL,KAAMO,CAAAA,UAAN,CAAiB/B,IAAjB,CAA+B,CAC7B,GAAIgC,CAAAA,kBAAJ,CACA,GAAI,CACFA,kBAAkB,CAAG,yCAAkBhC,IAAlB,CAArB,CACD,CAAC,MAAOiC,GAAP,CAAY,CACZC,OAAO,CAACC,KAAR,CAAcF,GAAd,EACA,KAAM,+BAAkBjC,IAAlB,CAAN,CACD,CAED,GAAIoC,CAAAA,QAAQ,CAAG,KAAM,+BACnBzD,QADmB,CAEnBqD,kBAFmB,CAGnBpD,cAHmB,CAArB,CAMA;AACA,GAAIoB,IAAI,GAAK,SAAT,EAAsBoC,QAAQ,GAAK,IAAvC,CAA6C,CAC3CA,QAAQ,CAAG,wBAAX,CACD,CAED,GAAIA,QAAQ,GAAK,IAAjB,CAAuB,CACrB,KAAM,+BAAkBJ,kBAAlB,CAAN,CACD,CAED,GAAIK,CAAAA,OAAO,CAAGD,QAAQ,CAACE,OAAT,CAAiB,KAAjB,CAAwB,GAAxB,CAAd,CAEAD,OAAO,CAAI,GAAEA,OAAO,CAAC,CAAD,CAAP,GAAe,GAAf,CAAqB,GAArB,CAA2B,EAAG,GAAEA,OAAO,CACjDC,OAD0C,CAClC,GAAIC,CAAAA,MAAJ,CAAY,UAAS3D,cAAc,CAAC4D,IAAf,CAAoB,GAApB,CAAyB,IAA9C,CADkC,CACkB,EADlB,EAE1CF,OAF0C,CAElC,UAFkC,CAEtB,EAFsB,CAElB,EAF3B,CAIAD,OAAO,CAAGA,OAAO,GAAK,EAAZ,CAAiB,GAAjB,CAAuBA,OAAjC,CAEA,KAAMI,CAAAA,UAAU,CAAG,yCAAkBJ,OAAlB,CAAnB,CACA,KAAMK,CAAAA,gBAAgB,CAAGC,YAAMH,IAAN,CAAW,OAAX,CAAoBC,UAApB,CAAzB,CACA,KAAMG,CAAAA,gBAAgB,CAAGD,YAAMH,IAAN,CAAW,OAAX,CAAoBC,UAApB,CAAzB,CACA,KAAMI,CAAAA,gBAAgB,CAAGT,QAAQ,CAACU,UAAT,CAAoB,iBAApB,EACrBC,OAAO,CAACC,OAAR,CAAgBZ,QAAhB,CADqB,CAErB,eAAKzD,QAAL,CAAeyD,QAAf,CAFJ,CAIApC,IAAI,CAAG2C,YAAMM,SAAN,CAAgBZ,OAAhB,CAAP,CAEA,MAAO,IAAIa,CAAAA,OAAJ,CAAkB,CAACF,OAAD,CAAUG,MAAV,GAAqB,CAC5C;AACA,KAAMC,CAAAA,cAAc,CAAG,wCAAiBpD,IAAjB,CAAvB,CACA,KAAMuB,CAAAA,SAAS,CAAGhD,OAAO,CAAC6E,cAAD,CAAzB,CAEA,GAAI7B,SAAJ,CAAe,CACb,GAAIA,SAAS,CAACZ,MAAV,GAAqBrC,KAAzB,CAAgC,CAC9B0E,OAAO,GACP,OACD,CAED,GAAIzB,SAAS,CAACZ,MAAV,GAAqBtC,QAAzB,CAAmC,CACjCc,aAAa,CAAEkE,IAAf,CAAoBD,cAApB,CAAoCE,cAApC,EACA,OACD,CACF,CAEDC,GAAG,CAACC,KAAJ,CAAW,eAAcJ,cAAe,EAAxC,EAEA7E,OAAO,CAAC6E,cAAD,CAAP,CAA0B,CACxBV,gBADwB,CAExBE,gBAFwB,CAGxBC,gBAHwB,CAIxBlC,MAAM,CAAExC,KAJgB,CAA1B,CAMAgB,aAAa,CAAEkE,IAAf,CAAoBD,cAApB,CAAoCE,cAApC,EAEAtE,WAAW,CAACyE,UAAZ,GAEA,QAASH,CAAAA,cAAT,CAAwBrB,GAAxB,CAAoC,CAClC,GAAIA,GAAJ,CAAS,MAAOkB,CAAAA,MAAM,CAAClB,GAAD,CAAb,CACTe,OAAO,GACR,CACF,CAjCM,CAAP,CAkCD,CA5EI,CA8ELU,UAAU,CAACC,GAAD,CAAuBC,GAAvB,CAA4CC,IAA5C,CAA4D,cACpE,GAAI,YAACF,GAAG,CAACG,GAAL,SAAC,SAAShB,UAAT,CAAoB,oBAApB,CAAD,CAAJ,CAAgD,MAAOe,CAAAA,IAAI,EAAX,CAEhD,KAAM,CAAEE,KAAF,EAAY,eAAMJ,GAAG,CAACG,GAAV,CAAgB,IAAhB,CAAlB,CACA,KAAM9D,CAAAA,IAAI,CAAG+D,KAAK,CAAC/D,IAAnB,CACA,GAAI,CAACA,IAAL,CAAW,MAAO6D,CAAAA,IAAI,EAAX,CAEX,KAAMG,CAAAA,OAAO,CAAG,IAAM,CACpB,KAAMC,CAAAA,IAAI,CAAG5C,UAAU,CAAC0C,KAAK,CAAC/D,IAAP,CAAvB,CACA,GAAI,CAACiE,IAAL,CAAW,OACXL,GAAG,CAACM,KAAJ,CAAU,SAAWC,IAAI,CAACC,SAAL,CAAeH,IAAf,CAAX,CAAkC,MAA5C,EACD,CAJD,CAKA,KAAMI,CAAAA,YAAY,CAAGnD,WAAW,CAAC,IAAM8C,OAAO,EAAd,CAAkB,IAAlB,CAAhC,CAEAL,GAAG,CAACW,EAAJ,CAAO,OAAP,CAAgB,IAAM,CACpBC,aAAa,CAACF,YAAD,CAAb,CACD,CAFD,EAGAR,IAAI,GACL,CAhGI,CAAP,CAkGD,CAED,QAAS1C,CAAAA,sBAAT,CACE1C,OADF,CAEES,eAFF,CAGEL,cAHF,CAIE,CACA,KAAM2F,CAAAA,cAAmB,CAAG,EAA5B,CAEAC,MAAM,CAACC,IAAP,CAAYnG,OAAZ,EAAqBoG,OAArB,CAA8B3E,IAAD,EAAU,CACrC,KAAM,CAAEY,cAAF,CAAkBD,MAAlB,EAA6BpC,OAAO,CAACyB,IAAD,CAA1C,CAEA;AACA;AACA,GAAIW,MAAM,GAAKrC,KAAf,CAAsB,OAEtB;AACA;AACA;AACA,GAAIY,eAAe,CAACyC,QAAhB,CAAyB3B,IAAzB,CAAJ,CAAoC,OAEpC,GAAIY,cAAc,EAAIC,IAAI,CAACC,GAAL,GAAaF,cAAb,CAA8B/B,cAApD,CAAoE,CAClE2F,cAAc,CAACtE,IAAf,CAAoBF,IAApB,EACD,CACF,CAfD,EAiBA,GAAIwE,cAAc,CAAC3C,MAAf,CAAwB,CAA5B,CAA+B,CAC7B2C,cAAc,CAACG,OAAf,CAAwB3E,IAAD,EAAe,CACpC,MAAOzB,CAAAA,OAAO,CAACyB,IAAD,CAAd,CACD,CAFD,EAGA;AACAvB,OAAO,CAACgF,UAAR,GACD,CACF,CAED;AACA;AACA,KAAMxE,CAAAA,WAAY,CAMhB2F,WAAW,CAACnG,OAAD,CAAeC,aAAf,CAAqD,MALxDA,aAKwD,aAJxDD,OAIwD,aAHxDoG,QAGwD,aAFxDC,YAEwD,QAC9D,KAAKpG,aAAL,CAAqBA,aAArB,CACA,KAAKD,OAAL,CAAeA,OAAf,CACA;AACA,KAAKoG,QAAL,CAAgB,KAAhB,CACA,KAAKC,YAAL,CAAoB,KAApB,CACD,CAEDrB,UAAU,EAAG,CACX;AACA;AACA;AACA;AACA,GAAI,KAAKoB,QAAT,CAAmB,CACjB,KAAKC,YAAL,CAAoB,IAApB,CACA,OACD,CAED,KAAKD,QAAL,CAAgB,IAAhB,CACA,GAAI,CAACE,mBAAL,CAAiB,CACf;AACA;AACA,IAAK,KAAM1F,CAAAA,QAAX,GAAuB,MAAKX,aAAL,CAAmBK,SAA1C,CAAqD,CACnDM,QAAQ,CAACC,KAAT,CAAemC,OAAf,CAAuBuD,IAAvB,GACD,CACF,CAED,KAAKvG,OAAL,CAAagF,UAAb,GACD,CAED/D,aAAa,EAAG,CACd,KAAKmF,QAAL,CAAgB,IAAhB,CACD,CAED7D,YAAY,EAAG,CACb,KAAK6D,QAAL,CAAgB,KAAhB,CAEA,GAAI,KAAKC,YAAT,CAAuB,CACrB,KAAKA,YAAL,CAAoB,KAApB,CACA,KAAKrB,UAAL,GACD,CACF,CA/Ce","sourcesContent":["import { EventEmitter } from 'events'\nimport { IncomingMessage, ServerResponse } from 'http'\nimport { join, posix } from 'path'\nimport { parse } from 'url'\nimport { webpack, isWebpack5 } from 'next/dist/compiled/webpack/webpack'\nimport * as Log from '../build/output/log'\nimport {\n normalizePagePath,\n normalizePathSep,\n} from '../next-server/server/normalize-page-path'\nimport { pageNotFoundError } from '../next-server/server/require'\nimport { findPageFile } from './lib/find-page-file'\nimport getRouteFromEntrypoint from '../next-server/server/get-route-from-entrypoint'\n\nexport const ADDED = Symbol('added')\nexport const BUILDING = Symbol('building')\nexport const BUILT = Symbol('built')\n\nexport let entries: {\n [page: string]: {\n serverBundlePath: string\n clientBundlePath: string\n absolutePagePath: string\n status?: typeof ADDED | typeof BUILDING | typeof BUILT\n lastActiveTime?: number\n }\n} = {}\n\nexport default function onDemandEntryHandler(\n watcher: any,\n multiCompiler: webpack.MultiCompiler,\n {\n pagesDir,\n pageExtensions,\n maxInactiveAge,\n pagesBufferLength,\n }: {\n pagesDir: string\n pageExtensions: string[]\n maxInactiveAge: number\n pagesBufferLength: number\n }\n) {\n const { compilers } = multiCompiler\n const invalidator = new Invalidator(watcher, multiCompiler)\n\n let lastAccessPages = ['']\n let doneCallbacks: EventEmitter | null = new EventEmitter()\n\n for (const compiler of compilers) {\n compiler.hooks.make.tap(\n 'NextJsOnDemandEntries',\n (_compilation: webpack.compilation.Compilation) => {\n invalidator.startBuilding()\n }\n )\n }\n\n function getPagePathsFromEntrypoints(entrypoints: any): string[] {\n const pagePaths = []\n for (const entrypoint of entrypoints.values()) {\n const page = getRouteFromEntrypoint(entrypoint.name)\n if (page) {\n pagePaths.push(page)\n }\n }\n\n return pagePaths\n }\n\n multiCompiler.hooks.done.tap('NextJsOnDemandEntries', (multiStats) => {\n const [clientStats, serverStats] = multiStats.stats\n const pagePaths = new Set([\n ...getPagePathsFromEntrypoints(clientStats.compilation.entrypoints),\n ...getPagePathsFromEntrypoints(serverStats.compilation.entrypoints),\n ])\n\n for (const page of pagePaths) {\n const entry = entries[page]\n if (!entry) {\n continue\n }\n\n if (entry.status !== BUILDING) {\n continue\n }\n\n entry.status = BUILT\n entry.lastActiveTime = Date.now()\n doneCallbacks!.emit(page)\n }\n\n invalidator.doneBuilding()\n })\n\n const disposeHandler = setInterval(function () {\n disposeInactiveEntries(watcher, lastAccessPages, maxInactiveAge)\n }, 5000)\n\n disposeHandler.unref()\n\n function handlePing(pg: string) {\n const page = normalizePathSep(pg)\n const entryInfo = entries[page]\n let toSend\n\n // If there's no entry, it may have been invalidated and needs to be re-built.\n if (!entryInfo) {\n // if (page !== lastEntry) client pings, but there's no entry for page\n return { invalid: true }\n }\n\n // 404 is an on demand entry but when a new page is added we have to refresh the page\n if (page === '/_error') {\n toSend = { invalid: true }\n } else {\n toSend = { success: true }\n }\n\n // We don't need to maintain active state of anything other than BUILT entries\n if (entryInfo.status !== BUILT) return\n\n // If there's an entryInfo\n if (!lastAccessPages.includes(page)) {\n lastAccessPages.unshift(page)\n\n // Maintain the buffer max length\n if (lastAccessPages.length > pagesBufferLength) {\n lastAccessPages.pop()\n }\n }\n entryInfo.lastActiveTime = Date.now()\n return toSend\n }\n\n return {\n async ensurePage(page: string) {\n let normalizedPagePath: string\n try {\n normalizedPagePath = normalizePagePath(page)\n } catch (err) {\n console.error(err)\n throw pageNotFoundError(page)\n }\n\n let pagePath = await findPageFile(\n pagesDir,\n normalizedPagePath,\n pageExtensions\n )\n\n // Default the /_error route to the Next.js provided default page\n if (page === '/_error' && pagePath === null) {\n pagePath = 'next/dist/pages/_error'\n }\n\n if (pagePath === null) {\n throw pageNotFoundError(normalizedPagePath)\n }\n\n let pageUrl = pagePath.replace(/\\\\/g, '/')\n\n pageUrl = `${pageUrl[0] !== '/' ? '/' : ''}${pageUrl\n .replace(new RegExp(`\\\\.+(?:${pageExtensions.join('|')})$`), '')\n .replace(/\\/index$/, '')}`\n\n pageUrl = pageUrl === '' ? '/' : pageUrl\n\n const bundleFile = normalizePagePath(pageUrl)\n const serverBundlePath = posix.join('pages', bundleFile)\n const clientBundlePath = posix.join('pages', bundleFile)\n const absolutePagePath = pagePath.startsWith('next/dist/pages')\n ? require.resolve(pagePath)\n : join(pagesDir, pagePath)\n\n page = posix.normalize(pageUrl)\n\n return new Promise<void>((resolve, reject) => {\n // Makes sure the page that is being kept in on-demand-entries matches the webpack output\n const normalizedPage = normalizePathSep(page)\n const entryInfo = entries[normalizedPage]\n\n if (entryInfo) {\n if (entryInfo.status === BUILT) {\n resolve()\n return\n }\n\n if (entryInfo.status === BUILDING) {\n doneCallbacks!.once(normalizedPage, handleCallback)\n return\n }\n }\n\n Log.event(`build page: ${normalizedPage}`)\n\n entries[normalizedPage] = {\n serverBundlePath,\n clientBundlePath,\n absolutePagePath,\n status: ADDED,\n }\n doneCallbacks!.once(normalizedPage, handleCallback)\n\n invalidator.invalidate()\n\n function handleCallback(err: Error) {\n if (err) return reject(err)\n resolve()\n }\n })\n },\n\n middleware(req: IncomingMessage, res: ServerResponse, next: Function) {\n if (!req.url?.startsWith('/_next/webpack-hmr')) return next()\n\n const { query } = parse(req.url!, true)\n const page = query.page\n if (!page) return next()\n\n const runPing = () => {\n const data = handlePing(query.page as string)\n if (!data) return\n res.write('data: ' + JSON.stringify(data) + '\\n\\n')\n }\n const pingInterval = setInterval(() => runPing(), 5000)\n\n req.on('close', () => {\n clearInterval(pingInterval)\n })\n next()\n },\n }\n}\n\nfunction disposeInactiveEntries(\n watcher: any,\n lastAccessPages: any,\n maxInactiveAge: number\n) {\n const disposingPages: any = []\n\n Object.keys(entries).forEach((page) => {\n const { lastActiveTime, status } = entries[page]\n\n // This means this entry is currently building or just added\n // We don't need to dispose those entries.\n if (status !== BUILT) return\n\n // We should not build the last accessed page even we didn't get any pings\n // Sometimes, it's possible our XHR ping to wait before completing other requests.\n // In that case, we should not dispose the current viewing page\n if (lastAccessPages.includes(page)) return\n\n if (lastActiveTime && Date.now() - lastActiveTime > maxInactiveAge) {\n disposingPages.push(page)\n }\n })\n\n if (disposingPages.length > 0) {\n disposingPages.forEach((page: any) => {\n delete entries[page]\n })\n // disposing inactive page(s)\n watcher.invalidate()\n }\n}\n\n// Make sure only one invalidation happens at a time\n// Otherwise, webpack hash gets changed and it'll force the client to reload.\nclass Invalidator {\n private multiCompiler: webpack.MultiCompiler\n private watcher: any\n private building: boolean\n private rebuildAgain: boolean\n\n constructor(watcher: any, multiCompiler: webpack.MultiCompiler) {\n this.multiCompiler = multiCompiler\n this.watcher = watcher\n // contains an array of types of compilers currently building\n this.building = false\n this.rebuildAgain = false\n }\n\n invalidate() {\n // If there's a current build is processing, we won't abort it by invalidating.\n // (If aborted, it'll cause a client side hard reload)\n // But let it to invalidate just after the completion.\n // So, it can re-build the queued pages at once.\n if (this.building) {\n this.rebuildAgain = true\n return\n }\n\n this.building = true\n if (!isWebpack5) {\n // Work around a bug in webpack, calling `invalidate` on Watching.js\n // doesn't trigger the invalid call used to keep track of the `.done` hook on multiCompiler\n for (const compiler of this.multiCompiler.compilers) {\n compiler.hooks.invalid.call()\n }\n }\n\n this.watcher.invalidate()\n }\n\n startBuilding() {\n this.building = true\n }\n\n doneBuilding() {\n this.building = false\n\n if (this.rebuildAgain) {\n this.rebuildAgain = false\n this.invalidate()\n }\n }\n}\n"]}
\No newline at end of file