EditorConfig ジェネレーター

.editorconfig

リポジトリで使っているエコシステムを選んでください。選ぶたびに、その言語に必要なルールをまとめたセクションが追加されます。

次へ

リポジトリのルートに置いた .editorconfig は、このプロジェクトがファイルをどう整形するかを最新の IDE すべてに伝え、タブかスペースかの議論をファイル単位で決着させます。難しいのは全体のブロックではなく、言語ごとのセクションです。YAML はそもそもタブでインデントできず、make は先頭がスペースのレシピ行を受け付けず、CRLF で保存したシェルスクリプトは実行できません。リポジトリで使っている言語を選べば、このジェネレーターがそれぞれに必要なセクションを書き出し、そのセクションがある理由を横に添えます。

.editorconfig の作り方

  1. 1

    リポジトリで使っている言語を選ぶ

    JavaScript、JSON、HTML と CSS、YAML、Python、PHP、Go、Rust、Ruby、Java、Markdown、Makefile、シェルスクリプト、Windows のバッチファイル。チェックを入れるたびにセクションが 1 つ追加されます。

  2. 2

    すべてのファイルが引き継ぐルールを決める

    インデントのスタイルと幅、改行コード、文字コード、末尾の改行、行末の空白、行の長さの上限。これらは先頭の `[*]` ブロックに入り、その下の各セクションは、その言語が実際に必要とする項目だけを上書きします。

  3. 3

    各セクションがある理由を読む

    ファイルの横の表が、書き出されたセクションを 1 つずつ説明します。チームに不要なものは、コミットする前に削除できます。

  4. 4

    リポジトリのルートにコピーする

    `.gitignore` と同じ場所に `.editorconfig` という名前で保存します。次にファイルを開いたときからエディタが読み込みます。ビルド手順もプラグインの設定も必要ありません。

.editorconfig の役割

プロジェクトのルートに置いた .editorconfig というファイルは、書式の規約を宣言します。EditorConfig に対応したエディタ(主要な IDE と最近のほとんどのテキストエディタ)は、ファイルを開いたときにそのルールを適用します。探索は編集中のファイルからディレクトリツリーを上へたどり、root = true と書かれた最初のファイルで止まります。

出力例

既定の設定(スペース、インデント幅 4、LF、utf-8)と、あらかじめチェックされている 2 つのセクションでは、次のように生成されます。

root = true

[*]
indent_style = space
indent_size = 4
end_of_line = lf
charset = utf-8
trim_trailing_whitespace = true
insert_final_newline = true
max_line_length = 120

[*.{md,markdown}]
trim_trailing_whitespace = false

[{Makefile,makefile,GNUmakefile,*.mk}]
indent_style = tab

Python、Go、YAML にチェックを入れると、それぞれのセクションが下に追加され、その言語のフォーマッターが強制する慣習がすでに書き込まれた状態になります。

主なディレクティブ

ディレクティブ 指定できる値 補足
root true プロジェクトのルートで指定すると、探索がそこで止まります
charset latin1, utf-8, utf-8-bom, utf-16be, utf-16le 通常は utf-8 を選びます。仕様はバイトオーダーマーク(BOM)を推奨しておらず、utf-16 系はプロジェクト内のすべてのファイルに適用されるため、ほとんどのビルドツールが読めなくなります
end_of_line lf, crlf, cr クロスプラットフォームで開発するなら lf、Windows 専用のリポジトリだけ crlf
indent_style space, tab
indent_size 整数、または tab indent_style = tab でも無視されません。tab_width がこの値にフォールバックするため、タブの表示幅を決めます
tab_width 整数 既定で indent_size と同じ値になるため、指定が必要になることはまれです
insert_final_newline true, false ファイルを POSIX に沿った形に保ち、差分を余計に汚しません
trim_trailing_whitespace true, false 行末の空白が改行を意味する Markdown ではオフにします
max_line_length 正の整数、または unset コア仕様にはなく、プロパティの wiki に載っています。制限をなくしたいときは 0 と書かず、この行を省きます

スタイルの好みではなく、ビルドを壊す 3 つのルール

.editorconfig の項目の多くは好みの問題です。しかし次の 3 つは違います。言語ごとのセクションを用意する価値があるのは、この 3 つがあるからです。

  • YAML はインデントにタブ文字を使えません。 リンターの警告ではなく、構文エラーです。タブでインデントしているプロジェクトで GitHub Actions のワークフロー、Docker Compose のファイル、Kubernetes のマニフェストを扱っているなら、YAML のセクションでスペースに戻す必要があります。
  • make はレシピ行の先頭に本物のタブを必要とします。 スペースだと missing separator. Stop. と表示され、ビルドが止まります。[{Makefile,makefile,GNUmakefile,*.mk}] が複数の綴りを並べているのはこのためです。EditorConfig はファイル名を大文字と小文字を区別して照合しますが、リポジトリには Makefile と makefile の両方が存在するからです。
  • CRLF で保存されたシェルスクリプトは実行できません。 カーネルが復帰文字をインタプリタのパスの一部として読み取り、/bin/bash^M: bad interpreter: No such file or directory のように表示します。Windows のバッチファイルには逆向きの問題があります。cmd.exe は goto や call :label の移動先をバイト位置で探すため、LF だけの .bat は違う行へ飛んだり、エラーも出さずに途中で止まったりします。

