こんにちは!
モンスターストライク(以下、モンスト)でサーバーエンジニアをしている山田です。
モンストのサーバーサイドアプリケーションでは、Ruby をベースとした技術スタックを採用しています。今回のテーマである ERB(Embedded Ruby)は、社内向けの管理ツール群で広く利用されています。
本記事では、モンストのサーバーサイド全体にあるerbに対し、erb_lintをかけている際にぶつかった問題とその問題の解決方法について書きます。
そもそもerb_lintって何?
RuboCopのように、ERBファイルのコードスタイルを整えるツールです。
不要な空白やインデントのズレ、タグのスペースなどを検出してくれます。
一部は自動修正も可能(--autocorrect)となっています。
今回発生した問題点
あるerbに対し、erb_lintをautocorrectでかけたところ下記のような問題が発生しました。
ここではsampleを例として出します。
実行前
<input type="text"
class="form-control"
name="example_date" id="example_date"
value="aaa">
</input>
↓
実行後
<input type="text"
class="form-control"
name="example_date" id="example_date"
value="aaa">
<input>
??? ということでなぜかinputタグが1つ増えました😇
いったいなぜ、、、
大前提
さて、今出したHTMLですが、そもそも文法として間違えています(ぇ
タグはVoid element(空要素)にあたるので、本来閉じタグはいりません。
なので、上記は間違えているのですが、このように誤った</input>タグを使用していたとしても、ブラウザは「無視して処理を続ける」という動作を行うため、現在まで誤っていても特には問題にならなかったわけです。
https://developer.mozilla.org/ja/docs/Glossary/Void_element
ですが、今回erb_lintをかけたことにより、このVoid elementを閉じてしまっているタグが勝手に通常のタグに戻されてしまい、問題が表面化してきました。
では何が起きたのか
答えはerb_lintのテストにありました。
こちらのテストを見ると、入力値</br>が期待値<br/>となっていることがわかります。この<br>、実は<input>同様、Void element(空要素)であるため、</br>というタグは存在しません。
そのため、</input>でも同様の挙動がなされるということになります。
つまり、この挙動はerb_lintのAuto Correctで想定されていた動作で、誤った終了タグを置くと、自動で有効なタグに置き換えられてしまうということでした😇
その証拠にSELF_CLOSING_TAGSにも記載があります。
つまり、これはerb_lintで想定された通りでした。そ、そんな、、、😭
これに対して何を行ったか
今回の問題の原因がわかったので、全てのerbファイルから誤った終了タグを使用している箇所を探し出しました。具体的には、上に記載のあるSELF_CLOSING_TAGSに該当するタグの閉じタグをerb内から探し出し、それを全て除去しました。
これにより、タグが強制的に置き換えられ、意図していない挙動をするケースを取り除くことができました。
まとめ
今回はerb_lintをかけている際に発生した問題とその解決策を示しました。
現状も全てのerbに対し、erb_lintをかけておりますので、全てかけ終わった際には、また記事にしたいと思います。
最後まで読んでいただき、ありがとうございました。