OK let’s dive in real quick!
GraphQL is a query language and runtime that enables efficient data retrieval and manipulation from APIs. It allows clients to request specific data they need, reducing over-fetching and under-fetching issues commonly found in REST APIs. Its key benefits include increased flexibility, reduced network traffic, and improved developer productivity.
Now think of fragments as reusable units of fields used on the client side that can be defined and included in multiple queries. They allow you to define a set of fields once and use them in multiple places, making your queries more modular and concise.
Writing fragments is a good way to enhance code organization, reduce duplication, and make it easier to maintain and update queries as your schema evolves. They are particularly useful when you have common fields that are shared across different queries or when you want to abstract complex field selections into smaller, reusable components.
Let’s take a look at this example
#First we define a fragment for a user
fragment UserFragment on User {
id
name
email
age
}
# A query using the defined fragment
# We use ...UserFragment to include within the user query
query GetUser {
user(id: 123) {
...UserFragment
}
}
# Another query using the same fragment
# We use ...UserFragment to include within the users query
query GetUsers {
users {
...UserFragment
}
}
OK with that being said let’s look at how we can query a fragment based on certain conditions from parent.
To query fragments based on certain conditions from a parent, you can use conditional directives or arguments in GraphQL. The specific implementation may vary depending on the GraphQL server or library you are using.
Let’s see how we can accomplish this using Apollo Client.
Let’s try to query a user’s profile and return all the fields. But we will conditionally include the user’s private posts or maybe liked posts based on the user Id, so we check if the post owner’s id is equal to the user Id. This can be a useful feature in a social media app.
OK let’s dive in!
Here are the steps
First, we define the fragment for the user’s post, let’s call it UserLikedPostsFragment.
const userLikedPostsFragment = gql`
fragment UserLikedPostsFragment on User {
likedPosts {
id
content
}
}
`;
The userLikedPostsFragment specifies the field for the user’s posts, it includes the id and the content fields for each post.
We then determine if the user is the owner of the post by comparing the user ID and the post owner’s ID. If they match, we set includeLikedPosts to true; otherwise, we set it to false
// Assuming we have the user's ID
const userId = 'bldo123';
// Assuming we have post owner id
const postOwnerId = '456jsksi';
// Check if the user ID matches the post's owner ID
const isPostOwner = (userId === postOwnerId);
// Determine if we should include the user's liked posts in the query
const includeLikedPosts = isPostOwner;
Then, we create a GET_USER query that accepts the userId variable and an additional includeLikedPosts variable we just created. Inside the query, we conditionally include the UserLikedPostsFragment using the spread syntax (...) and the @include directive. The @include directive controls whether the fragment is included based on the value of includeLikedPosts
const GET_USER = gql`
query GetUser($userId: ID!) {
user(id: $userId) {
id
name
email
...UserLikedPostsFragment @include(if: $includeLikedPosts)
}
}
`;
learn more about directives in Apollo-Client here
Then we can go on to execute our query
client.query({
query: GET_USER,
variables: {
userId,
includeLikedPosts,
},
}).then((result) => {
// Handle query result anyhow you wish
console.log(result.data.user);
});
Notice the $includeLikedPosts variable is passed as a query variable when executing the query. Its value is determined based on the logic in the code (in this case, whether the user is the owner of the post).
By passing the variables (userId and includeLikedPosts) and the query to client.query, we can execute the query and handle the results accordingly.
So the LikedPosts will be returned if the condition is met that’s is if
userId === postOwnerId
Here’s the code snippet demonstrating how you can conditionally include the user’s posts based on the user ID using fragments in Apollo Client:
import { ApolloClient, InMemoryCache, gql } from '@apollo/client';
const client = new ApolloClient({
uri: 'https://your-graphql-api-endpoint',
cache: new InMemoryCache(),
});
const userLikedPostsFragment = gql`
fragment UserLikedPostsFragment on User {
likedPosts {
id
content
}
}
`;
//Assuming we have the user's ID
const userId = 'bldo123';
// Assuming the user owns the post
const postOwnerId = '456jsksi';
//Check if the user ID matches the post's owner ID
const isPostOwner = (userId === postOwnerId);
// Determine if we should include the user's liked posts in the query
const includeLikedPosts = isPostOwner;
client.query({
query: GET_USER,
variables: {
userId,
includeLikedPosts,
},
}).then((result) => {
// Handle query result
console.log(result.data.user);
});
Hope you enjoyed the post. If you did hit the ❤️ button, share and follow for more amazing content. Bye 👋
Top comments (0)