How to load web worker using webpack's worker loader
Asked Answered
P

2

10

I'm trying to load a web worker script into my React application by using webpack's worker loader. However, I get a module not found error.

ERROR in ./src/index.js Module not found: Error: Can't resolve './file.worker' in 'C:\Users\wyrm\Documents\Project\src'

This is my src/index.js which is the entry point for webpack

import React from "react";
import ReactDOM from "react-dom";
import Worker from "./file.worker";

const worker = new Worker();
worker.postMessage({ message: "Hello there" });

const Index = () => <div>Hello there General Kenobi!</div>;

ReactDOM.render(<Index />, document.getElementById("index"));

I have my web worker script called file.worker.js in the Project/public folder

/* eslint-env worker */

onmessage = e => {
  const message = e.data;
  console.log(`[From Main]: ${message}`);
};

And this is my webpack config file:

const HtmlWebPackPlugin = require("html-webpack-plugin");

const htmlPlugin = new HtmlWebPackPlugin({
  template: "./src/index.html",
  filename: "./index.html"
});

module.exports = {
  module: {
    rules: [
      {
        test: /\.js$/,
        exclude: /node_modules/,
        use: [{ loader: "babel-loader" }, { loader: "eslint-loader" }]
      },
      {
        test: /\.worker\.js$/,
        use: [{ loader: "worker-loader", options: { publicPath: "/public/" } }]
      }
    ]
  },
  plugins: [htmlPlugin]
};

According to the webpack documentation, all I need to do is to add the following to my config file, which I have done:

// webpack.config.js
{
  module: {
    rules: [
      {
        test: /\.worker\.js$/,
        use: { loader: 'worker-loader' }
      }
    ]
  }
}

I went to the further step of specifying the public path as documented here:

// App.js
// This will cause the worker to be downloaded from `/workers/file.worker.js`
import Worker from './file.worker.js';

// webpack.config.js
{
  loader: 'worker-loader'
  options: { publicPath: '/workers/' }
}

But even though I have specified the publicPath to be Project/public, the error thrown seems to indicate that it's looking in the Project/src folder for the web worker script. It also seems to me that webpack looks for the web worker script in the Project/public folder by default anyway, so by right it should be redundant to specify Project/public for the publicPath?

I should also mention that I'm using webpack dev server. Could it be that I'm missing some sort of configuration for my webpack dev server, and it's not picking up my web worker script?

I really can't figure out why I'm getting a module not found error when it seems like I've followed the documentation properly.

Project directory
Project
- dist
  - index.html
  - main.js
- public
  - file.worker.js
- src
  - index.html
  - index.js
- .babelrc
- .eslintrc.json
- package.json
- webpack.config.js
Plus answered 29/12, 2018 at 2:13 Comment(0)
M
3

Try moving the file.worker.js into src. That's where you're looking for it with import Worker from "./file.worker";

Martella answered 16/5, 2019 at 10:13 Comment(0)
P
3

try the follwing:

import Worker from 'worker-loader!./file.worker.js';

You need to specify which loader(i.e. worker-loader) is going to load the worker explicitly.

Also, i dont think you need to configure the publicPath option.

Pericycle answered 16/5, 2019 at 11:17 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.