このうち 2 つは、全体のブロックで解決するどころか、全体のブロックが原因で起きることがあります。このジェネレーターがそこを見張っているのはそのためです。タブを選んで YAML のセクションを追加しなかった場合、あるいは CRLF を選んでシェルスクリプトのセクションを追加しなかった場合、書き出されたファイルは、そこに名前すら出てこないファイルを壊します。パイプラインが落ちてから気づくことにならないよう、ジェネレーターは出力の上でその点を伝えます。utf-16 系の文字コードも同じです。プロジェクト内のすべてのファイルに適用されますが、make、シェルのインタプリタ、Python は、その文字コードで保存されたソースを読めません。

このジェネレーターが書き出す言語ごとの慣習

言語 / ファイル セクション 設定する内容と理由
JavaScript、TypeScript *.{js,jsx,mjs,cjs,ts,tsx} 2 スペース。Prettier の既定値
JSON *.{json,jsonc} 2 スペース。npm が package.json に書き込む幅
HTML、CSS、テンプレート *.{html,htm,css,scss,sass,less,vue,svelte} 2 スペース。Sass のインデント構文はこれがないと解析できません
YAML *.{yml,yaml} 2 スペース。プロジェクトがタブを使っていてもここはスペース
Python *.{py,pyi} 4 スペース。PEP 8 と Black に準拠
PHP *.php 4 スペース。PSR-12 に準拠。WordPress はタブ、Drupal は 2 スペース
Go {*.go,go.mod} タブ。gofmt がタブでインデントするため
Rust *.rs 4 スペース。rustfmt の既定値
Ruby {*.rb,*.rake,Gemfile,Rakefile} 2 スペース。RuboCop の既定値
Java *.java 4 スペース。Oracle の規約に準拠。Google の Java スタイルは 2 スペース
Markdown *.{md,markdown} 行末の空白を残す。Markdown ではそれが改行を意味するため
Makefile {Makefile,makefile,GNUmakefile,*.mk} タブ。make が必須とするため
シェルスクリプト *.{sh,bash,zsh} LF。プロジェクトの他の部分がどうであれ固定
Windows のバッチ *.{bat,cmd} CRLF。cmd.exe がラベルの位置をバイト位置で探すため

この表に入っていないものに注目してください。行の長さです。PEP 8 は 79、Black は 88、PSR-12 は緩い上限として 120、rustfmt は 100 を挙げています。どれかを言語ごとのセクションに書き込むと、プロジェクト全体に対して選んだ上限を知らないうちに上書きしてしまいます。そのためジェネレーターは max_line_length を [*] ブロックだけに残し、これらの数値はこのページに載せています。必要だと判断したときに、自分で適用してください。

お使いのエディタは対応していますか?

ネイティブ対応:VS Code、JetBrains の IntelliJ 系、Visual Studio、Sublime Text、Xcode、Notepad++。Vim、Emacs、Neovim などは小さなプラグインが必要です。ファイルは単純な INI 形式なので、リンターやフォーマッターからも読み取れます。Prettier や一部の言語サーバーが歩調を合わせられるのはこのためです。

よくある質問

プロジェクトのルートに、先頭へ root = true を書いて置きます。特定のパスだけ上書きしたい場合は、サブディレクトリに .editorconfig を追加できます。探索は編集中のファイルからツリーを上へたどり、最初に見つかった root = true のファイルで止まります。

入力欄に 0 を指定すると、ジェネレーターは max_line_length をファイルに出力しません。このプロパティについて文書化されている値は正の整数と、仕様全体で使える unset だけです。unset は親のファイルから引き継いだ値を打ち消すためのものですが、これは最上位のファイルなので打ち消す相手がなく、行がないことが同じ意味になります。書いてはいけないのは max_line_length = 0 で、このツールも以前はそう出力していました。仕様は対応していない値を無視するようプラグインに求めているため、上限 0 は上限 0 にはならず、何も起こらない行にしかなりません。

いいえ。EditorConfig は空白と改行コードを、どのエディタでも、つまりチームメンバーが使っていてあなたが使っていないエディタでも同じように扱います。Prettier や言語ごとのリンターは、クォート、セミコロン、末尾のカンマといった、より踏み込んだスタイル規則を担当します。両者は互いを補い合う関係で、Prettier は基本的な設定をあなたの .editorconfig から読み取ります。

YAML がインデントにタブ文字をまったく認めていないからです。タブでインデントしたワークフローや compose のファイルは、どのツールが読むより前の段階で構文解析に失敗します。ジェネレーターは他の場所ではタブを維持し、YAML のセクションだけを上書きします。上書きしたときは、ファイルの上にその旨を表示します。

リポジトリ内の Windows 向けツールが実際に必要としているなら end_of_line = crlf を設定します。たいていは、ここでは lf にしたうえで .gitattributes に * text=auto を書くほうが良い選択です。こうすると git がコミット時に改行コードを正規化し、チェックアウトでは OS に合った改行になります。

選んだ内容はファイルの組み立てに使われ、ステップ間ではページのリンクに含めて引き渡されます。設定を共有したりブックマークしたりできるのはこのためです。ページを生成した後、サーバーには何も保存されません。

関連ツール

このツールは他の言語でも利用できます