djangoテンプレートファイルのコードフォーマット（コード整形）はVSCodeが一番でした

# 概要

Djangoのテンプレートファイルのコードフォーマット（コード整形）に適したツールを調べてみた結果です。対象はEclipse+PyDev、VSCode、PyCharmです。

# 背景

当方はDjangoを活用したWebアプリケーション開発をEclipse＋PyDevプラグインで行っています。Pythonは動的言語なのでエディタの機能はあまり期待してなかったのですが想像以上に快適でした。コード補完は効きますし定義元への移動も可能。

もちろん「import候補を提案してくれたらなぁ」などJava等の静的言語環境と比較すると劣るところはありますが許容範囲です。が、一点だけ「これは困る」というのがあり、それはテンプレートファイルのコード整形が使えないことでした。

例えば以下のように場所を移動してインデントが乱れたタグをフォーマットすると、、、

```html
{% extends "base_main_content.html" %}

{% block menu_items %}
            <ul class="nav flex-column">
	         {% for menu_item in menu_items %}
              <li class="nav-item">
	           {% if menu_item.is_title %}
                  <p class="h6"><i class="{{ menu_item.icon_class }}"></i> {{ menu_item.name }}</p>
	           {% else %}
                <a class="nav-link {% if request.path == menu_item.path %}active{% endif %}" href="{{ menu_item.path }}">
                  <i class="{{ menu_item.icon_class }}"></i> {{ menu_item.name }}
                </a>
              {% endif %}
              </li>
	         {% endfor %}
            </ul>
{% endblock %}
```

こんな悲惨なことになります。どんなルールになっているのかさっぱりわかりません。涙

```html
{% extends "base_main_content.html" %} {% block menu_items %}
<ul class="nav flex-column">
  {% for menu_item in menu_items %}
  <li class="nav-item">{% if menu_item.is_title %}
    <p class="h6">
      <i class="{{ menu_item.icon_class }}"></i> {{ menu_item.name }}
    </p> {% else %} <a
    class="nav-link {% if request.path == menu_item.path %}active{% endif %}"
    href="{{ menu_item.path }}"> <i
      class="{{ menu_item.icon_class }}"></i> {{ menu_item.name }}
  </a> {% endif %}
  </li> {% endfor %}
</ul>
{% endblock %}
```

# 結論

VSCodeが良かったです。上述した例だと以下のようになります。

```html

{% extends "base_main_content.html" %}

{% block menu_items %}
<ul class="nav flex-column">
    {% for menu_item in menu_items %}
    <li class="nav-item">
        {% if menu_item.is_title %}
        <p class="h6"><i class="{{ menu_item.icon_class }}"></i> {{ menu_item.name }}</p>
        {% else %}
        <a class="nav-link {% if request.path == menu_item.path %}active{% endif %}" href="{{ menu_item.path }}">
            <i class="{{ menu_item.icon_class }}"></i> {{ menu_item.name }}
        </a>
        {% endif %}
    </li>
    {% endfor %}
</ul>
{% endblock %}
```

以下のStackOverflowの投稿だと「VSCodeで間違って整形しまうまでVSCodeが好きでした。どうすれば無効化できる？！」的な質問があったので、期待してなかったのですが、その投稿から２年経過するうちに進化したようです。バッチリです。Djangoテンプレートの特殊タグの配置・改行などなんら問題ありません。

[vscode html autoformat on django template - Stack Overflow](https://stackoverflow.com/questions/42170561/vscode-html-autoformat-on-django-template)

インストールしたままの設定だと120文字で折り返されてしまうので、そこだけ調整（無制限）にしました。これで長い行を維持しておきたい箇所（例えばCDNからスクリプトやCSSを読み込んでいる場合）も期待どおりになりました。

**設定画面の表示**
![](https://i.gyazo.com/e1744e0f17d643f7d9545dca8783a60d.png)

**折り返り文字数（`html.format.wrapLineLength`）を無制限**
![](https://i.gyazo.com/30b86e917be7fa4df169cff8776c9017.png)

[【参考】VSCodeのフォーマット設定項目](https://code.visualstudio.com/docs/languages/html#_formatting)

ちなみ前述したEclipse上でグチャグチャになったコードは直してくれませんでした。VSCodeは元の構造を維持することを重視しているのかもしれません。

詳細は調査していませんがVSCodeがhtmlで整形しているのはインデントや閉じタグ前のスペース付与とかだけかもしれませんが、テンプレートで整形したいことの大半はそこなので全く問題ありません。

それにしてもVSCodeいいですね。現在は小さなPythonスクリプト開発で利用している程度ですが、VSCode用のPyDev（[PyDev on VSCode](http://www.pydev.org/vscode/)）も鋭意開発中（デバッガーが未実装）されているようですし、どこかで試してみようと思いました。

ちなみにPyCharmも試しましたが、微妙な感じ（例えば`{{ xxx }}`の途中で改行されてしまう）でした。（調整できるのかもしれませんが。）