Agent Actions

In the previous lesson you made programmatic changes to a document. In plain language it would be described as:
When published, write the current date and time to a field if it is not already set
With AI tooling now omnipresent, your ambitions can be much grander. Agent Actions allows you to work with Sanity documents with built-in AI to either Generate, Transform or Translate content with instructions.
Agent Actions can be triggered via the API, or using Sanity Client perhaps in a Sanity Function or script.
Generate can create new, or update existing, documents by following an instruction (or "prompt").
In this lesson you'll create a script using this API to write new content to the details
field in an event.
import {getCliClient} from 'sanity/cli'
const client = getCliClient({apiVersion: 'vX'})const EVENT_QUERY = `*[_type == "event" && !defined(details)][0]._id`
async function run() { const eventId = await client.fetch(EVENT_QUERY)
console.log({eventId})}
run()
This script:
- Imports a function to get the Sanity Client configured by the Sanity CLI
- Updates its configuration to use API Version
vX
(currently required for Agent Actions) - Queries for the first event it can find where
details
has no value - Logs that event ID to the console
# in apps/studiopnpm dlx sanity@latest exec scripts/details.ts
In response you should see a warning about the API Version and the ID of the document it found
This is an experimental API version, which will change without warning and may have serious bugs.{ eventId: '57c1561e-378c-4124-9aa2-88c0db96a037' }
In the previous script you only retrieved the document ID, which is required for an Agent Action to target a document.
In the updated script below, the GROQ query is more refined to only find an event document with a "headline" and "venue" so that the value of these fields can be used to create a rich instruction
for the action.
Also note the schemaId
which has been set to the default name for deployed schemas. This was done for you when you completed Deploying your Studio.
import {getCliClient} from 'sanity/cli'
const client = getCliClient({apiVersion: 'vX'})const EVENT_QUERY = `*[ _type == "event" && defined(headline) && defined(venue) && !defined(details)][0]{ _id, headline->{ name }, venue->{ name }}`
type EventDocument = { _id: string headline: {name: string} venue: {name: string}}
async function run() { const event = await client.fetch<EventDocument>(EVENT_QUERY)
await client.agent.action .generate({ schemaId: '_.schemas.default', documentId: event._id, instruction: 'Create a short description of what attendees can expect when they come to this event. The headline artist is "$headline" and the venue is "$venue".', instructionParams: { headline: event.headline.name, venue: event.venue.name, }, target: [{path: ['details']}], }) .then((res) => { console.log('Wrote description:', res.details[0].children[0].text) }) .catch((err) => { console.error(err) })}
run()
Because this script will now need permissions to modify documents, you will now need to run this script with the --with-user-token
argument.
event
document with a details
field# in apps/studiopnpm dlx sanity@latest exec scripts/details.ts --with-user-token
You should receive confirmation in your terminal that a document was updated, something like:
Wrote description: Experience an unforgettable night at the Austin City Limits Music Festival with the electrifying sounds of ...
Double check the document in your Studio (it should've been moved to the top of the document list). You'll notice that if the action was run against a published document, this new value was written to a new draft document and will need to be published.
You've manually performed your first Agent Action, think of all the content operations you could now automate!
With that, you're done! Let's test everything you've learned in a final quiz.