Introduction

The GraphQL Content API is a powerful way to query and mutate data in Penzle CMS. GraphQL is a query language for APIs that Facebook developed, allowing you to request only the data you need in the format you need.

The GraphQL Content API in Penzle provides a flexible and efficient way to interact with your content, whether you're building a website, mobile app, or any other type of digital experience. With the GraphQL Content API, you can retrieve specific fields from entries and assets and use filtering and sorting to refine query results.

In addition to its flexibility and efficiency, the GraphQL Content API is easy to use and learn. The GraphQL syntax is concise and intuitive, providing a clear and well-documented way to interact with your content.

Whether you're a seasoned developer or just getting started, the GraphQL Content API in Penzle can help you build better digital experiences faster.

In the following sections, we'll walk you through how to set up the GraphQL Content API in Penzle, retrieve and mutate content, and some advanced concepts and best practices to help you get the most out of this powerful API.

An overview of the API

The GraphQL API in Penzle CMS is a powerful way to retrieve and manipulate your content. With the GraphQL API, you can retrieve only the data that you need, define relationships between your content, and make efficient and effective queries and mutations.

The base URL for the CDA is:

https://api.penzle.com/api/graphql

GraphQL Basics

At its core, GraphQL is a query language for your API. It allows you to define your data in terms of types, and to retrieve and manipulate that data using queries and mutations.

When working with the GraphQL API in Penzle CMS, there are several key concepts to understand:

  • Types: In GraphQL, types define the structure of your data. You can define types for your content, such as entries and assets, and use these types to retrieve and manipulate your content.
  • Fields: Fields represent the data that is contained in your types. You can retrieve specific fields using queries and mutations.
  • Queries: Queries are used to retrieve data from your API. They allow you to specify the types and fields that you want to retrieve, and can include filtering, sorting, and pagination to refine your results.
  • Mutations: Mutations are used to manipulate data in your API. They allow you to create, update, and delete entries and assets, and can be used to perform more complex operations on your content.

Authentication

Authentication is an important aspect of working with the GraphQL API in Penzle CMS. In order to access your content and perform queries and mutations, you need to authenticate with the Penzle Content Delivery API (CDA) or the Penzle Content Management API (CMA).

A. Authentication Options

Penzle CMS provides several authentication options for working with the GraphQL API, depending on your use case:

  • API key: An API key is a simple way to authenticate with the Penzle CDA or CMA. You can generate an API key in your Penzle account settings and include it in your GraphQL queries or mutations.
  • OAuth: OAuth is a more advanced authentication option that allows you to grant access to the Penzle API on behalf of a user. This is useful if you're building an application that requires access to a user's Penzle account.

More details about Penzle authentication can be found in our reference guide.

B. Authenticating with an API Key

If you're using an API key to authenticate with the Penzle GraphQL API, you can include the key in your queries and mutations using the Authorization header.

For example, the following query includes an API key in the Authorization header:

query {
  entries(content_type: "blogPost") {
    items {
      title
      body
      date
    }
  }
}

To include an API key in your query or mutation, you can use the following syntax:

{
  "Authorization": "Bearer YOUR_API_KEY_HERE"
}

Be sure to replace YOUR_API_KEY_HERE with your actual API key.

C. Authenticating with OAuth

If you're using OAuth to authenticate with the Penzle GraphQL API, you'll need to follow the OAuth 2.0 authorization flow to obtain an access token. This flow involves several steps, including redirecting the user to the Penzle authentication page, obtaining an authorization code, and exchanging the code for an access token.

For more information on how to authenticate with the Penzle API using OAuth, see the Penzle documentation.

Querying Content

One of the core features of the GraphQL API in Penzle is the ability to retrieve content from your project using GraphQL queries. With the GraphQL Content API, you can retrieve entries and assets with specific fields, filter and sort your queries, and request only the data you need.

Retrieving Entries and Assets

To retrieve entries and assets using the GraphQL Content API, you'll need to write a GraphQL query that specifies which fields you want to retrieve. For example, the following query retrieves all entries from a specific content type, and includes only the title, date, and body fields:

query {
  entries(content_type: "blogPost") {
    items {
      title
      date
      body
    }
  }
}

