> ## Documentation Index
> Fetch the complete documentation index at: https://docs.aftersell.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Objet cart

> La forme de l'objet cart du SDK du panier Aftersell et de ses lignes : chaque champ du panier, les lignes du panier, les bundles et les plans de vente.

Une seule forme d'objet circule dans tout le SDK. C'est ce que renvoie [`getCart()`](/fr/aftersell/cart/sdk-actions#getcart), ce que [`cart_loaded` et `cart_updated`](/fr/aftersell/cart/sdk-events) transmettent à votre gestionnaire, et ce que reçoit un [bloc Custom code](/fr/aftersell/cart/custom-code-blocks).

<Note>
  **Tous les montants sont dans l'unité mineure de la devise** (centimes pour l'USD), jamais une chaîne formatée. `5779` correspond à \$57.79. Utilisez [`formatMoney`](/fr/aftersell/cart/sdk-actions#formatmoneycents) pour l'afficher.
</Note>

<div id="the-cart">
  ## Le panier
</div>

| Champ                  | Type                     | Description                                                                                                                                                            |
| ---------------------- | ------------------------ | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `token`                | `string`                 | Le token de panier Shopify.                                                                                                                                            |
| `items`                | `AftersellCartLine[]`    | Les lignes d'articles. Voir [lignes du panier](#cart-lines).                                                                                                           |
| `itemCount`            | `number`                 | Quantité totale d'articles, telle que l'acheteur la voit.                                                                                                              |
| `hasSubscriptionItems` | `boolean`                | `true` lorsqu'au moins une ligne de `items` porte un plan de vente, y compris les lignes d'options complémentaires que `itemCount` exclut. `false` sur un panier vide. |
| `totalPrice`           | `number`                 | Total actuel, en centimes.                                                                                                                                             |
| `originalTotalPrice`   | `number`                 | Total avant réductions, en centimes.                                                                                                                                   |
| `totalDiscount`        | `number`                 | Total des réductions, en centimes.                                                                                                                                     |
| `compareAtTotalPrice`  | `number \| null`         | Somme du prix comparatif (MSRP) de chaque ligne × quantité, en centimes. `null` lorsqu'indisponible, revenez alors à `originalTotalPrice`.                             |
| `currency`             | `string`                 | Code de devise.                                                                                                                                                        |
| `discountCodes`        | `string[]`               | Codes de réduction acceptés sur le panier, triés. `[]` lorsqu'il n'y en a aucun.                                                                                       |
| `attributes`           | `Record<string, string>` | Attributs du panier. En lecture seule depuis le SDK.                                                                                                                   |

<Warning>
  **`itemCount` n'est pas toujours la somme de `items`.** `items` reflète le vrai panier Shopify, y compris les lignes d'options complémentaires que le tiroir masque, comme la protection d'expédition. `itemCount` est le nombre visible par l'acheteur qui correspond au badge du panier. Pour « combien d'articles l'acheteur a-t-il choisis », utilisez `itemCount` ; pour itérer sur les lignes que le panier affiche, utilisez `items`.

  Deux choses sont entièrement absentes de `items` : les lignes masquées avec [`setHidden`](/fr/aftersell/cart/sdk-hooks#registerlinetransform), et les [enfants de bundle](#bundles), qui sont regroupés sur leur ligne d'ancrage. Les deux comptent toujours dans les totaux du panier, qui viennent directement de Shopify.
</Warning>

```js theme={"theme":{"light":"snazzy-light","dark":"github-dark"}}
window.aftersell.cart.events.on('cart_updated', (state) => {
  console.log(state.itemCount, 'items');
  console.log('Total:', window.aftersell.cart.actions.formatMoney(state.totalPrice));
  console.log('Saved:', window.aftersell.cart.actions.formatMoney(state.totalDiscount));
  console.log('Codes:', state.discountCodes.join(', ') || 'none');
});
```

<div id="cart-lines">
  ## Lignes du panier
</div>

Chaque entrée de `items`, et l'`item` de [`item_added`](/fr/aftersell/cart/sdk-events#item_added) et [`item_removed`](/fr/aftersell/cart/sdk-events#item_removed) :

| Champ                 | Type                             | Description                                                                                                                                                                          |
| --------------------- | -------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| `key`                 | `string`                         | La clé Shopify de la ligne. Passez-la aux [actions](/fr/aftersell/cart/sdk-actions) sur les articles.                                                                                |
| `productId`           | `number`                         | ID de produit Shopify.                                                                                                                                                               |
| `variantId`           | `number`                         | ID de variante Shopify.                                                                                                                                                              |
| `handle`              | `string`                         | Handle du produit.                                                                                                                                                                   |
| `title`               | `string`                         | Titre d'affichage.                                                                                                                                                                   |
| `productTitle`        | `string`                         | Titre du produit sans la variante.                                                                                                                                                   |
| `variantTitle`        | `string \| null`                 | Libellé de la variante, ou `null`.                                                                                                                                                   |
| `variantOptions`      | `Array<{ name, value }>`         | Options sélectionnées, par ex. `[{ name: 'Size', value: 'Medium' }]`. Shopify émet `Title: Default Title` pour un produit à variante unique.                                         |
| `quantity`            | `number`                         | Quantité de cette ligne.                                                                                                                                                             |
| `linePrice`           | `number`                         | Prix de la ligne, en centimes.                                                                                                                                                       |
| `finalLinePrice`      | `number`                         | Prix de la ligne après réductions, en centimes.                                                                                                                                      |
| `originalLinePrice`   | `number`                         | Prix de la ligne avant réductions, en centimes.                                                                                                                                      |
| `compareAtPrice`      | `number \| null`                 | Prix comparatif de la variante (MSRP) **par unité**, en centimes. `null` lorsqu'il n'y en a pas.                                                                                     |
| `properties`          | `Record<string, string> \| null` | Propriétés de la ligne d'article.                                                                                                                                                    |
| `internalProperties`  | `Record<string, string>`         | Surcouche d'affichage uniquement issue de [`registerLineTransform`](/fr/aftersell/cart/sdk-hooks#registerlinetransform). Jamais persistée vers Shopify. `{}` lorsqu'il n'y en a pas. |
| `discountAllocations` | `Array<{ title, amount }>`       | Réductions appliquées à cette ligne. `amount` est en centimes. `[]` lorsqu'il n'y en a pas.                                                                                          |
| `isGiftCard`          | `boolean`                        | Indique si la ligne est une carte cadeau.                                                                                                                                            |
| `sellingPlan`         | `{ id, name } \| null`           | Le plan d'abonnement actif, ou `null` pour un achat unique.                                                                                                                          |
| `bundle`              | `AftersellCartBundle \| null`    | Modèle de vue de [bundle](#bundles) sur la ligne d'ancrage ; `null` sur les lignes hors bundle et les enfants.                                                                       |
| `metadata`            | `Record<string, unknown>`        | Données d'[enrichissement](/fr/aftersell/cart/sdk-hooks#registercartenricher) indexées par `id` d'enrichisseur. `{}` jusqu'à ce qu'un enrichisseur le remplisse.                     |

<Warning>
  `properties` peut contenir des saisies fournies par l'acheteur, comme le champ de texte personnalisé d'un formulaire produit. Affichez-le en tant que texte, jamais en tant que HTML brut.
</Warning>

<div id="identifying-a-line">
  ### Identifier une ligne
</div>

Utilisez `key` pour tout ce qui agit sur une ligne, et `variantId` ou `productId` pour tout ce qui identifie un *produit* :

```js theme={"theme":{"light":"snazzy-light","dark":"github-dark"}}
// ✅ Acting on a line: use key.
window.aftersell.cart.actions.removeItem(line.key);

// ✅ Recognising a product: use variantId.
const hasGift = state.items.some((line) => line.variantId === GIFT_VARIANT_ID);
```

La même variante peut apparaître sur plusieurs lignes lorsque les propriétés diffèrent. Deux mugs gravés avec des textes de gravure différents sont deux lignes partageant un même `variantId`. C'est pourquoi les actions prennent `key`.

<div id="prices-on-a-line">
  ### Les prix d'une ligne
</div>

Trois prix, faciles à confondre :

| Vous voulez                                       | Utilisez                      |
| ------------------------------------------------- | ----------------------------- |
| Ce que l'acheteur paie pour cette ligne           | `finalLinePrice`              |
| Ce qu'elle coûtait avant les réductions du panier | `originalLinePrice`           |
| Le prix barré MSRP, par unité                     | `compareAtPrice` × `quantity` |

```js theme={"theme":{"light":"snazzy-light","dark":"github-dark"}}
// Is this line discounted?
const isDiscounted = line.finalLinePrice < line.originalLinePrice;

// Is it free? (A common way to detect a gift line.)
const isFree = line.finalLinePrice === 0;
```

<div id="bundles">
  ## Bundles
</div>

Lorsque des lignes sont regroupées en bundle, la ligne d'**ancrage** porte un objet `bundle`. Les enfants y sont intégrés et n'apparaissent plus seuls dans `items`. Consultez [Regrouper les lignes de bundle d'une autre application](/fr/aftersell/cart/sdk-use-case-bundles) pour savoir comment le regroupement est configuré.

| Champ          | Type                     | Description                                                      |
| -------------- | ------------------------ | ---------------------------------------------------------------- |
| `id`           | `string`                 | Identifiant du bundle.                                           |
| `source`       | `'native' \| 'grouped'`  | Un bundle natif Shopify, ou des lignes regroupées par Aftersell. |
| `memberKeys`   | `string[]`               | La `key` de chaque ligne du bundle.                              |
| `children`     | `AftersellBundleChild[]` | Le contenu du bundle.                                            |
| `displayPrice` | `number`                 | Le prix affiché pour le bundle, en centimes.                     |

Chaque enfant porte `key` (`null` pour un composant natif), `title`, `variantTitle`, `quantity`, `perAnchorQty`, `imageUrl`, `finalLinePrice`, `originalLinePrice` et `compareAtPrice`.

```js theme={"theme":{"light":"snazzy-light","dark":"github-dark"}}
// Skip bundle children when totalling your own line list.
const topLevel = state.items.filter((line) => !isBundleChild(line, state));
```

<div id="subscription-plans">
  ## Plans d'abonnement
</div>

Le plan actif d'une ligne est `sellingPlan`, ou `null` pour un achat unique. Pour une réponse à l'échelle du panier entier, lisez `hasSubscriptionItems` plutôt que de parcourir les lignes vous-même, car il compte aussi les lignes d'options complémentaires que `items` présente mais que `itemCount` ignore :

```js theme={"theme":{"light":"snazzy-light","dark":"github-dark"}}
if (state.hasSubscriptionItems) {
  // The cart contains at least one subscription line.
}

const subscriptions = state.items.filter((line) => line.sellingPlan);
console.log(subscriptions.length, 'subscription lines');
```

Les plans *disponibles* sur une ligne, ceux du sélecteur, ne figurent pas sur l'objet cart. Façonnez-les avec [`registerSubscriptionOptionsTransform`](/fr/aftersell/cart/sdk-hooks#registersubscriptionoptionstransform) et [`registerDefaultSubscriptionOptionSelector`](/fr/aftersell/cart/sdk-hooks#registerdefaultsubscriptionoptionselector).

<div id="where-to-go-next">
  ## Pour aller plus loin
</div>

* **[Actions](/fr/aftersell/cart/sdk-actions)** : lire et modifier le panier.
* **[Événements](/fr/aftersell/cart/sdk-events)** : d'où vient cet objet.
* **[Hooks](/fr/aftersell/cart/sdk-hooks)** : ajoutez vos propres données à une ligne avec un enrichisseur.
* **[Cas d'usage](/fr/aftersell/cart/sdk-use-cases)** : des solutions complètes qui lisent ces champs.
