Compute and AI

Functions quick start

Start building with Functions by initializing and deploying a new function to Sanity's infrastructure.

Functions allow you to run small, single-purpose code whenever your content in Sanity changes. This guide explains how to set up your project, create your first Blueprint, initialize a Function, and deploy it to Sanity's infrastructure.

Avoid recursive loops

Prerequisites:

  • sanity CLI v3.88.1 or higher is required to interact with Blueprints and Functions. You can always run the latest CLI commands with npx sanity@latest.
  • Node.js v22.x. We highly suggest working on this version as it is the same version that your functions will run when deployed to Sanity.
  • An existing project and a role with project update permissions.

Set up your project

To create your first function, you need to initialize a blueprint. Blueprints are templates that describe Sanity resources. In this case, a blueprint describes how your function will connect with your Sanity project. We recommend keeping functions and blueprints a level above your Studio directory.

For example, if you have a Marketing Website that uses Sanity, you may have a structure like this:

marketing_site/
├─ studio/
├─ next-app/

If you initialize the blueprint in the marketing_site directory, functions and future resources will live alongside the studio and next-app directory.

marketing_site/
├─ studio/
├─ next-app/
├─ functions/
│  ├─ myFunction/
│  │  ├─ index.js

Functions and Blueprints match your workflow

If you're using version control, you may also want to add the following lines to your .gitignore file.

Create a blueprint

Initialize your first blueprint with the init command. It will prompt you for the following:

  • Format: This guide uses JSON.
  • Project: Select your project. This is the project that will trigger functions.

This creates a few configuration files in your project directory.

Create a function

Use the blueprints add function command to add a new function. The CLI prompts you for the following:

  • Function name: Set a name for your function. This determines the function name and the name of its directory. For this example, we'll call it "logEvent".
  • Function type: Select the document action that will trigger the function. For this example, select Document Publish.
  • Function language: Select your preferred language. For this example, we'll select TypeScript.

After defining the name and selecting a type, Blueprints updates the blueprints.json config, creates a local functions directory, a subdirectory with the function name, and some starter code.

Every function consists of a handler exported by index.js.

The handler receives a context and an event. The context contains information to help you interact with your Sanity datastore, such as clientOptions to configure a @sanity/client.

The event contains information about the action that triggered the function. The most useful property is event.data, which contains the contents of the document. You can learn more in the Function handler reference.

Limit the scope with GROQ

Right now, the function runs every time any document publishes. This includes system documents. You'll almost always want to scope your functions to specific scenarios with GROQ filters.

Open the blueprints.json file and you should see the following:

Add a filter property to the event object. Set it to match a document type that works for your project.

Only include the filter contents, the portion inside the square brackets, of your GROQ query. For example, rather than *[_type == 'post'], only include _type == 'post'.

You can also include a projection property in event to shape the contents passed to the event. Like with filter, only include the inner contents of the curly brace wrapper. Projections don't limit what fields trigger the function, only which data is passed into the function.

Limited GROQ support

Test the function locally

You can test functions locally with the functions test command. Local testing is a great way to experiment without affecting your usage quota.

To test a function without passing in any data, run the following:

If you run this on the starter function from earlier, you'll see a response similar to the following:

You can also pass in JSON as a file (--file) or data string (--data) to substitute the event payload.

Capture a document for easier testing

Update your function to log the event and you'll see the data/file contents in the Logs part of the output the next time you run the test command.

Test ignores event settings

Deploy a function

Once you're satisfied that the function works as expected, you can deploy it by deploying the blueprint.

You can begin using your function when the deployment is finished. If you set a filter earlier, edit a document that matches it and publish the changes to trigger the function.

If you need to change the function, update your code and re-run the deploy command to push the new changes live.

Check the logs

When you tested the function locally, you saw the logs directly in your console. Once deployed, the function and its logs are in the cloud.

View the logs with the functions logs command. Replace logEvent with your function name.

This command outputs the function's logs. Try updating your document, publishing the change, and running the command again to see new logs.

System documents

Destroy a deployed blueprint

Sometimes you want to remove a deployed function so it won't run anymore or affect any future usage quotas. The blueprints destroy command removes, or undeploys, the blueprint and all of its functions from Sanity's infrastructure. It does not remove your local files.

Remove the test function:

To remove the function from the blueprint locally, you can remove it from the resources array in the blueprints.json file, then delete the logEvent folder from the functions directory.

Redeploying a destroyed blueprint

When you run blueprints destroy, it's as if you never used blueprints init during setup. The only difference is you still have all the files in your directory. To use this blueprint again and redeploy it, you'll need to let Sanity know about it. You can do this by running the following:

This launches an editing interface that lets you reconfigure the blueprint, if needed, and it reconnects the blueprint to Sanity. Now you can add more functions or redeploy. Keep in mind that any environment variables added before destroying the blueprint will not carry over.

Was this page helpful?