How to reuse schema sections across multiple schemas in Sanity?

6 replies
Last updated: Oct 6, 2023
Can someone help me find documentation on how to reuse schema sections? Example, I have a color picker I want to use in multiple places and schemas. Thanks.
AI Update

I can help you with reusing schema sections in Sanity! The key is to define reusable field definitions or object types that you can reference throughout your schemas.

Creating Reusable Fields

For a color picker you want to use in multiple places, you have a few approaches:

1. Define a reusable field configuration:

Create a shared field definition that you can spread into multiple schemas:

// In a shared file like schemas/fields/colorPicker.ts
import { defineField } from 'sanity'

export const colorPickerField = defineField({
  name: 'color',
  title: 'Color',
  type: 'color',
  options: {
    disableAlpha: true
  }
})

// Then use it in your document schemas
import { defineType } from 'sanity'
import { colorPickerField } from './fields/colorPicker'

export const myDocumentType = defineType({
  name: 'myDocument',
  type: 'document',
  fields: [
    colorPickerField,
    // ... other fields
  ]
})

2. Create a reusable object type:

If you want a more complex reusable structure, define a custom object type using defineType:

// In schemas/objects/colorSettings.ts
import { defineType } from 'sanity'

export const colorSettings = defineType({
  name: 'colorSettings',
  title: 'Color Settings',
  type: 'object',
  fields: [
    {
      name: 'backgroundColor',
      title: 'Background Color',
      type: 'color'
    },
    {
      name: 'textColor',
      title: 'Text Color',
      type: 'color'
    }
  ]
})

// Use it in your schemas
export const pageType = defineType({
  name: 'page',
  type: 'document',
  fields: [
    {
      name: 'colorScheme',
      type: 'colorSettings' // Reference your reusable object type
    }
  ]
})

3. Factory function for variations:

If you need the same field with different names across schemas, create a factory function:

// schemas/fields/colorPickerFactory.ts
import { defineField } from 'sanity'

export const createColorField = (name: string, title: string) => 
  defineField({
    name,
    title,
    type: 'color',
    options: {
      disableAlpha: true
    }
  })

// Use it
const brandColor = createColorField('brandColor', 'Brand Color')
const accentColor = createColorField('accentColor', 'Accent Color')

The defineField helper provides TypeScript support and autocomplete, making it the recommended approach for defining any field in Sanity. By extracting common field definitions into shared modules, you maintain consistency across your schema and make updates easier—change the color picker configuration once, and it updates everywhere you've used it.

Show original thread
6 replies
I saw a conversation recently regarding this link: https://www.sanity.io/docs/schema-field-types#81e2f304a9a8 which itself harkens back to this one: https://www.sanity.io/docs/schemas-and-forms
The basic idea is that you can write documents or objects, and while setting up the Desk Tool only shows
documents in each pane, you can add any custom objects you want as well to the schema by simply setting up your config to let it know they exist.
Basically, if they're in the schema, they're officially usable.

A great guide came out too where this happens twice in a kind of nested way, and it demonstrates the flexibility of the concept:
https://www.sanity.io/guides/create-a-time-duration-object-field
Thank you. I will poke around at these links.
So what I ended up doing is this:

Make a file for the schema:
export default defineType({
  name: "colorPicker",
  title: "Color Picker",
  description:
    "Changes the background color of this section. Default is 'water'.",
  type: "string",
  options: {
    list: [
      { title: "Water",         value: "water", },
      { title: "Sunshine",         value: "sunshine",  },
      { title: "Ocean",         value: "ocean",   },
      {  title: "Forest",         value: "forest",  },
      { title: "Grey",         value: "grey", },
    ],
  },
});
In the schema I want to use it, I just do this:

defineField({
   name: "colorPicker",
   title: "Color Picker",
   type: "colorPicker",
 }),
Then import into sanity.config.ts
Is it working okay for you?
Yeah so that is working as I wanted now.
Sweet!

Sanity – Build the way you think, not the way your CMS thinks

Sanity is the developer-first content operating system that gives you complete control. Schema-as-code, GROQ queries, and real-time APIs mean no more workarounds or waiting for deployments. Free to start, scale as you grow.

Was this answer helpful?