【Rome v10】垂直統合ツールチェーンRomeがついにstableになったよ

# Romeってなに？

フロントエンドはいまだに混沌の極みです。
○○には××、△△には□□、🌝🌝には♨♨、といった具合で様々なツールを駆使しなければなりません。
異なる作者が作っている異なる思想のツールの詰め合わせなので、ツールによっては設定項目が喧嘩したり、無意味な設定があったり、設定ファイル形式が異なるなんてこともよくあります。
それらをどうにかするためにツール詰め合わせツールなんてものも現れていますが、広範に対応するため最大公約数的な設定しかなされておらず、細かく調整するには結局それぞれのツールについて深く知らなければなりません。
私は単にWebサイトを作りたいだけであって開発環境構築マニアではないので、そんな面倒なことをやりたいわけではないんだ。

ということで、そんな混沌をどうにかすべく登場したのが[Rome](https://rome.tools/)です。
最初から最後までをひとつの設計思想で貫き通すことで、設定が容易になり、無駄を省き、高いパフォーマンスを発揮します。

で、Romeは元々JavaScriptで書かれていたのですが、JavaScriptだとどうしても遅いということで一年前に[JavaScriptからRustに移行する](https://qiita.com/rana_kualu/items/dcadf11b3e97db1dded6)と発表しました。
そしてついに先日2022/11/08、stable版が公開されました。

以下は公式ブログのRome v10リリース記事、[Announcing Rome v10](https://rome.tools/blog/2022/11/08/rome-10.html)の日本語訳です。


# Announcing Rome v10

**Rome v10**を発表できることをうれしく思います。
[Rustへの書き替え](https://rome.tools/blog/2021/09/21/rome-will-be-rewritten-in-rust.html)を始めて以来、初めての安定版リリースとなります。
Romeは、数十種類は存在するフロントエンドツールを、たったひとつの冴えたツールに統一するためにゼロから構築された、全く新しい野心的なプロジェクトです。

このリリースには、高速なLinterとFormatterが含まれています。
これらに必要な設定は最低限であり、美しくもわかりやすい分析を行い、そしてJavaScriptとTypeScriptを最初からサポートしています。

Romeの[Formatter](https://rome.tools/blog/2022/04/05/rome-formatter-release.html)はPrettierにインスパイアされており、ほとんどのユーザはほんのわずか、もしくは一切の変更なしに移行が可能です。
[Linter](https://docs.rome.tools/lint/rules/)はコミュニティの標準に従った推奨ルールセットに基いており、そして問題が検出されれるとすぐに対処できるような情報提供を行います。

ここまでの話は、まだまだ始まりにすぎません。
来年には他のフロントエンド言語のサポートが予定されています。
さらにコンパイル、バンドル、テストなど、残るRomeスタックの実装を進めていきます。


## Getting Started 

Romeを始めるのに必要なコマンドはたった3つです。
`package.json`のあるプロジェクトで実行してください。

```rust
# インストール
npm install --save-dev rome

# 作成
npx rome init

# Formatter
npx rome format <files>

# もしくはLinter
npx rome check <files>
```

我々は、我々がRomeを作るときに感じた楽しさと同じくらい、あなたがRomeを使うことを楽しむことを願っています。
もし何か問題があれば、[Discord](https://discord.gg/rome)の`#support`チャンネルや[GitHub](https://github.com/rome/tools)に報告してください。

[ドキュメント](https://docs.rome.tools/)
[VSCodeエクステンション](https://marketplace.visualstudio.com/items?itemName=rome.rome)


どうして我々がRomeを作ろうと思ったのか、そしてRomeが他のWebエコシステムと何がちがうのか、興味がある方は是非以下も読んでみてください。

## Why Rome?

### Traditional approach

これまでのアプローチ

Web開発のエコシステムは、開発サイクルにおける様々なニーズを満たすための様々なツールが豊富に存在します。
例として有名なツールのごく一部を紹介します。

コードフォーマッター：Prettier, dprint
Linter：ESLint, Stylelint
テストランナー：Vitest, Jest, AVA
トランスパイラ：Babel, SWC, TypeScript
バンドラ：webpack, esbuild, Vite, SWC, Rollup, Parcel

選択肢が豊富なことはいいことです。
しかし、あなたがそれらを評価し、インストールし、設定に費やす時間は、あなたがプロジェクトに取り組んでいない時間です。
ツールスタックを揃えることは仕事より前の話であり、プロジェクトに合わせてそれらを維持し継続していくには、専門的な知識と継続的な時間の投資が必要です。

この問題点は、[Create React App](https://create-react-app.dev/)が100k近くのスターを集めていることからも明らかです。
Create React Appは、既存のツールを取り集めることでReactの開発スタックを提供します。

このアプローチの問題点は、それらのツールスタック全てを隠蔽しきれないことです。
多くのツールは、それぞれ異なるフォーマット、異なる設定、異なる開発環境を使用しています。

### Our approach

我々のアプローチ

Romeはゼロから作られた、[モノリシックなアプリ](https://en.wikipedia.org/wiki/Monolithic_application)です。
そこには依存のないフォーマッターとLinterがあり、そして今後はコンパイラ、バンドラ、テストランナーなども参加します。
このモノリシックなアーキテクチャは、これまでの多くのツールが寄り集まった開発スタックでは実現することのできない、新しい開発者体験の扉を開きます。

・不要な作業の削除

Prettierでファイルを整形し、ESLintで検証することは、同じファイルを2回パースするということであり、不必要な時間を費やすことを意味します。
Romeが高速である理由は、同じことを2度行わないからです。
たとえば開発中にファイルの検証を既に行っていた場合は、バンドル時にはファイルのパースすら行いません。

・繰り返しを減らす

Romeは、プロジェクト内の設定ファイルの数を減らし、設定の繰り返しを避けるため、全てのツールを1つの設定ファイルで管理します。
ESLintとwebpack両方の設定ファイルにReactプラグインのための設定を追加するなんてことは必要ありません。
ReactのLinterとJSXトランスパイラとFastRefreshの設定を有効にするために必要な変更は、一か所です。

・学ぶのは一度でいい

複数のツールを使う開発スタックでは、エンジニアは各ツールについてそれぞれコマンド、設定、コマンドライン引数、出力フォーマットを学習し、覚えなければなりません。
RomeはCLI引数や出力形式が全て標準化されており、一度だけ覚えればもうそれ以上覚える必要はありません。

・低い参入障壁

バンドルサイズの調査や調整といった高度な分析や確認は、しばしば追加のツールが必要となり、既存のエディタやLinterと有機的に結合されていません。
このような複雑さは多くの人にとって高い参入障壁となっており、CIパイプラインやオートメーションへの組み込みに困難をもたらします。

Romeはエディタファースト設計とエンドツーエンドアーキテクチャにより、その障壁を大幅に低減します。
エディタに情報を取り込み、CIとして実行可能なLint情報を表示します。

我々は、これらのアーキテクチャによって実現される機能に対して、みなさんが我々と同じくらい期待してくれることを願っています。

複数のツールを集めてツールチェーンを作り上げることは、必ずしも開発者に良い体験を保証するものではありません。
それぞれのツールは個別に、それぞれの価値をもたらすものでなくてはなりません。

次のセクションでは、我々の新しいLinterについて、それがどのように開発者体験を向上させるか解説します。


## New Linter 

RomeのLinterは、導入しやすく、エディタと統合されており、わかりやすい診断結果を出すように心がけています。

JavaScript、TypeScript、JSX、Reactの[60以上のルール](https://docs.rome.tools/lint/rules)をサポートしており、6000ファイルを300ms以下で処理できます。

次のセクションでは、なぜエラーリカバリがエディタ統合に不可欠なのか、そして我々の診断に対する哲学を表明します。


### Error Recovery 

エディタ統合に不可欠なのは、エディタと同様にシンタックスエラーを優雅に処理することです。
たとえばエディタのコードハイライトは、コードにシンタックスエラーが含まれていても変わらずに機能し続けます。
すなわち、Linterでは、ファイル内のシンタックスエラーによって別のエラーや警告が消えてはいけないということです。

この問題について、ESLintと、RomeのVSCode拡張の挙動を比較する画像を作成しました。
ESLintでは、`==`のところにもっと厳密な等式使うことを推奨する警告が現れたり消えたりしますが、Romeでは常に表示され続けます。

![eslint-rome-comparison.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/26088/8af64ca5-a3fb-df0e-ac1b-9de9d1125ee9.gif)

左がESLintを導入したVSCode、右がRomeを導入したVSCodeです。
いずれのエディタでも、`if(a == b)`の部分に警告が表示されます。
ESLintでは、ユーザが未完成のコード`console.`を追加すると警告が消えてしまいます。
`console.log("Test")`まで完成させると、ようやく警告が復活します。
Romeでは、警告がずっと消えないようにシンタックスエラーを優雅に処理しています。

Romeは、エラーに強いパーサとASTの設計により、シンタックスエラーの存在するファイルについてもLintすることができます。
ASTの設計については、[Rust rewrite blog post](https://rome.tools/blog/2021/09/21/rome-will-be-rewritten-in-rust.html#whats-the-deal-with-abstract-syntax-trees)の記事で詳しく解説しています。


### Rich and Comprehensible Diagnostics 

リッチでわかりやすい診断結果。

診断結果を読んで理解することは、ソフトウェアエンジニアの仕事のひとつです。
だからこそ、診断結果をいくら読んでも意味がわからないなんてことはあってはならないことです。

Romeは、何が問題なのか、なぜ問題なのかを明示し、場合によっては修正を促すような、[非常に高い水準の診断結果を出力します](https://github.com/rome/tools/blob/main/crates/rome_diagnostics/CONTRIBUTING.md#what-is-a-diagnostic)。
単に結果を伝えるだけでなく、コードや差分などのリッチコンテンツも表示するため、より理解が早まるでしょう。

例として、以下のコードの診断結果を見てみましょう。


```js
function test(callback) {
  try {
    return callback();
  } catch (e) {
    console.log(e);
    throw e;
  }

  return 20;
}
```

こうなります。

```js
  main.tsx:9:3 lint/nursery/noUnreachable ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
  
    ✖ This code will never be reached ...
    
       7 │   }
       8 │ 
     > 9 │   return 20;
         │   ^^^^^^^^^^
      10 │ }
    
    ℹ ... because either this statement will return from the function ...
    
      1 │ function test(callback) {
      2 │   try {
    > 3 │     return callback();
        │     ^^^^^^^^^^^^^^^^^^
      4 │   } catch (e) {
      5 │     console.log(e);
    
    ℹ ... or this statement will throw an exception beforehand
    
      4 │   } catch (e) {
      5 │     console.log(e);
    > 6 │     throw e;
        │     ^^^^^^^^
      7 │   }
      8 │ 
```

このコードは`return 20`に決して辿り着かないことを報告し、さらにコードから問題のあるステートメントを分析します。

今のところ、さすがに全ての診断がここまで詳細な出力をするわけではありませんが、我々は時間をかけて改善していく予定です。
もし診断結果に理解できないようなところがあれば、[issueを出してくれるようお願いします](https://github.com/rome/tools/issues)。


## Try it. 

[ぜひRomeを試してみてください](https://docs.rome.tools/guides/getting-started/)。

Romeを採用したユーザからは、速度の大幅な改善、設定の簡略化、依存関係の大幅な削減、node_modulesフォルダサイズの減少などが報告されています。

https://twitter.com/lgarron/status/1568797657128382464
https://twitter.com/lgarron/status/1568797658692866050

まだインストールする気になれませんか？
それでしたら[Playground](https://docs.rome.tools/playground)で試してみてください。


## Acknowledgments

Romeは一日にしてならず。
多くの人々の協力のもとに成り立っています。
Romeを築くことに貢献してくれた全ての人に感謝します。
特に

### [Boshen](https://github.com/Boshen)

T262パーサのテストスイートとベンチマークをCIパイプラインに統合しました。
これはパーサのパフォーマンスを追跡するうえでのゲームチェンジャーになりました。
またTwitterやDiscordにおいて、RomeのJavaScript lexerやparserについての多くの貢献をしてくれました。


### [IWANABETHATGUY](https://github.com/IWANABETHATGUY)

20近くのLintルールの追加、playgroundのASTとシンタックスハイライト対応、JavaScriptパーサへの多くの貢献。

### [Denis Bezrukov](https://github.com/denbezrukov)

JavaScriptフォーマッタへの無数の貢献。
特にnodeの書式、JSXの空白の処理、末尾カンマなど。

### [rust-analzyer](https://rust-analyzer.github.io/)

rust-analzyerはRustを書くことを楽しくしてくれました。
またRomeの[AST表現](https://github.com/rome/tools/tree/main/crates/rome_rowan)や[パーサー](https://github.com/rome/tools/tree/main/crates/rome_js_parser)にインスピレーションを与えました。

### [RSLint](https://github.com/rslint/rslint)

特に[Stupremee](https://github.com/rslint/rslint/commits?author=Stupremee)と[RDambrosio016](https://github.com/RDambrosio016)に感謝を。
彼らはRomeがJavaScriptパーサと診断システムをforkできるよう手助けしてくれました。

### [Prettier](https://prettier.io/)

Romeのフォーマッターは、Prettierのアーキテクチャやスタイルに大きな影響を受けています。
PrettierがWebエコシステムのフォーマットに与えた影響は多大であり、我々はその足跡を辿るだけで時間と意思決定を削減することができました。

### [ESLint](https://eslint.org/)

RomeのLinterルールのほとんどは、ESLintの相応するものから採用しています。
これら推奨パターンを確立したESLintに大きく感謝します。
彼らの作業なしには、我々はこのような成果を上げることはできなかったでしょう。


# 感想

正直永遠のベータ版のままだと思っていたので、きちんとstableまで辿り着いたことにはちょっと驚きました。
それどころか開発も[非常に活発](https://github.com/rome/tools/commits/main)であり、今後も期待できそうなプロジェクトですね。

ただまあ[Webサイト](https://rome.tools/)を見てわかるとおり、coming soonな項目がまだいくつもあるため、今すぐ本番導入というのは少々難しいかもしれません。
というか、現状だと正直ただのLinterですね。

![02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/26088/0dae306c-b2b6-4783-04a9-d98be3dccb56.png)


はやいところワークフローの完成まで辿り着いてほしいところです。
最新技術を駆使した結果1行変更してデプロイに30分みたいな本末転倒が散見される昨今、Romeを導入することでユーザ体験がいったいどれほど劇的に変わるのか、楽しみなところです。