laravel-mixを使ってpugを使うのは諦めた方がいいかもしれない話【エラー多発】

こんにちは。のせっち@nosecchi01です。
フリーランスでマークアップ、ワードプレス構築を中心にやっております。

laravel-mixでマークアップ環境を構築する方法を解説済みで、実際に実案件でも使っています。

今回は、laravel-mixでpugを使うのは諦めた方がよさそう(2021年4月時点)というお話です。

laravel外で使う前提です。

説明通りにやってもエラー

laravel-mix x pug導入の定番パッケージはlaravel-mix-pugでしょう。

上記のgithubに記載の通りの手順で進めてみます。

npm install laravel-mix-pug --save-dev

package.jsonの作成と、laravel-mixは既にインストール済みの前提です。

インストールできたら、webpack.mix.jsに下記を記述します。

let mix = require('laravel-mix');
mix.pug = require('laravel-mix-pug');
 
mix
   .pug('src/*.pug', 'dist')
   .setPublicPath('dist');

そして、適当にindex.pug等を作ってコンパイル

npx mix

そうすると下記のようなエラーがでるはずです。

Error: ENOENT: no such file or directory, open '/Users/yukinose/Desktop/laravel-mix-test/src/dist/index.html'


[webpack-cli] Error: ENOENT: no such file or directory, stat '/Users/yukinose/Desktop/laravel-mix-test/src/dist/index.html'
    at Object.statSync (fs.js:1009:3)
    at Object.statSync (/Users/yukinose/Desktop/laravel-mix-test/node_modules/graceful-fs/polyfills.js:312:16)
    at File.size (/Users/yukinose/Desktop/laravel-mix-test/node_modules/laravel-mix/src/File.js:34:19)
    at Object.size (/Users/yukinose/Desktop/laravel-mix-test/node_modules/laravel-mix/src/webpackPlugins/CustomTasksPlugin.js:71:31)
    at _ (/Users/yukinose/Desktop/laravel-mix-test/node_modules/webpack/lib/stats/DefaultStatsFactoryPlugin.js:893:31)
    at /Users/yukinose/Desktop/laravel-mix-test/node_modules/webpack/lib/stats/DefaultStatsFactoryPlugin.js:2240:9
    at Hook.eval [as call] (eval at create (/Users/yukinose/Desktop/laravel-mix-test/node_modules/tapable/lib/HookCodeFactory.js:19:10), <anonymous>:5:16)
    at Hook.CALL_DELEGATE [as _call] (/Users/yukinose/Desktop/laravel-mix-test/node_modules/tapable/lib/Hook.js:14:14)
    at /Users/yukinose/Desktop/laravel-mix-test/node_modules/webpack/lib/stats/StatsFactory.js:277:7
    at StatsFactory._forEachLevel (/Users/yukinose/Desktop/laravel-mix-test/node_modules/webpack/lib/stats/StatsFactory.js:100:19) {
  errno: -2,
  syscall: 'stat',
  code: 'ENOENT',
  path: '/Users/yukinose/Desktop/laravel-mix-test/src/dist/index.html'
}

1行目に注目してください。

Error: ENOENT: no such file or directory, open '/Users/yukinose/Desktop/laravel-mix-test/src/dist/index.html'

パスがおかしいです。

webpack.mix.jsで指定したコンパイル先はdistなのに、エラー文ではsrc/distとなっていて、「ディレクトリが見つからないよ」、と言ってきています…。

ここまでのまとめ:指定通りに設定してもパスがおかしくなりコンパイルできない。

解決策…しかし、足りない

GitHubでIssueを見てみると、色々な議論がなされています。
下記を参照。

解決策として挙げられているのがこちらの投稿です。

I was having the same problem. After debugging I realized that by now the plugin outputs the compiled files to the relative path we configure to get the templates from. Let’s say that the templates are at src/templates/myfile.pug. The output file will be src/template/<my_dist_folder>/myfile.html. Even calling mix.setPublicPath didn’t solve the problem form me.

My solution was to calculate the relative from the template filte path to the public folder:

// ...
mix.pug('src/templates/*.pug', path.relative('src/templates', 'dist'), {});
// ...

こちらを参考にwebpack.mix.jsを書き換えてみます。

let mix = require('laravel-mix');
const path = require('path');
mix.pug = require('laravel-mix-pug');

