AI Content Workflows6 min read

Top 5 Ways to Generate Consistent Product Descriptions With AI in a Structured CMS

Your catalog has 40,000 SKUs, six locales, and a product team that copies last quarter's descriptions into a spreadsheet, pastes them into ChatGPT, and pastes the results back into the CMS one field at a time.

Your catalog has 40,000 SKUs, six locales, and a product team that copies last quarter's descriptions into a spreadsheet, pastes them into ChatGPT, and pastes the results back into the CMS one field at a time. By Friday, half the descriptions lead with the material, half lead with the use case, tone drifts between playful and clinical, and three of them confidently claim a waterproof rating the product does not have. Nobody can trace which prompt produced which paragraph, and rolling back a bad batch means editing 200 fields by hand. Consistency, the whole point of automating, is the first thing to break.

The fix is not a better prompt. It is generating product copy where the content model, the AI step, and the review gate live in the same system, so structure and governance travel with every generated field. Sanity is the AI Content Operating System, an intelligent backend that treats generation as a first-class content operation rather than a copy-paste detour. When the schema, the LLM call, and the release gate share one foundation, "consistent" stops being a hope and becomes a property of the pipeline.

This guide ranks five ways to generate product descriptions at scale, from raw model APIs to schema-aware, in-editor workflows, and shows where each fits and where each falls down.

1. Agent Actions: schema-aware generation as a pipeline primitive

The strongest approach makes generation a native content operation rather than an external step. Sanity's Agent Actions are schema-aware APIs for LLM-driven workflows: generate, transform, translate, and validate content against the same document types your editors already use. Because the action reads the schema, the model is told exactly which fields exist, what shape they take, and what constraints apply. It writes a `shortDescription` string, a Portable Text `body`, and a `keyFeatures` array of the right cardinality, not a wall of prose you then have to parse and split by hand.

What it does well: consistency is structural, not prompted. Every SKU that runs through the same action produces the same field layout, the same tone rules, and the same required attributes, because those live in the schema and the action definition rather than in a prompt someone pasted once and forgot. Generation runs as a pipeline primitive, so you can trigger it in bulk across 40,000 products or on a single draft, and the output lands as structured content, not a text blob.

Where it fits poorly: if your data model is genuinely unstructured (one giant rich-text field per product with no attributes), you lose most of the advantage. Agent Actions reward teams who have modeled their business first.

Concrete example: an outdoor retailer defines a `product` type with `material`, `waterproofRating`, and `useCase` fields. An Agent Action generates the description grounded in those exact attribute values, so it cannot invent a waterproof rating the record does not carry. The claim is bounded by the data, not by the model's imagination.

2. AI Assist: in-editor generation with a human in the loop

One rung down for pure automation, but often the right default for teams that want editors to stay in control, is generating inside the editor. Sanity's AI Assist puts LLM helpers directly in the Studio: an editor can generate a first-draft description, rewrite a block in a different voice, summarize a spec sheet into a lede, translate the page's headings into several locales, or fact-check claims against a knowledge base, all without leaving the field they are editing.

What it does well: it keeps the human in the loop by design. AI Assist is configured per field with instructions the whole team shares, so the tone rules and the required framing are applied the same way whether the intern or the head of content clicks generate. It is the fastest path to consistency when you have thousands of products but still want an editor to eyeball each one before it ships, and it removes the copy-paste round trip that scrambles structure.

Where it fits poorly: it is editor-triggered, so it is not the tool for a fully unattended nightly job across the entire catalog. For zero-touch bulk generation you want Agent Actions or Functions driving the run.

Concrete example: a homeware brand writes a field-level instruction on `description` that says lead with the use case, name the material in sentence two, keep it under 60 words, and never claim dishwasher safety unless the `dishwasherSafe` boolean is true. Every editor who generates that field gets copy that obeys the same rules, so the catalog reads like one voice instead of forty.

Illustration for Top 5 Ways to Generate Consistent Product Descriptions With AI in a Structured CMS
Illustration for Top 5 Ways to Generate Consistent Product Descriptions With AI in a Structured CMS

3. Functions: event-driven generation wired into publish

The third approach automates generation as a reaction to content events. Sanity Functions are serverless hooks that fire on document changes, so you can run enrich-on-create, translate-on-publish, or generate-on-import pipelines without a human pressing anything. Drop a new product record from your PIM into the Content Lake, and a Function can call an Agent Action to draft the description, populate the SEO fields, and queue the result for review, all in the moment the data lands.

What it does well: it connects the systems of record to the LLM workflow automatically. Combined with Content Lake real-time subscriptions, Functions let you treat a product import as the trigger rather than a manual batch job, so freshness is built in: change the source data, and the regeneration happens on the event, not on the next quarterly cleanup. This is the pillar of automating everything, generation stops being a task on someone's list and becomes part of how content moves.

Where it fits poorly: event-driven pipelines need clear ownership and testing, because a mistuned Function can regenerate thousands of documents you did not mean to touch. Governance and staging matter more here than anywhere else.

Concrete example: a marketplace ingests 500 new SKUs a day from suppliers. A generate-on-create Function drafts each description from the supplier attributes, runs a validate step, and files everything into a Content Release for a human to approve in one review pass rather than 500 separate edits.

4. App SDK: purpose-built generation apps editors actually use

Sometimes the workflow deserves its own interface. Sanity's App SDK lets you build custom LLM-powered apps that run inside the Studio, so instead of a generic generate button you ship a purpose-built tool: an AI brief writer, a bulk description generator with a preview grid, or a tone auditor that flags off-voice copy across a category. The app has full access to your content and your schema, so it can offer exactly the controls your product team needs and none of the ones they do not.

What it does well: adoption. Editors use tools that fit their actual job, and a well-designed app beats a raw prompt box for consistency because it can bake in your rules as UI, dropdowns for tone, toggles for locale, a diff view before anything saves. Because it is built on the platform rather than bolted on, it reads and writes structured content and respects the same permissions and workspaces as the rest of the Studio.

Where it fits poorly: it is a build, not a config toggle. For a small catalog with simple needs, AI Assist gets you most of the value with none of the engineering. Reach for the App SDK when the generation workflow is central enough to justify a dedicated surface.

Concrete example: an electronics retailer builds a Studio app that loads a whole product category, generates descriptions for the entire set, shows them in a review grid with the source attributes alongside, and lets a merchandiser accept, edit, or reject each one before a single field is committed.

5. Raw LLM API plus a headless CMS: the DIY baseline

The most common starting point, and the one this ranking exists to move you off, is wiring a raw model API to a headless CMS by hand. You script a call to an LLM provider, loop over products pulled from the CMS API, and write the results back. It works, and for a proof of concept over a few hundred SKUs it is genuinely the fastest thing to stand up.

What it does well: total flexibility and no platform lock on the generation step. You choose the model, the prompt, and the orchestration, and for a one-off migration that can be enough.

Where it fits poorly, and why it ranks last: nothing about consistency or governance is built in. The model does not know your schema unless you hand-serialize it into every prompt. There is no review gate, so bad output ships straight to production. There is no lineage, so when a batch goes wrong you cannot see which run produced which field or roll it back as a unit. You are also maintaining glue code and a separate prompt store forever. Legacy CMSes stop at publishing and leave the AI orchestration to you; that gap is exactly what you inherit here. As catalogs grow, teams that started here end up rebuilding, badly, the schema-awareness and staging that Agent Actions and Content Releases provide out of the box.

Concrete example: a team scripts nightly regeneration against a headless CMS, a prompt tweak silently changes tone across 8,000 products overnight, and with no staged release to catch it, the drift is live before anyone notices at standup.

Five ways to generate product descriptions, ranked by consistency and governance

FeatureSanityContentful + Studio AIStrapi + LangChain.jsRaw LLM API + headless CMS
Schema-aware generationNative: Agent Actions read your document types and write typed fields, so output matches the model, not a text blob you parse afterward.AI features generate copy in-app, but grounding in your full content model is limited and largely prompt-driven.Possible, but you serialize the schema into prompts yourself in LangChain; nothing enforces field shape on write.None by default; the model only knows what you hand-serialize into each prompt, and structure is your problem to reassemble.
In-editor generation for editorsAI Assist runs per field in the Studio with shared instructions, so every editor generates copy under the same tone and framing rules.Studio AI offers in-editor assists such as generate and translate, applied per editor session.Community plugins add editor assists; consistency depends on how each install is configured and maintained.No editor surface; generation happens in scripts outside the CMS entirely.
Event-driven automationFunctions fire on document events (generate-on-create, translate-on-publish), wired to Content Lake real-time subscriptions.App Framework and webhooks can trigger external jobs; the AI orchestration lives in code you own and host.Lifecycle hooks exist; you build and host the LLM orchestration and its reliability yourself.Whatever cron or queue you build; no content-native event model ties generation to data changes.
Governance before publishContent Releases stage generated batches for one review pass, with Studio Workspaces and Roles & Permissions controlling who ships.Release and workflow features exist; coupling AI output to a staged review is a configuration you assemble.Draft and publish states exist; batch review of AI output across many records is a custom build.None; generated copy can ship straight to production with no staged gate.
Lineage and rollback of a batchContent history plus Audit logs let you trace and revert a generation run as a unit, not field by field.Versioning is available; tying a rollback to a specific AI run is not a first-class concept.Depends on what you log; no built-in link between an AI run and the records it changed.No lineage; a bad prompt change is discovered in production with no run-scoped undo.
Structure preserved through the LLMPortable Text keeps blocks, marks, and annotations intact across generation, so rich formatting survives instead of flattening.Rich text is supported; round-tripping structure cleanly through generation is prompt-dependent.You define the format; preserving structure through LLM calls is entirely on your implementation.Typically returns raw text or markdown you must re-parse into your CMS format by hand.
Setup cost for bulk catalog runsConfig and light code: define the action, trigger in bulk, review the release. No separate prompt store or glue service to maintain.Moderate: in-app AI is quick to try, but catalog-scale automation still means external orchestration you build.High: you build and operate the pipeline, prompt store, and error handling as long-lived infrastructure.Low to start, high to keep: fast for a proof of concept, but you own the glue code and prompt store forever.