Skip to content

fix(docs): correct false claim that .mount() resolves to .use()#803

Open
braden-w wants to merge 1 commit intoelysiajs:mainfrom
braden-w:braden-w/fix-mount-docs
Open

fix(docs): correct false claim that .mount() resolves to .use()#803
braden-w wants to merge 1 commit intoelysiajs:mainfrom
braden-w:braden-w/fix-mount-docs

Conversation

@braden-w
Copy link
Contributor

@braden-w braden-w commented Feb 27, 2026

The Elysia 0.6 release blog and the main mount documentation page both claim that passing an Elysia instance to .mount() will "resolve to use automatically, providing type-safety and support for Eden by default." This isn't true, and hasn't been for some time.

What .mount() actually does

Looking at the Elysia source (src/index.ts#L5544-L5655), the mount method handles an Elysia instance by calling .compile() on it and then extracting its .fetch — the exact same thing it does for any other WinterCG-compliant handler. There is no call to .use() anywhere in the method.

Here's the relevant source, annotated:

// Source: https://github.com/elysiajs/elysia/blob/bbaf6b7/src/index.ts#L5567-L5607

mount(
    path: string | ((request: Request) => MaybePromise<Response>) | AnyElysia,
    handleOrConfig?: ((request: Request) => MaybePromise<Response>) | AnyElysia | { detail?: DocumentDecoration },
    config?: { detail?: DocumentDecoration }
) {
    if (
        path instanceof Elysia ||
        typeof path === 'function' ||
        path.length === 0 ||
        path === '/'
    ) {
        // Whether it's a plain function or an Elysia instance,
        // the result is the same: extract a raw fetch handler.
        // Elysia instances just get .compile().fetch called first.
        const run =
            typeof path === 'function'
                ? path
                : path instanceof Elysia
                    ? path.compile().fetch          // <-- Elysia instance: compile, grab .fetch
                    : handleOrConfig instanceof Elysia
                        ? handleOrConfig.compile().fetch
                        : typeof handleOrConfig === 'function'
                            ? handleOrConfig         // <-- Plain function: use as-is
                            : (() => { throw new Error('Invalid handler') })()

        // Wrap it so the URL path is rewritten for the sub-app
        const handler: Handler = ({ request, path }) =>
            run(new Request(replaceUrlPath(request.url, path), request))

        // Register as a catch-all wildcard, hidden from OpenAPI/Eden
        this.route('ALL', '/*', handler as any, {
            parse: 'none',       // No body parsing — raw request passthrough
            ...config,
            detail: {
                ...config?.detail,
                hide: true        // Hidden from docs/type system
            },
            config: {
                mount: run
            }
        })

        return this
    }

    // Path-prefixed mount — same pattern: extract fetch, register hidden wildcard
    const handle =
        handleOrConfig instanceof Elysia
            ? handleOrConfig.compile().fetch   // <-- Same treatment for Elysia instances
            : typeof handleOrConfig === 'function'
                ? handleOrConfig
                : (() => { throw new Error('Invalid handler') })()

    // ... registers this.route('ALL', path, ...) and this.route('ALL', path + '/*', ...)
    // Both with { parse: 'none', detail: { hide: true } }
}

Why the documentation claim is wrong

The code above shows that mount() never calls .use(). For both code paths (with and without a path prefix), an Elysia instance is treated identically to a Hono app or any other fetch-compatible handler:

  1. .compile().fetch — the Elysia instance is compiled down to a single (Request) => Response function
  2. parse: 'none' — no Elysia body parsing; the raw request is passed through as-is
  3. hide: true — routes are explicitly hidden from the OpenAPI schema and type system

This means:

  • No type inference propagated to the parent app
  • No Eden Treaty support (routes aren't in the type system)
  • No OpenAPI/Swagger documentation (routes are hidden)
  • No WebSocket support (just raw request/response)

The only difference between mount(path, hono.fetch) and mount(path, elysiaApp) is that Elysia calls .compile() first. The end result is identical — it's a black-box fetch handler either way.

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Feb 27, 2026

Walkthrough

Documentation updated to clarify that Elysia's .mount() always extracts the .fetch handler (does not resolve to .use()), so mounted routes do not provide type inference, Eden Treaty support, or OpenAPI schemas; recommends using .use() for type-safe composition.

Changes

Cohort / File(s) Summary
Blog post update
docs/blog/elysia-06.md
Replaced note about automatic .mount().use() resolution with an inline info block stating .mount() extracts .fetch and does not provide .use()-style composition; added recommendation to use .use() for type safety.
Mount pattern docs
docs/patterns/mount.md
Updated header badge target, added tip recommending .use() for full type safety/Eden Treaty/OpenAPI support, clarified runtime support wording, and noted that .mount() does not preserve type inference or OpenAPI schemas.

Estimated code review effort

🎯 1 (Trivial) | ⏱️ ~3 minutes

Poem

🐰 I nibble docs and tidy the trail,
I hop where notes once slightly failed,
Mount brings handlers, loose and spry,
But .use() keeps types held high. ✨

🚥 Pre-merge checks | ✅ 3
✅ Passed checks (3 passed)
Check name Status Explanation
Title check ✅ Passed The title directly and accurately summarizes the main change: correcting a false documentation claim that .mount() resolves to .use(), which is the core objective of the PR.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@docs/patterns/mount.md`:
- Around line 30-34: Update the typo in the tip text that mentions the standard:
change "WinterTC" to the correct name "WinterCG" where .mount is described (the
sentence about mounting non-Elysia, WinterTC-compliant handlers); keep the rest
of the text intact and ensure the .use() reference remains unchanged.

ℹ️ Review info

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between a33d572 and 74a6844.

📒 Files selected for processing (2)
  • docs/blog/elysia-06.md
  • docs/patterns/mount.md

Comment on lines +30 to +34
::: tip
**.mount** is intended for mounting non-Elysia, WinterTC-compliant handlers. Mounted routes are registered as a wildcard handler and are **not** included in OpenAPI/Swagger documentation, Eden Treaty type inference, or WebSocket support.

To compose Elysia instances with full type safety, Eden Treaty support, and OpenAPI documentation, use [**.use()**](/essential/plugin) instead.
:::
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

Fix the standard name typo.

The tip box uses "WinterTC" but the correct name of the standard is "WinterCG" (Winter Community Group). This is inconsistent with the blog post (lines 118-122 of elysia-06.md) which correctly uses "WinterCG".

📝 Proposed fix
 ::: tip
-**.mount** is intended for mounting non-Elysia, WinterTC-compliant handlers. Mounted routes are registered as a wildcard handler and are **not** included in OpenAPI/Swagger documentation, Eden Treaty type inference, or WebSocket support.
+**.mount** is intended for mounting non-Elysia, WinterCG-compliant handlers. Mounted routes are registered as a wildcard handler and are **not** included in OpenAPI/Swagger documentation, Eden Treaty type inference, or WebSocket support.
 
 To compose Elysia instances with full type safety, Eden Treaty support, and OpenAPI documentation, use [**.use()**](/essential/plugin) instead.
 :::
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
::: tip
**.mount** is intended for mounting non-Elysia, WinterTC-compliant handlers. Mounted routes are registered as a wildcard handler and are **not** included in OpenAPI/Swagger documentation, Eden Treaty type inference, or WebSocket support.
To compose Elysia instances with full type safety, Eden Treaty support, and OpenAPI documentation, use [**.use()**](/essential/plugin) instead.
:::
::: tip
**.mount** is intended for mounting non-Elysia, WinterCG-compliant handlers. Mounted routes are registered as a wildcard handler and are **not** included in OpenAPI/Swagger documentation, Eden Treaty type inference, or WebSocket support.
To compose Elysia instances with full type safety, Eden Treaty support, and OpenAPI documentation, use [**.use()**](/essential/plugin) instead.
:::
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@docs/patterns/mount.md` around lines 30 - 34, Update the typo in the tip text
that mentions the standard: change "WinterTC" to the correct name "WinterCG"
where .mount is described (the sentence about mounting non-Elysia,
WinterTC-compliant handlers); keep the rest of the text intact and ensure the
.use() reference remains unchanged.

…lysia instances

.mount() always extracts the .fetch handler — it never calls .use().
Mounted routes are registered as hidden wildcard handlers without type
inference, Eden Treaty, or OpenAPI support. Added clarifying tip to the
mount docs page and a correction notice on the 0.6 blog post.
@braden-w braden-w force-pushed the braden-w/fix-mount-docs branch from 74a6844 to 93c77de Compare February 27, 2026 00:18
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant