Skip to content

[Bug]: When generating HTML files using html-webpack-plugin + Handlebars, the syntax for including partial templates using {{> partialName}} in the Handlebars template is not working #12652

@gxchen0802

Description

@gxchen0802

System Info

  • System: MacOS Ventura 13.4
  • CPU: arm64 Apple M2 Pro
  • npmPackages:
    • "@rspack/cli": "~1.7.1",
    • "@rspack/core": "~1.7.1",
    • "handlebars": "~4.7.8",
    • "handlebars-loader": "~1.7.3",
    • "html-webpack-plugin": "~5.6.5",
  • nodejs: v20.19.2

Details

This is an Rspack configuration example using html-webpack-plugin. The plugin automatically generates HTML files, but the Handlebars template syntax {{> partialName}} for including partial templates fails to work, resulting in the following error:

ERROR in × Template execution failed: Error: The partial meta could not be compiled when running in runtime-only mode

ERROR in × Error: The partial meta could not be compiled when running in runtime-only mode
│
│ - index.hbs:1044 Object.invokePartialWrapper [as invokePartial]
│ /Users/website/rspack-test/src/index.hbs:1044:13
│
│ - index.hbs:1484 Object.main
│ /Users/website/rspack-test/src/index.hbs:1484:28
│
│ - index.hbs:1148 main
│ /Users/website/rspack-test/src/index.hbs:1148:32
│
│ - index.hbs:1152 ret
│ /Users/website/rspack-test/src/index.hbs:1152:12
│
│ - index.js:791
│ [rspack-test]/[html-webpack-plugin]/index.js:791:16
│
│ - async Promise.all

Reproduce link

https://github.com/gxchen0802/rspack-handlebars-project.git

Reproduce Steps

Implementation Steps and Complete Configuration

Step 1: Install All Dependencies

# Core dependencies: Handlebars + loader + HTML plugin
npm install @rspack/cli @rspack/core handlebars handlebars-loader html-webpack-plugin --save-dev

Step 2: Project Directory Structure

rspack-test-project/
├── handlebars/
│   └──  meta.hbs
├── src/
│   ├── index.hbs          # Main Handlebars template (for html-webpack-plugin)
│   └── index.js           # Project entry JS
├── rspack.config.js       # Core configuration file
└── package.json

Step 3: Complete rspack.config.js Configuration

const path = require('path');
const HtmlWebpackPlugin = require('html-webpack-plugin');
const distPath = path.resolve(__dirname, 'dist');

module.exports = {
    cache: false,
    mode: 'development',
    devtool: 'source-map',
    entry: {
        index: ['./src/index.js']
    },
    output: {
        path: distPath,
        publicPath: '/dist/',
        filename: 'js/[name].js'
    },
    resolve: {
        extensions: ['.js',   '.hbs', '.*'],
        alias: {
            handlebars: path.resolve(__dirname, 'handlebars'),
            src: path.resolve(__dirname, 'src')
        },
        fallback: { crypto: false }
    },
    module: {
        rules: [
            {
                test: /\.(j|t)sx?$/,
                exclude: /(node_modules|plugins)/,
                use: [{  loader: 'builtin:swc-loader' }]
            },
            {
                test: /\.hbs$/,
                exclude: /node_modules/,
                use: [
                    {
                        loader: 'handlebars-loader',
                        options: {
                            // Core: Specify the lookup directory for partial templates (supports arrays)
                            partialDirs: [
                                path.resolve(__dirname, 'handlebars'),
                                path.resolve(__dirname, 'src')
                            ]
                        }
                    }
                ]
            }
        ]
    },
    plugins: [
        // HTML generation plugin configuration
        new HtmlWebpackPlugin({
            filename: 'html/index.html',
            template: './src/index.hbs',
            templateParameters: {
                title: 'Rspack + Handlebars + HTML Plugin',
                container: 'respack-demo-container'
            },
            inject: 'body',
            chunks: ['index'],
            minify: false
        })
    ],
    stats: 'normal'
};

Step 4: Template Examples (Verify Partial Syntax)

  1. src/handlebars/meta.hbs (partial template, can use global data):
<meta charset="utf-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
<meta name="renderer" content="webkit|ie-comp|ie-stand" />
<meta name="viewport" content="width=device-width, initial-scale=1">
<meta name="format-detection" content="telphone=no, email=no" />
<meta name="HandheldFriendly" content="true" />
<meta name="MobileOptimized" content="320" />
<meta name="screen-orientation" content="portrait" />
<meta name="x5-orientation" content="portrait" />
<meta name="full-screen" content="yes" />
<meta name="x5-fullscreen" content="true" />
<meta name="browsermode" content="application" />
<meta name="x5-page-mode" content="app" />
<meta name="msapplication-tap-highlight" content="no" />
<meta name="robots" content="index,follow" />
<meta http-equiv="pragma" content="no-cache" />
<meta http-equiv="cache-control" content="no-cache" />
<meta http-equiv="expires" content="0" />
<meta name="author" content="test" />
  1. src/index.hbs (main template, using {{> partialName}} to include partials):
<!DOCTYPE html>
<html lang="zh-CN">
<head>
    {{> meta}}
    <title>{{ title }}</title>
</head>
<body>
    <div id="root" class="container">{{container}}</div>
</body>

</html>
  1. src/index.js (entry JS):
console.log('Page loaded successfully, Handlebars partial syntax supported!');
  1. package.json configuration:
{
    "author": "gxchen",
    "description": "rspack test project",
    "devDependencies": {
        "@rspack/cli": "~1.7.1",
        "@rspack/core": "~1.7.1",
        "handlebars": "~4.7.8",
        "handlebars-loader": "~1.7.3",
        "html-webpack-plugin": "~5.6.5",
        "prettier": "~3.7.4"
    },
    "license": "ISC",
    "main": "app.js",
    "name": "rspack-test",
    "private": true,
    "scripts": {
        "start": "npm run build",
        "build": "rspack build"
    },
    "version": "1.0.0"
}

Step 5: Run

  1. Execute the build command:
npm run build

Metadata

Metadata

Assignees

No one assigned

    Labels

    pending triageThe issue/PR is currently untouched.

    Type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions