Hono.js: 最速を目指すNode.jsフレームワーク

[![Group102.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3967621/cd13dd48-2c9b-8ebd-f6b4-7c3449ec588b.png)](https://leapcell.io/?lc_t=q_hono)

## Why Learn Hono

[![hono-title.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3967621/2591d71e-bab7-4ea1-f5fa-249fdf9e9db9.png)](https://leapcell.io/?lc_t=q_hono)


既に市場にはNode.js用の多くのバックエンドライブラリやフレームワークが存在しています。以前、私はいくつかの小規模なプロジェクトでNest.jsを使ったことがあります。それは機能が充実しており、プロジェクトを迅速に実装できます。しかし、私の小規模プロジェクトにとって、その多くの機能は本当に必要以上であり、高度なカプセル化がされており、コードを書く際の自由度が少ないです。

偶然にも、私はオンラインでHonoに出会いました。そのドキュメントを読んでみると：
- **超高速 🚀** - ルータのRegExpRouterは本当に速いです。線形ループを使用していません。とにかく速いです。
- **軽量 🪶** - `hono/tiny`プリセットは12kB未満です。Honoは依存関係がゼロで、Web標準APIのみを使用しています。
- **マルチランタイム 🌍** - これはCloudflare Workers、Fastly Compute@Edge、Deno、Bun、Lagon、AWS Lambda、またはNode.jsで動作します。同じコードがすべてのプラットフォームで動きます。
- **高機能 🔋** - Honoには組み込みミドルウェア、カスタムミドルウェア、サードパーティミドルウェア、およびヘルパーが付属しています。すべてが揃っています。
- **快適なDX 🛠️** - とてもきれいなAPIと優れたTypeScriptサポートがあります。今では「型」があります。

## ユースケース
Honoは、Expressに似たシンプルなウェブアプリケーションフレームワークですが、フロントエンドはありません。ミドルウェアと組み合わせることで、より大きなアプリケーションを構築することができます。以下はいくつかのユースケースの例です：
- ウェブインターフェースの構築
- バックエンドサーバープロキシ
- CDNフロントエンド
- エッジアプリケーション
- ライブラリ用の基本的なサーバー
- フルスタックアプリケーション

さて、学習を始めましょう。

## Hello World
[https://hono.dev/docs/getting-started/basic](https://hono.dev/docs/getting-started/basic)

`port`を設定することで、ポートを変更できます。
```javascript
import { Hono } from 'hono';

const app = new Hono();

app.get('/', (c) => {
    return c.text('Hello Hono!');
});

export default app;
```
実行するには：
```bash
npm run dev
```
アクセスするには： [http://localhost:8787](http://localhost:8787)

## ルート

### HTTPメソッド
```javascript
app.get('/', (c) => c.text('GET /'));
app.post('/', (c) => c.text('POST /'));
app.put('/', (c) => c.text('PUT /'));
app.delete('/', (c) => c.text('DELETE /'));
```
### 階層型ルート
```javascript
const apiRoutes = app
  .basePath("/api")
  .route("/expenses", route1)
  .route("/", route2);
```
前の`basePath("/api")`はすべてのルートに`/api`のプレフィックスを追加します。
```javascript
export const route1 = new Hono()
  .post("/", async (c) => {
        return c.json({ });
    });
```
上記のルートには[http://localhost:8787/api/expenses](http://localhost:8787/api/expenses)からアクセスできます。

## リクエスト
### リクエストパラメータとクエリの取得
```javascript
app.get('/posts/:id', (c) => {
    const page = c.req.query('page');
    const id = c.req.param('id');
    return c.text(`You want see ${page} of ${id}`);
});
```
結果を表示するには： [http://localhost:8787/posts/1?page=12](http://localhost:8787/posts/1?page=12)

### リクエストボディの内容取得
```javascript
app.put("/posts/:id{[0-9]+}", async (c) => {
    const data = await c.req.json();
    return c.json(data);
});
```

## レスポンス
`text()`以外にも、`json()`、`html()`、`notFound()`、`redirect()`など、多くのメソッドがあり、リクエストに対して異なる種類のデータを返すことができます。`html()`は直接JSXを返すことができます。

### JSX
```javascript
import type { FC } from 'hono/jsx';

const app = new Hono();

const Layout: FC = (props) => {
    return (
        <html>
            <body>{props.children}</body>
        </html>
    );
};

const Top: FC<{ messages: string[] }> = (props: {
    messages: string[]
}) => {
    return (
        <Layout>
            <h1>Hello Hono!</h1>
            <ul>
                {props.messages.map((message) => {
                    return <li>{message}!!</li>;
                })}
            </ul>
        </Layout>
    );
};

app.get('/', (c) => {
    const messages = ['Good Morning', 'Good Evening', 'Good Night'];
    return c.html(<Top messages={messages} />);
});

export default app;
```
ファイル拡張子を`.tsx`に変更するだけで、直接JSXを書くことができ、非常にReact風です。

## バリデータ
バリデータは`zod`と`@hono/zod-validator`を通じて実装され、クライアントから送信されたリクエストが指定されたデータ形式に合致しているかどうかをチェックします。
**インストール**: `yarn add zod @hono/zod-validator`
例えば、リクエストにおいて、クライアントが送信するデータ形式が次のようになる必要がある場合：
`account: string; password: string`
```javascript
import { z } from "zod";
import { zValidator } from "@hono/zod-validator";

const loginSchema = z.object({
    account: z.string(),
    password: z.string(),
});

app.post("/login", zValidator("json", loginSchema), async (c) => {
    // 何か処理をする
    const user = c.req.valid("json");
    return c.json({ });
});
```
`zod`のドキュメントからもっと学ぶことができます。また、IDEは`user`に対して直接型ヒントを表示することができます。

## [Leapcell: The Advanced Serverless Platform for Nodejs Hosting](https://leapcell.io/?lc_t=q_hono)

[![barndpic.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3967621/6e8d22cd-293e-6388-528d-24e4b3aba15b.png)](https://leapcell.io/?lc_t=q_hono)


最後に、Honoアプリをデプロイするのに非常に適したプラットフォームを紹介しましょう： [Leapcell](https://leapcell.io/?lc_t=q_hono)。

[Leapcell](https://leapcell.io/?lc_t=q_hono)は次の特徴を持つサーバーレスプラットフォームです：
1. **多言語サポート**
    - JavaScript、Python、Go、またはRustで開発できます。
2. **無制限のプロジェクトを無料でデプロイ**
    - 使用量に対してのみ支払います — リクエストがなければ、料金はかかりません。
3. **比類なきコスト効率**
    - 使った分だけ支払い、アイドル時の料金はありません。
    - 例：25ドルで平均応答時間60msの694万件のリクエストをサポートします。
4. **簡素化された開発者体験**
    - 直感的なUIで簡単にセットアップできます。
    - 完全自動化されたCI/CDパイプラインとGitOps統合。
    - リアルタイムのメトリクスとロギングで実行可能な洞察を得ることができます。
5. **簡単なスケーラビリティと高性能**
    - 自動スケーリングで高い並列性を簡単に処理できます。
    - オペレーションオーバーヘッドはゼロ — 開発に集中できます。

[Docs](https://docs.leapcell.io/)でもっと探検してみてください！

Leapcell Twitter: [https://x.com/LeapcellHQ](https://x.com/LeapcellHQ)