Money Forward Developers Blog

株式会社マネーフォワード公式開発者向けブログです。技術や開発手法、イベント登壇などを発信します。サービスに関するご質問は、各サービス窓口までご連絡ください。

20230215130734

10年もののRailsアプリの持続可能性を求めて -なぜ初手でCoffeeScript廃止を選んだのか-

シニアソフトウェアエンジニアのusadamasaです。 マネーフォワード クラウド会計とそれに関連するマイクロサービス群の開発運用を担当しています。
本記事では、クラウド会計という10年もののRailsアプリの持続可能性をいかにして確保していくかの取り組みをご紹介します。

TL;DR

私が所属するチームでは、クラウド会計の開発運用における課題を整理し、それぞれの課題に対して解決策を検討し、実行するための取り組みを進めています。
最初にクラウド会計の全体の構造を明らかにし、課題を可視化、組織の共通認識としました。
その上で銀の弾丸を求めるのではなく、有期かつ漸進的な改善のプロジェクトとして計画することが成果に繋がります。

クラウド会計の現状

クラウド会計はマネーフォワード クラウドの代表的なプロダクトの一つです。 2013年にリリースされてから10年、多くの機能追加や改善を重ね、現在では沢山の事業者様に利用されています。
しかしながら、その10年の間、社会におけるソフトウェア技術は大きく変化し、社内外の環境にも変化がありました。 クラウド会計についてもその変化により、開発運用において以下のような課題が生じています。

  • コードベースの肥大化と複数の技術スタックの混在
  • 開発者の入れ替わりによる知識の喪失
  • リファクタリングの困難さ
  • アクセシビリティの向上に向けた取り組み
  • etc…

とりわけこれまでの現代におけるフロントエンド領域の技術スタックの変化は著しく、クラウド会計の開発当初からは大きく様変わりしています。 クラウド会計もそれらに追従すべく様々な取り組みをしているものの、10年もののコードベースすべてをその都度置き換えることは困難でした。 そのため、開発された時期によって異なる技術スタックや思想が採用されており、画面によっては全く異なるアプローチが取られています。

その状況をまとめたのが以下の図です。1

クラウド会計のアーキテクチャ図

緑がRubyの世界、オレンジがJavaScriptの世界を表現しています。 赤いマルとアルファベットは、技術方式を示しています。2

課題の整理

このような状況では以下の課題が生じます。

  • 開発者に要求されるスキルセットの多様化
  • ビルドシステムの複雑化
  • パフォーマンスの低下
  • リファクタリングの困難さ
  • コードベースの肥大化

もっとも強い課題感があったのは、開発者に要求されるスキルセットの多様化です。 図のようなCoffeeScript、Vanilla JS、TypeScriptすべての技術スタックに習熟している開発者は少数であり、その確保は困難です。 一方、開発者に学習を促し言語を習得してもらうというのも、合理的な技術スタックの組合せであれば妥当な判断でしょうが、歴史的背景によるものとなるとそうもいきません。 そして、自分が関われない領域というのはどうしても当事者意識が低下し、それによる品質の低下およびユーザ価値の提供の毀損に繋がります。

このようなアーキテクチャの図示と課題の整理によって開発者およびマネージャ層と認識を揃えていきました。 その結果、クラウド会計のフロントエンド領域では技術スタックの統廃合が必要である、という合意が形成されました。

戦略

さて、どのように統廃合すべきかですが、上述の採用市場の要素、開発組織内の過去の意思決定、そして作業の容易性から、 まずはCoffeeScriptを廃止することにしました。3

CoffeeScriptをVanilla JSに変換するには、Decaffeinateというツールを使うことで一定機械的に実現出来ることがわかっていました。
これは、いきなりReact化すること、つまりコンセプトの異なるアーキテクチャに移行することに比べるととてもリスクが低く、プロジェクトの予測可能性が非常に高いと判断できます。 そのため、CoffeescriptをVanilla JSに変換することを最初のステップとして取り組むことにしました。

Decaffeinateによる変換

DecaffeinateはCoffeeScriptをVanilla JSに変換するためのツールです。このツールについては、すでに沢山の記事で紹介されているため、ここでは詳細な説明は割愛します。

非常に様々な記事を参考にさせていただきましたが、いくつかの記事を掲載させていただきます。

作業を進めるにあたっての課題と対策

以降は具体的な戦術の話となります。

リリース戦略

