@meteorjs/rspack 0.0.67 → 0.1.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.
package/index.d.ts CHANGED
@@ -5,7 +5,7 @@ import {
5
5
  defineConfig as _rspackDefineConfig,
6
6
  Configuration as _RspackConfig,
7
7
  } from '@rspack/cli';
8
- import { HtmlRspackPluginOptions, RuleSetConditions } from '@rspack/core';
8
+ import { HtmlRspackPluginOptions, RuleSetConditions, SwcLoaderOptions } from '@rspack/core';
9
9
 
10
10
  export interface MeteorRspackConfig extends _RspackConfig {
11
11
  meteor?: {
@@ -56,6 +56,11 @@ type MeteorEnv = Record<string, any> & {
56
56
  * @returns A config object with optimization configuration
57
57
  */
58
58
  splitVendorChunk: () => Record<string, object>;
59
+ /**
60
+ * Extend Rspack SWC loader config.
61
+ * @returns A config object with SWC loader config
62
+ */
63
+ extendSwcConfig: (swcConfig: SwcLoaderOptions) => Record<string, object>;
59
64
  }
60
65
 
61
66
  export type ConfigFactory = (
@@ -139,10 +139,32 @@ function splitVendorChunk() {
139
139
  });
140
140
  }
141
141
 
142
+ /**
143
+ * Extend SWC loader config
144
+ * Usage: extendSwcConfig()
145
+ *
146
+ * @returns {Record<string, object>} `{ meteorRspackConfigX: { optimization: { ... } } }`
147
+ */
148
+ function extendSwcConfig(swcConfig) {
149
+ return prepareMeteorRspackConfig({
150
+ module: {
151
+ rules: [
152
+ {
153
+ test: /\.(?:[mc]?js|jsx|[mc]?ts|tsx)$/i,
154
+ exclude: /node_modules|\.meteor\/local/,
155
+ loader: 'builtin:swc-loader',
156
+ options: swcConfig,
157
+ },
158
+ ],
159
+ },
160
+ });
161
+ }
162
+
142
163
  module.exports = {
143
164
  compileWithMeteor,
144
165
  compileWithRspack,
145
166
  setCache,
146
167
  splitVendorChunk,
168
+ extendSwcConfig,
147
169
  makeWebNodeBuiltinsAlias,
148
170
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@meteorjs/rspack",
3
- "version": "0.0.67",
3
+ "version": "0.1.1",
4
4
  "description": "Configuration logic for using Rspack in Meteor projects",
5
5
  "main": "index.js",
6
6
  "type": "commonjs",
package/rspack.config.js CHANGED
@@ -17,6 +17,7 @@ const {
17
17
  compileWithRspack,
18
18
  setCache,
19
19
  splitVendorChunk,
20
+ extendSwcConfig,
20
21
  makeWebNodeBuiltinsAlias,
21
22
  } = require('./lib/meteorRspackHelpers.js');
22
23
 
@@ -280,6 +281,7 @@ module.exports = async function (inMeteor = {}, argv = {}) {
280
281
  enabled === 'memory' ? undefined : cacheStrategy
281
282
  );
282
283
  Meteor.splitVendorChunk = () => splitVendorChunk();
284
+ Meteor.extendSwcConfig = (customSwcConfig) => extendSwcConfig(customSwcConfig);
283
285
 
284
286
  // Add HtmlRspackPlugin function to Meteor
285
287
  Meteor.HtmlRspackPlugin = (options = {}) => {
@@ -604,83 +606,92 @@ module.exports = async function (inMeteor = {}, argv = {}) {
604
606
  cacheStrategy),
605
607
  };
606
608
 
607
- // Load and apply project-level overrides for the selected build
608
- // Check if we're in a Meteor package directory by looking at the path
609
- const isMeteorPackageConfig = projectDir.includes('/packages/rspack');
610
- if (fs.existsSync(projectConfigPath) && !isMeteorPackageConfig) {
611
- // Check if there's a .mjs or .cjs version of the config file
612
- const mjsConfigPath = projectConfigPath.replace(/\.js$/, '.mjs');
613
- const cjsConfigPath = projectConfigPath.replace(/\.js$/, '.cjs');
614
-
615
- let configPath = projectConfigPath;
616
- if (fs.existsSync(mjsConfigPath)) {
617
- configPath = mjsConfigPath;
618
- } else if (fs.existsSync(cjsConfigPath)) {
619
- configPath = cjsConfigPath;
620
- }
621
-
622
- // Use require for CommonJS modules and dynamic import for ES modules
623
- let projectConfig;
609
+ // Helper function to load and process config files
610
+ async function loadAndProcessConfig(configPath, configType, Meteor, argv, isAngularEnabled) {
624
611
  try {
612
+ // Load the config file
613
+ let config;
625
614
  if (path.extname(configPath) === '.mjs') {
626
615
  // For ESM modules, we need to use dynamic import
627
616
  const fileUrl = `file://${configPath}`;
628
617
  const module = await import(fileUrl);
629
- projectConfig = module.default || module;
618
+ config = module.default || module;
630
619
  } else {
631
620
  // For CommonJS modules, we can use require
632
- projectConfig = require(configPath)?.default || require(configPath);
621
+ config = require(configPath)?.default || require(configPath);
633
622
  }
623
+
624
+ // Process the config
625
+ const rawConfig = typeof config === 'function' ? config(Meteor, argv) : config;
626
+ const resolvedConfig = await Promise.resolve(rawConfig);
627
+ const userConfig = resolvedConfig && '0' in resolvedConfig ? resolvedConfig[0] : resolvedConfig;
628
+
629
+ // Define omitted paths and warning function
630
+ const omitPaths = [
631
+ "name",
632
+ "target",
633
+ "entry",
634
+ "output.path",
635
+ "output.filename",
636
+ "output.publicPath",
637
+ ...(Meteor.isServer ? ["optimization.splitChunks", "optimization.runtimeChunk"] : []),
638
+ ].filter(Boolean);
639
+
640
+ const warningFn = path => {
641
+ if (isAngularEnabled) return;
642
+ console.warn(
643
+ `[${configType}] Ignored custom "${path}" — reserved for Meteor-Rspack integration.`,
644
+ );
645
+ };
646
+
647
+ // Clean omitted paths and merge Meteor Rspack fragments
648
+ let nextConfig = cleanOmittedPaths(userConfig, {
649
+ omitPaths,
650
+ warningFn,
651
+ });
652
+ nextConfig = mergeMeteorRspackFragments(nextConfig);
653
+
654
+ return nextConfig;
634
655
  } catch (error) {
635
- console.error(`Error loading rspack config from ${configPath}:`, error);
636
- throw error;
656
+ console.error(`Error loading ${configType} from ${configPath}:`, error);
657
+ if (configType === 'rspack.config.js') {
658
+ throw error; // Only rethrow for project config
659
+ }
660
+ return null;
637
661
  }
662
+ }
638
663
 
639
- const rawUserConfig =
640
- typeof projectConfig === 'function'
641
- ? projectConfig(Meteor, argv)
642
- : projectConfig;
643
- const resolvedUserConfig = await Promise.resolve(rawUserConfig);
644
- const userConfig =
645
- resolvedUserConfig && '0' in resolvedUserConfig
646
- ? resolvedUserConfig[0]
647
- : resolvedUserConfig;
648
-
649
- const omitPaths = [
650
- "name",
651
- "target",
652
- "entry",
653
- "output.path",
654
- "output.filename",
655
- "output.publicPath",
656
- ...(Meteor.isServer
657
- ? ["optimization.splitChunks", "optimization.runtimeChunk"]
658
- : []),
659
- ].filter(Boolean);
660
- const warningFn = path => {
661
- if (isAngularEnabled) return;
662
- console.warn(
663
- `[rspack.config.js] Ignored custom "${path}" — reserved for Meteor-Rspack integration.`,
664
- );
665
- };
666
-
667
- let nextUserConfig = cleanOmittedPaths(userConfig, {
668
- omitPaths,
669
- warningFn,
670
- });
671
- nextUserConfig = mergeMeteorRspackFragments(nextUserConfig);
664
+ // Load and apply project-level overrides for the selected build
665
+ // Check if we're in a Meteor package directory by looking at the path
666
+ const isMeteorPackageConfig = projectDir.includes('/packages/rspack');
667
+ console.log("--> (rspack.config.js-Line: 665)\n isMeteorPackageConfig: ", isMeteorPackageConfig);
668
+ if (fs.existsSync(projectConfigPath) && !isMeteorPackageConfig) {
669
+ // Check if there's a .mjs or .cjs version of the config file
670
+ const mjsConfigPath = projectConfigPath.replace(/\.js$/, '.mjs');
671
+ const cjsConfigPath = projectConfigPath.replace(/\.js$/, '.cjs');
672
672
 
673
- if (Meteor.isClient) {
674
- clientConfig = mergeSplitOverlap(
675
- clientConfig,
676
- nextUserConfig
677
- );
673
+ let projectConfigPathToUse = projectConfigPath;
674
+ if (fs.existsSync(mjsConfigPath)) {
675
+ projectConfigPathToUse = mjsConfigPath;
676
+ } else if (fs.existsSync(cjsConfigPath)) {
677
+ projectConfigPathToUse = cjsConfigPath;
678
678
  }
679
- if (Meteor.isServer) {
680
- serverConfig = mergeSplitOverlap(
681
- serverConfig,
682
- nextUserConfig
683
- );
679
+
680
+ const nextUserConfig = await loadAndProcessConfig(
681
+ projectConfigPathToUse,
682
+ 'rspack.config.js',
683
+ Meteor,
684
+ argv,
685
+ isAngularEnabled
686
+ );
687
+
688
+ if (nextUserConfig) {
689
+ if (Meteor.isClient) {
690
+ clientConfig = mergeSplitOverlap(clientConfig, nextUserConfig);
691
+ }
692
+ if (Meteor.isServer) {
693
+ serverConfig = mergeSplitOverlap(serverConfig, nextUserConfig);
694
+ }
684
695
  }
685
696
  }
686
697
 
@@ -721,6 +732,31 @@ module.exports = async function (inMeteor = {}, argv = {}) {
721
732
  );
722
733
  config = mergeSplitOverlap(config, testClientExpandConfig);
723
734
 
735
+ // Check for override config file (extra file to override everything)
736
+ if (projectConfigPath) {
737
+ const configDir = path.dirname(projectConfigPath);
738
+ const configFileName = path.basename(projectConfigPath);
739
+ const configExt = path.extname(configFileName);
740
+ const configNameWithoutExt = configFileName.replace(configExt, '');
741
+ const configNameFull = `${configNameWithoutExt}.override${configExt}`;
742
+ const overrideConfigPath = path.join(configDir, configNameFull);
743
+
744
+ if (fs.existsSync(overrideConfigPath)) {
745
+ const nextOverrideConfig = await loadAndProcessConfig(
746
+ overrideConfigPath,
747
+ configNameFull,
748
+ Meteor,
749
+ argv,
750
+ isAngularEnabled
751
+ );
752
+
753
+ if (nextOverrideConfig) {
754
+ // Apply override config as the last step
755
+ config = mergeSplitOverlap(config, nextOverrideConfig);
756
+ }
757
+ }
758
+ }
759
+
724
760
  if (Meteor.isDebug || Meteor.isVerbose) {
725
761
  console.log('Config:', inspect(config, { depth: null, colors: true }));
726
762
  }