📆 Don't miss our Sanity Showcase virtual meetup on March 20th!

How to create a custom data structure for quotes in Portable Text

9 replies
Last updated: Aug 22, 2021
What you describe here is essentially a data structure that consists of a quote (a text string) and an author name (a text string). Portable Text lets you insert custom data structures in between paragraphs (which also are their own objects really. The way I’d do this would be to first define a new object type:
// quote.js
export default {
  name: 'quote',
  type: 'object',
  title: 'Quote',
  fields: [
    {
      name: 'text',
      type: 'text', // <= This can also be a Portable Text field
      title: '',
    },
    {
      name: 'author',
      type: 'string', // <= This could be a reference to an author document type, if you had that
      title: 'Author',
    }
  ]
}
Remember to import this into your schemas in
schema.js
and then you can add the following to your Portable Text field (I’ve made a simple one here:
// portableText.js
export default {
  name: 'portableText',
  type: 'array',
  title: 'Portable Text',
  of: [
    {
      type: 'block',
    },
    {
      type: 'quote',
    }
  ]
}

Aug 22, 2021, 9:13 AM
Come think of it, you could also add support for an URL in the quote (reasoning in a bit):
// quote.js
export default {
  name: 'quote',
  type: 'object',
  title: 'Quote',
  fields: [
    {
      name: 'text',
      type: 'text', // <= This can also be a Portable Text field
      title: '',
    },
    {
      name: 'author',
      type: 'string', // <= This could be a reference to an author document type, if you had that
      title: 'Author',
    },
    {
      name: 'url',
      type: 'url',
      title: 'URL',
      description: 'Source on the web', 
     }
  ]
}

Aug 22, 2021, 9:16 AM
Amazing! This was really helpful and I’ve already got it set up in my codebase now. Very quick and easy to implement 😀👍
Aug 22, 2021, 9:17 AM
And the serializer for this in the frontend can be something like this:
// portableText.js
const serializers = {
  type: {
    quote: ({ text, author, url }) => {
      return (
        <figure>
          <blockquote cite={url}>
            {text}
          </blockquote>
          {author && <figcaption>{author}</figcaption>}
        </figure>
      )
    }
  }
}
Just went on a
🐰 🕳️ on how to properly markup this with HTML5. Not super obvious tbh. This seems like a reasonable solve .
Aug 22, 2021, 9:25 AM
Any idea why the above code wouldn’t work?
I’m getting the data through in my block content as I can see the quote in GrapQL.

When I add the word ‘test’ in after the {text} variable, in the serializer, that’s showing up i.e.:

<blockquote>{text} test</blockquote>
But the actual text and author is not showing up.

The serializers are in a separate js file and are piped into my block content like:

<BlockContent serializers={serializers} />
Aug 22, 2021, 9:39 AM
oh, I forgot the pattern should be
// portableText.js
const serializers = {
  type: {
    quote: ({node: { text, author, url }}) => {
      return (
        <figure>
          <blockquote cite={url}>
            {text}
          </blockquote>
          {author && <figcaption>{author}</figcaption>}
        </figure>
      )
    }
  }
}
That is including
node
in
({node: { text, author, url }})
Aug 22, 2021, 9:44 AM
sorry about that
Aug 22, 2021, 9:44 AM
Lovely, that’s working now. Thanks again, this was really helpful 👍
Aug 22, 2021, 9:46 AM

Sanity– build remarkable experiences at scale

Sanity is a modern headless CMS that treats content as data to power your digital business. Free to get started, and pay-as-you-go on all plans.

Was this answer helpful?

Related answers

Get more help in the community Slack

TopicCategoriesFeaturedRepliesLast Updated
Rendering nested block contentJan 18, 2021
GraphQL query resolving references on a _raw field in GatsbyMay 17, 2022
Error: unable to resolve image URL from source (undefined)Sep 11, 2022
Examples of customized dashboards/admin pages and the queryable feature of Portable Text.May 1, 2020
Extracting referenced images from an object array in Sanity.ioMay 17, 2020
How to preview content inside a reference array in Sanity.ioAug 14, 2020
Hi, I need help with Iframe preview, I have a `route` schema with unique `slug` (`/lb/123`) and also I have `page` schema...Dec 21, 2020
Hi! How to add a doc via sanity client that has a *weak* reference? If I do this, it throws an error `key "weak" not allowed...Feb 2, 2021
How come images are returning with just a _ref in their assets?Feb 3, 2021
Troubleshooting reference fields in a Next.js Landing page templateMay 2, 2020

Related contributions

Turbo Start Sanity
- Template

The battle-tested Sanity template that powers Roboto Studio's websites

Go to Turbo Start Sanity

Schema UI - Next.js Sanity Starter
- Template

A Next.js starter template with Next.js 15, Tailwind CSS, shadcn/ui, and Sanity CMS with Live Editing. Get production-ready React components with matching Sanity schemas and queries. Build dynamic pages faster while keeping full control over customization.

Serge Ovcharenko
Go to Schema UI - Next.js Sanity Starter

The Swaddle
- Made with Sanity

A new brand identity to represent a more mature company, to signify The Swaddle’s evolution from publisher to production house, combined with an easier to navigate platform that can surface multiple content types - drawing readers through The Swaddle’s content offering.

Nightjar
Go to The Swaddle