1
/
5

RubyKaigi 2023 参加記 #9 - Yet Another Ruby Parser(Day 2)

Photo by Markus Winkler on Unsplash

こんにちは! Wantedlyでエンジニアをしているnasaです。
本記事では2日目のセッション「Yet Another Ruby Parser」について紹介していきます。

本セッションは、Shopifyが開発している新しいRubyパーサーYARPに関するものでした。新しいパーサーを開発するモチベーションや技術的に困難だったことが話されていました。

YARPの状況

YARPは現時点のRubyの構文は100%カバーしているようです。
開発が始まったのが6ヶ月前なのでものすごい開発スピードだと思いました。

ShopifyやGitHubなど複数の大規模アプリケーションで動作確認を行い、問題なく動作することを確認したようです。またCRubyだけでなくJRuby, TruffleRubyでも動作するようです。

どこまで難しいことなのか分かりませんが、半年でここまで出来ることに驚きです。相当開発力が高い組織だと感じました。

参考までにYARPのコード量を貼っておきます(もしかしたらRuby parserのコードを拝借しているのかも?)

:) % tokei
===============================================================================
 Language            Files        Lines         Code     Comments       Blanks
===============================================================================
 C                      43        19043        16709          940         1394
 C Header               19         1591         1029          264          298
 Java                    1           11            7            0            4
 JSON                    2          129          129            0            0
 Makefile                1           44           32            2           10
 Rakefile                7          701          528           48          125
 Ruby                 1830        77595        75034          403         2158
 Ruby HTML              11         1016          879            0          137
 Plain Text              1           25            0           20            5
 TypeScript              1          199          120           53           26
 YAML                    3         1897         1830            0           67
-------------------------------------------------------------------------------
 Markdown               14          633            0          459          174
 |- C                    2           68           33           26            9
 |- Ruby                 2           25           19            1            5
 (Total)                            726           52          486          188
===============================================================================
 Total                1933       102884        96297         2189         4398
===============================================================================

Yet Another Ruby Parser

なぜ新しいRubyパーサーが必要なのでしょうか?
YARPは下記の3つのモチベーションから開発が始まりました。

  • エラートレラント
  • ポータビリティ
  • 保守性

それぞれ説明します。

エラートレラント

エラートレラントはその名の通り、パーサーで何か問題が発生した場合でも可能な限り意味のある結果を返却することです。

本来パーサーはASTを作ることが責務でしたがLSPのことを考えると不十分です。
LSPは常にソースコードをパースして開発者にとってよりより情報を返却するかと思います。このときソースコードは開発者によって絶え間なく変更されています。

そのため下記のようなシンタックスエラーとなるコードが存在するタイミングがあり、パーサーはこれを扱う必要が出てきます。

def main
  puts "hello"

上記のコードだとendが無いので補完やユーザーへのレポートがあると開発者フレンドリーですね。

このようにシンタックスエラー時でも開発者にとって有益な情報を返却することがパーサーには求められています。

LSPを例として説明しましたが、その他の開発ツールやRubyインタプリタのエラーメッセージでも活用できそうですね。(Rustだとエラーメッセージがかなり充実しているのでRubyもそうなるととっても嬉しいです!)

ポータビリティ

現状のRubyのパーサーはCRuby, JRuby, TruffleRubyで分散しています。またRuby処理系だけでなくsorbet, steep, ruby-lspなどの開発ツールにもパーサーが実装されています。(5~10個は紹介されていましたが忘れてしまった、、)

この状況を解決するために、YARPはRuby以外の実装やツールでも利用可能なパーサーを目指しているようです。

ポータビリティ実現のためにこれらの設計方針を取っているようです。

  1. CRubyの内部構造に依存しない: YARPはCRubyには依存せず、独立した構造として開発されています。
  2. 外部のパーサージェネレーターやツールに依存しない: 外部のパーサージェネレーターやツールに依存しない。これにより、他の実装やツールでもYARP組み込むことが出来る。

保守性

現状のRubyパーサーの保守性には言及してなかったので、なにか課題感があって〜という話では無さそうです。(聞き逃してないならば)

僕の想像ですが、ポータビリティを上げ様々なプロジェクトから使われる様になった場合更に保守性に気を使う必要が出てきたんですかねー。

YARPではドキュメントとテストカバレッジにフォーカスして保守性が高い状態を維持しているようです。

ドキュメンテーションは、コントリビューター向けの開発プロセス、アーキテクチャ、提供しているAPIなど様々なものがあります。

off topic

YARPのセッションについては以上です。
RubyKaigi2023ではYARP以外にもパーサーのセッションがありLramaというRubyパーサーが紹介されていました。

https://rubykaigi.org/2023/presentations/spikeolaf.html#day1

ここからはYARPとLramaについて共通点や差異を書いてみようとも思います。
ただし、あまり踏み込んだ話は出来ないので浅い話です。

共通点

保守性の話はYARPのみでしたが、error tolerantやポータビリティの話は共通していました。
最近のRubyの情勢(?)は追えていませんでしたがかなりホット分野なのでしょうか?

実装方針はかなり違うようですが目指す世界は共通しているようですね。

差異

個人的には、実装方針がかなり違うなと思っていてLramaはCRubyと同じくパーサージェネレーターを使う方針ですがYARPはジェネレーターを使わず手で実装されています。

僕はパーサーに詳しくないので現時点ではよく分かっていませんが、この実装方針の差異が今後どのように影響していくのか興味があります。

余談ですが、Lramaのセッションでパーサージェネレーター(というかLRパーサー)はDSLの表現力が足りていないだけでまだまだやれるんだぞ!と話されていました。

感想

RubyKaigi2023ではパーサーに関するセッションが多くある印象です。(僕は3つ聞いた)
馴染みのない分野だったので難しく面白いと感じました。僕のようにパーサー面白そう!と感じた人は多く居たのではないでしょうか?
本記事の読者の中にも興味を持ってくれた人がいれば嬉しいです。

Lrama、YARPの今後が楽しみです!

最後に参考になりそうなリンクを張っておきます!今後より深く理解して発信できたらと思います。

Wantedly, Inc.からお誘い
この話題に共感したら、メンバーと話してみませんか?
Wantedly, Inc.では一緒に働く仲間を募集しています
5 いいね!
5 いいね!

同じタグの記事

今週のランキング

近藤 アサンさんにいいねを伝えよう
近藤 アサンさんや会社があなたに興味を持つかも