skip to Main Content

I’m running into the issue of when I create variants that it complains the first one already exists and then doesn’t add the stock amount or price but the rest is fine.

This is how the data looks like from the product we are trying to add:

  {
    "title": "Ladies Cambridge Stretch Pants - Navy",
    "bodyHtml": "<ul>nt<li>220 g/m²</li>nt<li>70% polyester, 26% rayon, 4% spandex stretch</li>nt<li>sizes&nbsp;30 - 46</li>n</ul>n",
    "vendor": "Amrod",
    "productType": "Pants Skirts And Belts",
    "images": [
      {
        "src": "https://amrcdn.amrod.co.za/amrodprod-blob/ProductImages/BAS-8025/BAS-8025-N_1024X1024.jpg",
        "altText": "Ladies Cambridge Stretch Pants - Navy"
      },
      {
        "src": "https://amrcdn.amrod.co.za/amrodprod-blob/ProductImages/BAS-8025/BAS-8025-N_1024X1024.jpg",
        "altText": "Ladies Cambridge Stretch Pants - Navy"
      }
    ],
    "options": [
      {
        "name": "Size",
        "values": [
          "30",
          "32",
          "34",
          "36",
          "38",
          "40",
          "42",
          "44",
          "46"
        ]
      },
      {
        "name": "Color",
        "values": [
          "NAVY"
        ]
      }
    ],
    "variants": [
      {
        "price": 199.99,
        "sku": "30-NAVY",
        "inventoryQuantity": 29,
        "options": [
          "30",
          "NAVY"
        ]
      },
      {
        "price": 199.99,
        "sku": "32-NAVY",
        "inventoryQuantity": 172,
        "options": [
          "32",
          "NAVY"
        ]
      },
      {
        "price": 199.99,
        "sku": "34-NAVY",
        "inventoryQuantity": 167,
        "options": [
          "34",
          "NAVY"
        ]
      },
      {
        "price": 199.99,
        "sku": "36-NAVY",
        "inventoryQuantity": 151,
        "options": [
          "36",
          "NAVY"
        ]
      },
      {
        "price": 199.99,
        "sku": "38-NAVY",
        "inventoryQuantity": 0,
        "options": [
          "38",
          "NAVY"
        ]
      },
      {
        "price": 199.99,
        "sku": "40-NAVY",
        "inventoryQuantity": 117,
        "options": [
          "40",
          "NAVY"
        ]
      },
      {
        "price": 199.99,
        "sku": "42-NAVY",
        "inventoryQuantity": 65,
        "options": [
          "42",
          "NAVY"
        ]
      },
      {
        "price": 199.99,
        "sku": "44-NAVY",
        "inventoryQuantity": 102,
        "options": [
          "44",
          "NAVY"
        ]
      },
      {
        "price": 199.99,
        "sku": "46-NAVY",
        "inventoryQuantity": 62,
        "options": [
          "46",
          "NAVY"
        ]
      }
    ]
  }

And this is the mutation I’m using:

const createVariants = async (productId, variants) => {
  const variantCreateMutation = `
  mutation CreateVariant($input: ProductVariantInput!) {
    productVariantCreate(input: $input) {
      productVariant {
        id
        inventoryItem {
          id
        }
      }
      userErrors {
        field
        message
      }
    }
  }
  `;

  const createdVariants = [];

  for (const variant of variants) {
    try {
      const variantResponse = await shopifyAPI.post(
        "",
        JSON.stringify({
          query: variantCreateMutation,
          variables: {
            input: {
              productId,
              price: variant.price,
              sku: variant.sku,
              options: variant.options,
            },
          },
        })
      );

      if (
        variantResponse.data.errors ||
        variantResponse.data.data.productVariantCreate.userErrors.length > 0
      ) {
        console.error(
          "Error creating variant:",
          variantResponse.data.errors ||
            variantResponse.data.data.productVariantCreate.userErrors
        );
      } else {
        console.log(`Variant created: ${variant.sku}`);
        const inventoryItemId =
          variantResponse.data.data.productVariantCreate.productVariant.inventoryItem.id
            .split("/")
            .pop();
        createdVariants.push({
          inventoryItemId,
          inventoryQuantity: variant.inventoryQuantity,
        });
      }
    } catch (error) {
      console.error("Network or Server Error:", error);
    }
  }

  return createdVariants;
};

I’m not sure why it does that with the first variant. I’ve seen some say I should use productVariantsBulkCreate but that just gives me even more errors and with my being new to shopify and graphql I was wondering if there is something I’m missing?

Any advice would be appreciated <3

2

Answers


  1. Chosen as BEST ANSWER

    This was fixed. The issue stemmed from where I was creating the products:

    const createProduct = async (product) => {
      const productCreateMutation = `
      mutation CreateProductWithOptions($input: ProductInput!, $media: [CreateMediaInput!]) {
        productCreate(input: $input, media: $media) {
          product {
            id
            media(first: 10) {
              nodes {
                alt
                mediaContentType
                preview {
                  status
                }
              }
            }        
            options {
              id
              name
              position
              values
              optionValues {
                id
                name
                hasVariants
              }
            }
            variants(first: 20) {
              nodes {
                id
                title
                selectedOptions {
                  name
                  value
                }
              }
            }
          }
          userErrors {
            field
            message
          }
        }
      }
      `;
    
      const encodeURL = (url) => {
        return encodeURI(url);
      };
    
      const mediaInput = product.images.map((image) => ({
        originalSource: encodeURL(image.src),
        alt: image.altText || "",
        mediaContentType: "IMAGE",
      }));
    
      const productOptions = product.options.map((option) => ({
        name: option.name,
        values: option.values.map((value) => ({ name: value })),
      }));
    
      try {
        const productResponse = await shopifyAPI.post(
          "",
          JSON.stringify({
            query: productCreateMutation,
            variables: {
              input: {
                title: product.title,
                bodyHtml: product.bodyHtml,
                vendor: product.vendor,
                productType: product.productType,
                // productOptions: productOptions,
                metafields: [
                  {
                    namespace: "custom",
                    key: "sync_from_api",
                    type: "boolean",
                    value: "true",
                  },
                ],
              },
              media: mediaInput,
            },
          })
        );
    
        if (
          productResponse.data.errors ||
          productResponse.data.data.productCreate.userErrors.length > 0
        ) {
          console.error(
            "Error creating product:",
            productResponse.data.errors ||
              productResponse.data.data.productCreate.userErrors
          );
          return null;
        }
    
        return productResponse.data.data.productCreate.product.id;
      } catch (error) {
        console.error("Network or Server Error:", error);
        return null;
      }
    };
    

    I was setting productOptions and then doing the same with the variants so the first one would be made in the initial product creation and when it comes to creating the variants for each product it would complain it exists.


  2. productOptions was your problem – I don’t have that tag at all and see the same error. I think this stuff is really poorly documented and coded… by Shopify…

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search