FG
๐Ÿ’ป Software๐ŸŒ Web & Full-Stack

feat: Lazy load routers

Fresh5 days ago
Mar 14, 20260 views
Confidence Score59%
59%

Problem

Describe the feature you'd like to request Basically `next/dynamic` but for the backend. Recently our tRPC router has been growing significantly for many reasons but mostly due to heavy third party SDKs. The problem with this is that even if we're not calling that specific procedure we still load ALL the router dependencies when calling any procedure. This impacts performance and cold boots significantly. Describe the solution you'd like to see Splitting big tRPC routers into lazy loadable chunks could help loading only what is needed when a procedure is called. I would imagine some pseudo code like this: Describe alternate solutions Other aternatives involve moving all the procedure code into a separate file a use imports for that as done in here. Also lazy loading only third party libraries (like Stripe, Google, etc.) seems to help. But it would be a much nicer DX being able to simply lazy load full routers and support it natively. Additional information _No response_ ๐Ÿ‘จโ€๐Ÿ‘งโ€๐Ÿ‘ฆ Contributing - [X] ๐Ÿ™‹โ€โ™‚๏ธ Yes, I'd be down to file a PR implementing this feature! <sub>TRP-19</sub>

Unverified for your environment

Select your OS to check compatibility.

1 Fix

Canonical Fix
Unverified Fix
New Fix โ€“ Awaiting Verification

Implement Lazy Loading for tRPC Routers

Medium Risk

The current implementation of tRPC routers loads all dependencies at once, regardless of whether specific procedures are called. This results in increased load times and performance issues, especially when third-party SDKs are involved.

Awaiting Verification

Be the first to verify this fix

  1. 1

    Refactor Router Structure

    Split the existing tRPC router into smaller, modular routers that can be lazy-loaded. Each module should contain related procedures and dependencies.

    typescript
    export const userRouter = createRouter().query('getUser', { resolve: () => { /* user fetching logic */ } });
    
    export const orderRouter = createRouter().query('getOrder', { resolve: () => { /* order fetching logic */ } });
  2. 2

    Implement Dynamic Import for Routers

    Utilize dynamic imports to load the routers only when needed. This can be achieved using `import()` syntax within the procedure resolver.

    typescript
    const getUser = async () => {
      const { userRouter } = await import('./routers/userRouter');
      return userRouter.getUser();
    };
  3. 3

    Update tRPC Configuration

    Modify the tRPC server configuration to support lazy loading of routers. Ensure that the main router can dynamically include the necessary modules based on incoming requests.

    typescript
    const appRouter = createRouter().merge('user.', userRouter).merge('order.', orderRouter);
  4. 4

    Test Lazy Loading Implementation

    Create unit tests to verify that the routers are loaded only when their procedures are called. Measure the performance before and after the implementation.

    typescript
    describe('Lazy Loading Routers', () => {
      it('should load userRouter only when getUser is called', async () => {
        const userRouter = await import('./routers/userRouter');
        expect(userRouter).toBeDefined();
      });
    });

Validation

Confirm that the application loads faster and that only the necessary routers are loaded when specific procedures are called. Use performance profiling tools to measure improvements.

Sign in to verify this fix

Environment

Submitted by

AC

Alex Chen

2450 rep

Tags

trpctypescriptapi