CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/npm-pmmmwh--react-refresh-webpack-plugin

Webpack plugin to enable React Fast Refresh (Hot Reloading) for React components during development

Pending

Quality

Pending

Does it follow best practices?

Impact

Pending

No eval scenarios have been run

Overview
Eval results
Files

loader-configuration.mddocs/

Loader Configuration

The ReactRefreshLoader injects React Refresh HMR code into JavaScript and TypeScript modules, enabling Fast Refresh functionality at the module level.

Capabilities

ReactRefreshLoader Function

Webpack loader that processes module source code to inject React Refresh runtime.

/**
 * A simple Webpack loader to inject react-refresh HMR code into modules.
 * @this {import('webpack').LoaderContext<ReactRefreshLoaderOptions>}
 * @param {string} source The original module source code.
 * @param {import('source-map').RawSourceMap} [inputSourceMap] The source map of the module.
 * @param {*} [meta] The loader metadata passed in.
 * @returns {void}
 */
function ReactRefreshLoader(
  this: import('webpack').LoaderContext<ReactRefreshLoaderOptions>,
  source: string,
  inputSourceMap?: import('source-map').RawSourceMap,
  meta?: any
): void;

Loader Usage

Configure the loader in your Webpack configuration:

// webpack.config.js
module.exports = {
  module: {
    rules: [
      {
        test: /\.[jt]sx?$/,
        exclude: /node_modules/,
        use: [
          {
            loader: '@pmmmwh/react-refresh-webpack-plugin/loader',
            options: {
              const: true,
              esModule: false
            }
          },
          // Other loaders like babel-loader
          'babel-loader'
        ],
      },
    ],
  },
};

Loader Options

Configuration interface for customizing loader behavior.

interface ReactRefreshLoaderOptions {
  /**
   * Enables usage of ES6 `const` and `let` in generated runtime code.
   */
  const?: boolean;
  
  /**
   * Enables strict ES Modules compatible runtime.
   */
  esModule?: boolean | ESModuleOptions;
}

Const Option

Controls whether ES6 const and let keywords are used in generated runtime code.

const?: boolean;

Usage Examples:

// Enable modern syntax (recommended)
{
  loader: '@pmmmwh/react-refresh-webpack-plugin/loader',
  options: {
    const: true
  }
}

// Use legacy var declarations for older environments
{
  loader: '@pmmmwh/react-refresh-webpack-plugin/loader',
  options: {
    const: false
  }
}

Default: Determined by Webpack's compilation.runtimeTemplate.supportsConst()

ES Module Option

Configures ES Modules compatibility for the refresh runtime at the loader level.

esModule?: boolean | ESModuleOptions;

interface ESModuleOptions {
  /**
   * Files to explicitly exclude from flagged as ES Modules.
   */
  exclude?: string | RegExp | (string | RegExp)[];
  
  /**
   * Files to explicitly include for flagged as ES Modules.
   */
  include?: string | RegExp | (string | RegExp)[];
}

Usage Examples:

// Enable ES Modules for all processed files
{
  loader: '@pmmmwh/react-refresh-webpack-plugin/loader',
  options: {
    esModule: true
  }
}

// Conditional ES Module usage
{
  loader: '@pmmmwh/react-refresh-webpack-plugin/loader',
  options: {
    esModule: {
      include: /\.mjs$/,
      exclude: /legacy/
    }
  }
}

Default: Auto-detection based on module system

Normalized Loader Options

Internal interface representing processed loader options after normalization.

interface NormalizedLoaderOptions {
  /**
   * Enables usage of ES6 `const` and `let` in generated runtime code.
   */
  const: boolean;
  
  /**
   * Enables strict ES Modules compatible runtime.
   */
  esModule?: boolean | ESModuleOptions;
}

Module System Detection

The loader automatically detects the module system being used:

/** @type {'esm' | 'cjs'} */
type ModuleSystem = 'esm' | 'cjs';

Detection Logic:

  1. Check package.json type field ("module" → ESM, "commonjs" → CJS)
  2. Check file extension (.mjs → ESM, .cjs → CJS)
  3. Analyze import/export statements in source code
  4. Fall back to CommonJS if undetermined

Source Map Support

The loader preserves and generates source maps for debugging:

Features:

  • Preserves existing source maps from previous loaders
  • Generates identity source maps when none exist
  • Maintains accurate line/column mappings after code injection
  • Works with Webpack's source map options

Usage:

// webpack.config.js
module.exports = {
  devtool: 'eval-source-map', // Enable source maps
  module: {
    rules: [
      {
        test: /\.[jt]sx?$/,
        use: [
          '@pmmmwh/react-refresh-webpack-plugin/loader',
          'babel-loader'
        ]
      }
    ]
  }
};

Generated Runtime Code

The loader injects runtime setup and module refresh code:

CommonJS Example:

// Injected at module start
__webpack_require__.$Refresh$.runtime = require('react-refresh');

// Original module code...

// Injected at module end
if (module.hot) {
  module.hot.accept();
  $RefreshReg$(Component, 'ComponentName');
}

ES Module Example:

// Injected at module start
import * as __react_refresh_runtime__ from 'react-refresh';
__webpack_require__.$Refresh$.runtime = __react_refresh_runtime__;

// Original module code...

// Injected at module end
if (import.meta.webpackHot) {
  import.meta.webpackHot.accept();
  $RefreshReg$(Component, 'ComponentName');
}

Options Validation

The loader validates options using a JSON schema:

Schema Location: loader/options.json

Validation Error Example:

// Invalid loader configuration
{
  loader: '@pmmmwh/react-refresh-webpack-plugin/loader',
  options: {
    invalidOption: 'value' // Will cause validation error
  }
}

Loader Utilities

The loader provides utility functions for advanced integration scenarios.

const {
  getIdentitySourceMap,
  getModuleSystem,
  getRefreshModuleRuntime,
  normalizeOptions,
} = require('@pmmmwh/react-refresh-webpack-plugin/loader/utils');

/**
 * Creates an identity source map for a source file
 * @param {string} source - Source code content
 * @param {string} filename - Source file path
 * @returns {import('source-map').RawSourceMap} - Identity source map
 */
function getIdentitySourceMap(source: string, filename: string): RawSourceMap;

/**
 * Determines the module system used by a file
 * @param {object} ModuleFilenameHelpers - Webpack filename helpers
 * @param {NormalizedLoaderOptions} options - Normalized loader options
 * @returns {Promise<'esm' | 'cjs'>} - Module system type
 */
function getModuleSystem(
  ModuleFilenameHelpers: any,
  options: NormalizedLoaderOptions
): Promise<'esm' | 'cjs'>;

/**
 * Generates React Refresh module runtime code
 * @param {object} Template - Webpack template utilities
 * @param {object} config - Runtime configuration
 * @returns {string} - Generated runtime code
 */
function getRefreshModuleRuntime(
  Template: any,
  config: { const: boolean; moduleSystem: 'esm' | 'cjs' }
): string;

/**
 * Normalizes loader options with defaults
 * @param {ReactRefreshLoaderOptions} options - Raw loader options
 * @returns {NormalizedLoaderOptions} - Normalized options
 */
function normalizeOptions(options: ReactRefreshLoaderOptions): NormalizedLoaderOptions;

Loader Context Requirements

The loader requires specific Webpack context:

  • Webpack Version: 5.2.0+
  • Hot Module Replacement: Must be enabled
  • Module Rules: Should target React component files
  • Babel Integration: Requires react-refresh/babel plugin

Warning Handling:

// The loader will warn if HMR is not enabled
if (!context.hot) {
  logger.warn(
    'Hot Module Replacement (HMR) is not enabled! ' +
    'React Refresh requires HMR to function properly.'
  );
}

Install with Tessl CLI

npx tessl i tessl/npm-pmmmwh--react-refresh-webpack-plugin

docs

client-utilities.md

error-overlay.md

index.md

loader-configuration.md

plugin-configuration.md

plugin-utilities.md

runtime-utilities.md

socket-integrations.md

tile.json