mooriii's blog

article icon

Honoはどうやってマルチランタイムを実現したのか?

最近本業でもHonoを使うようになり、ランタイム関係なく動かせることに感動しています。 そこで、どういった経緯でHonoがマルチランタイムに対応することとなったのか気になったので軽く調査してみました。

Honoとは?

Honoとは様々な環境で動く、超軽量&超高速なウェブフレームワークで、以下の特徴を持ちます。

  • ランタイムに依存しない
  • 高速かつ軽量
  • 充実したエコシステム(MiddlewareやAdaptorが豊富)
  • RPCによる型安全な開発

Web標準のAPIを利用することでゼロ依存を実現し、エッジランタイムでも高速に動作するように設計されています。

GitHub - yusukebe/hono: Ultrafast web framework for Cloudflare Workers, Deno, and Bun. Fast, but not only fast.Ultrafast web framework for Cloudflare Workers, Deno, and Bun. Fast, but not only fast. - yusukebe/hono
favicon of https://github.com/yusukebe/honogithub.com
ogp of https://opengraph.githubassets.com/ed720bf3abd0b9283cd709563abce020244b6300abad4bcdc7ceb1e02615b945/yusukebe/hono

どうやってマルチランタイムを実現したのか?

元々はCloudflare Workers向けのフレームワークとして作られた

今でこそDenoやBunなどいろいろな環境で動くフレームワークとして注目を集めていますが、元々はCloudflare Workersに特化したものとして作られていたそうです。

動機は単純で、Cloudflare Workersで動くアプリケーションを開発するためのフレームワークが世の中にあまりないと思ったこと。それから、ルータ1を自作してみたかったことも理由の1つですね。 -- 「Honoはあくまでオープンソースプロダクト」開発者でコントリビューターの私が会社員になった理由

「Honoはあくまでオープンソースプロダクト」開発者でコントリビューターの私が会社員になった理由 - Findy Engineer LabWebフレームワーク「Hono」の開発者である和田裕介(@yusukebe)さんに、Cloudflare入社後もオープンソース開発を仕事として続ける理由や、開発者のために開発したいというモチベーションについて伺いました。
favicon of https://findy-code.io/engineer-lab/yusukebefindy-code.io
ogp of https://cdn.image.st-hatena.com/image/scale/734ee3057b3870d4c09777ff9e74b5e43322a989/backend=imagemagick;height=1300;version=1;width=1300/https%3A%2F%2Fcdn-ak.f.st-hatena.com%2Fimages%2Ffotolife%2Fb%2Fblog-media%2F20240119%2F20240119115014.jpg

CDNエッジ&サーバーレスという制約

Cloudflare Workersはサーバーレス環境ということで、高速に起動することが求められます。 CDNのエッジで動かすということもあり、スクリプトサイズの制限がかなり厳しめです(1MB)。 さらに、(一部を除き)Node.js依存のモジュールが動かないという制約があります。

そのため(?)HonoではWeb標準APIのみを利用することで依存をゼロにし、軽量でかつNode.jsに依存しないことによる高速な起動を実現しています。

スクリプトのサイズが1MB以内、使えるAPIが極端に限られているなど制約がありますが、それはそれで単一機能のシンプルなアプリケーションを作る気にさせてくれます。

-- 略 --

もちろん外部モジュールを使うことが出来ますが、node.js依存のモジュールは動きません。というかモジュール、だいぶ動きません。そこで、上記のみのAPIを使って、依存ゼロの軽いフレームワークがあったらいいなと作りました。 -- Hono[炎]っていうイケてる名前のフレームワークを作っている

