Staged upload ve bulkOperationRunMutation ile toplu içe aktarma

Bir mutation’ı binlerce kez çalıştırın: değişkenlerden oluşan JSONL dosyasını stagedUploadsCreate ile yükleyin, ardından bulkOperationRunMutation’ı başlatın.

API
Admin GraphQL API
İşlemler
stagedUploadsCreate, bulkOperationRunMutation, bulkOperation
Erişim yetkileri
Çalıştırdığınız mutation’ın yetkileri; örneğin productSet için write_products
API sürümü
2026-10
Son kontrol

Kısaca

Toplu veri içe aktarmak için her kayıt için bir satır değişken içeren bir JSONL dosyası hazırlayın, stagedUploadsCreate ile (resource BULK_MUTATION_VARIABLES, httpMethod POST) yükleme alanı ayırın ve dosyayı dönen url’ye multipart form olarak gönderin. Ardından mutation’ınızı ve key parametresini stagedUploadPath olarak bulkOperationRunMutation’a verin. Shopify mutation’ı her satır için bir kez çalıştırır ve sonuçları JSONL olarak döndürür.

Nasıl kullanılır

  1. products.jsonl dosyasını yazın: her satırda, tek bir mutation çağrısının değişkenlerini taşıyan bir JSON nesnesi.
  2. ReserveImportUpload’u resource BULK_MUTATION_VARIABLES ve httpMethod POST ile gönderin.
  3. Dosyayı stagedTargets[0].url adresine multipart form olarak POST edin: dönen her parametre bir alan, dosya en sonda (bkz. upload.txt).
  4. StartProductImport’u mutation metniyle ve key parametresini stagedUploadPath olarak vererek gönderin.
  5. İşlemi sorgulayın ya da bulk_operations/finish webhook’una abone olun, ardından sonuç dosyasını indirin. Her satırdaki __lineNumber (0’dan başlar) sizin girdinizdeki satırı gösterir.

Kod

products.jsonl
{"input":{"handle":"linen-shirt","title":"Linen shirt","status":"ACTIVE","productOptions":[{"name":"Size","values":[{"name":"S"},{"name":"M"}]}],"variants":[{"optionValues":[{"optionName":"Size","name":"S"}],"sku":"LS-S","price":"49.00"},{"optionValues":[{"optionName":"Size","name":"M"}],"sku":"LS-M","price":"49.00"}]}}
{"input":{"handle":"wool-scarf","title":"Wool scarf","status":"DRAFT","productOptions":[{"name":"Title","values":[{"name":"Default Title"}]}],"variants":[{"optionValues":[{"optionName":"Title","name":"Default Title"}],"sku":"WS-01","price":"35.00"}]}}
staged-uploads-create.graphql
mutation ReserveImportUpload($input: [StagedUploadInput!]!) {
  stagedUploadsCreate(input: $input) {
    stagedTargets {
      url
      resourceUrl
      parameters {
        name
        value
      }
    }
    userErrors {
      field
      message
    }
  }
}
staged-uploads-create.variables.json
{
  "input": [
    {
      "resource": "BULK_MUTATION_VARIABLES",
      "filename": "products.jsonl",
      "mimeType": "text/jsonl",
      "httpMethod": "POST"
    }
  ]
}
staged-uploads-create.response.json
{
  "data": {
    "stagedUploadsCreate": {
      "stagedTargets": [
        {
          "url": "https://shopify-staged-uploads.storage.googleapis.com/",
          "resourceUrl": null,
          "parameters": [
            {"name": "key", "value": "tmp/1234567890/bulk/00000000-0000-0000-0000-000000000000/products.jsonl"},
            {"name": "Content-Type", "value": "text/jsonl"},
            {"name": "success_action_status", "value": "201"},
            {"name": "acl", "value": "private"},
            {"name": "policy", "value": "<policy from the response>"},
            {"name": "x-goog-credential", "value": "<credential from the response>"},
            {"name": "x-goog-algorithm", "value": "GOOG4-RSA-SHA256"},
            {"name": "x-goog-date", "value": "20261102T090000Z"},
            {"name": "x-goog-signature", "value": "<signature from the response>"}
          ]
        }
      ],
      "userErrors": []
    }
  }
}
upload.txt
# Send every parameter from stagedTargets[0].parameters as a form field,
# in the order returned, and the file last. The upload is a multipart POST
# to stagedTargets[0].url; a 201 response means the file is staged.
curl -X POST "https://shopify-staged-uploads.storage.googleapis.com/" \
  -F "key=tmp/1234567890/bulk/00000000-0000-0000-0000-000000000000/products.jsonl" \
  -F "Content-Type=text/jsonl" \
  -F "success_action_status=201" \
  -F "acl=private" \
  -F "policy=<policy from the response>" \
  -F "x-goog-credential=<credential from the response>" \
  -F "x-goog-algorithm=GOOG4-RSA-SHA256" \
  -F "x-goog-date=20261102T090000Z" \
  -F "x-goog-signature=<signature from the response>" \
  -F "file=@products.jsonl"

