1

I'm working on a WordPress plugin using React. I started off https://github.com/robicse11127/wp-react-kickoff as a base and everything works fine, except for the part where it generates one single bundle for the whole React app. Since my plugin consists in multiple separate apps for different parts of the dashboard and another distinct app for the front, it doesn't make much sense to use one single bundle file; I'd rather have each part bundled separately and loaded where needed: dashboard app in the dashboard, editor app in the edit posts pages, public app on the public pages, etc.

I tried using webpack chunks like described [here][1], but couldn't make it work properly. It actually somewhat worked in the dedicated React app I created with create-react-app to build my components before moving to WordPress, but wp-react-kickoff seems to work quite differently (no public folder, no index.html, which is actually what I want) and I couldn't make it work.

Here's what I'd like to have:

my-plugin
|___admin
    |___css
        |___...
    |___js
        |___dashboard.js
        |___editor.js
        |___settings.js
|___includes
    |___... wp plugin stuff
|___public
    |___css
        |___...
    |___js
        |___app.js
|___src
    |___components
        |___ ...
    |___app.js
    |___dashboard.js
    |___editor.js
    |___settings.js
    |___index.js
|___package.json
|___webpack.config.js

Currently I use src/index.js to load my separate apps (dashboard, editor, settings and app, this last one being the public part) and all of them get bundled in a dist/bundle.js that is loaded by WordPress on both admin and front sides. How can I make it so that my different apps end up is separate files in public/js and admin/js like above? Bonus question, I'm currently using external CSS edited manually and I'm considering moving to SASS to be bundled with webpack along with the React apps, using the same separate files logic. Can this be done?

Solution

Ok, quick update, I got it working somehow. Not like expected, ie not using chunks, but using multiple commands. In the end here's what my webpack.config.js looks like:

const path = require("path")
const MiniCssExtractPlugin = require("mini-css-extract-plugin")
const wpScriptsWebpackConfig = require("@wordpress/scripts/config/webpack.config")

module.exports = {
  ...wpScriptsWebpackConfig,
  output: {
    path: path.join(__dirname, "/build"),
    filename: "[name].min.js",
  },
  plugins: [
    new MiniCssExtractPlugin({
      filename: "[name].min.css",
    }),
    ...wpScriptsWebpackConfig.plugins.filter(
      plugin => !(plugin instanceof MiniCssExtractPlugin)
    )
  ],
}

Since posting my question I included blocks in my plugin, hence the use of wp-scripts. And here's what my package.json looks like:

{
  "name": "plugin-name",
  "version": "4.0.0",
  "license": "GPLv2",
  "main": "index.js",
  "dependencies": {
    "@wordpress/api-fetch": "^6.29.0",
    "@wordpress/block-editor": "^12.0.0",
    "@wordpress/blocks": "^12.9.0",
    "@wordpress/components": "^23.9.0",
    "@wordpress/data": "^9.2.0",
    "@wordpress/element": "^5.9.0",
    "@wordpress/url": "^3.33.0",
    "axios": "^0.21.4",
    "countries-list": "^2.6.1",
    "immer": "^9.0.12",
    "react-router-dom": "^6.11.1",
    "zustand": "^3.7.1"
  },
  "devDependencies": {
    "@babel/core": "^7.21.8",
    "@babel/preset-env": "^7.21.5",
    "@babel/preset-react": "^7.18.6",
    "@wordpress/scripts": "^26.3.0",
    "autoprefixer": "^10.4.14",
    "babel-loader": "^9.1.2",
    "css-loader": "^6.7.3",
    "mini-css-extract-plugin": "^2.7.5",
    "postcss": "^8.4.23",
    "postcss-loader": "^7.3.0",
    "postcss-nested": "^6.0.1",
    "react": "^18.2.0",
    "react-dom": "^18.2.0",
    "sass": "^1.62.1",
    "sass-loader": "^13.2.2",
    "solid-js": "^1.7.4",
    "style-loader": "^3.3.2",
    "webpack": "^5.81.0",
    "webpack-cli": "^5.0.2",
    "webpack-dev-server": "^4.13.3"
  },
  "scripts": {
    "copy:app:css": "cp build/app.*.css admin/css",
    "copy:app:js": "cp build/app.*.js admin/js",
    "copy:app": "npm run copy:app:js && npm run copy:app:css",
    "copy:blocks:css": "cp build/blocks.*.css admin/css",
    "copy:blocks:js": "cp build/blocks.*.js admin/js",
    "copy:blocks": "npm run copy:blocks:js && npm run copy:blocks:css",
    "copy:dashboard:css": "cp build/dashboard.*.css admin/css",
    "copy:dashboard:js": "cp build/dashboard.*.js admin/js",
    "copy:dashboard": "npm run copy:dashboard:js && npm run copy:dashboard:css",
    "copy:indexes:css": "cp build/indexes.*.css admin/css",
    "copy:indexes:js": "cp build/indexes.*.js admin/js",
    "copy:indexes": "npm run copy:indexes:js && npm run copy:indexes:css",
    "copy:settings:css": "cp build/settings.*.css admin/css",
    "copy:settings:js": "cp build/settings.*.js admin/js",
    "copy:settings": "npm run copy:settings:js && npm run copy:settings:css",
    "copy:library:css": "cp build/library.*.css public/css",
    "copy:library:js": "cp build/library.*.js public/js",
    "copy:library": "npm run copy:library:js && npm run copy:library:css",
    "copy": "npm run copy:app && npm run copy:blocks && npm run copy:dashboard && npm run copy:indexes && npm run copy:settings && npm run copy:library",
    "clean": "rm -f admin/css/*.min.css admin/js/*.min.js public/css/*.min.css public/js/*.min.js",
    "build": "wp-scripts build src/*.js --progress && npm run copy",
    "start": "wp-scripts start src/*.js",
    "watch": "wp-scripts start src/*.js --progress"
  }
}

Now when running npm run build all scripts are properly built, pushed in a build/ folder at the root on the plugin's directory, and the additional npm commands just move everything where it's supposed to go. That's not the cleanest you can get, but it works so I'm not asking more for now. How that helps!

  • Arrived here looking for the same thing. Did you find the proper way to build the admin from the public separately? Thanks – Jorge Feb 05 '23 at 20:26
  • @Jorge Yeah, got it working somehow, I just update my post with my current solution. Not a solution per-se, but it works :) – Charlie Merland May 13 '23 at 10:22

0 Answers0