@plaudit/webpack-extensions 2.95.0 → 2.96.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,150 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.defaultRequestToExternal = defaultRequestToExternal;
4
+ exports.defaultRequestToExternalModule = defaultRequestToExternalModule;
5
+ exports.defaultRequestToHandle = defaultRequestToHandle;
6
+ exports.camelCaseDash = camelCaseDash;
7
+ exports.isConcatenatedModule = isConcatenatedModule;
8
+ exports.isEntrypoint = isEntrypoint;
9
+ const WORDPRESS_NAMESPACE = '@wordpress/';
10
+ const BUNDLED_PACKAGES = [
11
+ '@wordpress/admin-ui',
12
+ '@wordpress/dataviews',
13
+ '@wordpress/dataviews/wp',
14
+ '@wordpress/fields',
15
+ '@wordpress/grid',
16
+ '@wordpress/icons',
17
+ '@wordpress/interface',
18
+ '@wordpress/style-runtime',
19
+ '@wordpress/ui',
20
+ '@wordpress/undo-manager',
21
+ '@wordpress/views',
22
+ ];
23
+ /**
24
+ * Default request to global transformation
25
+ *
26
+ * Transform @wordpress dependencies:
27
+ * - request `@wordpress/api-fetch` becomes `[ 'wp', 'apiFetch' ]`
28
+ * - request `@wordpress/i18n` becomes `[ 'wp', 'i18n' ]`
29
+ *
30
+ * @param {string} request Module request (the module name in `import from`) to be transformed
31
+ * @return {string|string[]|undefined} The resulting external definition. Return `undefined`
32
+ * to ignore the request. Return `string|string[]` to map the request to an external.
33
+ */
34
+ function defaultRequestToExternal(request) {
35
+ switch (request) {
36
+ case 'moment':
37
+ return request;
38
+ case '@babel/runtime/regenerator':
39
+ return 'regeneratorRuntime';
40
+ case 'lodash':
41
+ case 'lodash-es':
42
+ return 'lodash';
43
+ case 'jquery':
44
+ return 'jQuery';
45
+ case 'react':
46
+ return 'React';
47
+ case 'react-dom':
48
+ case 'react-dom/client':
49
+ return 'ReactDOM';
50
+ case 'react/jsx-runtime':
51
+ case 'react/jsx-dev-runtime':
52
+ return 'ReactJSXRuntime';
53
+ }
54
+ if (request.includes('react-refresh/runtime')) {
55
+ return 'ReactRefreshRuntime';
56
+ }
57
+ if (BUNDLED_PACKAGES.includes(request)) {
58
+ return undefined;
59
+ }
60
+ if (request.startsWith(WORDPRESS_NAMESPACE)) {
61
+ return [
62
+ 'wp',
63
+ camelCaseDash(request.substring(WORDPRESS_NAMESPACE.length)),
64
+ ];
65
+ }
66
+ return undefined;
67
+ }
68
+ /**
69
+ * Default request to external module transformation
70
+ *
71
+ * Currently only @wordpress/interactivity and `@wordpress/interactivity-router`
72
+ * are supported.
73
+ *
74
+ * Do not use the boolean shorthand here, it's only handled for the
75
+ * `requestToExternalModule` option.
76
+ *
77
+ * @param {string} request Module request (the module name in `import from`) to be transformed
78
+ * @return {string|undefined} The resulting external definition.
79
+ * - Return `undefined` to ignore the request (do not externalize).
80
+ * - Return `string` to map the request to an external.
81
+ * - Return `Error` to emit an error.
82
+ */
83
+ function defaultRequestToExternalModule(request) {
84
+ if (request === '@wordpress/interactivity') {
85
+ // This is a special case. Interactivity does not support dynamic imports at
86
+ // this time. We add the external "module" type to indicate that webpack
87
+ // should externalize this as a module (instead of our default `import()`
88
+ // external type) which forces @wordpress/interactivity imports to be
89
+ // hoisted to static imports.
90
+ return `module ${request}`;
91
+ }
92
+ switch (request) {
93
+ case '@wordpress/interactivity-router':
94
+ case '@wordpress/a11y':
95
+ return `import ${request}`;
96
+ }
97
+ const isWordPressScript = Boolean(defaultRequestToExternal(request));
98
+ if (isWordPressScript) {
99
+ throw new Error(`Attempted to use WordPress script in a module: ${request}, which is not supported yet.`);
100
+ }
101
+ return undefined;
102
+ }
103
+ /**
104
+ * Default request to WordPress script handle transformation
105
+ *
106
+ * Transform @wordpress dependencies:
107
+ * - request `@wordpress/i18n` becomes `wp-i18n`
108
+ * - request `@wordpress/escape-html` becomes `wp-escape-html`
109
+ *
110
+ * @param {string} request Module request (the module name in `import from`) to be transformed
111
+ * @return {string|undefined} WordPress script handle to map the request to. Return `undefined`
112
+ * to use the same name as the module.
113
+ */
114
+ function defaultRequestToHandle(request) {
115
+ switch (request) {
116
+ case '@babel/runtime/regenerator':
117
+ return 'regenerator-runtime';
118
+ case 'lodash-es':
119
+ return 'lodash';
120
+ case 'react-dom/client':
121
+ return 'react-dom';
122
+ case 'react/jsx-runtime':
123
+ return 'react-jsx-runtime';
124
+ }
125
+ if (request.includes('react-refresh/runtime')) {
126
+ return 'wp-react-refresh-runtime';
127
+ }
128
+ if (request.startsWith(WORDPRESS_NAMESPACE)) {
129
+ return 'wp-' + request.substring(WORDPRESS_NAMESPACE.length);
130
+ }
131
+ return undefined;
132
+ }
133
+ /**
134
+ * Given a string, returns a new string with dash separators converted to
135
+ * camelCase equivalent. This is not as aggressive as `_.camelCase` in
136
+ * converting to uppercase, where Lodash will also capitalize letters
137
+ * following numbers.
138
+ *
139
+ * @param {string} string Input dash-delimited string.
140
+ * @return {string} Camel-cased string.
141
+ */
142
+ function camelCaseDash(string) {
143
+ return string.replace(/-([a-z])/g, (_, letter) => letter.toUpperCase());
144
+ }
145
+ function isConcatenatedModule(module) {
146
+ return 'modules' in module && Array.isArray(module.modules);
147
+ }
148
+ function isEntrypoint(group) {
149
+ return !!group && group.constructor.name === 'Entrypoint';
150
+ }
@@ -90,7 +90,7 @@ function replaceDefaultURLProcessing(useWebpackResourceFiltering) {
90
90
  }