In this query, we're using the entries field to retrieve all entries of type blogPost. The items field returns an array of all the matching entries, and we're using the title, date, and body fields to specify which fields we want to retrieve for each entry. To retrieve assets, you can use the assets field in a similar way. For example, the following query retrieves all assets in a space, and includes only the title and description fields:


query {
  assets {
    items {
      title
      description
    }
  }
}

Filtering Query Results

To filter your query results in the GraphQL Content API, you can use the where argument in your queries. The where argument allows you to filter your query results based on specific criteria, such as the value of a particular field.

For example, the following query retrieves only the entries of type blogPost that have the featured field set to true:

query {
  entries(content_type: "blogPost", where: { featured: true }) {
    items {
      title
      body
    }
  }
}

In this query, we're using the where argument to filter the entries based on their featured field. The where argument takes an object with one or more properties that define the filtering criteria.

You can also use a variety of comparison operators to filter your query results, such as gt (greater than), lt (less than), in (in a set of values), and more. For example, the following query retrieves only the blog posts that were published after a specific date:

query {
  entries(content_type: "blogPost", where: { date_gt: "2022-01-01" }) {
    items {
      title
      date
      body
    }
  }
}

In this query, we're using the date_gt argument to retrieve only the blog posts that were published after January 1, 2022.

In this query, we're using the where argument to filter the blog posts based on their featured field, the order argument to sort the blog posts by their date field in descending order, and the limit argument to retrieve only the 10 most recent blog posts.

Sorting Query Results

To sort your query results in the GraphQL Content API, you can use the order argument in your queries. The order argument allows you to sort your query results based on specific fields, in ascending or descending order.

For example, the following query retrieves all entries of type blogPost, sorted by their date field in descending order:

query {
  entries(content_type: "blogPost", order: "date_DESC") {
    items {
      title
      date
      body
    }
  }
}

In this query, we're using the order argument to sort the blog posts by their date field in descending order.

You can also sort your query results by multiple fields, by chaining the fields together with underscores. For example, the following query retrieves all entries of type product, sorted by their category field in ascending order, and then by their pricefield in descending order:

query {
  entries(content_type: "product", order: "category_ASC_price_DESC") {
    items {
      title
      category
      price
    }
  }
}

In this query, we're using the order argument to sort the products first by their category field in ascending order, and then by their price field in descending order.

Paginating Query Results

To paginate your query results in the GraphQL Content API, you can use the skip and limit arguments in your queries. The skip argument allows you to skip a specified number of items in your query results, while the limit argument allows you to retrieve only a specified number of items.

For example, the following query retrieves the first 10 blog posts, skipping the first two items:

query {
  entries(content_type: "blogPost", skip: 2, limit: 10) {
    items {
      title
      date
      body
    }
  }
}

In this query, we're using the skip argument to skip the first two blog posts, and the limit argument to retrieve the next 10 blog posts.

You can also use these arguments in combination with filtering and sorting to retrieve specific subsets of your query results. For example, the following query retrieves the 10 most recent blog posts that have the featured field set to true:

query {
  entries(content_type: "blogPost", where: { featured: true }, order: "date_DESC", limit: 10) {
    items {
      title
      date
      body
    }
  }
}

In this query, we're using the where argument to filter the blog posts based on their featured field, the order argument to sort the blog posts by their date field in descending order, and the limit argument to retrieve only the 10 most recent blog posts.

Request Specific Fields

When retrieving data from Penzle using the GraphQL Content API, you may not always need all of the fields that are associated with a particular entry or asset. To reduce the amount of data that is returned by your queries, you can request only the specific fields that you need.

A. Requesting Fields from Entries

To request specific fields from entries in the GraphQL Content API, you can include the names of the fields in your query. For example, the following query retrieves only the title and body fields for all entries of type blogPost:

query {
  entries(content_type: "blogPost") {
    items {
      title
      body
    }
  }
}

In this query, we're using the title and body fields to specify which fields we want to retrieve for each blog post. We're not including any other fields in the query, which can help reduce the amount of data that is returned.

You can also request fields from nested objects within an entry. For example, the following query retrieves the title and url fields from the coverImage object for all entries of type blogPost:

query {
  entries(content_type: "blogPost") {
    items {
      title
      coverImage {
        url
      }
    }
  }
}

