Comment téléverser votre catalogue pour SiteChat

A secure merchant key unlocks catalog upload APIs that send products and images into SiteChat search and chat

Si vous utilisez SiteChat sur votre propre site web (et non une boutique Shopify), vous pouvez envoyer des enregistrements de produits structurés à Shoply afin que les acheteurs puissent les trouver dans le chat SiteChat et dans la recherche de produits.

Ces points de terminaison utilisent le même Settings → Store owner API secret que le reste de la Shoply Merchant API, et la page Product Catalog de l’admin SiteChat peut les appeler avec votre jeton d’accès administrateur connecté. Les boutiques Shopify continuent de synchroniser les données du catalogue via Shopify ; ces routes de téléversement sont disponibles uniquement pour les comptes SiteChat qui ne synchronisent pas déjà un catalogue Magento.

Dans l’admin SiteChat, Product Catalog ouvre un espace de style Shopify avec Products, Collections et Inventory. Vous pouvez ajouter ou modifier des produits, importer des fichiers CSV/Excel, regrouper des produits dans des collections manuelles et ajuster les quantités en stock.

Quelles API sont disponibles ?

APIMéthodeCe qu’elle fait
/merchant/products/batchPOSTCrée ou remplace entièrement jusqu’à 50 produits en une seule requête
/merchant/productsPOSTCrée ou remplace entièrement un produit
/merchant/productsGETRelit un produit importé par source et external_id
/merchant/productsPATCHMet partiellement à jour un produit ; remplacer des variantes ou des metafields nécessite la version issue de GET
/merchant/productsDELETEArchive en douceur un produit (status=archived)
/merchant/products/listGETParcourt les produits importés page par page pour les tableaux d’administration
/merchant/products/imagesPOSTTéléverse une image de produit et renvoie une URL HTTPS publique
/merchant/collectionsGET / POSTListe ou crée des collections manuelles
/merchant/collections/{id}GET / PUT / DELETELit, remplace ou archive une collection
/merchant/inventoryGETListe les lignes de stock (quantités des produits et variantes)
/merchant/inventory/adjustPOSTDéfinit la quantité suivie pour un produit ou une variante

Les enregistrements réussis de produits demandent à Shoply de reconstruire l’index de la boutique. Tant que cette reconstruction n’est pas terminée, les réponses indiquent index_status: "pending". Les produits publiés apparaissent ensuite à la fois dans l’index produit et dans les connaissances utilisées par le chat SiteChat.

Qui peut utiliser ces API ?

  • Votre boutique doit être un compte SiteChat (app_platform est SiteChat).
  • Les clés de boutique Shopify (y compris tout domaine *.myshopify.com) sont rejetées.
  • L’authentification doit utiliser soit un secret API propriétaire de boutique valide, soit un jeton d’accès administrateur SiteChat pour le store_key exact de la requête.
  • Les jetons Shopify Admin API ne peuvent pas appeler ces routes.

Créez ou faites tourner le secret propriétaire de la même manière que pour les autres intégrations Merchant API : How to Use the Shoply Merchant API. Dans la console d’administration SiteChat, ouvrez Product Catalog pour gérer les produits, collections et inventaire — ou importer un fichier CSV ou Excel — sans gérer vous-même le secret.

Comment fonctionne l’authentification ?

Depuis un connecteur serveur

Appelez l’API depuis un backend de confiance via HTTPS. Placez une chaîne JSON dans l’en-tête Authorization :

json
{ "store_key": "YOUR_SITECHAT_STORE_KEY", "store_owner_api_secrete": "YOUR_STORE_OWNER_API_SECRET" }

store_owner_api_secrete est le nom de champ public, y compris son orthographe historique. store_owner_api_secret est également accepté. Il ne s’agit pas d’un jeton Bearer.

Depuis l’admin SiteChat

La page Product Catalog envoie à la place votre session administrateur connectée :

json
{ "store_key": "YOUR_SITECHAT_STORE_KEY", "admin_auth_token": "YOUR_SITECHAT_ACCESS_TOKEN" }

access_token est accepté comme alias de admin_auth_token.

Le paramètre de requête store_key doit correspondre à l’en-tête. Conservez les secrets propriétaire uniquement dans des variables d’environnement côté serveur — jamais dans un script de vitrine, une URL ou un dépôt public.

bash
export SHOPLY_STORE_KEY="your-sitechat-store-key" export SHOPLY_STORE_OWNER_API_SECRETE="shoply_owner_key_example123.secret-value"

Comment téléverser des produits ?

POST https://api.shoplyai.ai/merchant/products/batch?store_key=YOUR_SITECHAT_STORE_KEY

