1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798 |
- /** @typedef {string | string[] | import('webpack').Entry} StaticEntry */
- /** @typedef {StaticEntry | import('webpack').EntryFunc} WebpackEntry */
- const EntryParseError = new Error(
- [
- '[ReactRefreshPlugin]',
- 'Failed to parse the Webpack `entry` object!',
- 'Please ensure the `entry` option in your Webpack config is specified.',
- ].join(' ')
- );
- /**
- * Webpack entries related to socket integrations.
- * They have to run before any code that sets up the error overlay.
- * @type {string[]}
- */
- const socketEntries = [
- 'webpack-dev-server/client',
- 'webpack-hot-middleware/client',
- 'webpack-plugin-serve/client',
- 'react-dev-utils/webpackHotDevClient',
- ];
- /**
- * Checks if a Webpack entry string is related to socket integrations.
- * @param {string} entry A Webpack entry string.
- * @returns {boolean} Whether the entry is related to socket integrations.
- */
- function isSocketEntry(entry) {
- return socketEntries.some((socketEntry) => entry.includes(socketEntry));
- }
- /**
- * Injects an entry to the bundle for react-refresh.
- * @param {WebpackEntry} [originalEntry] A Webpack entry object.
- * @param {import('./getAdditionalEntries').AdditionalEntries} additionalEntries An object that contains the Webpack entries for prepending and the overlay feature
- * @returns {WebpackEntry} An injected entry object.
- */
- function injectRefreshEntry(originalEntry, additionalEntries) {
- const { prependEntries, overlayEntries } = additionalEntries;
- // Single string entry point
- if (typeof originalEntry === 'string') {
- if (isSocketEntry(originalEntry)) {
- return [...prependEntries, originalEntry, ...overlayEntries];
- }
- return [...prependEntries, ...overlayEntries, originalEntry];
- }
- // Single array entry point
- if (Array.isArray(originalEntry)) {
- if (originalEntry.length === 0) {
- throw EntryParseError;
- }
- const socketEntryIndex = originalEntry.findIndex(isSocketEntry);
- let socketAndPrecedingEntries = [];
- if (socketEntryIndex !== -1) {
- socketAndPrecedingEntries = originalEntry.splice(0, socketEntryIndex + 1);
- }
- return [...prependEntries, ...socketAndPrecedingEntries, ...overlayEntries, ...originalEntry];
- }
- // Multiple entry points
- if (typeof originalEntry === 'object') {
- const entries = Object.entries(originalEntry);
- if (entries.length === 0) {
- throw EntryParseError;
- }
- return entries.reduce(
- (acc, [curKey, curEntry]) => ({
- ...acc,
- [curKey]:
- typeof curEntry === 'object' && curEntry.import
- ? {
- ...curEntry,
- import: injectRefreshEntry(curEntry.import, additionalEntries),
- }
- : injectRefreshEntry(curEntry, additionalEntries),
- }),
- {}
- );
- }
- // Dynamic entry points
- if (typeof originalEntry === 'function') {
- return (...args) =>
- Promise.resolve(originalEntry(...args)).then((resolvedEntry) =>
- injectRefreshEntry(resolvedEntry, additionalEntries)
- );
- }
- throw EntryParseError;
- }
- module.exports = injectRefreshEntry;
- module.exports.socketEntries = socketEntries;
|