Help us understand the problem. What is going on with this article?

npmパッケージのhtmllintについて - Lintルールのカスタマイズ -

More than 1 year has passed since last update.

HTMLの構文チェックにnpmパッケージの「htmllint」を使っているのですが、カスタマイズ関連でいつも忘れてググってしまうので備忘録として残す。

概要

htmllintについて

「htmllint」をgulpで利用している場合はgulp-htmllint
CLI で実行する場合はhtmllint-cli を使います。

node.js が入っている前提で進めます。

// インストール
$ npm install -g htmllint --save-dev

ルートディレクトリに.htmllintrcファイルを生成します。
以下コマンドで自動生成されます。
自動生成された.htmllintrcにはデフォルトでLintルールが記載されています。
それについては後ほど。

// .htmllintrc 自動生成
$ htmllint init

LintチェックしてほしいHTMLファイルを指定すれば対象ページの構文チェックが行われます。

$ htmllint ファイルパス指定

デフォルトのLintルールでほぼほぼ空のHTMLをLintかけてみます。

index.html
<!DOCTYPE html>
<html>
<head>
  <meta charset="UTF-8">
  <title>HTMLLint</title>
</head>
<body>
</body>
</html>

結果。怒られました。

$ htmllint index.html
index.html: line 4, col 1, indenting spaces must be used in groups of 4
index.html: line 5, col 1, indenting spaces must be used in groups of 4

Lintのルールでは、インデントの空白4文字分と決めているのに
このHTMLのインデントは空白2文字分になってるよ。と怒られています。

とはいえ、私は空白2文字分でいきたいので
ルールの方を変えていきます。

Lintルールのカスタマイズ

先ほど自動生成された .htmllintrc を見てみると色々書かれています。
構文ルールのデフォルト値が指定されています。

{
    "plugins": [],  // npm modules to load

    "maxerr": false,
    "raw-ignore-regex": false,
    "attr-bans": [
        "align",
        "background",
        "bgcolor",
        "border",
        "frameborder",
        "longdesc",
        "marginwidth",
        "marginheight",
        "scrolling",
        "style",
        "width"
    ],
    "indent-delta": false,
    "indent-style": "nonmixed",
    "indent-width": 4,
    "indent-width-cont": false,
    "spec-char-escape": true,
    "text-ignore-regex": false,
    "tag-bans": [
        "style",
        "b",
        "i"
    ],
    "tag-close": true,
    "tag-name-lowercase": true,
    "tag-name-match": true,
    "tag-self-close": false,
    "doctype-first": false,
    "doctype-html5": false,
    "attr-name-style": "dash",
    "attr-name-ignore-regex": false,
    "attr-no-dup": true,
    "attr-no-unsafe-char": true,
    "attr-order": false,
    "attr-quote-style": "double",
    "attr-req-value": true,
    "attr-new-line": false,
    "attr-validate": true,
    "id-no-dup": true,
    "id-class-no-ad": true,
    "id-class-style": "underscore",
    "class-no-dup": true,
    "class-style": false,
    "id-class-ignore-regex": false,
    "img-req-alt": true,
    "img-req-src": true,
    "html-valid-content-model": true,
    "head-valid-content-model": true,
    "href-style": false,
    "link-req-noopener": true,
    "label-req-for": true,
    "line-end-style": "lf",
    "line-no-trailing-whitespace": true,
    "line-max-len": false,
    "line-max-len-ignore-regex": false,
    "head-req-title": true,
    "title-no-dup": true,
    "title-max-len": 60,
    "html-req-lang": false,
    "lang-style": "case",
    "fig-req-figcaption": false,
    "focusable-tabindex-style": false,
    "input-radio-req-name": true,
    "input-req-label": false,
    "table-req-caption": false,
    "table-req-header": false,
    "tag-req-attr": false
}

どんな意味なのか下に書いていきますが、たくさんあるので
よく変更されがちなもののみ抜粋して下に記載します。大体はデフォルトのままでいいと思います。

構文エラーになった時のエラーメッセージも合わせて記載します。

ドキュメントはこちら
Options List

attr-bans

デフォルト:["align", "background", "bgcolor", "border", "frameborder", "longdesc", "marginwidth", "marginheight", "scrolling", "style", "width"]
属性禁止を指定する

// 構文エラーメッセージ : <img>にwidthをHTML上に記述した場合(<img src="" alt="" width="">)
the `width` attribute is banned

indent-style

デフォルト: "nonmixed"
インデントの空白をタブを使うか半角スペースを使うか

  • "tabs" : タブ使用
  • "spaces" : スペース使用
  • "nonmixed" : タブでもスペースでもどちらでも良いけど統一はしてね
  • "false" : 無制限
// 構文エラーメッセージ
invalid value for option indent-style: nonmixed

indent-width

デフォルト:4
インデント空白を何文字分

// 構文エラーメッセージ
indenting spaces must be used in groups of 4

tag-bans

デフォルト:["style", "b", "i"]
使用禁止のタグを指定する

// 構文エラーメッセージ : <style>を使用した場合
the style tag is banned