In this query, we're using the coverImage object to retrieve the url field for each blog post. The coverImage object is a nested object within the blogPost entry, and we can specify the url field by including it within the coverImage object in the query.

B. Requesting Fields from Assets

To request specific fields from assets in the GraphQL Content API, you can include the names of the fields in your query. For example, the following query retrieves only the title and description fields for all assets:

query {
  assets {
    items {
      title
      description
    }
  }
}

In this query, we're using the title and description fields to specify which fields we want to retrieve for each asset. We're not including any other fields in the query, which can help reduce the amount of data that is returned.

You can also request fields from nested objects within an asset. For example, the following query retrieves the title and url fields from the file object for all assets:

query {
  assets {
    items {
      title
      file {
        url
      }
    }
  }
}

In this query, we're using the file object to retrieve the url field for each asset. The file object is a nested object within the asset, and we can specify the url field by including it within the file object in the query.

Fragments to Reuse Fields Across Queries

When working with the GraphQL Content API in Penzle CMS, you may find that you need to reuse the same set of fields across multiple queries. To avoid duplicating your code and to make your queries more readable, you can use GraphQL fragments.

A. Defining GraphQL Fragments

A GraphQL fragment is a reusable set of fields that can be included in multiple queries. To define a fragment in Penzle, you can use the fragment keyword, followed by a name for the fragment and a set of fields.

For example, the following fragment defines a set of fields that can be used to retrieve information about a blog post:

fragment BlogPostFields on BlogPost {
  title
  body
  date
  author {
    name
    email
  }
  tags {
    name
  }
}

In this fragment, we're defining a set of fields that can be used to retrieve the title, body, date, author, and tags fields for a blog post. We're also including nested fields for the author object and the tags array.

B. Using GraphQL Fragments in Queries

Once you've defined a GraphQL fragment, you can include it in any query that requires the same set of fields. To include a fragment in a query, you can use the ...<fragmentName> syntax.

For example, the following query retrieves the title, body, and date fields for all blog posts, using the BlogPostFields fragment:

query {
  entries(content_type: "blogPost") {
    items {
      ...BlogPostFields
    }
  }
}

fragment BlogPostFields on BlogPost {
  title
  body
  date
}

In this query, we're using the ...BlogPostFields syntax to include the BlogPostFields fragment, which defines the set of fields that we want to retrieve for each blog post.

You can also include multiple fragments in a single query, and you can include fragments within other fragments. This allows you to build complex queries that reuse sets of fields in a flexible and customizable way.

Best Practices

When working with the GraphQL Content API in Penzle CMS, there are several strategies you can use to optimize your queries and mutations. By following these best practices, you can improve the performance of your application and reduce the load on the server.

Optimizing GraphQL Queries

A. Use Specific Query and Mutation Fields

When defining your queries and mutations, be sure to request only the fields that you need. Requesting too many fields can result in a large amount of data being returned, which can slow down your application and increase server load.

To reduce the amount of data that is returned by your queries and mutations, you can use the techniques described earlier, such as filtering, sorting, pagination, and field selection. By carefully selecting the fields that you need and using these techniques to refine your results, you can optimize your queries and mutations and make your application more efficient.

B. Avoid N+1 Query Problems

The N+1 query problem occurs when a query retrieves a list of items, and then performs an additional query for each item in the list to retrieve related data. For example, if you retrieve a list of blog posts and then perform a separate query for each post to retrieve the author's name, you are performing N+1 queries.

To avoid N+1 query problems, you can use GraphQL's built-in support for nested queries and mutations. By defining your queries and mutations in a way that allows you to retrieve all of the necessary data in a single query or mutation, you can reduce the number of requests that are required and improve the performance of your application.

C. Cache Query Results

Caching query results can help reduce the load on the server and improve the performance of your application. By caching the results of frequently executed queries, you can avoid the need to perform the same query multiple times, and instead retrieve the results from the cache.

To implement caching in your Penzle CMS application, you can use a variety of caching mechanisms, such as client-side caching, server-side caching, or a third-party caching service. By choosing the caching mechanism that is best suited to your application, you can optimize the performance of your queries and mutations and provide a better user experience.

