Sanity.io: a really good CMS
Tags: webdev, javascript, beginners, programming
Published: 2022-06-30 03:28:53

A couple weeks ago, I had to figure how to serve dynamic content for my personal website. While researching, I was led to the concept of a CMS (Content Management System). Most CMSs have the concept of the frontend and backend both being included, but that wouldn't work for my use case, since I already had a frontend up and running. 

### Headless CMS
This is where I learned about the concept of a Headless CMS. The concept of a Headless CMS is that you only get the backend, and instead you ping an API for your data.

I started searching for a good list of Headless CMSs, but none of them were quite as quick to setup as I expected. Most of them required you to host them somewhere, and I *definitely* did not want to spend money in order to host my stuff on a server.

### Introduction to Sanity
![benjamin ashbaugh (who has a profile picture of a cow) saying "If you’re looking for something that will let you get set up quickly for free without needing to self-host, I recommend sanity.io"](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ca8gsp359m9rxa1h9gns.png) 

While I was searching for a good CMS for my website, a certain [Benjamin Ashbaugh](https://benjaminashbaugh.me/) (yes, I can confirm he is a cow) in [Hack Club's](https://hackclub.com/) Slack workspace told me about a certain CMS called Sanity. It didn't require me to host my own instance anywhere and was really easy to edit through a tool called Sanity Studio.

So I decided to give it a try, since the worse that could happen is that I don't have a good experience and lose hours of my life ¯\_(ツ)_/¯

### Let's-a-go!
![Mario running](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/wjqcs3ual505x84olu4w.png)
 
Sanity has a really good [starter guide](https://www.sanity.io/get-started/1) to introduce you to the technology, so I would recommend following that to get the basic repository set up

### Difference between Sanity Studio and Content Lake

Sanity Studio is a really intuitive tool used to manipulate data from Sanity itself (sort of like how Prisma Studio). Content Lake is the data itself that comes from handling data in Sanity Studio. Clients can access the Content Lake from the API that Sanity provides.

### Schema
After you get Sanity Studio working, you're probably going to have to generate a schema.

One file will be labeled `schema.js`, which will be the gateway to our schema. Here is an example of it:

```js
// First, we must import the schema creator
import createSchema from "part:@sanity/base/schema-creator";

// Then import schema types from any plugins that might expose them
import schemaTypes from "all:part:@sanity/base/schema-type";
import project from "./project";

// Then we give our schema to the builder and provide the result to Sanity
export default createSchema({
  // We name our schema
  name: "default",
  // Then proceed to concatenate our document type
  // to the ones provided by any plugins that are installed
  types: schemaTypes.concat([
    /* Your types here! */
    project,
  ]),
});
```

You might be wondering what exactly is the `project` import doing there. Well, that's our second file, the actual schema of the entity in question, `project.js`. Here is an example of that file:

```js
export default {
  name: "project",
  type: "document",
  title: "Project",
  fields: [
    {
      name: "name",
      type: "string",
      title: "Name",
    },
    {
      name: "description",
      type: "string",
      title: "Description",
    },
    {
      name: "demo",
      type: "string",
      title: "Demo",
    },
    {
      name: "github",
      type: "string",
      title: "Github",
    },
    {
      title: "Technologies",
      name: "technologies",
      type: "array",
      of: [{ type: "string" }],
    },
    {
      title: "Image",
      name: "image",
      type: "image",
    }
  ],
};
```

Here, first of all, we import an object as the default export. Then, we define the `name`, `type`, and `title`. In our `project.js` file, we specify that it is a `"document"`. Now, you might be wondering the difference between the `name` and the `title`. The name is most likely how Sanity refers to the data internally, while `title` is just how it's presented to the user.

The `fields` array contains a bunch of objects specifying the different fields in the schema. You can find more about schema types [here](https://www.sanity.io/docs/schema-types)

## Sanity Client

To access data from the Content Lake, I'm going to use a client for Sanity. Alternatively, you can use the [HTTP API](https://www.sanity.io/docs/http-api).

I'm going to use the Node.js API, so I can simply install it with

```bash
npm install @sanity/client
```
or
```bash
yarn install @sanity/client
```

Then, we are going to create a new file (anywhere you want) with any name you want (I'm going to use `client.js`)

Then, use the code
```js
import sanityClient from "@sanity/client";

export const client = sanityClient({
  projectId: "PROJECT_ID_PROVIDED_IN_SANITY.JSON",
  dataset: "DATASET_PROVIDED_IN_SANITY.JSON"
  useCdn: true,
});
```
Here, we're using the `useCdn:true`, because the CDN is much faster to respond and gives us more API calls in our free tier. Although, it doesn't update the content as quickly as without the CDN, so do keep that in mind.

Then, to get the content, we can use  

```js
const projects = await client.fetch(
    `
    *[_type == "project"]
  `
);
```

This basically selects everything document that has the type of "project" (e.g. every piece of content that follows the schema in `project.js` from the earlier example. Remember to run this in an `async` function by the way.

If you're curious about the query language that is used by Sanity, check out the guide [here](https://www.sanity.io/docs/how-queries-work) and the [cheatsheet](https://www.sanity.io/docs/query-cheat-sheet)

## End
So that's pretty much. Leave a reaction on the beautiful panel to your left (or a comment below)!

Follow me on Twitter: https://twitter.com/ShubhamPatilsd
Follow me on GitHub: https://github.com/ShubhamPatilsd