Sanity CMS - All About It
Odipo Otieno (KwargDevs)
Posted on October 12, 2024
Here’s an in-depth explanation of the key Sanity concepts and how to use it with front-end frameworks like Next.js and React.js:
1. Sanity Content Studio
Content Studio is where you manage your content visually. It's customizable and built with React, making it flexible for creating different data structures for various types of content.
How to Set Up:
- Install Sanity CLI:
npm install -g @sanity/cli
- Initialize a Sanity project:
sanity init
Follow the prompts to select a project template and choose settings (project name, dataset, etc.).
- Start the Content Studio:
sanity start
This will open the Content Studio at http://localhost:3333
. You can now manage your content here.
2. Schemas
Schemas in Sanity define the structure of your content, similar to defining models in a database. You’ll define schemas in the schemas
folder of your Sanity project.
Example: Create a Blog Schema
- Create a schema file
blog.js
inside theschemas
folder:
export default {
name: 'blog',
title: "'Blog Post',"
type: 'document',
fields: [
{
name: 'title',
title: "'Title',"
type: 'string',
},
{
name: 'body',
title: "'Body',"
type: 'portableText', // For rich text fields
},
{
name: 'author',
title: "'Author',"
type: 'reference',
to: [{ type: 'author' }], // Reference to another document type
},
{
name: 'publishedAt',
title: "'Published At',"
type: 'datetime',
},
],
};
- Add the schema to
schema.js
:
import blog from './blog';
export default createSchema({
name: 'default',
types: schemaTypes.concat([blog]),
});
- Restart the studio to load the new schema:
sanity start
This schema creates a structure for blog posts, including fields for a title, body, author reference, and published date.
3. Documents
Documents are content entries in Sanity. Once your schemas are defined, you can create documents based on those schemas in the Content Studio.
How to Create a Document in the Studio:
- Open your Sanity Studio (
http://localhost:3333
). - Choose "Blog Post" (or your schema name) from the sidebar.
- Fill in the form with content (e.g., title, body, and author) and hit Publish.
4. Portable Text
Portable Text is Sanity’s flexible rich text editor, which allows you to define how different text elements (like images, headings, or custom components) appear in your content.
Using Portable Text in Schema:
- In your schema, specify a field as
type: 'portableText'
. - You can extend Portable Text to include custom blocks:
export default {
name: 'body',
title: 'Body',
type: 'array',
of: [
{ type: 'block' }, // Basic block elements like paragraphs
{ type: 'image' }, // Custom image blocks
],
};
5. Sanity Client
The Sanity Client is used in your front-end framework (like React or Next.js) to fetch content from Sanity. It uses GROQ, a querying language designed specifically for Sanity.
Install the Sanity Client:
In your Next.js or React.js project, install the Sanity client:
npm install @sanity/client @sanity/image-url
Set up the Sanity Client:
- Create a
sanity.js
file in your front-end project to configure the client:
import sanityClient from '@sanity/client';
export const client = sanityClient({
projectId: 'yourProjectId', // found in sanity.json or sanity studio
dataset: 'production',
apiVersion: '2023-01-01', // use a specific API version
useCdn: true, // 'false' if you want the latest data
});
Example GROQ Query:
To fetch blog posts, use GROQ with the client:
import { client } from './sanity';
const query = `*[_type == "blog"]{title, body, publishedAt}`;
const blogs = await client.fetch(query);
You now have all blog posts fetched and can render them in your Next.js or React components.
6. Image Handling
Sanity provides powerful image handling capabilities, allowing you to crop, resize, and optimize images with ease.
Use Image URLs with Transformations:
- Install the
@sanity/image-url
package:
npm install @sanity/image-url
- Set up the image URL builder:
import imageUrlBuilder from '@sanity/image-url';
import { client } from './sanity';
const builder = imageUrlBuilder(client);
export function urlFor(source) {
return builder.image(source);
}
- Use in a Next.js or React component:
import { urlFor } from './sanity';
const Blog = ({ blog }) => (
<div>
<h1>{blog.title}</h1>
<img src={urlFor(blog.image).width(800).url()} alt="Blog Image" />
</div>
);
This example shows how to generate an optimized image URL from Sanity for rendering in your component.
7. Data Relationships
You can create relationships between documents in Sanity by using the reference
type. This is useful for linking data like blog authors and their posts.
Example: Author Reference in Blog Post Schema
{
name: 'author',
title: 'Author',
type: 'reference',
to: [{ type: 'author' }]
}
In the Content Studio, you can then select an author document as a reference while creating a blog post.
8. Real-Time Collaboration
Sanity offers real-time collaboration, where multiple users can work on the same document simultaneously. Changes appear instantly for all users working on the content.
This feature is built into the Sanity Studio automatically, and you don't need to do any special setup to enable it.
9. Integrating Sanity with Next.js/React.js
To integrate Sanity with a Next.js or React.js project, follow these steps:
Example: Fetch Blog Data in Next.js
- Use
getStaticProps
to fetch Sanity data at build time:
import { client } from '../sanity';
export async function getStaticProps() {
const blogs = await client.fetch(`*[_type == "blog"]`);
return {
props: { blogs },
};
}
const BlogList = ({ blogs }) => (
<div>
{blogs.map(blog => (
<div key={blog._id}>
<h2>{blog.title}</h2>
<p>{blog.body[0]?.children[0]?.text}</p>
</div>
))}
</div>
);
export default BlogList;
- In React.js, use
useEffect
to fetch data dynamically:
import { client } from './sanity';
import { useState, useEffect } from 'react';
const BlogList = () => {
const [blogs, setBlogs] = useState([]);
useEffect(() => {
const fetchBlogs = async () => {
const data = await client.fetch(`*[_type == "blog"]`);
setBlogs(data);
};
fetchBlogs();
}, []);
return (
<div>
{blogs.map(blog => (
<div key={blog._id}>
<h2>{blog.title}</h2>
<p>{blog.body[0]?.children[0]?.text}</p>
</div>
))}
</div>
);
};
export default BlogList;
Summary:
- Sanity Studio: Manage content visually and customize data structure with schemas.
- Schemas: Define content structure (documents, objects, references).
- Portable Text: Flexible rich text editor with support for custom components.
- Sanity Client: Fetch content using GROQ in React/Next.js.
- Image Handling: Easily generate optimized image URLs.
- Data Relationships: Link documents using references.
- Real-Time Collaboration: Built-in for team workflows.
This setup allows you to efficiently manage, query, and display content in front-end frameworks like Next.js and React.js.
Posted on October 12, 2024
Join Our Newsletter. No Spam, Only the good stuff.
Sign up to receive the latest update from our blog.