42.7 Sharing Types Between Frontend and Backend in a Monorepo

Let’s be honest: you’ve probably duct-taped an interface from your backend into your frontend before. You copied it, pasted it, held your breath, and prayed nothing changed. It’s the digital equivalent of trying to match paint colors by memory. The moment you update the backend, the frontend shatters into a million type errors, and you’re left picking up the pieces. We’re done with that. In a monorepo, your frontend and backend aren’t just neighbors; they’re roommates sharing a single brain. They should be consuming the exact same type definitions from a single source of truth. No more drift, no more lies.

42.6 TypeScript in Middleware and Edge Functions

Right, so you’ve got your tRPC routes humming and your Next.js pages rendering. Feels good, doesn’t it? That end-to-end type safety is like a warm blanket on a cold night. But now you want to get fancy. You want to intercept requests, add some auth, set some headers, or maybe run some logic at the edge. You’re diving into middleware and edge functions, and you’re wondering if TypeScript’s warm blanket turns into a straitjacket here. The answer is: it depends on how much you fight the framework. Let’s get into it.

42.5 Server Components and Client Components: Typing the Boundary

Right, let’s talk about the great divide. You’ve got your Server Components, living their best life on the server, churning out HTML and doing database things without a care in the world. And you’ve got your Client Components, over in the browser, handling user events and making things feel alive. They’re two different countries with different languages. Your job, as a TypeScript diplomat, is to broker a peace treaty between them so data can cross the border without getting strip-searched.

42.4 Next.js TypeScript Configuration and Page Types

Alright, let’s get our Next.js house in order for TypeScript. This isn’t just about slapping a tsconfig.json file in there and calling it a day. We’re building the foundation for a full-stack TypeScript monolith, and a solid foundation means you don’t have to worry about the walls caving in later when you’re trying to deploy a server action at 2 AM. First, the good news: if you bootstrapped your project with create-next-app@latest and said yes to TypeScript, you got a pretty decent tsconfig.json out of the box. The Next.js team has done a solid job pre-configuring the compiler for their specific environment. But you, my brilliant friend, are not a default kind of person. You need to know what these knobs do.

42.3 tRPC with Next.js: API Routes and the Client

Right, so you’ve decided to build something that doesn’t make you want to tear your hair out. Good choice. tRPC with Next.js is essentially that: a way to have your frontend and backend hold hands so tightly that you can’t mess up the data between them. It’s end-to-end typesafety, and once you use it, you’ll feel like you’ve been coding with one hand tied behind your back your whole life. We’re going to set this up using Next.js’s API Routes, because they’re simple, they’re there, and they work.

42.2 Defining Procedures and Routers in tRPC

Right, let’s get our hands dirty. You’ve set up your tRPC context and type definitions, which means you’ve built the foundation and the plumbing. Now we get to the good part: actually building the procedures that will shuttle data between your frontend and backend. This is where you stop configuring and start doing. Think of a tRPC router as a neatly organized toolbox. Each procedure is a specific tool—a hammer, a screwdriver, a weirdly shaped wrench you’ll use once and forget about. Our job is to forge these tools and arrange them so you can find exactly what you need without dumping the entire box on the floor.

42.1 tRPC: End-to-End Type Safety Without a Schema

Right, so you’ve decided you’re tired of the soul-crushing tedium of manually keeping your frontend and backend types in sync. You’ve written a User type on the server, only to immediately copy-paste it into a @/types folder on the client, and you already know that the moment you add a lastLogin field, you’ll forget to update the client and everything will explode in production. It’s a ritual as old as time, and frankly, it’s beneath us.

— joke —

...