Add React Apps to a WordPress Site

This tutorial will show a quick way to add a React app to a WordPress website. There are more advanced ways to handle this but this will get you started.

Jump to changelog

1. Create a React App

Note: If you already have an existing React app you want to use, skip to the next section.

The rest of tutorial will use this To Do App based on a Mozilla React tutorial.

In the terminal, navigate to where you want to install the app on your computer and run the following command:

git clone https://github.com/jtleathers/moz-todo-react.git

Open that newly created “moz-todo-react” folder in your code editor. Run the following command:

npm run build

To test the app, run this command:

npm run dev

Make any changes you want to the app and then once you verify the app is working, move on to the next section.

2. Define the “homepage” in package.json

Edit the “package.json” file in your React app to change the “homepage” value.

You will set this value to the URL path of where you intend to host your React app. In our case, that will be within a WordPress plugin folder we are going to call “react-plugin”. Since our WordPress plugin will be built to run multiple React apps, we will create subfolders for each app in the plugin.

This tutorial will use the To Do app so I am eventually going to name that sub-folder “todo”.

Based on this, I know the end of my URL will be: /wp-content/plugins/react-plugin/todo/

The first part of your URL will depend on your environment and your WordPress installation’s folder name. If you are working locally with something like MAMP, it may look like this:

http://localhost:8888/testing/wp-content/plugins/react-plugin/todo/

If you are working on a live server it may look like this:

https://example.com/wp-content/plugins/react-plugin/tod/

Once you have determined your URL, paste that in as the value of “homepage” in the package.json file. Mine looks like this:

"homepage": "http://localhost:8888/testing/wp-content/plugins/react-plugin/todo/",

Note: If you are working locally but eventually will move this site to a live server, you will have to come back and change this value in the future to your live URL and re-build your React app.

3. Change the “root” ID in index.html and main.jsx

Open the “index.html” file in the root folder of the React app.

Change the ID of “root” to “todo”.

Open “main.jsx” in the “src” folder.

Change the ID in the element selector from “root” to “todo”.

Note: We do this so you can run multiple React apps on the same page and avoid ID conflicts. If you were doing this process with a different app, simply choose a new unique ID.

(Optional) Rename Build Files

If you do not want to use the randomly generated file names that are created when running a build, you can edit “vite.config.js” and use the build.rollupOptions if using Vite. Here is an example:

export default defineConfig({
  plugins: [react()],
  build: {
    rollupOptions: {
      output: {
        entryFileNames: `assets/[name].js`,
        chunkFileNames: `assets/[name].js`,
        assetFileNames: `assets/[name].[ext]`
      }
    }
  }
})

After doing this, you should end up with file names in the dist folder of “index.css” and “index.js”. This will make your life easier if you are going to run the build multiple times and re-add them to the plugin.

4. Build the App

Build the app by running the following in the terminal:

npm run build

5. Create a WordPress Plugin

To start with, create a simple WordPress plugin inside of your “plugins” folder. Create a folder called “react-plugin” and create a file in that folder called “react-plugin.php”.

At the top of the PHP file, add a Plugin Header comment like this:

<?php
/**
 * Plugin Name:       React Plugin
 * Plugin URI:        https://github.com/jtleathers/react-plugin/
 * Description:       Add simple React apps to WordPress websites.
 * Version:           1.0.0
 * Requires at least: 6.4
 * Requires PHP:      8.0
 * Author:            Jonathon Leathers
 * Author URI:        https://jonathonleathers.com/
 * License:           GPL v2 or later
 * License URI:       https://www.gnu.org/licenses/gpl-2.0.html
 * Update URI:        false
 */

You can now Activate that plugin on your WordPress website.

6. Add the React Files to the WordPress Plugin

Copy the “dist” folder from your React app into the “react-plugin” folder you created in your WordPress installation.

Rename the copied folder from “dist” to “todo”.

Note: The folder name needs to match the end of the URL you added to the “homepage” value in the “package.json” file. You can put multiple “dist” folders for different React apps into this same plugin as long as you rename them.

7. Enqueue the React Files

Inside the “todo” folder, open the “assets” sub-folder to find the JS and CSS files. There should be one JavaScript file that begins with “index-“.

Edit the “react-plugin.php” file to register that JavaScript file in WordPress. The code below can be copied and pasted and only the bold text may need to be changed.

function react_plugin_scripts() {
    wp_register_script( 'todo-app', plugins_url( '/todo/assets/index-546f0deb.js', __FILE__ ), array(), '1.0.0', true );
}
add_action( 'wp_enqueue_scripts', 'react_plugin_scripts' );

If your app includes some CSS, you should find one CSS file that begins with “index-” inside of the assets folder. Add the code to register that CSS file in the wrapper function shown above.

wp_register_style( 'todo-app-styles', plugins_url( '/todo/assets/index-546f0deb.css', __FILE__ ), array(), '1.0.0' );

Note: If you are going to run multiple React apps through this plugin, you can add one wp_register_script and one wp_register_style for each React app’s JS file and CSS file.

Note: If you ever re-build your React app and copy those files into the WordPress plugin, the file names will change and will need to be updated here. Alternatively, use the optional steps above to force Vite to always re-build the files with the same name.

8. Create a Shortcode to Display the App

Create a shortcode to output the React app within any WordPress Page, Post or template file. The ID attribute in the code below must match the ID you set in the React app. The handles in the enqueue functions below must match the handles you registered in the previous step.

function todo_app( $atts ) {
    ob_start(); ?>
    <noscript>You need to enable JavaScript to view this page.</noscript>
    <div id="todo"></div>
    <?php
    $html = ob_get_clean();
    wp_enqueue_script( 'todo-app' );
    wp_enqueue_style( 'todo-app-styles' );
    return $html;
}
add_shortcode( 'react-todo', 'todo_app' );

Note: If you are adding multiple React apps with this plugin, you can create a new shortcode function for each React app. You will need to rename the function, rename the shortcode, update the ID value, and update the enqueue script handle.

9. Test the React App

At this point you should be able to use that shortcode and see the React App load on the front-end of the WordPress site.

To use our example, open any Page or Post in your WordPress site and add the following shortcode to the Block Editor:

[react-todo]

If it worked, you should see the To Do App appear on that Page or Post on the front-end. Check out this demo page for a working version.

Final Thoughts

As I mentioned, this is a quick and dirty way of handling this. It does require editing multiple files and re-building the app when moving from a local to a live environment but it gets the job done if that is not a major concern.

Credit: https://betterprogramming.pub/how-to-embed-react-apps-in-wordpress-sites-96a21b995290

Changelog

Update Apr 28, 2024: Added a link to a working demo of the To Do App on a WordPress website and fixed the numbering.

Update Mar 14, 2024: Replaced the example app with a newer app built using Vite. Removed a section specific to CRA and added an example of rollupOptions for Vite. Rearranged and numbered the steps.

Update Jan 11, 2024: The original example uses CRA but some notes below have been updated to assume you are using a Vite app instead.