91
91
  function injectPostcssConfigOverrides(rules, config, variables, postcssFunctionsConfig, verbose) {
92
92
  const postcssConfig = (0, static_configs_1.postcssConfigBuilder)(verbose, name => variables(name) ?? (name === 'ENV' ? '' : undefined), postcssFunctionsConfig);
93
- return recursivelyAddParentDirectoryStepToImagesAndFonts(rules.map(rule => {
93
+ return rules.map(rule => {
94
94
  if (rule && typeof rule === 'object') {
95
95
  if (Array.isArray(rule.use)) {
96
96
  for (const useItem of rule.use) {
@@ -130,26 +130,6 @@ function injectPostcssConfigOverrides(rules, config, variables, postcssFunctions
130
130
  }
131
131
  }
132
132
  return rule;
133
- }), config);
134
- }
135
- function recursivelyAddParentDirectoryStepToImagesAndFonts(rules, config) {
136
- if (config.outputDir) {
137
- return rules;
138
- }
139
- return rules.map(rule => {
140
- if (rule && typeof rule === 'object') {
141
- if (typeof rule.generator === 'object') {
142
- const ruleGeneratorFilename = rule.generator["filename"];
143
- if (typeof ruleGeneratorFilename === 'string' && (ruleGeneratorFilename.startsWith("images/") || ruleGeneratorFilename.startsWith("fonts/"))) {
144
- rule.generator["filename"] = `../${ruleGeneratorFilename}`;
145
- rule = { ...rule, generator: { ...rule.generator, filename: `../${ruleGeneratorFilename}` } };
146
- }
147
- }
148
- if (rule.oneOf) {
149
- rule = { ...rule, oneOf: recursivelyAddParentDirectoryStepToImagesAndFonts(rule.oneOf, config) };
150
- }
151
- }
152
- return rule;
153
133
  });
154
134
  }
155
135
  function injectSupportForInliningSVGsAsStrings(rules) {
@@ -167,7 +147,7 @@ function injectSupportForInliningSVGsAsStrings(rules) {
167
147
  }
168
148
  function buildVerifiedConfig(config) {
169
149
  config = (0, shared_1.applyStandards)(config);
170
- const { standaloneBlocks = false, stats = 'errors-warnings', variables: rawVariables, verbose = process.argv.includes('--verbose') || process.env['VERBOSE'] === 'true', postcss = {}, externals, assumeGlobalizedPlauditLibraries = true, processTranslationConfigs = true, combineAssetMetadata = true, useWebpackResourceFiltering = true, plainEntrypointsVersion = 1, srcDir = "", useUnifiedLoader = false, includePostInitFallback = false, omitDistDev = false, onlyRunPostCSSOnPCSS = false, useBlockSupportsAsThemeJsonDefaults = true, } = config;
150
+ const { standaloneBlocks = false, stats = 'errors-warnings', variables: rawVariables, verbose = process.argv.includes('--verbose') || process.env['VERBOSE'] === 'true', postcss = {}, externals, assumeGlobalizedPlauditLibraries = true, processTranslationConfigs = true, useWebpackResourceFiltering = true, plainEntrypointsVersion = 1, srcDir = "", useUnifiedLoader = false, includePostInitFallback = false, omitDistDev = false, onlyRunPostCSSOnPCSS = false, useBlockSupportsAsThemeJsonDefaults = true, } = config;
171
151
  let outputDir = config.outputDir ?? "";
172
152
  if (outputDir && useUnifiedLoader && !omitDistDev && (process.env['SERVER_MODE'] ?? 'development') === 'development') {
173
153
  outputDir += "-dev";
@@ -204,31 +184,54 @@ function buildVerifiedConfig(config) {
204
184
  extensionsVersion = 3; // Version 3 is a backwards-compatible upgrade of version 2, so we can automatically upgrade everything
205
185
  }
206
186
  const cfg = {
207
- currentVariables, postcss, standaloneBlocks, stats, variablesFilePath, verbose, externals, assumeGlobalizedPlauditLibraries, processTranslationConfigs, combineAssetMetadata,
187
+ currentVariables, postcss, standaloneBlocks, stats, variablesFilePath, verbose, externals, assumeGlobalizedPlauditLibraries, processTranslationConfigs,
208
188
  useWebpackResourceFiltering, outputDir, extensionsVersion, plainEntrypointsVersion, srcDir, srcPrefixes, targetHandlePrefix, useUnifiedLoader, includePostInitFallback, omitDistDev,
209
189
  onlyRunPostCSSOnPCSS, useBlockSupportsAsThemeJsonDefaults
210
190
  };
211
191
  // Destination -> source map
212
192
  const allocatedDestinations = {};
213
- const partiallyVerifiedSources = rawSources.map(rawSource => {
214
- const { destination, additionalDependencies = [], assumeGlobalizedPlauditLibraries = cfg.assumeGlobalizedPlauditLibraries, bundleAnalyzer = false, directoryLayout, externalize, withLegacyBlocksIn = false, lazyLoader, pathQueryParameters: rawPathQueryParameters, enqueuingFlags: rawEnqueuingFlags } = rawSource[1];
215
- const { flags: queryEnqueuingFlags, remainder: pathQueryParameters } = (0, path_query_and_related_helpers_1.unpackEnqueuingControlFlagsFromPathQueryParameters)(rawPathQueryParameters, rawSource[0], 'path query parameters');
216
- const enqueuingFlags = (0, path_query_and_related_helpers_1.mergeTwoEnqueuingControlFlagSets)(rawSource[0], rawEnqueuingFlags, queryEnqueuingFlags);
193
+ const partiallyVerifiedSources = rawSources.map(([src, config]) => {
194
+ const { destination, additionalDependencies = [], assumeGlobalizedPlauditLibraries = cfg.assumeGlobalizedPlauditLibraries, bundleAnalyzer = false, directoryLayout, externalize, withLegacyBlocksIn = false, lazyLoader, pathQueryParameters: rawPathQueryParameters, enqueuingFlags: rawEnqueuingFlags, locations: rawSourceLocations, } = config;
195
+ const { flags: queryEnqueuingFlags, remainder: pathQueryParameters, handle: pathQueryHandle } = (0, path_query_and_related_helpers_1.unpackEnqueuingControlFlagsFromPathQueryParameters)(rawPathQueryParameters, src, 'path query parameters');
196
+ const enqueuingFlags = (0, path_query_and_related_helpers_1.mergeTwoEnqueuingControlFlagSets)(src, rawEnqueuingFlags, queryEnqueuingFlags);
217
197
  const normalizedParts = { additionalDependencies, assumeGlobalizedPlauditLibraries, bundleAnalyzer, directoryLayout, externalize, withLegacyBlocksIn, lazyLoader };
218
- const locations = typeof rawSource[1].locations === 'string' || typeof rawSource[1].locations === 'function'
219
- ? { handle: rawSource[1].locations } : rawSource[1].locations ?? {};
198
+ let locations;
199
+ if (pathQueryHandle === undefined) {
200
+ locations = typeof rawSourceLocations === 'string' || typeof rawSourceLocations === 'function'
201
+ ? { handle: rawSourceLocations } : rawSourceLocations ?? {};
202
+ }
203
+ else {
204
+ const rawSourceHandle = typeof rawSourceLocations === 'string' || typeof rawSourceLocations === 'function'
205
+ ? rawSourceLocations : rawSourceLocations?.handle;
206
+ if (rawSourceHandle === undefined) {
207
+ locations = { handle: pathQueryHandle };
208
+ }
209
+ else if (typeof rawSourceHandle === 'string') {
210
+ if (rawSourceHandle !== pathQueryHandle) {
211
+ throw new ReferenceError(`Encountered mismatched handles "${rawSourceHandle}" and "${pathQueryHandle}" when preparing "${src}"`);
212
+ }
213
+ locations = { handle: pathQueryHandle };
214
+ }
215
+ else {
216
+ throw new ReferenceError(`Encountered a function handle and a path query handle when preparing "${src}"`);
217
+ }
218
+ // This is just a means of merging the new handle into the rawSourceLocations config without mutating the base config
219
+ if (rawSourceLocations !== undefined && typeof rawSourceLocations !== 'function' && typeof rawSourceLocations !== 'string') {
220
+ locations = { ...rawSourceLocations, ...locations };
221
+ }
222
+ }
220
223
  if (typeof locations.registerScriptArgs === 'string' && !['lazy', 'eager', 'inline'].includes(locations.registerScriptArgs)) {
221
224
  throw new ReferenceError("The only supported string values for registerScriptArgs are 'lazy', 'eager', and 'inline'");
222
225
  }
223
226
  if (destination !== undefined) {
224
227
  const effectiveDestination = toEffectiveWebpackDestination(destination);
225
- allocatedDestinations[effectiveDestination] = rawSource[0]; // We need to pre-populate the allocatedDestinations map with statically declared destinations
226
- return [rawSource[0], { ...normalizedParts, locations, destination, effectiveDestination, staticallyDeclaredDestination: true, pathQueryParameters, enqueuingFlags }];
228
+ allocatedDestinations[effectiveDestination] = src; // We need to pre-populate the allocatedDestinations map with statically declared destinations
229
+ return [src, { ...normalizedParts, locations, destination, effectiveDestination, staticallyDeclaredDestination: true, pathQueryParameters, enqueuingFlags }];
227
230
  }
228
231
  else {
229
- const naiveDestination = deriveNaiveDestinationFromUnverifiedSourceEntry(rawSource, srcPrefixes);
232
+ const naiveDestination = deriveNaiveDestinationFromUnverifiedSourceEntry(src, destination, srcPrefixes);
230
233
  const effectiveDestination = toEffectiveWebpackDestination(naiveDestination);
231
- return [rawSource[0], { ...normalizedParts, locations, destination: naiveDestination, effectiveDestination, staticallyDeclaredDestination: false, pathQueryParameters, enqueuingFlags }];
234
+ return [src, { ...normalizedParts, locations, destination: naiveDestination, effectiveDestination, staticallyDeclaredDestination: false, pathQueryParameters, enqueuingFlags }];
232
235
  }
233
236
  });
234
237
  const dynamicEffectiveDestinationsWithExpectedNaiveDuplicates = partiallyVerifiedSources
@@ -247,7 +250,7 @@ function toEffectiveWebpackDestination(destination) {
247
250
  const pathParts = (0, node_path_1.parse)(destination);
248
251
  return (0, node_path_1.join)(pathParts.dir, pathParts.name);
249
252
  }
250
- function deriveNaiveDestinationFromUnverifiedSourceEntry([src, { destination }], srcPrefixes) {
253
+ function deriveNaiveDestinationFromUnverifiedSourceEntry(src, destination, srcPrefixes) {
251
254
  if (destination !== undefined) {
252
255
  return destination;
253
256
  }
@@ -377,7 +380,7 @@ function buildCommonPluginConfig(webpackConfig, config, bundleAnalyzer, assumeGl
377
380
  ?? [];
378
381
  plugins.splice(0, 0, new PackageConfigSanityChecker_1.PackageConfigSanityChecker());
379
382
  if (bundleAnalyzer) {
380
- plugins.splice(0, 0, new (require("webpack-bundle-analyzer").BundleAnalyzerPlugin)({ analyzerMode: 'static' }));
383
+ plugins.splice(0, 0, new (require("webpack-bundle-analyzer").BundleAnalyzerPlugin)({ analyzerMode: 'static', openAnalyzer: bundleAnalyzer !== 'no-auto-open' }));
381
384
  }
382
385
  const removeEmptyScriptsPlugin = new webpack_remove_empty_scripts_1.default({
383
386
  stage: webpack_remove_empty_scripts_1.default.STAGE_AFTER_PROCESS_PLUGINS,
@@ -400,8 +403,8 @@ function buildCommonPluginConfig(webpackConfig, config, bundleAnalyzer, assumeGl
400
403
  console.error("Once those commands have finished, re-run whichever command had this error. If it still doesn't work, report the issue immediately.");
401
404
  throw new Error("Cannot apply externals when they have been disabled via CLI flag. This will greatly increase bundle size and will likely cause the build to fail");
402
405
  }
403
- const builtDependencyExtractionWebpackPlugin = (0, dependency_extraction_webpack_plugin_config_builder_1.makeDependencyExtractionPlugin)(config.externals, assumeGlobalizedPlauditLibraries, true, externalize);
404
- plugins[dependencyExtractionPluginIndex] = builtDependencyExtractionWebpackPlugin.instance;
406
+ const builtDependencyExtractionWebpackPlugin = (0, dependency_extraction_webpack_plugin_config_builder_1.makeDependencyExtractionPlugin)(config.externals, assumeGlobalizedPlauditLibraries, externalize);
407
+ plugins[dependencyExtractionPluginIndex] = builtDependencyExtractionWebpackPlugin;
405
408
  plugins.push(new BrowserSyncPlugin_1.BrowserSyncPlugin());
406
409
  return {
407
410
  plugins, removeEmptyScriptsPlugin,
package/package.json CHANGED
@@ -1,7 +1,11 @@
1
1
  {
2
2
  "name": "@plaudit/webpack-extensions",
3
- "version": "2.95.0",
3
+ "version": "2.96.1",
4
4
  "license": "SEE LICENSE IN LICENSE.md",
5
+ "repository": {
6
+ "type": "git",
7
+ "url": "git+https://github.com/plaudit/plaudit-webpack-extensions.git"
8
+ },
5
9
  "files": [
6
10
  "/dist",
7
11
  "README.md",
@@ -35,6 +39,14 @@
35
39
  "@types/postcss-functions": "^4.0.4",
36
40
  "@types/tapable": "^2.3.0",
37
41
  "@types/webpack-sources": "^3.2.3",
42
+ "atob": "^2.1.2",
43
+ "css-loader": "^6.2.0",
44
+ "glob": "^7.1.2",
45
+ "jest": "^30.0.0",
46
+ "lodash": "^4.17.21",
47
+ "mini-css-extract-plugin": "^2.9.2",
48
+ "mkdirp": "^3.0.1",
49
+ "rimraf": "^5.0.10",
38
50
  "typescript": "^6.0.3",
39
51
  "webpack-bundle-analyzer": "^4.10.2"
40
52
  },
@@ -82,6 +94,10 @@
82
94
  "clean": "rm -rf dist",
83
95
  "build:clean": "pnpm run clean && pnpm run build",
84
96
  "watch": "tsc -w",
97
+ "test": "pnpm run build && pnpm run test:no-build",
98
+ "test:no-build": "rm -rf tests/.tmp/coverage/jest && NODE_V8_COVERAGE=tests/.tmp/coverage/jest jest",
99
+ "test:paths": "pnpm run build && jest tests/integration-2x/paths",
100
+ "test:gaps": "node tests/tools/coverage-gaps.js",
85
101
  "update": "pnpm add --config '@plaudit/pnpm-plugin-plaudit-config@*' && pnpm up"
86
102
  }
87
103
  }