🔥

Hono の Grouping routes for RPC と Middleware を使用する

2024/01/20に公開

はじめに

この記事では、Next.js の Route Handlers で、Hono の Grouping routes for RPCMiddleware を使用する方法をメモとして残します。

動作しないコード

import { Hono } from "hono"
import { logger } from 'hono/logger'
import { handle } from 'hono/vercel'

const authorsApp = new Hono()
  .get("/", (c) => c.json({ result: "list authors" }))
  .post("/", (c) => c.json({ result: "create an author" }, 201))
  .get("/:id", (c) => c.json({ result: `get ${c.req.param("id")}` }))

const booksApp = new Hono()
  .get("/", (c) => c.json({ result: "list books" }))
  .post("/", (c) => c.json({ result: "create a book" }, 201))
  .get("/:id", (c) => c.json({ result: `get ${c.req.param("id")}` }))

const app = new Hono().basePath("api").route("/authors", authorsApp).route("/books", booksApp)
app.use('*', logger())

export type AppType = typeof app

export const GET = handle(app)
export const POST = handle(app)

Grouping routes for RPC を参考に、下記のコードに、.basePath("api") を追加しました。

const app = new Hono().route("/authors", authorsApp).route("/books", booksApp);

何故動作しないか

Routing priority に記載があるように、handler より先に middleware を書く必要があります。

If you have the middleware that you want to execute, write the code above the handler.

app.use('*', logger())
app.get('/foo', (c) => c.text('foo'))

動作するコード

上記を踏まえ、handler より先に middleware を書くために、コードを複数行に分割します。

  • 分割前
const app = new Hono().basePath("api").route("/authors", authorsApp).route("/books", booksApp)
app.use('*', logger())

export type AppType = typeof app
  • 分割後
const app = new Hono().basePath("api")
app.use('*', logger())
app.route("/authors", authorsApp).route("/books", booksApp)

export type AuthorsAppType = typeof authorsApp
export type BooksAppType = typeof booksApp

分割後は、ミドルウェアが機能し、下記のようなログが表示されます。

app  |   <-- GET /api/authors
app  |   --> GET /api/authors 200 2ms

おわりに

この記事では、Hono の Grouping routes for RPCMiddleware を使用する際の注意点を記載しました。
Grouping routes for RPC をそのまま使用してしまいましたが、ドキュメントの注意書きを忘れないことが大事ですね。

shinaps テックブログ

Discussion