json
{ "source": "woocommerce-main", "products": [ { "external_id": "123", "title": "Trail shoes", "description": "Water-resistant hiking shoes.", "url": "https://example.com/products/trail-shoes", "currency": "USD", "price": "49.95", "original_price": "59.95", "available": true, "status": "published", "images": ["https://example.com/images/trail-shoes.jpg"], "categories": ["Footwear"], "metafields": {"material": "Leather"}, "variants": [ { "external_id": "124", "title": "Brown / 42", "sku": "TRAIL-BR-42", "price": "49.95", "available": true, "metafields": {"color": "Brown", "size": "42"} } ] } ] }

Champs obligatoires et règles

  • Champs produit obligatoires : external_id, title, url, currency, price et available. status prend par défaut la valeur published.
  • Inventaire optionnel : définissez tracks_inventory sur true et une quantity non négative sur le produit ou la variante. Shoply déduit alors la disponibilité du stock (quantity > 0) et stocke total_inventory pour les listes d’administration.
  • source nomme la connexion du catalogue (pas nécessairement une plateforme). Utilisez un nom stable comme woocommerce-main. Caractères autorisés : lettres minuscules, chiffres, underscores et tirets ; jusqu’à 64 caractères. Les produits créés via formulaire dans l’admin utilisent par défaut la source admin.
  • L’identité du produit est la combinaison de la boutique, de la source et de l’ID externe. Les upserts POST par lot et unitaires sont des remplacements complets, pas des patchs : les champs optionnels omis sont effacés. Utilisez PATCH pour les mises à jour partielles.
  • Les lots contiennent 1 à 50 produits et au plus 2 000 000 octets de requête. Le JSON validé de chaque produit est limité à 128 000 octets, avec au maximum 250 variantes.
  • Préférez des chaînes décimales pour les prix. La devise est un code majuscule à trois lettres.
  • Les URL de produits et d’images doivent être en HTTP(S). L’importation ne récupère pas ces URL pour vous.
  • Utilisez des metafields publics pour les spécifications produit recherchables (l’équivalent dans SiteChat des metafields produit Shopify). Les valeurs doivent être de simples chaînes. L’ancien champ attributes est accepté comme alias. Les metadata produit privées ne sont plus prises en charge.
  • Les produits draft et archived sont exclus du prochain index publié. Les produits publiés en rupture de stock restent indexés avec leur disponibilité associée.
  • Les collections manuelles stockent un titre, une description, un statut et une liste d’appartenances produit (source + external_id). Les collections intelligentes/basées sur des règles ne sont pas prises en charge dans cette version.

Exemple de réponse réussie

json
{ "results": [ { "external_id": "123", "product_id": "sitechat_product::woocommerce-main::<sha256-of-external-id>", "status": "stored" } ], "index_status": "pending", "index_revision": 1 }

Shoply valide l’intégralité de la requête avant l’écriture. Un HTTP 200 peut tout de même lister certains résultats failed avec error: "storage_error". Inspectez chaque résultat et relancez les produits en échec. Si index_status vaut request_failed, le stockage a réussi mais l’indexation n’a pas été planifiée — relancez également les produits stockés.

Exemple Python

python
import json import os import requests store_key = os.environ["SHOPLY_STORE_KEY"] headers = { "Authorization": json.dumps({ "store_key": store_key, "store_owner_api_secrete": os.environ["SHOPLY_STORE_OWNER_API_SECRETE"], }) } response = requests.post( "https://api.shoplyai.ai/merchant/products/batch", params={"store_key": store_key}, headers=headers, json={ "source": "custom", "products": [{ "external_id": "123", "title": "Trail shoes", "url": "https://example.com/products/trail-shoes", "currency": "USD", "price": "49.95", "available": True, }], }, timeout=60, ) response.raise_for_status() result = response.json() failed = [item["external_id"] for item in result["results"] if item["status"] != "stored"] if failed: raise RuntimeError(f"Products need retry: {failed}") if result["index_status"] == "request_failed": raise RuntimeError("Products saved, but retry the batch to request indexing")

Comment vérifier un produit importé ?

GET https://api.shoplyai.ai/merchant/products?store_key=YOUR_SITECHAT_STORE_KEY&source=woocommerce-main&external_id=123

Utilisez le même en-tête Authorization. La réponse inclut schema_version, updated_at, index_status et le product normalisé. Les enregistrements manquants renvoient HTTP 404.

Après qu’un nouvel index a été publié par l’indexeur en arrière-plan, le statut de relecture par produit devient indexed, excluded (pour les produits brouillon ou archivés) ou limit_exceeded. Utilisez GET /merchant/products/list pour l’affichage d’administration. Archivez en douceur avec DELETE /merchant/products (ou définissez status sur archived / draft) pour exclure un produit du prochain index publié ; il n’y a pas de suppression définitive dans cette version.

python
record = requests.get( "https://api.shoplyai.ai/merchant/products", params={ "store_key": store_key, "source": "woocommerce-main", "external_id": "123", }, headers=headers, timeout=30, ) record.raise_for_status() print(record.json()["index_status"], record.json()["product"]["title"])