DecaffeinateはBulk-decaffeinateというラッパーのツールを導入することで、一括での変換が可能です。 しかしながら、クラウド会計のCoffeeScriptファイルは、約250ファイル、2万行に及びます。
これらを一気に変換することは困難が伴うため、以下のようなステップで進めることにしました。

  1. 変換対象のファイルリストを作成し、それらの行数と課題を洗い出す
  2. 一部のファイルを変換し、その変換結果をレビューする
  3. 行数の少ないファイルから変換を進める
  4. 変換に問題がないことが確認でき次第、1ファイルずつデプロイ・リリースをする。

このように、一気に変換することはせず、段階を踏んで変換を進めることで、変換による問題とその対処を最小限に抑えられました。

他チームとの調整

本プロジェクトによる変換作業と同時に、他のチームでもフロントエンドの改修が発生することはわかっていました。 そのため事前に関連チームとの調整を行い、同時に触ることがないようにしました。 他チームの改修は、CoffeeScriptの変換よりも常に優先度を高く設定し、この取り組みが他チームの進捗に影響を与えないようにしました。

コード品質の期待感調整

Decaffeinateによる変換は、完璧な変換を保証するものではありませんし、リファクタリングをしてくれるものでもありません。 そのため、変換後のコードの品質については、レビュアーと期待感を調整する必要があります。 事前に合意したこととしては、明らかな不具合でなければ、変換後のコードについてはリファクタリングを行わない、ということでした。 また、デッドコードに関しては、対象ファイルがまるごと未使用の場合には削除するが、それ以外の場合にはそのままにする、としました。

周囲への共有

この取り組みは、実作業1名(私)、レビュアー1名の2名体制で進めました。 そのため、進捗状況を他チームに共有する場は特別なく、全体の報告会での共有程度でした。
しかし、この取り組みが他チームに影響を与えないようにするためには、進捗状況を共有することが重要と考えました。かといって全体に説明の場を設けることは大げさだと感じました。 そのため、メンバー層にまで状況を共有するための簡単な中間レポートを作成し、改善していっているという空気感を作りました。4

中間レポートをSlackで共有した様子

(小ネタ) Classと継承と変換順序

繰り返しになりますが、Decaffeinateによる変換は、完璧な変換を保証するものではないため、元の実装や変換の順序によっては問題が生じることがあります。 そのうちの1つをご紹介します。

CoffeeScriptおよびJavaScript(ES2015以降)にはそれぞれClassの構文がサポートされています。 ご存じのようにRailsのアセットパイプラインではCoffeeScriptはJavaScriptにトランスパイルされます。 私たちの設定ではCoffeeScriptのClass構文はES2015以前の構文に変換されるようになっていました。 これが原因で、親クラスと子クラスでCoffeeScriptとJavaScriptが混在するとその組合せによって実行時エラーが発生することがありました。

表にすると以下です。

親クラス 子クラス 動作
CoffeeScript CoffeeScript OK
CoffeeScript JavaScript OK
JavaScript CoffeeScript NG
JavaScript JavaScript OK

詳細な説明は避けますがClassのインスタンス化に纏わる現象でした。 この問題を回避するため、継承を用いたコードについては子クラス側から変換をするなどのケアが求められました。 私たちのコードベースではClassはごく少数の機能でのみ使われていたため軽微な計画変更で済みましたが、既存コードの設計スタイルによっては計画に大きな影響が出る可能性があります。

プロジェクトの状況

2023年8月から開始し、2024年3月末で無事完了しました。途中複数回の中断および年末年始があったため、全体としては6ヶ月程度の期間を要しました。 プロジェクト計画時点での見積もりとほぼほぼ合致する結果となり、満足しています。

今後の展開とまとめ

ようやく技術スタックの統廃合に向けたアクションが始まりました。 今回はすぐ得られる果実を求めての取り組みでしたが、今後はより大きなステップを踏んでいけると考えています。
引き続き、クラウド会計のアーキテクチャ的課題の解消に取り組んでいきます。

脚注


  1. この図を作るのに一ヶ月かかりました。
  2. 図はRailsアプリのフロントエンドに着目した図です。全体としては他プロダクトやマイクロサービスが存在します。
  3. 私自身はフロントエンド領域には明るくないため、周囲の意見を大いに参考にしました。
  4. プロジェクト中に明らかになったクラウド会計全体の課題を徐々に共有する意図もありました。