Skip to content

Commit 9eebd8c

Browse files
committed
Update Webpack config (note: not working yet)
1 parent 736a7e2 commit 9eebd8c

2 files changed

Lines changed: 67 additions & 416 deletions

File tree

sample/webpack.config.js

Lines changed: 67 additions & 78 deletions
Original file line numberDiff line numberDiff line change
@@ -1,88 +1,77 @@
1+
const { merge } = require("webpack-merge");
2+
const { configs } = require("@nativescript/webpack/dist/configuration");
3+
const { getPlatformName } = require("@nativescript/webpack/dist/helpers/platform");
4+
const { env: _env } = require("@nativescript/webpack");
5+
16
/**
2-
* @see https://github.com/NativeScript/NativeScript/tree/feat/ns7-finishing-touches/packages/webpack/templates
3-
* @see https://github.com/NativeScript/NativeScript/pull/8801/files
7+
* @param config {import("webpack-chain").Config}
8+
* @param env {import("@nativescript/webpack").IWebpackEnv}
9+
* @returns {import("webpack-chain").Config}
410
*/
5-
const webpackConfig = require("./webpack.typescript");
6-
const webpack = require("webpack");
7-
const ReactRefreshWebpackPlugin = require('@pmmmwh/react-refresh-webpack-plugin');
11+
module.exports = function (config, env = _env){
12+
configs.base(config, env);
13+
14+
const platform = getPlatformName();
15+
const mode = env.production ? 'production' : 'development';
16+
const production = mode === 'production';
17+
18+
// todo: use env
19+
let isAnySourceMapEnabled = true;
820

9-
module.exports = (env) => {
10-
env = env || {};
11-
const hmr = env.hmr;
12-
const production = env.production;
13-
const isAnySourceMapEnabled = !!env.sourceMap || !!env.hiddenSourceMap;
21+
config.resolve.extensions.prepend('.tsx').prepend(`.${platform}.tsx`);
22+
config.resolve.alias.set('react-dom', 'react-nativescript');
1423

15-
const baseConfig = webpackConfig(env);
24+
config.module
25+
.rule('ts')
26+
.test([...config.module.rule('ts').get('test'), /\.tsx$/]);
1627

17-
/** Find the rule for transpiling ts files ("ts-loader"), and modify it to test for .tsx files too. */
18-
const tsxRule = baseConfig.module.rules.find(rule => rule.use && rule.use.loader === "ts-loader");
19-
tsxRule.test = /\.(ts|tsx)$/;
20-
tsxRule.use = [
21-
/**
22-
* Add React Refresh HMR support.
23-
* @see https://github.com/pmmmwh/react-refresh-webpack-plugin/blob/55028c6355b31e697e21bf3e9a48613a7b94bee7/examples/typescript-without-babel/webpack.config.js#L18-L21
24-
*/
25-
hmr && !production && {
26-
loader: "babel-loader",
27-
options: {
28-
sourceMaps: isAnySourceMapEnabled ? "inline" : false,
29-
babelrc: false,
30-
plugins: ['react-refresh/babel']
31-
}
32-
},
33-
tsxRule.use,
34-
].filter(Boolean);
28+
config.plugin('DefinePlugin').tap((args) => {
29+
args[0] = merge(args[0], {
30+
/** For various libraries in the React ecosystem. */
31+
__TEST__: false,
32+
/**
33+
* Primarily for React Fast Refresh plugin, but technically the allowHmrInProduction option could be used instead.
34+
* Worth including anyway, as there are plenty of Node libraries that use this flag.
35+
*/
36+
'process.env.NODE_ENV': JSON.stringify(mode),
37+
});
3538

36-
/**
37-
* Modify "nativescript-dev-webpack/hmr/hot-loader" to test for .tsx files
38-
* (and also js files, which it should have been doing to begin with!)
39-
*/
40-
const nativeScriptDevWebpackHotLoader = baseConfig.module.rules.find(rule =>
41-
rule.use === "@nativescript/webpack/hmr/hot-loader"
42-
);
43-
nativeScriptDevWebpackHotLoader.test = /\.(ts|tsx|js|css|scss|html|xml)$/;
39+
return args;
40+
});
4441

45-
/** We don't officially support JSX. Makes the webpack config rather more complicated to set up. */
46-
baseConfig.resolve.extensions = [".tsx", ...baseConfig.resolve.extensions];
47-
baseConfig.resolve.alias["react-dom"] = "react-nativescript";
42+
// todo: env flag to forceEnable?
43+
config.when(env.hmr && !production, (config) => {
44+
config.module
45+
.rule('ts')
46+
.use('babel-loader|react-refresh')
47+
.loader('babel-loader')
48+
.before('ts-loader')
49+
.options({
50+
sourceMaps: isAnySourceMapEnabled ? 'inline' : false,
51+
babelrc: false,
52+
plugins: ['react-refresh/babel'],
53+
});
4854

49-
/** Augment NativeScript's existing DefinePlugin definitions with a few more of our own. */
50-
const existingDefinePlugin = baseConfig.plugins.find(plugin =>
51-
plugin && plugin.constructor && plugin.constructor.name === "DefinePlugin"
52-
);
53-
baseConfig.plugins.splice(
54-
baseConfig.plugins.indexOf(existingDefinePlugin),
55-
1,
56-
new webpack.DefinePlugin({
57-
...existingDefinePlugin.definitions,
58-
/** For various libraries in the React ecosystem. */
59-
"__DEV__": production ? "false" : "true",
60-
"__TEST__": "false",
61-
/**
62-
* Primarily for React Fast Refresh plugin, but technically the allowHmrInProduction option could be used instead.
63-
* Worth including anyway, as there are plenty of Node libraries that use this flag.
64-
*/
65-
"process.env.NODE_ENV": JSON.stringify(production ? "production" : "development"),
66-
}),
67-
);
55+
config
56+
.plugin('ReactRefreshPlugin')
57+
.use(require('@pmmmwh/react-refresh-webpack-plugin'), [
58+
{
59+
/**
60+
* Maybe one day we'll implement an Error Overlay, but the work involved is too daunting for now.
61+
* @see https://github.com/pmmmwh/react-refresh-webpack-plugin/issues/79#issuecomment-644324557
62+
*/
63+
overlay: false,
64+
/**
65+
* If you (temporarily) want to enable HMR on a production build:
66+
* 1) Set `forceEnable` to `true`
67+
* 2) Remove the `!production` condition on `tsxRule` to ensure that babel-loader gets used.
68+
*/
69+
forceEnable: false,
70+
},
71+
]);
72+
});
6873

69-
if(hmr && !production){
70-
baseConfig.plugins.push(new ReactRefreshWebpackPlugin({
71-
/**
72-
* Maybe one day we'll implement an Error Overlay, but the work involved is too daunting for now.
73-
* @see https://github.com/pmmmwh/react-refresh-webpack-plugin/issues/79#issuecomment-644324557
74-
*/
75-
overlay: false,
76-
/**
77-
* If you (temporarily) want to enable HMR on a production build:
78-
* 1) Set `forceEnable` to `true`
79-
* 2) Remove the `!production` condition on `tsxRule` to ensure that babel-loader gets used.
80-
*/
81-
forceEnable: false,
82-
}));
83-
} else {
84-
baseConfig.plugins = baseConfig.plugins.filter(p => !(p && p.constructor && p.constructor.name === "HotModuleReplacementPlugin"));
85-
}
74+
console.log(`Webpack 5 config:`, config);
8675

87-
return baseConfig;
88-
};
76+
return config;
77+
}

0 commit comments

Comments
 (0)