honojs/hono

Wrong type with InferResponseType<> and status code when using .route() method

Closed this issue · 1 comments

What version of Hono are you using?

4.3.1

What runtime/platform is your app running on?

Bun

What steps can reproduce the bug?

This code reproduce the bug. You need to create a now router and import it to the current app router exposed to the client

import { Hono } from "hono"
import { hc } from "hono/client"

const myRouter = new Hono()
  .get("/", (c) => {
    const randomBoolean = Math.random() < 0.5
    if (!randomBoolean) {
      return c.json({ error: "not found" }, 404)
    }

    return c.json({ success: true }, 200)
  })

const app = new Hono()
  .basePath("/api")
  .route("/hello", myRouter)

const client = hc<typeof app>("/")

type ResponseType200 = InferResponseType<typeof client.api.hello.$get, 200>
type ResponseType404 = InferResponseType<typeof client.api.hello.$get, 404>

What is the expected behavior?

In the previous code, ResponseType200 should be of type { success: boolean } and ResponseType404 should be of type { error: string }

What do you see instead?

ResponseType200 and ResponseType404 are both typed as

{ success: boolean } | { error: string }

Additional information

In the 4.3.0 releaseStatus code type the example show a working example that doesn't use .route() method. I think the issue came from the type merging with this method.

The error

CleanShot 2024-05-04 at 15 38 34@2x

✅ Types in the custom router that I want

CleanShot 2024-05-04 at 15 39 47@2x

❌ Types of the main router with my custom router imported with the .route()

CleanShot 2024-05-04 at 15 40 16@2x

the type MergeSchemaPath seems to flatten the schema. If I overwrite the type like this

export type MergeSchemaPath<OrigSchema extends Schema, SubPath extends string> = Prettify<{
  [P in keyof OrigSchema as MergePath<SubPath, P & string>]: 
    OrigSchema
}>

it breaks a lot of things with the client and other things, but make my types working

CleanShot 2024-05-04 at 17 19 26@2x