カラーモード

gulp v4.0.2 を使っている環境で markuplint v3.3.0 を導入するとエラーになる

gulp
Node.js

まずはじめに、markuplint は素晴らしツールなのでみんなも使おう。

この記事の公開後、すぐにmarkuplintモジュールを修正された。

markuplint v3.3.1 にアップデートしたところこの記事のエラーは起きず、A 環境もワークアラウンドなしにテスト結果が正しく表示された。対応してくれてありがとう!

gulp v4.0.2 を使っている個人の環境(以後「A 環境」と記す)で、markuplint を v2.x から v3.3.0 に上げて npx markuplint を実行したところ、下記のようなエラーが出てテスト結果が正しく表示されなかった。

  0:
  1: <!DOCTYPE•html>
<markuplint> error: TypeError: debug_1.green.bold is not a function
    at Collection.toString (/aswsome_dir/node_modules/@markuplint/rules/lib/permitted-contents/utils.js:232:44)
    at order (/aswsome_dir/node_modules/@markuplint/rules/lib/permitted-contents/order.js:87:56)
    at start (/aswsome_dir/node_modules/@markuplint/rules/lib/permitted-contents/start.js:50:38)
    at contentModel (/aswsome_dir/node_modules/@markuplint/rules/lib/permitted-contents/content-model.js:18:38)
    at /aswsome_dir/node_modules/@markuplint/rules/lib/permitted-contents/index.js:20:62
    at /aswsome_dir/node_modules/@markuplint/ml-core/lib/ml-dom/node/document.js:2012:24
    at loop (/aswsome_dir/node_modules/@markuplint/ml-core/lib/ml-dom/helper/walkers.js:37:24)
    at loop (/aswsome_dir/node_modules/@markuplint/ml-core/lib/ml-dom/helper/walkers.js:42:13)
    at loop (/aswsome_dir/node_modules/@markuplint/ml-core/lib/ml-dom/helper/walkers.js:42:13)
    at sequentialWalker (/aswsome_dir/node_modules/@markuplint/ml-core/lib/ml-dom/helper/walkers.js:45:5) (@markuplint/ml-core) /aswsome_dir/dist/archives/index.html:0:0

テストした HTML や markuplint のルールには特におかしなところはない。しかも他環境では markuplint v3.3.0 を利用しても error: TypeError: debug_1.green.bold is not a function エラーにならない。おそらく A 環境の dependencies の何かが原因だろうとあたりをつけた。

さらに、A 環境の dependencies と markuplint の組み合わせを一つずつ試していく途中で、markuplint を先にインストールするか後にインストールするかで結果が異なることに気がついた。

ということで、A 環境の dependencies で検証した内容と結果を表に記す。なお、検証した Node.js のバージョンは v14.19.3 / v16.13.2 / v18.13.0 で、どのバージョンでも検証結果は同じであった。

npm i -D <one-dependencides>
npm i -D markuplint
npx markuplint dist/**/*.html

上記をパターン 1 とし、パターン 2 では npm i -D markuplint<one-dependencies> より先に実行する。検証前に毎回 package-lock.json と node_modules ディレクトリを削除し、package.json の devDependencies フィールドを空にする。

表のマークの意味
  • ✅: テスト結果が正しく表示される(markuplint としての error や warning の有無にかかわらず、エラー表示にならない)
  • ❌: テスト結果が正しく表示されない(error: TypeError: debug_1.green.bold is not a functionが発生する)
npm モジュール バージョン 後に npm i -D markuplint 先に npm i -D markuplint
@prettier/plugin-pug ^2.4.1
autoprefixer ^10.4.13
browser-sync ^2.28.1
css-mqpacker ^7.0.0
gulp ^4.0.2
gulp-changed ^4.0.3
gulp-front-matter ^2.0.0-7
gulp-if ^3.0.0
gulp-imagemin ^8.0.0
gulp-layout 0.0.4
gulp-markdown ^7.0.0
gulp-plumber ^1.2.1
gulp-postcss ^9.0.1
gulp-prettify ^0.5.0
gulp-rename ^2.0.0
husky ^8.0.3
list-stream ^2.1.0
pretty-quick ^3.1.3
pug ^3.0.2
stylelint ^15.2.0
stylelint-config-recommended ^10.0.1
textlint ^13.3.1
textlint-rule-preset-ja-spacing ^2.3.0
textlint-rule-preset-ja-technical-writing ^7.0.0

A 環境で検証した限りでは、gulp といくつかの gulp-* プラグインでのみ、npm i -D markuplint を後にするとテスト結果が正しく表示されいことが読み取れる。そして先に npm i -D markuplint すると、どの gulp/gulp-* でもテスト結果は正しく表示されることもわかった。

なぜそうなのかまでは調べていないが、 markuplint に v3 から導入された debug モジュールが、gulp 周りの何らかとソーレンソーしているのだろう。つまりわからない。

手元での対応

とりあえず markuplint を gulp/gulp-* より先にインストールできれば期待通り動くということはわかった。

意気揚々と A 環境の node_modules ディレクトリを削除し npm i -D markuplint から始めたしたところ、どうやら他のモジュールも一緒にインストールされてしまうようで、テスト結果にエラーが出てしまった。

そこで、package.json の devDependencies から gulp/gulp-* の指定をいったん退避させてから npm i し、その後に gulp/gulp-* の指定を復帰させて再び npm i した。

そうした A 環境で npx markuplint を実行すると、テスト結果は正しく表示された。やったね!

CI での対応

CI を利用している場合、npm i を gulp/gulp-* とそれ以外とで2回に分ければよい。すなわち gulp/gulp-* を後に実行する。

# .github/workflows/test.yml
name: test

on: [push]

jobs:
  build:
    name: Test
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v1
      - name: install dependencies exclude gulp-*
        run: npm i -D @prettier/plugin-pug autoprefixer browser-sync css-mqpacker husky list-stream markuplint pretty-quick pug stylelint stylelint-config-recommended
      - name: install dependencies gulp-*
        run: npm i -D gulp gulp-changed gulp-front-matter gulp-if gulp-imagemin gulp-layout gulp-markdown gulp-plumber gulp-postcss gulp-prettify gulp-rename
      - name: build
        run: npm run build
      - name: test
        run: npm run test

これで CI 上でも Run failed にならない。

解決策はあくまでワークアラウンド

これら措置は個人リポジトリだからできるが、案件で採用する場合はワークアラウンドであることをしっかり認識してほしい。

かといってこの方法以外で gulp v4 と markuplint v3 を共存させることは、どちらかのモジュールが対応する以外にないように思える。

ということで markuplint のオーナーである@ゆうてんにもこの現象は共有済みだ。既に Issue にもしてもらった

どういう結果になるかわからないが、OSS を利用する者の責務として、問題を共有し広めるためにこの記事を書いた。

もちろん、gulp を使っていない環境ならば、markuplint のテスト結果は正しく表示される。少なくとも僕の他の個人環境では error: TypeError: debug_1.green.bold is not a function エラーは起こらなかった。

座して待とう。