mix
  .pug('src/*.pug', path.relative('src/', 'dist'), {})
  .setPublicPath('dist'); 

2行目のpathの定義を忘れずに

これでもう一度コンパイル

npx mix
✔ Compiled Successfully in 86ms
┌──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────┬───────────┐
│                                                                                                                                                                     File │ Size      │
├──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────┼───────────┤
│                                                                                                                                                              /index.html │ 255 bytes │
└──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────┴───────────┘
webpack compiled successfully

通りました!

しかし、これで全て解説するわけではありません。

ここまでのまとめ:有志の方が解決策を出してくれていて、一応動くようになる。

問題点:コンパイルできるのはディレクトリ直下のpugファイルのみ

ディレクリ構成が下記のようならコンパイル可能です。

src
 - index.pug
 - about.pug

しかし、下記はNG。

src
 - index.pug
 - about
  - index.pug

フォルダ > index.pugとするとコンパイルされません…。

ディレクトリ構成を許容できるのでしたら、使用可能かと思いますが、他にも僕が気づいていないエラーがあるかもしれません。

パッケージのメンテナンスがされていないので、laravel-mixやwebpackのバージョンアップにより完全に使えなくなる可能性があります。

laravel-mix-pugは3年以上パッケージの更新がされておらず、Issueの質問やpull requestに対しても一切反応していないので、パッケージの更新を待つのは期待薄です。(2021年4月時点)

larave-mix-pug-recursiveというのがある

さきほどの、GitHub Issueで解決策を提示していた文章の下に、更にコメントがあることがわかります。

Thanks everyone. I’ve forked the latest from matejsvajger/laravel-mix-pug and made a pull request #14 with the recursive compiling fix from rivergod@c5658a2.

With this fix I can now compile my entire folder of pug templates:

.pug('_theme/**/*.pug', dist, {
   excludePath: '_theme'
})

In the meantime I’ve published the fork to NPM as laravel-mix-pug-recursive. (first time publishing an npm package, so please correct me if I went about this the incorrect way)
https://www.npmjs.com/package/laravel-mix-pug-recursive

まず前半、
この問題を解決するためのpull requestを出した(#14)とあります。

ただし、こちらのpull requestは何のコメントもマージもされていません…。(2021年4月時点)

そして、後半です。

laravel-mix-pugをフォークして、laravel-mix-pug-recursiveというパッケージを作ったぞ!とあります。
それがこちら、

パス問題を解決したものとして、リリースしてくれたもの、、、のはずですが、
こちらを使うと下記のエラーが、

[webpack-cli] TypeError: Cannot read property 'glob' of undefined
    at Object.pug (/Users/yukinose/Desktop/laravel-mix-test/node_modules/laravel-mix-pug-recursive/src/index.js:17:30)
    at Object.<anonymous> (/Users/yukinose/Desktop/laravel-mix-test/webpack.mix.js:6:4)
    at Module._compile (/Users/yukinose/Desktop/laravel-mix-test/node_modules/v8-compile-cache/v8-compile-cache.js:192:30)
    at Object.Module._extensions..js (internal/modules/cjs/loader.js:1158:10)
    at Module.load (internal/modules/cjs/loader.js:986:32)
    at Function.Module._load (internal/modules/cjs/loader.js:879:14)
    at Module.require (internal/modules/cjs/loader.js:1026:19)
    at require (/Users/yukinose/Desktop/laravel-mix-test/node_modules/v8-compile-cache/v8-compile-cache.js:159:20)
    at module.exports (/Users/yukinose/Desktop/laravel-mix-test/node_modules/laravel-mix/setup/webpack.config.js:8:5)
    at /Users/yukinose/Desktop/laravel-mix-test/node_modules/webpack-cli/lib/webpack-cli.js:1386:43

… ダメですね。

GitHubを見ると同じエラーが出た方がIssueを上げています。

こちらに対しても反応がないようです。

ということで2021年4月時点ではこちらのパッケージも使えません。

まとめ

・pugを使いたい場合は大人しくGulpを使った方がよさそう。

この記事を書いた人

のせっち

福岡県出身。早稲田大学卒。創業100年の鉄鋼商社でバンコク駐在最年少抜擢。毎日擦り切れるまで働かなくても幸せに生きている人々を見てフリーランスになりました。
現在は、主にバンコクでWeb制作、物販を中心に生きています。