Hono[炎]っていうイケてる名前のフレームワークを作っている
favicon of https://zenn.dev/yusukebe/articles/0c7fed0949e6f7zenn.dev
ogp of https://res.cloudinary.com/zenn/image/upload/s--y8Q1KJtg--/c_fit%2Cg_north_west%2Cl_text:notosansjp-medium.otf_55:Hono%255B%25E7%2582%258E%255D%25E3%2581%25A3%25E3%2581%25A6%25E3%2581%2584%25E3%2581%2586%25E3%2582%25A4%25E3%2582%25B1%25E3%2581%25A6%25E3%2582%258B%25E5%2590%258D%25E5%2589%258D%25E3%2581%25AE%25E3%2583%2595%25E3%2583%25AC%25E3%2583%25BC%25E3%2583%25A0%25E3%2583%25AF%25E3%2583%25BC%25E3%2582%25AF%25E3%2582%2592%25E4%25BD%259C%25E3%2581%25A3%25E3%2581%25A6%25E3%2581%2584%25E3%2582%258B%2Cw_1010%2Cx_90%2Cy_100/g_south_west%2Cl_text:notosansjp-medium.otf_37:yusukebe%2Cx_203%2Cy_121/g_south_west%2Ch_90%2Cl_fetch:aHR0cHM6Ly9saDMuZ29vZ2xldXNlcmNvbnRlbnQuY29tL2EtL0FPaDE0R2pIMWY1VlpnSFMwLUJwekhzZjRGYXN0R1ZYTlpfZFh1U2pwdWNMNGc9czI1MC1j%2Cr_max%2Cw_90%2Cx_87%2Cy_95/v1627283836/default/og-base-w1200-v2.png

なぜCloudflare WorkersではNode.jsが使えない?

最近はDenoやBunなどの様々なランタイムが登場しているものの、jsのランタイムといえばまだまだNode.jsが想起されるかと思います。

エッジ環境で言うとAWS LambdaではNode.jsが動くのに、なぜCloudflare Workersでは動かないのでしょう?

その問いに対しては、公式ブログ にて以下のように答えています。

Nodeをベースにした場合、V8のサンドボックスの利点を失うことになります。代わりにプロセスレベル(別名コンテナベース)のサンドボックスを使用しなければなりませんが、これは前述のように安全性と効率性に欠けます。-- Cloudflare Workersのご紹介:エッジでJavaScript Service Workersを実行する

Cloudflare Workersのご紹介:エッジでJavaScript Service Workersを実行するYou'll soon be able to deploy JavaScript to Cloudflare's edge, written against an API similar to Service Workers.
favicon of https://blog.cloudflare.com/introducing-cloudflare-workersblog.cloudflare.com

Node.jsはもともとサーバー上で長時間動作するプロセスを実行することを想定して設計されています。 そのためファイルシステム(fs)、ネットワーク(net)、プロセス管理(process)など、ローカル環境やOSにアクセスする強力な機能があります。

Cloudflare Workersのようなサーバーレスプラットフォームでは、軽量かつ短期間で分離されたコンテキストにおいてコードを実行することが求められているため、Node.jsのようなランタイムをそのまま使用すると、強力すぎるAPIがセキュリティリスクとなり、Cloudflareが目指す軽量で安全なサーバーレス環境を実現できなくなってしまうのです。

さらにサーバーレスという特性上、Node.jsの場合スピンアップに時間がかかりコールドスタートに課題が残ります。 一方Cloudflare WorkersはV8上で直接実行されるため、起動時間が高速になっているのです。

結果的に依存を限りなく少なくすることによって、各ランタイムへの対応も比較的容易に可能になっています。 実際、コードをほとんど変えずにFastlyでも動いていたそうです。

おわりに

今日は雑にHonoがどのようにマルチランタイムを実現したのかを整理してみました。 その裏にはCloudflare Workersで動かすために作られたという背景が大きく影響していたようです。

Cloudflare Workersで動かすために作ろうとしたら、依存ゼロにする必要があってマルチランタイムに対応できたのか、元々マルチランタイム対応をしようとしていたのかは分かりませんが、どこでも動くウェブフレームワークという素敵なコンセプトで作られたHonoは今後も応援していきたいと思っています。

(最近はHonoでBFFを作っていてRPCの凄さに感動しています。)

ではまた次回お会いしましょう。

ねずみのおもちゃに食らいつくらてさん

この記事をシェアするx icon
アイコン画像
Takuto Mori@_mooriii

Wevoxというサービスのフロントエンジニアをしています。趣味は猫を眺めることです🐱