Create products without variant/options using productSet

Topic summary

Goal: create a simple product (single price, no visible options) via the productSet GraphQL mutation under the new product model.

  • Problem: Omitting productOptions/optionValues causes a validation error (variants.0.optionValues must not be null). Using a dummy option/value makes the option appear on the storefront.

  • Working approach: Define a hidden default option by setting productOptions name to “Title” and its single value to “Default Title”, and set the variant’s optionValues to match (optionName: “Title”, name: “Default Title”). This keeps the option invisible on the product page.

  • Clarification: Some themes misbehaved when the value wasn’t exactly the default variant. The key is case-sensitive matching: it must be “Default Title” (not “Default title”).

  • Outcome: Using “Title” + “Default Title” creates the true default variant behavior and avoids visible options. Multiple participants confirmed this resolves the issue.

  • Status: Resolved. Action: Ensure exact capitalization for the default variant mapping in productSet.

Summarized with AI on December 16. AI used: gpt-5.

I’m trying to follow the guide to sync data from an external source using the productSet migration https://shopify.dev/docs/apps/build/graphql/migrate/new-product-model/sync-data

My mutation looks like this:

mutation createProductAsynchronous($productSet: ProductSetInput!, $synchronous: Boolean!) {
    productSet(synchronous: $synchronous, input: $productSet) {
        product {
            id
        }
        productSetOperation {
            id
            status
            userErrors {
                code
                field
                message
            }
        }
        userErrors {
            code
            field
            message
        }
    }
}

I want to sync title, description and price so my productSet looks like this.

const productSet = {
            title: product.name,
            descriptionHtml: product.description,
            vendor: product.vendor,
            productOptions: [{
                name: "Dummy",
                position: 1,
                values: [{
                    name: "High"
                }]
            }],
            variants: [{
                optionValues: [{
                    optionName: "Dummy",
                    name: "High"
                }],
                price: product.price
            }]
        }

I don’t want the dummy “productOptions” to be needed as it shows up on the product listing. But if i omit productOptions/optionValues i get an error like:

Variable $productSet of type ProductSetInput! was provided invalid value for variants.0.optionValues (Expected value to not be null)

How can i create a simple product with one price and no options/variants?

1 Like

Hi Matthew,

Using the same mutation you could structure your variables to be something like this:

{
    "productSet": {
        "title": "Sample Product",
        "descriptionHtml": "

This is a sample product description.

",
        "vendor": "Sample Vendor",
        "productOptions": [
            {
                "name": "Title",
                "values": [
                    {"name": "Default Title"}
                ]
            }
        ],
        "variants": [
            {
                "price": "19.99",
                "optionValues": [
                    {
                        "optionName": "Title",
                        "name": "Default Title"
                    }
                ]
            }
        ]
    },
    "synchronous": false
}

Would this work for you?

5 Likes

yes that does work. i dont totally understand why my version gave me a selector for selecting the “Dummy” field on the product page, but your “Title” product option is invisible?

1 Like

Hi Liam,

Although this works, all products are created with one variant instead of the (normally hidden) default variant. This means that some themes won’t show a quick buy button. Also, some themes show the option names and values on the product detail page, which normally is just ‘Default title’.

Is there any way that productSet can be used to import simple products (only default variant) without having an option value and option name?

@Liam Thanks for this response - but this doesn’t create a default variant - see here for the test:
https://community.shopify.com/post/2814288

Do you have any insight as to how to create a default variant with productSet?

EDIT: never mind, the issue was capitalisation:
The correct value is related to capitalisation - it needs to be “Default Title” not “Default title” - to generate a default variant

1 Like

Hi AV_SL,

If you create the default variant exactly as Liam described (case
sensitive!!) , it works for me

1 Like