Features
TRPC

Type-Safe Backend Requests with tRPC

The boilerplate project includes tRPC, a framework for building type-safe APIs that ensures your front-end and back-end remain in sync. With tRPC, any changes in the backend will break the front-end during development, notifying you to make the necessary updates. This guide will help you understand how to add a new router and ensure your backend requests are type-safe.

Key Features

  • Type-Safe Requests: Ensures synchronization between front-end and back-end types.
  • Automatic Error Detection: Front-end will break during development if there are mismatches, alerting you to update your code.
  • Simple Router Configuration: Easily add new routers and procedures.

Setup

Step 1: Create a New Router

To add a new router, create a file in the src/server/routers directory. Here is an example of how to create a simple post router.

import { z } from "zod";
import { createPost } from "../service/post-service";
import { protectedProcedure, router } from "../trpc";
 
export const createPostRouter = () => {
  return router({
    createPost: protectedProcedure
      .input(
        z.object({
          text: z.string(),
          image: z.string().optional(),
        })
      )
      .mutation(async (opts) => {
        const userId = opts.ctx.session.user.id;
        const { image, text } = opts.input;
 
        try {
          const newPost = await createPost({
            text,
            image,
            userId,
          });
          return newPost;
        } catch (error: any) {
          throw new Error("Error creating post: " + error.message);
        }
      }),
  });
};

You can define your procedures as protectedProcedure or publicProcedure based on the requirement.

  • protectedProcedure: Requires authentication.
  • publicProcedure: Does not require authentication.

Step 2: Add the Router to _app.tsx

After creating the router, add it to your application by modifying src/server/routers/_app.tsx.

import { router } from "../trpc";
import { createPostRouter } from "./post";
 
// Combine your routers
export const appRouter = router({
  post: createPostRouter(),
  // Add more routers here
});
 
// Export type definition of API
export type AppRouter = typeof appRouter;

Step 3: Use Your Route in the Front-End

Here is an example of how you might use the createPost procedure in your front-end code:

import { trpc } from "../shared/utils/trpc";
 
const { mutateAsync: createPost } = trpc.post.createPost.useMutation();
 
const handleCreatePost = async (text: string, image?: string) => {
  try {
    await createPost({ text, image });
    console.log("Post created successfully");
  } catch (error) {
    console.error("Error creating post:", error);
  }
};
// Call this function as needed in your component

Summary

By following these steps, you can quickly and easily set up type-safe backend requests in your project using tRPC. This system ensures that any changes in the backend are reflected in the front-end, helping you maintain consistency and catch errors early in the development process.