tonkotu_sister
@tonkotu_sister (tonkotu san)

Are you sure you want to delete the question?

Leaving a resolved question undeleted may help others!

webpack5のpugで変数を取得できない

Q&A

Closed

前提・実現したいこと

webpack環境でA.pugというファイルで_B.pugで定義している変数を呼び出したい。

発生している問題・エラーメッセージ

webpack5でPugの変数を使う際に別ファイルで定義している変数を呼び出す(include)と以下のようなエラーが表示され、
変数の値が取得・展開できません。

ERROR in Template execution failed: TypeError: Cannot read property 'name' of undefined
ERROR in   TypeError: Cannot read property 'name' of undefined
  - A.pug:16 
    /Users//webpack_sample_v1_pug/src/pug/A.pug:16:471
  - A.pug:16 template
    /Users//webpack_sample_v1_pug/src/pug/A.pug:16:2110
  - index.js:450 
    [webpack_sample_v1_pug]/[html-webpack-plugin]/index.js:450:16
  - task_queues.js:97 processTicksAndRejections
    internal/process/task_queues.js:97:5
  - async Promise.all

ディレクトリ構造

webpack_sample_v1_pug
├ package.json
├ package-lock.json
├ webpack.config.js
├ node_modules
└ src
  └ js
  └ pug
    └ _B.pug
    └ A.pug
└ dist
  └ js

該当のソースコード

Pugファイル

_B.pug
- var site = {};
 - site.name = 'サイト名';
A.pug
include /_B.pug

doctype html
html(lang="jp")
    head
        meta(charset="UTF-8")
        title= site.name // 変数を取得・展開できない
    body
        script(src="./js/bundle.js")

webpack.config.js

// webpack.config.js
const path = require("path");
const MODE = "development";
const globule = require("globule");
const HtmlWebpackPlugin = require("html-webpack-plugin");
const webpack = require("webpack");

const app = {
  mode: MODE,
  entry: ["./src/js/index.js"],
  output: {
    path: path.resolve(__dirname, "dist"),

    filename: "./js/bundle.js",
  },
  devtool: "source-map",
  module: {
    rules: [
      {
        test: /\.js$/,
        use: [
          {
            loader: "babel-loader",
            options: {
              presets: ["@babel/preset-env"],
            },
          },
        ],
      },
      {
        test: /\.pug$/,
        use: [
          {
            loader: "pug-loader",
            options: {
              pretty: true,
              root: path.resolve(__dirname, "src/pug"),
            },
          },
        ],
      },
    ],
  },
  devServer: {
    static: {
      watch: true,
      directory: `${__dirname}/src`,
    },

    open: true,
  },
  plugins: [
    new webpack.ProvidePlugin({
      $: "jquery",
    }),
  ],

  target: ["web", "es5"],
  devtool: "source-map",
  watchOptions: {
    ignored: /node_modules/,
  },
};

const templates = globule.find("./src/pug/**/*.pug", {
  ignore: ["./src/pug/**/_*.pug"],
});

templates.forEach((template) => {
  const fileName = template.replace("./src/pug/", "").replace(".pug", ".html");
  app.plugins.push(
    new HtmlWebpackPlugin({
      filename: `${fileName}`,
      template: template,
      inject: false,
      minify: false,
    })
  );
});

module.exports = app;

package.json

{
  "scripts": {
    "build": "webpack --mode production",
    "dev": "webpack --mode development",
    "watch": "webpack --mode development --watch",
    "start": "webpack serve --mode development"
  },
  "devDependencies": {
    "@babel/core": "^7.15.5",
    "@babel/preset-env": "^7.15.6",
    "autoprefixer": "^10.3.7",
    "babel-loader": "^8.2.2",
    "copy-webpack-plugin": "^9.0.1",
    "css-loader": "^6.2.0",
    "globule": "^1.3.3",
    "html-webpack-plugin": "^5.3.2",
    "html-webpack-pug-plugin": "^3.0.0",
    "mini-css-extract-plugin": "^2.3.0",
    "path": "^0.12.7",
    "postcss": "^8.3.9",
    "postcss-loader": "^6.1.1",
    "pug": "^2.0.4",
    "pug-loader": "^2.4.0",
    "sass": "^1.39.2",
    "sass-loader": "^12.1.0",
    "style-loader": "^3.2.1",
    "webpack": "^5.52.1",
    "webpack-cli": "^4.8.0",
    "webpack-dev-server": "^4.2.0"
  },
  "dependencies": {
    "jquery": "^3.6.0"
  },
  "browserslist": [
    "> 3% in JP",
    "ie 11",
    "android 4.4",
    "last 1 versions"
  ]
}

試したこと

・A.pug内で変数を定義、そして展開すると問題なくコンパイルができました。
・_B.pugで変数作成・タグに変数の値を代入した状態で、includeすると展開ができました。※下記参照願います。

// _B.pug
- var text = 'サンプル';
// A.pug
@include _B.pug
// 結果 'サンプル'が表示される

どうかご教授の方よろしくお願い致します。。。

0

1Answer

Comments

  1. @tonkotu_sister

    Questioner

    ご回答ありがとうございます!
    失礼しました。転記ミスでございました。。。
    改めて変数定義している部分を修正致しましたのでご確認をお願い致します。
    - var site.name = 'サイト名';



    - var site = {};
    - site.name = 'サイト名';
  2. pug-loader だと変数のスコープがファイルで閉じているように見えます。

    site 変数をどのファイルからも参照できるようにするには、 pug-loader の globals オプションを以下のように指定してください。
    {
    loader: "pug-loader",
    options: {
    globals: ["site"],
    pretty: true,
    root: path.resolve(__dirname, "src/pug"),
    },
    }

    そして _B.pug では var を使わずに site を参照してください。

    - site = {}
    - site.name = 'サイト名'
  3. @tonkotu_sister

    Questioner

    @uasi さん
    仰られた通りに変更すると問題なく変数を参照できるようになりました!
    本当にありがとうございます!!!
    感謝してもしきれません!!!

    お手間かけないように精進致します!ありがとうございました!

Your answer might help someone💌