Skip to content

Instantly share code, notes, and snippets.

@christopherafbjur
Last active May 30, 2023 19:32
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save christopherafbjur/39e33e914de292fe8b5ae5cbc2ab82aa to your computer and use it in GitHub Desktop.
Save christopherafbjur/39e33e914de292fe8b5ae5cbc2ab82aa to your computer and use it in GitHub Desktop.
Migration script example for sanity-plugin-icon-picker

Here's an example of a migration script using the utility function migrateIconName to migrate the icon name using the default options.outputFormat to using options.outputFormat: 'react'. If you want to migrate from default to react, pass react as the third argument. If you want to do it the other way around, simply skip passing a third argument.

IMPORTANT! Be sure to create a backup of your dataset before running migrations, so you can roll back in case something goes wrong. Before you run any migrations, you should know what you are doing. You can read more on migrations here.

In this example I'm migrating an object field icon that is a field of document type icons. The structure most likely looks different in your project, so tweak the script and use with caution.

import { createClient } from '@sanity/client'
import { migrateIconName } from 'sanity-plugin-icon-picker'

const token = process.env.SANITY_TOKEN
const projectId = process.env.SANITY_PROJECT_ID
const dataset = process.env.SANITY_DATASET
const apiVersion = '2023-03-01'

const client = createClient({
  apiVersion,
  projectId,
  dataset,
  token,
})

const fetchDocuments = () =>
  client.fetch(`*[_type == "icons" && !defined(migrated)][0...100] {...}`, {});

const buildPatches = (docs) => {
  return docs.map((doc) => {
    const icon = doc.icon;

    return {
      id: doc._id,
      patch: {
        set: {
          icon: {
            ...icon,
            name: migrateIconName(icon.name, icon.provider, 'react')
          },
          migrated: true,
        },
        ifRevisionID: doc._rev,
      },
    };
  });
};

const createTransaction = (patches) =>
  patches.reduce(
    (tx, patch) => tx.patch(patch.id, patch.patch),
    client.transaction()
  );

const commitTransaction = (tx) => tx.commit();

const migrateNextBatch = async () => {
  const documents = await fetchDocuments();
  const patches = buildPatches(documents);
  if (patches.length === 0) {
    console.log("No more documents to migrate!");
    return null;
  }
  console.log(
    `Migrating batch:\n %s`,
    patches
      .map((patch) => `${patch.id} => ${JSON.stringify(patch.patch)}`)
      .join("\n")
  );
  const transaction = createTransaction(patches);
  await commitTransaction(transaction);
  return migrateNextBatch();
};

migrateNextBatch().catch((err) => {
  console.error(err);
  process.exit(1);
});
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment