Skip to main content

13.2 - Queries and Mutations

In tRPC, queries and mutations are two fundamental types of procedures that you'll use to interact with your backend. Both serve distinct purposes, and understanding their roles will help you design a clean, efficient API.

Queries

Queries are used to fetch data from the server without causing any side effects. They are generally idempotent, meaning that no matter how many times you call a query with the same parameters, the result will be the same and no state on the server will change.

Common Use Cases for Queries

  • Fetching User Data: Retrieve information about a user, such as their profile details, preferences, or activity logs.
  • Listing Items: Get a list of items, such as products in an e-commerce store, posts in a blog, or messages in a chat.
  • Search Operations: Search for items or records based on certain criteria (e.g., search for posts by a keyword).

Example of a Query

Suppose you need to fetch a list of posts from the database:

const postRouter = router({
getAllPosts: procedure.query(() => {
// Logic to fetch all posts from the database
return getAllPostsFromDatabase();
}),

getPost: procedure.input(z.object({ id: z.string() })).query(({ input }) => {
// Logic to fetch a post by ID
return getPostFromDatabase(input.id);
}),
});

In this postRouter, the getAllPosts query fetches all the posts, while getPost fetches a specific post based on its ID. These queries are perfect examples of how to retrieve data without making changes to the server's state.


Mutations

Mutations are used to perform operations that change data on the server. They are typically used for creating, updating, or deleting records in your database. Unlike queries, mutations can cause side effects, such as modifying a record or triggering other processes like sending notifications.

Common Use Cases for Mutations

  • Creating New Records: Add new data to the database, like creating a new user account, adding a new post, or submitting a form.
  • Updating Existing Records: Modify existing data, such as updating user settings, editing a post, or changing the status of an order.
  • Deleting Records: Remove data from the database, like deleting a comment, removing a user, or canceling an order.

Example of a Mutation

Building on our blogging platform example, let’s create a mutation for updating a post:

const postRouter = router({
updatePost: procedure
.input(z.object({ id: z.string(), title: z.string(), content: z.string() }))
.mutation(({ input }) => {
// Logic to update a post's title and content based on its ID
return updatePostInDatabase(input.id, input.title, input.content);
}),

deletePost: procedure
.input(z.object({ id: z.string() }))
.mutation(({ input }) => {
// Logic to delete a post by ID
return deletePostFromDatabase(input.id);
}),
});