こんにちは。
GMOアドマーケティングのR.Sです。
今回はRuby3.1で追加された新機能の 「error_highlight」 を使うことで何が良くなるのか見ていこうと思います。
error_highlightとは
Ruby3.1で追加された新しい機能で、名前の通りエラーの該当箇所をわかりやすく表示してくれます。
NameErrorが発生した時に表示されるので、どれくらい便利なのか試してみようと思います。
動作環境
- Ruby 3.1.3
今後、Rails7の機能なども試すかもしれないので、今回は下記の記事を参考にDocker上にRails7とRuby3.1で環境構築しました。
比較してみる
導入前後で表示がどのように変わるかコンソールで軽く確認します。
まずは定義されてない変数を参照してみます。
- Ruby2.6.9の場合
1 2 3 4 5 6 7 |
irb(main):001:0> name = "名前" => "名前" irb(main):002:0> nama NameError (undefined local variable or method `nama' for main:Object) Did you mean? name |
- error_highlightが導入されたRuby3.1以降の場合
1 2 3 4 5 6 7 8 9 10 |
irb(main):001:0> name = "名前" => "名前" irb(main):002:0> nama (irb):2:in `<main>': undefined local variable or method `nama' for main:Object (NameError) nama ^^^^ Did you mean? name |
確かにハイライト表示されています。
導入前よりはぱっと見でわかりやすくなった気がしなくもないです。
が、これくらいのエラーならハイライト表示がなくてもNameErrorをちゃんと読めば大丈夫そうですよね。
ハッシュやJSONデータの取り扱いのときに本領発揮するらしいので、試してみます。
- Ruby2.6.9の場合
1 2 3 4 5 |
irb(main):001:0> hash = { apple: { price: 100, stock: 200 }} => {:apple=>{:price=>100, :stock=>200}} irb(main):002:0> hash[:orange][:price] NoMethodError (undefined method `[]' for nil:NilClass) |
- Ruby3.1以降の場合
1 2 3 4 5 6 7 8 |
irb(main):003:0> hash = { apple: { price: 100, stock: 200 }} => {:apple=>{:price=>100, :stock=>200}} irb(main):004:0> hash[:orange][:price] (irb):4:in `<main>': undefined method `[]' for nil:NilClass (NoMethodError) hash[:orange][:price] ^^^^^^^^ |
hash[:orange]がnilの場合はこういう表示になるようです。
確かに undefined method []’ for nil:NilClass (NoMethodError) だけよりわかりやすくなっています。実際にどんなときに使える?
受け取ったパラメータを参照するとき、- paramsがnil
- params[:data]がnil
なので、
1 2 3 |
p params p params[:data] |
のような形で出力して原因特定が必要です。(個人的にはRailsでのアプリ開発あるあるだと思う)
それをしなくて良くなるので、開発が結構楽になりそうな予感がします。
まとめ
今回はRuby3.1から導入されたerror_highlightを試して比較してみました。
視覚的にnilになっている部分がわかる良い機能に感じました。
Ruby3.1に組み込まれている機能なので、gemの追加などは不要です。
普段RubyやRailsを使って開発しているエンジニアの方は、試してみたくなる機能なのではないでしょうか。
おまけ
RubyKaigi2022で発表された「error_highlight: user-friendly error diagnostics」によると、Ruby3.2では、ArgumentErrorやTypeErrorでもハイライト表示されるようにアップデートされるみたいです。
さらに便利になりそう!