Comment mettre à jour en toute sécurité des variantes ou des metafields ?

Pour un PATCH contenant variants, metafields ou l’ancien champ attributes, commencez par lire le produit avec GET. Construisez la modification à partir de cette réponse et incluez sa valeur updated_at de niveau supérieur comme expected_updated_at dans le corps du PATCH. Cela s’applique également lors de la suppression de variantes ou de metafields.

python
current_response = requests.get( "https://api.shoplyai.ai/merchant/products", params={"store_key": store_key, "source": "woocommerce-main", "external_id": "123"}, headers=headers, timeout=30, ) current_response.raise_for_status() current = current_response.json() updated_metafields = {**current["product"].get("metafields", {}), "material": "Leather"} response = requests.patch( "https://api.shoplyai.ai/merchant/products", params={"store_key": store_key}, headers=headers, json={ "source": "woocommerce-main", "external_id": "123", "expected_updated_at": current["updated_at"], "metafields": updated_metafields, }, timeout=30, ) response.raise_for_status()

HTTP 409 signifie que la version était absente ou qu’une autre mise à jour a modifié le produit. Relisez le produit le plus récent et fusionnez à nouveau les changements souhaités avant de réessayer. N’attachez pas une nouvelle version à une ancienne liste de variantes : cela pourrait écraser des valeurs de stock plus récentes.

Les intégrations existantes qui effectuent un PATCH de ces champs sans version doivent être mises à jour. Les requêtes PATCH limitées aux scalaires, les ajustements d’inventaire dédiés et les remplacements complets via POST ou importation par lot ne nécessitent pas ce champ. Les remplacements complets remplacent toujours l’intégralité du produit.

Puis-je téléverser des images de produit ?

Oui. Si une image est déjà disponible à une URL HTTPS publique durable, placez cette URL dans la liste images du produit ou dans le champ image d’une variante. Les URL HTTPS S3 publiques fonctionnent. Les chemins bruts s3:// et les URL signées de courte durée ne fonctionnent pas.

Pour que Shoply héberge le fichier, téléversez les octets bruts de l’image depuis votre backend :

text
POST https://api.shoplyai.ai/merchant/products/images?store_key=YOUR_SITECHAT_STORE_KEY Content-Type: image/png

Envoyez les octets bruts du fichier, et non du JSON, du base64 ou des données de formulaire multipart. Les formats JPEG, PNG et WebP sont acceptés, jusqu’à 10 MiB et 20 millions de pixels. Les images animées ne sont pas prises en charge. Shoply convertit l’image en WebP et supprime les métadonnées intégrées.

python
with open("trail-shoes.png", "rb") as image_file: response = requests.post( "https://api.shoplyai.ai/merchant/products/images", params={"store_key": store_key}, headers={**headers, "Content-Type": "image/png"}, data=image_file, timeout=60, ) response.raise_for_status() image_url = response.json()["url"]

HTTP 201 renvoie url, content_type, size_bytes, width et height. Téléverser une image seule ne l’attache pas à un produit et ne demande pas d’indexation. Incluez l’URL renvoyée dans un produit complet et soumettez-le à nouveau via /merchant/products/batch.

La même image téléversée à nouveau pour le même compte réutilise son URL. Une image modifiée reçoit une nouvelle URL. Il n’existe pas de point de terminaison de suppression d’image dans cette version.

Quand les produits apparaissent-ils dans le chat et la recherche ?

Après un enregistrement par lot réussi, Shoply demande une reconstruction d’index en arrière-plan. Les réponses indiquent index_status: "pending" jusqu’à ce que le worker publie le nouvel index. Il n’existe aucune garantie de délai d’achèvement fixe.

  • Les produits publiés entrent à la fois dans la recherche produit et dans les connaissances utilisées par le chat SiteChat.
  • Les produits brouillon et archivés sont exclus lors de la prochaine reconstruction.
  • Si l’indexation n’a pas été planifiée (index_status: "request_failed"), relancez le lot pour les produits déjà stockés avec succès.

Quelles erreurs dois-je prévoir ?

Statut HTTPSignification
403Secret absent, invalide, expiré ou révoqué ; mauvaise boutique ; ou compte non-SiteChat
404Le produit importé demandé n’existe pas
413La requête ou l’image dépasse la limite de taille
415Le téléversement d’image a utilisé un Content-Type non pris en charge
422Champs invalides, IDs dupliqués, images animées ou trop volumineuses, ou limites du modèle dépassées
503Échec temporaire de stockage

Les secrets expirent après 90 jours. Créez un remplacement dans Settings → Store owner API secret avant l’expiration, et révoquez tout secret dont vous n’avez plus besoin. Le même secret peut également appeler les points de terminaison d’analytics, de conversations et de connaissances documentés dans le guide Merchant API.

Pour obtenir de l’aide sur une intégration, contactez Shoply AI.