
Grab your gear: The official Sanity swag store
Read Grab your gear: The official Sanity swag storeAbsolutely! Creating a document from a frontend form and saving it as a draft is a common pattern. Here's what you need to know:
drafts. to the Document IDWhen you create a document through the Sanity Client, you can make it a draft by prepending drafts. to the document's _id. This is exactly how Sanity Studio handles drafts internally.
Here's a simple example of how to do this:
import { createClient } from '@sanity/client'
const client = createClient({
projectId: 'your-project-id',
dataset: 'your-dataset',
useCdn: false, // We need fresh data when writing
token: 'your-write-token', // You'll need a token with write permissions
apiVersion: '2024-03-01'
})
// Handle form submission
async function handleFormSubmit(formData) {
const newDocument = {
_id: `drafts.${Date.now()}`, // Prepend 'drafts.' to create a draft
_type: 'yourDocumentType',
title: formData.title,
// ... other fields from your form
}
try {
const result = await client.create(newDocument)
console.log('Draft created:', result)
} catch (error) {
console.error('Error creating draft:', error)
}
}Authentication: You'll need an API token with write permissions. Create one in your Sanity project's settings. Never expose this token in client-side code - instead, proxy the request through an API route or serverless function.
Document ID: You can either:
drafts.my-custom-idPublishing: When you're ready to publish the draft, you can use the Sanity API to remove the drafts. prefix and create the published version.
If you're using Next.js (as mentioned in this community answer), create an API route to handle the form submission securely:
// pages/api/create-draft.js
import { createClient } from '@sanity/client'
const client = createClient({
projectId: process.env.NEXT_PUBLIC_SANITY_PROJECT_ID,
dataset: process.env.NEXT_PUBLIC_SANITY_DATASET,
token: process.env.SANITY_WRITE_TOKEN, // Keep this secret!
apiVersion: '2024-03-01',
useCdn: false
})
export default async function handler(req, res) {
if (req.method !== 'POST') {
return res.status(405).json({ message: 'Method not allowed' })
}
try {
const document = {
_id: `drafts.${Date.now()}`,
_type: req.body.type,
...req.body.fields
}
const result = await client.create(document)
res.status(200).json(result)
} catch (error) {
res.status(500).json({ error: error.message })
}
}This keeps your write token secure on the server side while allowing your frontend to create drafts safely!
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.
Content operations
Content backend


The only platform powering content operations
By Industry


Tecovas strengthens their customer connections
Build and Share

Grab your gear: The official Sanity swag store
Read Grab your gear: The official Sanity swag store