tag-self-close

デフォルト:false

最後に/を入れるかどうか(HTML5ルールにするのかそれ以下にするのか)

  • "always" : HTML4仕様 ( 例 <meta charset="UTF-8" />
  • "never" : HTML5仕様 ( 例 <meta charset="UTF-8">
  • false : 制限なし
// 構文エラーメッセージ : "always"で 「/」 なしにした場合
void element should always close itself

attr-name-style

デフォルト:"dash"
属性名の命名規則

  • "lowercase" : 小文字で表現
  • "underscore" : 小文字とアンダースコアで表現
  • "dash" : 小文字とハイフンで表現
  • "camel" : キャメルケースで表現
  • "bem" : BEMで表現
  • 自分で正規表現で指定 ('/^[a-z]+$/g'など).
// 構文エラーメッセージ
attribute names must match the format: 

attr-quote-style

デフォルト : "double"
属性値を囲う手段

  • "double" : ダブルクォーテーションのみ
  • "single" : シングルクォーテーションのみ
  • "quoted" : ダブルクォーテーションまたはシングルクォーテーション
  • false : 制限なし
// 構文エラーメッセージ : <body class='hoge'>
the `class` attribute is not double quoted

id-class-style

デフォルト : "underscore"
クラス名、id名の命名規則指定

  • "lowercase" : 小文字で表現
  • "underscore" : 小文字とアンダースコアで表現
  • "dash" : 小文字とハイフンで表現
  • "camel" : キャメルケースで表現
  • "bem" : BEMで表現
  • 自分で正規表現で指定 ('/^[a-z]+$/g'など).
// 構文エラーメッセージ
class value must match the format: underscore

class-style

デフォルト:false(制限なし)
id-class-style とほぼ同じ。
対象がクラスのみになります。
class-style がfalseの場合 id-class-style のルールが適用されます。

  • "lowercase" : 小文字で表現
  • "underscore" : 小文字とアンダースコアで表現
  • "dash" : 小文字とハイフンで表現
  • "camel" : キャメルケースで表現
  • "bem" : BEMで表現
  • "none" : 制限なし(id-class-style のルールも無視して制限なし)
  • 自分で正規表現で指定 ('/^[a-z]+$/g'など).

img-req-alt

デフォルト:true
<img>タグのalt属性の扱い

  • true : <img>タグのalt属性には必ず値を入れること
  • "allownull" : alt属性は必須だが値は空でもOK(alt=""でもOK)
  • false : 制限なし
// 構文エラーメッセージ
the `alt` property must be set for image tags

line-end-style

デフォルト:lf
改行コードの指定

  • "lf" : LF
  • "crlf" : CRLF
  • "cr" : CR
  • false : 制限なし
// 構文エラーメッセージ
line ending does not match format: lf

ここの部分だけLintルールを変えたいんだって時

.htmllint にルールを一通り書いていますが
HTMLに直接Lintルールを書くこともできます。
その場合、優先度はHTMLに書いたルールが高です。

<!-- htmllint Lintのオプション = "値" -->

こんな時に使いそうな場面の例

  1. クラス名を BEM で書いている(.htmllintrcclass-style : "bem"と設定)
  2. JSライブラリを利用する時、そのライブラリのクラス名がBEMではなくキャメルで書かれている
  3. このままだとJSライブラリを使用している部分がLintに引っかかる。 けどLintの設定はclass-style : "bem"と変えたくない

みたいなパターンがあるとします。

index.html
<div class="box">
  <div class="box__wrapper">
    <!-- ここからJSライブラリ使用 -->
    <div class="dropdown animate arrowTop open"> <!-- キャメルでアウト -->
      <div class="dropdownWrapper"> <!-- キャメルでアウト -->
        ....中略....
      </div>
    </div>
  </div>
</div>

今回はclass-styleのルールを変更したいので
<!-- htmllint class-style = "none" -->と書きます。(または"camel"
JSライブラリの部分だけ変更したい時は以下のように置きます。

index.html
<div class="box">
  <div class="box__wrapper">
    <!-- htmllint class-style = "none" -->
    <div class="dropdown">
      <div class="dropdownWrapper">
        ....中略....
      </div>
    </div>
  </div>
</div>

こうすることでLintはルールを変更した部分に対してはそこを見てLintチェックを行ってくれます。

複数指定も可能です。

<!-- htmllint class-style = "none"
     htmllint attr-name-style = "false"
     htmllint attr-validate = "false"
--> 

まとめ

  • 「htmllint」で Lintルールをカスタマイズする方法は.htmllintrcに記載するか、HTMLに直接記載する方法がある。
  • .htmllintrcのルールだけでなくHTMLごとに設定を変更できるため柔軟性がある

ページを作っていくと、いつのまにかLintに引っかかってる事がよくあります。こまめのチェック大事

今回記事にした部分に関するドキュメント

Options List
.htmllintrcオプションについて

Inline Configurations
HTMLにLintルールを記載する方法について

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
No comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
ユーザーは見つかりませんでした