# Pass the value of the "key" parameter as stagedUploadPath to bulkOperationRunMutation.
bulk-operation-run-mutation.graphql
mutation StartProductImport($mutation: String!, $stagedUploadPath: String!) {
  bulkOperationRunMutation(mutation: $mutation, stagedUploadPath: $stagedUploadPath) {
    bulkOperation {
      id
      status
    }
    userErrors {
      code
      field
      message
    }
  }
}
bulk-operation-run-mutation.variables.json
{
  "mutation": "mutation SetProduct($input: ProductSetInput!) { productSet(input: $input) { product { id handle } userErrors { code field message } } }",
  "stagedUploadPath": "tmp/1234567890/bulk/00000000-0000-0000-0000-000000000000/products.jsonl"
}
bulk-operation-run-mutation.response.json
{
  "data": {
    "bulkOperationRunMutation": {
      "bulkOperation": {
        "id": "gid://shopify/BulkOperation/1234567891",
        "status": "CREATED"
      },
      "userErrors": []
    }
  }
}
result.jsonl
{"data":{"productSet":{"product":{"id":"gid://shopify/Product/1111111111","handle":"linen-shirt"},"userErrors":[]}},"__lineNumber":0}
{"data":{"productSet":{"product":{"id":"gid://shopify/Product/1111111112","handle":"wool-scarf"},"userErrors":[]}},"__lineNumber":1}

Lintel tarafından yazıldı. MIT lisansı: kendi mağazanızda da müşteri işlerinizde de ücretsiz kullanabilirsiniz.

Sınırlar ve özel durumlar

  • JSONL dosyası en fazla 100 MB olabilir ve işlem 24 saat içinde bitmelidir.
  • bulkOperationRunMutation ve bulkOperationRunQuery’nin kendisi dışında her Admin mutation’ı kullanılabilir. Mutation yalnızca bir connection alanı içerebilir.
  • 2026-01’den itibaren bir uygulama, mağaza başına aynı anda en fazla beş bulk mutation işlemi çalıştırabilir.
  • Hatalar sonuç dosyasında satır bazında raporlanır; işlem bütünüyle yalnızca sistem hatasında başarısız olur. Toplu çalıştırmadan önce mutation’ı tek başına bir kez deneyin.
  • productSet bir bulk operation içinde her zaman senkron çalışır; synchronous argümanı burada dikkate alınmaz.

Sık sorulan sorular

GraphQL ile Shopify’a toplu ürün nasıl aktarılır?
Her satıra bir productSet girdisi koyduğunuz JSONL dosyasını stagedUploadsCreate ile yükleyin, ardından productSet mutation’ı ve yüklenen dosyanın key değeriyle bulkOperationRunMutation çalıştırın.
bulkOperationRunMutation istek sınırına (rate limit) takılır mı?
Hayır. bulkOperationRunMutation isteği normal Admin API istek sınırlarına tabi değildir. İşlemi başlatmak, takip etmek ya da iptal etmek için yalnızca birkaç düşük maliyetli istek yaparsınız.
stagedUploadPath’e ne yazılır?
stagedUploadsCreate yanıtındaki key adlı parametrenin değeri; yükleme url’sinin tamamı değil.
Hangi satırların başarısız olduğunu nasıl anlarım?
Sonuç dosyasını indirin. Her satırda __lineNumber ile birlikte ya mutation’ın userErrors dahil verisi ya da o satıra ait bir errors dizisi bulunur.
  • Gösterilen tarihte, 2026-10 sürümünün Admin veya Storefront API şemasıyla doğrulandı. İstek adresinizdeki sürümü kontrol edin.
  • Örneklerdeki ID’ler ve mağaza adresleri yer tutucudur. Kendi değerlerinizle değiştirin.
  • Admin API çağrıları uygulamanızdan bir erişim anahtarı (access token) ister. Admin API anahtarını asla vitrine ya da temaya koymayın.
  • MIT lisansı. Kodu kendi mağazanızda da müşteri işlerinizde de kullanabilirsiniz.

Mağazanız için kurulmasını, test edilmesini ve bakımını isterseniz: API entegrasyonları.

Geliştirmek istediğiniz bir şey mi var? Gelin, birlikte konuşalım.

Aynı anda sınırlı sayıda proje alıyoruz.

Gencer KarakayaShopify mühendisi

Proje özetinizi bir mühendis okur; size e-postayla yanıt veririz.