『Layered Design for Ruby on Rails Applications』、『Ruby on Railsパフォーマンスアポクリファ』
2023〜2024年ぐらいに出ていたRailsの本を後追いで読んだ1。
『Layered Design for Ruby on Rails Applications』
palkanさんによる。
- Packt: Layered Design for Ruby on Rails Applications: Discover practical design patterns and modern abstractions for maintainable Rails applications, Second Edition
- Amazon: Layered Design for Ruby on Rails Applications: Discover practical design patterns and modern abstractions for maintainable Rails applications
ただし、上記第2版が2025年に出ていたことに気づかず初版を買っていたので、読んだのは初版… 第2版はステートマシンや、LLMなどを扱う抽象層について加筆されているらしい。
概要
過剰な責務を抱えたモデルの保守性を上げるには、適切な粒度の責務をモデルから引き出して、必要十分なインタフェースを持つ抽象として整理する必要がある。本書では、レイヤードアーキテクチャのようなアーキテクチャパターンを参照しつつ、Webアプリの文脈でよく採用される抽象(わかりやすいものだとフォームオブジェクトやプレゼンターなど)を用いて、Railsらしく抽象層を積み上げていく方法をまとめている。そして、そのような設計の方法を「The Extended Rails Way」と呼んでいる。
流れとしては、まず執筆時点(2023年時点)で、Railsのコンポーネントがどのような抽象化を提供しているかについて解説している。そして、責務過剰なモデルに対して安易に適用されやすいサービスオブジェクトパターンと、その問題点について指摘する。それを受けて、サービスオブジェクトより適切な抽象を用いてモデルの責務を減らす方法と、モデル以外で必要になる抽象層のそれぞれを紹介している。2020年代に書かれた本として、わりあい最近に開発が活発なgemの紹介も多い。
感想
これまで類似の話題を扱ったものとして、『パーフェクトRuby on Rails【増補改訂版】』のPart 3があった。一方、本書は1冊を通して、モデルだけではなく、認可やアプリケーション設定周辺の設計にも踏み込んでいる。この点で、しばらく経験を積んでRailsの長短がわかってきた開発者が知っておきたいような、体系的な知識が手に入れられるようになっている。
本書では、実装方法として抽象層の基底クラスを作って規約を持ち込んだり、技術的側面で分けたディレクトリを抽象層として配置したりといったアプローチを採用している。個人的には、Railsの「モデル」はPoEAA的なドメインモデル以外でもよい、つまりActive Model互換なクラスと、関連するPOROも含めてapp/modelsに置いてよいと思っている。しかし、構造を強制するほうが開発がスケールしやすいこともあるだろうし、場合によるとは思う。
気になったところは、Active Recordを返すリポジトリを導入しようとする議論が生煮えで終わっていた点。実装として完全ではない旨の断りはあったが、リポジトリの元来の目的はデータストアの実装詳細を隠すことにあり、Active Recordオブジェクトを返すという設計だと実装詳細が漏れてしまうので、あまり意味をなしていないように感じた。混乱する読者もいそうなので、なくてもよかったのでは。
『Ruby on Railsパフォーマンスアポクリファ』
概要
Nateさんによる、Railsアプリのパフォーマンス改善のために必要な知識を簡潔にまとめている本。メールマガジンをまとめたものなので、1つ1つの項目が短く読みやすい。
内容としては、Railsアプリの計測方法、基礎となるPumaやRuby GVLの挙動、アムダールの法則を考慮したスレッド数やクラウドサービ上でのVMスペックの選定などが取り上げられている。フロントエンドや、自動テストの速度についての話題にも少し言及している。
感想
メールマガジンの再編集かつ分量が少なめなので、割とすぐに読めて、これまで手薄だった知識を補強できたのが助かった。具体的には、rack-mini-profilerについてや、GVLの時分割の概要、シェルコマンド実行への委譲などでも(GVLを解放して)実質的にマルチコア処理されるという話など。
他にはテストの速度についての話が印象に残っている。基本的な著者のスタンスは、Minitestのシンプルさやマルチスレッド機能によって、わかりやすくて速く、マルチスレッド下の挙動も検証できるテストを実現できる、というものである。RSpecの過度な複雑さや、FactoryBotを使ったテストセットアップの遅さについてはしっかり批判されている(少し単純化しすぎな点もありそうだが)。また、
テストは100アサーション/秒(RSpecであればexample/秒)かそれ以上の速度で実行する必要があります。速いテストは有用です。これより遅い場合、99%はデータベースやFactoryBotの使い方に問題があります
と書いてあって背筋が伸びる。
脚注
-
この時期Railsから離れていて優先度が下がったままだった ↩