VSCode debugging on running webpack-dev-server, skips breakpoints - reactjs

I have debugger for chrome extension installed. I run my app using
webpack-dev-server -d --config webpack.dev.js --inline
I'm running a react app, all source codes are under /src folder. I have js, ts and tsx files. When I put a breakpoint on render function, editor properly breaks execution, but when I put a breakpoint to an onClick event of a button, it doesn't break, it just continues the execution of the code.
related part of my webpack config is as follows:
mode: 'development',
devtool: 'source-map',
entry: {
bundle: [
'#babel/polyfill',
'react-hot-loader/patch',
`webpack-dev-server/client?http://${host}:${devPort}`,
'webpack/hot/only-dev-server',
path.resolve(__dirname, 'src/index.js'),
],
},
output: {
path: path.resolve(__dirname, 'public'),
publicPath: '/',
filename: '[name].[hash:16].js',
chunkFilename: '[id].[hash:16].js',
},
devServer: {
inline: true,
port: devPort,
contentBase: path.resolve(__dirname, 'public'),
hot: true,
writeToDisk: true,
publicPath: '/',
historyApiFallback: true,
host,
}
and my launch.json is as below:
{
"type": "chrome",
"request": "launch",
"name": "Launch Chrome",
"url": "http://localhost:8080",
"webRoot": "${workspaceFolder}/src",
"sourceMaps": true,
"sourceMapPathOverrides": {
"webpack:///./src/*.js": "${workspaceRoot}/src/*.js",
"webpack:///./src/*.tsx": "${workspaceRoot}/src/*.tsx",
"webpack:///./src/*.ts": "${workspaceRoot}/src/*.ts",
"webpack:///./node_modules/*": "${workspaceRoot}/node_modules/*"
}
}
What I'm missing?

I got this to work by using inline-source-map in my config file:
{
devtool: 'inline-source-map',
// ....
}
Now it works properly and breaks wherever I put the breakpoint.

I was facing the same issue with create-react-app. In webpack.config.js (after ejecting) I changed devtool: isEnvProduction? shouldUseSourceMap ? "inline-source-map" instead of "source-map" and now my breakpoints are constantly hitting!
Thanks for the tip!

Related

nx react module federation hot reload

