Rapidy Développeurs

Intégrer

Annulation et litiges

Ce qu'on peut encore arrêter, ce qu'on ne peut plus, et comment ouvrir un dossier.

Annuler

cancelShipment fonctionne tant que le colis n'est pas enlevé — y compris après qu'un livreur a accepté la mission. Le motif est obligatoire : il alimente l'audit et l'arbitrage des litiges.

Annuler proprement, et lire le refus
# Le corps d'erreur porte un code STABLE. Ne parsez jamais le message.
{
  "code": "CONFLICT",
  "message": "Cet envoi est déjà pris en charge",
  "details": { "shipment_id": "shp_…", "status": "PICKED_UP" }
}
import { RapidyError } from '@rapidy/sdk';

try {
  await rapidy.cancelShipment(shipmentId, 'client rétracté', 'awa');
} catch (err) {
  if (err instanceof RapidyError) {
    if (err.isConflict) {
      // Déjà assigné ou récupéré : l'annulation n'est plus possible.
    }
    // Seul isRetryable vaut une nouvelle tentative. Rejouer un 400 ou un 409
    // ne changera rien : ce sont des refus, pas des incidents.
    if (err.isRetryable) await retryLater();
  }
}
from rapidy_sdk import RapidyError

try:
    rapidy.cancel_shipment(shipment_id=shipment_id, reason="client rétracté", by="awa")
except RapidyError as err:
    if err.is_conflict:
        ...  # déjà assigné ou récupéré : l'annulation n'est plus possible
    # Seul is_retryable vaut une nouvelle tentative.
    if err.is_retryable:
        retry_later()
use Rapidy\Sdk\RapidyException;

try {
    $rapidy->cancelShipment($shipmentId, reason: 'client rétracté', by: 'awa');
} catch (RapidyException $e) {
    if ($e->isConflict()) {
        // Déjà assigné ou récupéré : l'annulation n'est plus possible.
    }
    // Seul isRetryable() vaut une nouvelle tentative.
    if ($e->isRetryable()) {
        retryLater();
    }
}
begin
  rapidy.cancel_shipment(shipment_id: shipment_id, reason: 'client rétracté', by: 'awa')
rescue Rapidy::Error => e
  # Déjà assigné ou récupéré : l'annulation n'est plus possible.
  retry_later if e.retryable?
  raise unless e.conflict?
end
_, err := client.CancelShipment(ctx, shipmentID, "client rétracté", "awa")
if err != nil {
    var apiErr *rapidy.Error
    if errors.As(err, &apiErr) {
        if apiErr.IsConflict() {
            // Déjà assigné ou récupéré : l'annulation n'est plus possible.
        }
        // Seul IsRetryable vaut une nouvelle tentative.
        if apiErr.IsRetryable() {
            retryLater()
        }
    }
}
try {
    rapidy.cancelShipment(shipmentId, "client rétracté", "awa");
} catch (RapidyException e) {
    if (e.isConflict()) {
        // Déjà assigné ou récupéré : l'annulation n'est plus possible.
    }
    // Seul isRetryable() vaut une nouvelle tentative.
    if (e.isRetryable()) {
        retryLater();
    }
}
try
{
    await rapidy.CancelShipmentAsync(shipmentId, "client rétracté", "awa");
}
catch (RapidyException e)
{
    if (e.IsConflict)
    {
        // Déjà assigné ou récupéré : l'annulation n'est plus possible.
    }
    // Seul IsRetryable vaut une nouvelle tentative.
    if (e.IsRetryable) await RetryLater();
}
try {
  await rapidy.cancelShipment(
    shipmentId: shipmentId, reason: 'client rétracté', by: 'awa');
} on RapidyException catch (e) {
  if (e.isConflict) {
    // Déjà assigné ou récupéré : l'annulation n'est plus possible.
  }
  // Seul isRetryable vaut une nouvelle tentative.
  if (e.isRetryable) await retryLater();
}

Au-delà de l'enlèvement, l'API répond 409. Ce n'est pas un incident à réessayer : c'est un refus. Le recours s'appelle un litige.

Annuler un envoi annule aussi la course en cours : le livreur cesse de la voir comme active, et sa réserve de risque est libérée. Vous n'avez rien à faire de plus.

Ouvrir un litige

openDispute ouvre un dossier sur un envoi : colis endommagé, perdu, non conforme, refusé.

Le règlement de cet envoi est retenu le temps que le dossier soit tranché. C'est voulu, pas une panne : sans cette retenue, un remboursement devrait se réclamer après coup, souvent auprès de quelqu'un qui a déjà retiré l'argent.

claimant_type vaut seller par défaut. Renseignez-le explicitement si le signalement vient d'ailleurs.

Choisir entre les deux

SituationLe bon geste
Le client se rétracte, le colis n'est pas particancelShipment
Le colis est chez le livreur, le client annuleopenDispute
Le colis est arrivé casséopenDispute
Le colis n'arrive pasopenDispute
Vous vous êtes trompé d'adresse avant l'enlèvementcancelShipment, puis un nouvel envoi

Ce que votre système doit prévoir

  1. Un envoi peut être annulé par l'autre bord. Le client final peut renoncer. Écoutez les webhooks plutôt que de supposer que l'état que vous avez posé tient.
  2. Un 409 n'est jamais à réessayer. Rejouer la même annulation ne changera pas l'état du colis. Voir Erreurs.
  3. Un litige n'est pas une fin. Il se résout, et le règlement reprend son cours.