Best Practices for Using the GraphQL

When working with the GraphQL Content API in Penzle CMS, several best practices can help you build efficient and effective applications. By following these best practices, you can improve the performance of your application, reduce the load on the server, and provide a better user experience.

A. Define Your Schema and Types Carefully

When defining your schema and types in Penzle CMS, be sure to carefully consider the structure of your content and the requirements of your application. By defining your schema and types in a way that is tailored to your content and your application's needs, you can reduce the complexity of your queries and mutations and improve the performance of your application.

It's also important to consider the relationships between your content types, and to use the appropriate fields and directives to define these relationships. By defining relationships between your content types using fields like link and reference, you can make it easier to retrieve related data in a single query or mutation.

B. Use Field Selection and Aliases

When querying your content in Penzle CMS, be sure to use field selection and aliases to retrieve only the data that you need. By carefully selecting the fields that you want to retrieve and using aliases to rename the fields, you can improve the performance of your application and reduce the amount of data that is returned by your queries.

C. Use Filtering, Sorting, and Pagination

Filtering, sorting, and pagination are powerful techniques that can help you refine your query results and improve the performance of your application. By using these techniques to retrieve only the data that you need and to limit the amount of data that is returned, you can make your queries more efficient and reduce the load on the server.

D. Use GraphQL Fragments to Reuse Fields Across Queries

As discussed earlier, using GraphQL fragments can help you reuse sets of fields across multiple queries and mutations, and reduce code duplication. By defining reusable sets of fields and including them in multiple queries and mutations, you can improve the readability and maintainability of your code, and make your application more efficient.

E. Optimize Your Queries and Mutations

Finally, it's important to optimize your queries and mutations in Penzle CMS to improve the performance of your application and reduce the load on the server. By following the tips and best practices outlined earlier in this document, you can make your queries and mutations more efficient and effective, and provide a better user experience.

Errors

Like any API, the Penzle GraphQL API may return errors in certain circumstances. These errors can be helpful in diagnosing and resolving issues in your application, and understanding them can help you build more robust and reliable software.

A. GraphQL Errors

When you send a query or mutation to the Penzle GraphQL API, it may return one or more errors in the response. These errors are typically returned in the errors field of the response, and can provide information about what went wrong and how to fix it.

Here are some common types of errors that you might encounter when working with the Penzle GraphQL API:

  • Validation errors: If your query or mutation is not valid, you may receive a validation error. This error indicates that there is a problem with the structure of your query or mutation, and provides information about what is invalid.
  • Authorization errors: If you are not authorized to perform a particular operation, you may receive an authorization error. This error indicates that you do not have the necessary permissions to perform the operation, and provides information about how to obtain the necessary permissions.
  • Runtime errors: If there is a problem with your query or mutation at runtime, you may receive a runtime error. This error indicates that there is a problem with the data or code that you are working with, and provides information about what went wrong.

B. HTTP Errors

In addition to GraphQL errors, the Penzle GraphQL API may return HTTP errors in certain circumstances. These errors typically indicate a problem with the connection between your application and the Penzle API, and may be caused by issues such as network connectivity, server issues, or incorrect authentication.

Here are some common HTTP errors that you might encounter when working with the Penzle GraphQL API:

  • 401 Unauthorized: If your authentication credentials are incorrect or missing, you may receive a 401 Unauthorized error. This error indicates that you are not authorized to access the resource that you are trying to access.
  • 403 Forbidden: If you are authenticated but do not have the necessary permissions to access a resource, you may receive a 403 Forbidden error. This error indicates that you are not authorized to access the resource that you are trying to access.
  • 404 Not Found: If you try to access a resource that does not exist, you may receive a 404 Not Found error. This error indicates that the resource that you are trying to access could not be found.

C. Handling Errors in Your Application

When working with the Penzle GraphQL API, it's important to handle errors in your application to provide a good user experience and to diagnose and resolve issues quickly.

To handle errors in your application, you can check for errors in the response from the Penzle API and handle them appropriately. For example, you might display an error message to the user, log the error for later analysis, or take other actions based on the specific error.

It's also a good practice to include error handling in your code when making API requests. For example, you might use try-catch blocks or similar constructs to handle errors and prevent your application from crashing.