I'm using module federation with nx and want to enable HMR.
I applied the hmr: true option in both project.json files. (for the host and the remote).
The problem that its working only for the remote, and when changing the code in the host project its not working and not updating it in the browser.
this is the configuration for the host project.json (I'm using nx server):
"serve": {
"executor": "#nrwl/react:module-federation-dev-server",
"defaultConfiguration": "development",
"options": {
"buildTarget": "client:build",
"hmr": true,
"port": 4200
},
"configurations": {
"development": {
"buildTarget": "client:build:development",
"open": true,
"watch": true,
"liveReload": true
},
"production": {
"buildTarget": "client:build:production",
"hmr": false
}
}
}
and this is in the remote project.json
"serve": {
"executor": "#nrwl/react:module-federation-dev-server",
"defaultConfiguration": "development",
"options": {
"buildTarget": "assets:build",
"hmr": true,
"port": 4201
},
"configurations": {
"development": {
"buildTarget": "assets:build:development"
},
"production": {
"buildTarget": "assets:build:production",
"hmr": false
}
}
}
It's not working with HMR. Well never got to make it work. But using live reload witht following config its working fine. I can even debug TS with source maps.
module.exports = merge(custom, common, {
mode: 'development',
output: {
filename: '[name].[contenthash].js',
path: path.join(__dirname, 'dev'),
publicPath: 'auto',
},
devServer: {
static: path.join(__dirname, 'dev'),
hot: false,
liveReload: true,
port: infinisoft.moduleFederation.devport
},
plugins: [
new MFLiveReloadPlugin({
port: infinisoft.moduleFederation.devport,
container: name,
standalone: true
}),
new ReactRefreshWebpackPlugin(),
new MinChunkSizePlugin({
minChunkSize: 10000, // Minimum number of characters
}),
moduleFederation,
new MiniCssExtractPlugin(),
new HtmlWebpackPlugin({
template: path.resolve(__dirname, 'src', 'config', 'index.html'),
}),
],
devtool: 'source-map',
});

Browser tab freezes when running webpack-dev-server in development mode using remote Module Federation module

Dependency versions:
webpack: 5.73.0
webpack-dev-server: 4.9.2
This occurs when running a host application via webpack-dev-server that consumes micro-apps via ModuleFederationPlugin.
Example host config:
module.exports = {
entry: path.resolve(__dirname, "src/index.js"),
mode: "development", // success when changed to "production"
devServer: {
port: 3000,
client: {
overlay: false,
},
},
output: {
path: path.resolve(__dirname, "./build"),
publicPath: "/",
filename: "[name].[contenthash].js",
clean: true,
},
module: {
rules: [
{
test: /\.jsx?$/,
loader: "babel-loader",
exclude: /node_modules/,
options: {
presets: ["#babel/preset-react"],
},
},
],
},
plugins: [
new ModuleFederationPlugin({
name: "Host",
remotes: {
ExampleModule: `ExampleModule#${
process.env.LOCAL_MODULE
? `http://localhost:3001/`
: "https://example.com/examplemodule/"
}remoteEntry.js`,
},
shared: [
{
react: { version: "16.13.0", singleton: true },
"react-dom": { version: "16.13.0", singleton: true },
},
],
}),
new HtmlWebpackPlugin({
template: path.join(__dirname, "public/index.html"),
}),
],
};
Example module config:
module.exports = {
entry: path.resolve(__dirname, "src/index.js"),
mode: "development", // set to "production" for build that is served statically
devServer: {
static: { directory: path.join(__dirname, "public") },
port: PORT,
},
output: {
path: path.resolve(__dirname, "./build"),
publicPath:
process.env.NODE_ENV === "development"
? `http://localhost:${PORT}/`
: "https://example.com/examplemodule/",
filename: "[name].[contenthash].js",
clean: true,
},
resolve: {
extensions: [".js", ".jsx"],
},
module: {
rules: [
{
test: /\.jsx?$/,
loader: "babel-loader",
exclude: /node_modules/,
options: {
presets: ["#babel/preset-react"],
},
},
],
},
plugins: [
new ModuleFederationPlugin({
name: "ExampleModule",
library: { type: "var", name: "ExampleModule" },
filename: "remoteEntry.js",
exposes: {
"./ExampleModule": "./src/ExampleModule",
},
shared: [
{
react: { version: "16.13.0", singleton: true },
"react-dom": { version: "16.13.0", singleton: true },
},
],
}),
new HtmlWebpackPlugin({
template: path.join(__dirname, "public/index.html"),
}),
],
};
When running both the host and ExampleModule via webpack-dev-server, the app works, consuming the module from localhost:3001 without issue.
However, when running the host via webpack-dev-server and consuming the production build of the module from a remote URL (using https://example.com/examplemodule/remoteEntry.js in the example above), the page becomes completely unresponsive immediately after the remote entry file is fetched. There is no output in the JavaScript console due to this, and there is no feedback in the CLI output, so there are no error messages to report. This occurs in any browser, and I am on macOS Monterey.
This only occurs when running webpack-dev-server for the host in the "development" Webpack mode. Switching to production mode will fix this issue. It also will not occur when serving the static build of the host, regardless of the Webpack mode used when creating the build.
Unfortunately, this is difficult to reproduce. I attempted to make an isolated example with a React host and remote module using the same dependencies and very similar webpack configs, but I cannot reproduce the issue this way yet, so it may be specific to application code I cannot share. I'm wondering if anyone else has experienced this.

webpack options has an unknown property 'hotOnly'. Invalid options object. Dev Server has been initialized using an options object

I am running the command npx webpack-dev-server --mode development in my react application and getting the preceding error.
[webpack-cli] Invalid options object. Dev Server has been initialized using an options object that does not match the API schema.
- options has an unknown property 'hotOnly'. These properties are valid:
Below is my webpack.config.js file.
const path = require("path");
const webpack = require("webpack");
module.exports = {
entry: "./src/index.js",
mode: "development",
module: {
rules: [
{
test: /\.(js|jsx)$/,
exclude: /(node_modules)/,
loader: "babel-loader",
options: {
presets: ["#babel/env"],
},
},
{
test: /\.css$/,
use: ["style-loader", "css-loader"],
},
],
},
resolve: {
extensions: ["*", ".js", ".jsx"],
},
output: {
path: path.resolve(__dirname, "dist/"),
publicPath: "/dist/",
filename: "bundle.js",
},
devServer: {
contentBase: path.join(__dirname, "public/"),
port: 3000,
publicPath: "https://localhost:3000/dist/",
hotOnly: true,
},
plugins: [new webpack.HotModuleReplacementPlugin()],
};
Any idea what is causing this issue?
So devServer|Webpack config is related to Options for webpack-dev-server
If your webpack is using webpack-dev-server version 4 you should use this migration guide
// your v3 config
devServer: {
contentBase: path.join(__dirname, "public/"),
port: 3000,
publicPath: "https://localhost:3000/dist/",
hotOnly: true,
},
in v4 will be
devServer: {
// contentBase
static : {
directory : path.join(__dirname, "public/")
},
port: 3000,
// publicPath
devMiddleware:{
publicPath: "https://localhost:3000/dist/",
}
// hotOnly
hot: "only",
},
It seems like the updated version of webpack doesn't support the property hotOnly, we should use the option hot instead. You can see a GitHub issue associated with this here.
devServer: {
hot: "only", // hot:true
},
The latest versions automatically apply HotModuleReplacementPlugin plugin when you set hot: true, so please check you don't have HotModuleReplacementPlugin in your plugins if you have hot: true/hot: "only". You will get a warning as " [webpack-dev-server] "hot: true" automatically applies HMR plugin, you don't have to add it manually to your webpack configuration." if you have the preceding settings.
plugins: [new webpack.HotModuleReplacementPlugin()],
If you are getting error "static heartbeatInterval = 1000; SyntaxError: Unexpected token =", make sure to use the node version is >= 12.13.0 as per the guide here.
If everything is done, you should be able to see an output as preceding when you run npx webpack-dev-server --mode development.
Thanks, #Tushar Mistry for providing the migration guide.
Below is my completed webpack.config.js file.
const path = require("path");
const webpack = require("webpack");
module.exports = {
entry: "./src/index.js",
mode: "development",
module: {
rules: [
{
test: /\.(js|jsx)$/,
exclude: /(node_modules)/,
loader: "babel-loader",
options: {
presets: ["#babel/env"],
},
},
{
test: /\.css$/,
use: ["style-loader", "css-loader"],
},
],
},
resolve: {
extensions: ["*", ".js", ".jsx"],
},
output: {
path: path.resolve(__dirname, "dist/"),
publicPath: "/dist/",
filename: "bundle.js",
},
devServer: {
static: {
directory: path.join(__dirname, "public/"),
},
port: 3000,
devMiddleware: {
publicPath: "https://localhost:3000/dist/",
},
hot: "only",
},
};
Or you can also use the old version as below.
"webpack": "4.41.5",
"webpack-cli": "3.3.10",
"webpack-dev-server": "3.10.1"
For me, comma was missing after devMiddleware property causing error.
Solved by installing an older version of webpack
"webpack-dev-server": "3.10.1"

Remove server from react-boilerplate

How should one do to remove server folder from react-boilerplate? Question is also asked here by another person https://github.com/react-boilerplate/react-boilerplate/issues/2110.
Removing just server folder will not work because the webpack dev configuration is utilising it for hot reload as well as your npm start command starts express server from this folder.
If you want to remove server folder completely and still want the application to be working as it was like hot reloading etc, follow the below steps. We will require webpack dev server in that case:
Remove ./server folder manually.
Install webpack-dev-server and react-hot-loader as dev dependencies.
In your ./internals/webpack/webpack.dev.babel.js, do the following modifications:
Change entry to this:
entry: [
require.resolve('react-app-polyfill/ie11'),
'react-hot-loader/patch',
`webpack-dev-server/client?http://localhost:3000/`,
'webpack/hot/only-dev-server',
path.join(process.cwd(), 'app/app.js'), // Start with js/app.js
],
Add publicPath in output:
output: {
filename: '[name].js',
chunkFilename: '[name].chunk.js',
publicPath: `http://localhost:3000/`,
},
Add webpack dev server config property in the same file:
devServer: {
port: 3000,
publicPath: `http://localhost:3000/`,
compress: true,
noInfo: false,
stats: 'errors-only',
inline: true,
lazy: false,
hot: true,
open: true,
overlay: true,
headers: { 'Access-Control-Allow-Origin': '*' },
contentBase: path.join(__dirname, '..', '..', 'app', 'build'),
watchOptions: {
aggregateTimeout: 300,
ignored: /node_modules/,
poll: 100,
},
historyApiFallback: {
verbose: true,
disableDotRule: false,
},
},
In ./internals/webpack/webpack.base.babel.js, add the line:
devServer: options.devServer,
And finally, modify your start script in package.json as below:
"start": "cross-env NODE_ENV=development node --trace-warnings ./node_modules/webpack-dev-server/bin/webpack-dev-server --color --config internals/webpack/webpack.dev.babel.js",
And you are good to go!!
Just remove with rm -rf ./server if you feel harassed :)

Webpack dev server React Content Security Policy error

I have my single page app running on webpack-dev-server. I can load and reload my entry route over at localhost:8080 and it works every time. However i can load localhost:8080/accounts/login only via a link from within the app i.e whenever i reload localhost:8080/accounts/login from the browser refresh button i get
Cannot GET /accounts/login/
as the server response, and on the console i get
Content Security Policy: The page’s settings blocked the loading of a
resource at self (“default-src http://localhost:8080”). Source:
;(function installGlobalHook(window) { ....
This is my CSP header on the single page app's index.html
<meta http-equiv="Content-Security-Policy"
content="default-src * 'self' 'unsafe-inline' 'unsafe-eval'">
I am also not using any devtool on my webpack.config.json. What am i missing.
If you use Webpack in your project, please add output.publicPath = '/' and devServer.historyApiFallback = true in your webpack config file.
More info: React-router urls don't work when refreshing or writting manually
I struggled a couple hours to fix this issue. There is a just simple code that you have to add. Just follow the instruction of below. If you face problem to browse from specific url to another url, you will be able to fix that also. If you would like to configure from webpack config file, then write below's code.
devServer: {
historyApiFallback: true
}
And If you would like to run by cli command, then use the below's code.
"start": "webpack-dev-server --history-api-fallback"
It worked for me. I had not to do anything else to fix this issue like meta tag or something else.
If you're using Rails and Webpacker and get this error, note that the initializer config/initializers/content_security_policy.rb has a Content Security Policy for Rails.env.development. Changing :https to :http on that line solved the error for me. (And remember that localhost is not the same as 127.0.0.1 as far as the CSP is concerned.)
adding output: { ..., publicPath: "/", } and devServer: { historyApiFallback: true } worked
in webpack.config.js
const path = require("path");
module.exports = {
mode: "development",
entry: "./src/index.js",
output: {
path: path.resolve(__dirname, "public"),
filename: "main.js",
publicPath: "/", // ++
},
target: "web",
devServer: {
port: "6060",
static: ["./public"],
open: true,
hot: true,
liveReload: true,
historyApiFallback: true, // ++
},
resolve: {
extensions: [".js", ".jsx", ".json", ".ts"],
},
module: {
rules: [
{
test: /\.(js|jsx)$/,
exclude: /node_modules/,
use: "babel-loader",
},
// CSS rules
{
test: /\.css$/i,
use: ["style-loader", "css-loader"],
},
],
},
};
I had similar issue. Had to remove the contentBase line from devServer configuration in webpack.config.js.
This is my webpack.config.js:
var path = require("path");
module.exports = {
devtool: 'inline-source-map',
entry: "./src/index.js",
output: {
path: path.resolve(__dirname, "dist"),
publicPath: "/assets/",
filename: "bundle.js"
},
devServer: {
port: 9002
},
module: {
rules: [
{ test: /\.js$/, use: 'babel-loader' }
]
}
};

Resources