Workspace

Guide de construction d'une boutique dropshipping (version Patounes)

Boutique de référence : Patounes (accessoires pour chiens et chats), construite avec Claude Code à partir de la boutique Maison Bien-Être. Ce guide rassemble tous les points de construction, dans l'ordre réel, avec les commandes, les formules, les scripts, les décisions et les pièges, pour recréer la même boutique sur une autre niche en un temps réduit. Il ne contient aucun secret : seuls les noms des variables sont indiqués. Il complète GUIDE-FABRICATION-BOUTIQUE.md (modèle Maison Bien-Être) avec ce qui a été appris sur Patounes.

21parties
~1 jourpour 60 produits
35 %marge cible
0 €capital d'avance
Aucun résultat pour cette recherche.

0. Comment utiliser ce guide

Pour une nouvelle boutique, remplacer ces variables partout (fichier central : src/lib/site.ts).

VariablePatounesNouvelle boutique
{{NOM}}Patounes…
{{SOUS_TITRE}}par : What else by Vinc…
{{DOMAINE}}patounes.whatelsebyvinc.com (sous-domaine)…
{{THEME}}accessoires et bien-être pour chiens et chats…
{{CATEGORIES}}chiens, chats2 maximum
{{SOUS_CATEGORIES}}3 par catégorie (6 au total)3 par catégorie
{{PAYS}}FR, BE, CH, LU…
{{DELAI}}7 à 20 jours ouvrésselon la route CJ
{{MARGE}}35 % (28 % pour la gamme d'appel)…
{{EMAIL}}contact@whatelsebyvinc.com…

Ordre conseillé : lire 1 à 3, suivre 16 (checklist), copier les consignes du 17, adapter selon le 19.

1. Architecture

Visiteur ─▶ Next.js (Vercel) ─▶ Stripe Checkout ─▶ paiement
              │                         │ webhook checkout.session.completed
              ▼                         ▼
      Neon Postgres ◀── commande + lignes (une seule requête, idempotent)
                                        │
                           CJ : créer la commande ─▶ payer sur le solde CJ
                                        │
                  cron quotidien : relance, paiement en attente, suivi
                                        │
                    alertes Slack (facultatif) · /admin pour les commandes à payer
BriqueChoix
FrameworkNext.js 16.4 (App Router, Turbopack), React 19.3, TypeScript
StyleTailwind CSS 4 (@tailwindcss/turbopack), thème sombre automatique, palette stone + accent amber
BaseNeon Postgres (@neondatabase/serverless)
HébergementVercel (déploiement par CLI, 1 cron par jour sur l'offre gratuite)
PaiementStripe Checkout (test puis réel)
FournisseurCJdropshipping API v2
Mesure@vercel/analytics (sans cookies)
CodeDépôt Git local (pas de GitHub sur Patounes)

Principes : zéro capital d'avance (le client finance CJ) · honnêteté (aucune promesse de santé, délais = moyenne) · idempotence (un événement rejoué ne crée rien en double) · le serveur relit les prix en base · les règles (livraison, retours, contact) sont écrites une seule fois (src/lib/faq.ts, src/lib/site.ts) et reprises partout.

2. Déroulé réel (Patounes) et durées indicatives

#ÉtapeQuiDurée
1Cadrage : niche, 2 catégories, 6 sous-catégories, domainevous + Claude15 min
2Socle Next.js, schéma SQL, pages, checkout, webhookClaude1 h
3Commande fournisseur CJ, cron, alertesClaude30 min
4Compte Vercel relié, déploiement, domaine, DNS Cloudflare, certificatvous + Claude30 min
5Base Neon, schéma, secrets locaux, variables Vercelvous + Claude30 min
6Vague 1 de produits (3) puis vague 2 (23) puis vague 3 (28)Claude1 h chacune
7Flux Google/Meta/Pinterest, 3 guides, JSON-LDClaude1 h
8Reprise des fonctionnalités de l'ancienne boutique (voir 5.2)Claude1 h
9Routine quotidienne de produitsClaude45 min
10Gamme d'appel (prix d'entrée) et rappel de bilanClaude30 min

Total : environ une journée de travail pour une boutique de 60 produits, hors comptes et validations.

3. Comptes et partage des tâches

À créer par vous (Claude ne crée pas de compte et n'accepte pas de conditions) : Vercel, Neon, Stripe, CJdropshipping (clé API), Cloudflare (DNS), GitHub (facultatif), Slack (webhook, facultatif), Google Merchant Center / Meta Commerce / Pinterest Business / Search Console (voir 12.4).

Vous (obligatoire)Claude
Créer les comptes, accepter les conditionsÉcrire tout le code, les textes, les scripts
Saisir les clés Stripe (secrète et webhook) dans Vercel ou dans un fichier localLire les secrets via des scripts, sans jamais les afficher
Recharger le solde CJ avec l'argent des ventesCréer les commandes, relancer, alerter
Définir ADMIN_PASSWORDPréparer l'écran /admin
Taper un vrai paiement de test (carte 4242…)Vérifier base, webhook, alertes ensuite
Valider les actions en mode réel et sur la base de productionPréparer, tester, déployer après accord

Outils en ligne de commande à avoir connectés : vercel (compte lié), neon (organisation choisie via --org-id), stripe (travaille dans le bac à sable par défaut), node ≥ 20, git, python + Pillow (planches de photos).

4. Fondations : Vercel, Neon, DNS, secrets

4.1 Projet

npx create-next-app@latest . --ts --tailwind --app --eslint --src-dir --use-npm --import-alias "@/*" --yes
npm i @neondatabase/serverless stripe @vercel/analytics

Next 16 : retirer cacheComponents et partialPrefetching du next.config.ts ; garder la règle turbopack pour Tailwind ("*.css": { loaders: ["@tailwindcss/turbopack"], as: "*.css" }) sinon @theme n'est pas reconnu. Images : images.remotePatterns pour **.cjdropshipping.com et cj-product-center.oss-accelerate.aliyuncs.com.

4.2 Vercel

vercel link --yes --project <nom>      # crée et relie le projet
vercel deploy --yes                    # le tout premier déploiement part en PRODUCTION
vercel deploy --prod --yes             # déploiements suivants
vercel domains add <sous-domaine> <projet>
vercel certs issue <sous-domaine>      # le certificat n'est pas toujours émis seul
vercel env add NOM production --sensitive --yes   # valeur lue sur l'entrée standard, jamais affichée
vercel env ls production               # noms seulement

Une variable ajoutée n'est prise en compte qu'au déploiement suivant. Ajouter chaque secret en production, preview et development. vercel.json : un seul cron quotidien (/api/cron/supplier-sync, 0 7 * * *).

4.3 DNS (Cloudflare)

Enregistrement A, nom = le sous-domaine, valeur 76.76.21.21, DNS uniquement (nuage gris, pas de proxy). Un sous-domaine s'écrit patounes.mondomaine.com : patounes-mondomaine.com serait un autre domaine à acheter. Vérifier : nslookup <sous-domaine> 1.1.1.1, puis vercel domains inspect, puis attendre le certificat.

4.4 Neon

npx neon@latest projects list --org-id <org>       # le CLI demande l'organisation sinon (interactif)
npx neon@latest connection-string --project-id <id> --pooled   # à rediriger vers un fichier, jamais à l'écran

Rejouer sql/schema.sql (uniquement create … if not exists). Installer les skills : npx neon@latest skills -s neon -s neon-postgres -y.

4.5 Fichiers de secrets locaux (tous ignorés par Git : .env*)

FichierContenu
.env.db.localDATABASE_URL
.env.cj.localCJ_API_KEY, CJ_ACCESS_TOKEN, CJ_REFRESH_TOKEN, CRON_SECRET
.env.stripe.localSTRIPE_SECRET_KEY, STRIPE_WEBHOOK_SECRET
.env.localcréé par Vercel (VERCEL_OIDC_TOKEN)

Ne jamais charger ces fichiers avec source : l'URL Neon contient des & que le shell coupe. Utiliser node --env-file=.env.db.local … ou les lire dans les scripts. Afficher seulement le préfixe d'une clé (sk_test / sk_live).

4.6 Variables d'environnement (noms)

DATABASE_URL · STRIPE_SECRET_KEY · STRIPE_WEBHOOK_SECRET · CJ_ACCESS_TOKEN · CRON_SECRET · NEXT_PUBLIC_SITE_URL · ADMIN_PASSWORD · (facultatif) ALERT_WEBHOOK_URL, NEXT_PUBLIC_CONTACT_EMAIL.

5. Code

5.1 Arborescence

src/app/            page.tsx · layout.tsx · sitemap.ts · robots.ts · icon.svg · favicon.ico · apple-icon.png
  produits/[slug]  categorie/[category](/[subcategory])  panier  suivi-commande  guides(/[slug])
  faq  livraison  retours  contact  a-propos  mentions-legales  cgv  confidentialite
  commande/succes  commande/meta (pont Meta)  flux/produits.xml/route.ts
  admin/avis  admin/commandes  api/{checkout,webhooks/stripe,cron/supplier-sync,order-status,avis,chat}
src/components/     ProductDetailV2 · ProductGallery · StickyBuyBar · ProductGrid · CategoryCards · CategoryNav ·
                    RotatingImage · ReviewForm · ChatWidget · SiteLogo · SiteFooter · LegalHeader · InfoPage · JsonLd
src/lib/            site · products · product-sections · db · stripe · cjdropshipping · fulfillment · orders · reviews ·
                    admin-auth · alerts · delivery · faq · guides · cart-context · chat/{engine,catalog}
sql/                schema.sql · ajustements/ (traces des vagues) · routine/ (traces quotidiennes)
scripts/            cj.mjs · wave*.json · gamme-appel.json · bilan-gamme.mjs · routine/{cj,q,ins}.mjs + jour.json

5.2 Reprendre une boutique existante (méthode la plus rapide)

Quand une boutique de même architecture existe déjà : copier les fichiers génériques éprouvés, puis adapter les chaînes propres à la niche. Fichiers génériques : components/*, lib/{admin-auth,alerts,cart-context,cjdropshipping, delivery,fulfillment,orders,product-sections,reviews,stripe,db}, app/{admin,api,commande,suivi-commande,categorie, produits,panier}. À réécrire : lib/products.ts (libellés), lib/guides.ts, lib/chat/catalog.ts (synonymes), CategoryCards, textes de l'accueil, layout.tsx, app/flux (catégorie Google), pages d'information. Rechercher ensuite les résidus : grep -rniE "<ancien nom>|<saison>|<ancienne niche>" src.

5.3 Particularités Next.js 16 à connaître

  • params et searchParams sont des Promesses ; cookies() est asynchrone.
  • Une page qui interroge la base et n'a pas dynamic = "force-dynamic" ni revalidate est pré-générée au build : si le build n'a pas DATABASE_URL, elle fige l'état « base indisponible » (ISR de 60 s la corrige à la première requête).
  • sitemap.ts doit être force-dynamic, sinon il ne voit pas les produits ajoutés après le build.
  • Les pages doivent tolérer une base absente (.catch(() => [])) : le build ne doit jamais casser.
  • Fichiers copiés depuis Windows : fins de ligne CRLF. Normaliser (sed -i 's/\r$//') avant tout remplacement par expression régulière, sinon les remplacements multi-lignes échouent sans erreur.
  • Logo : composant SVG inline (SiteLogo) + icon.svg, favicon.ico (16/32/48) et apple-icon.png (180) dans src/app/.

6. Base de données

Tables : products, orders, order_items, supplier_orders, reviews (schéma complet : sql/schema.sql). Colonnes clés de products : slug (unique), description (format strict, voir 7.2), price_cents, category, subcategory, in_stock, images (jsonb : la 1re = image_url), cj_product_id, cj_variant_id, cj_logistic_name.

Conventions : sql/schema.sql rejouable · chaque écriture de données laisse une trace datée dans sql/ajustements/AAAA-MM-JJ-sujet.sql (vagues, prix) ou sql/routine/AAAA-MM-JJ.sql (routine) · insertions paramétrées avec on conflict (slug) do nothing · changement de prix gardé : update products set price_cents = NEW where slug = 'x' and price_cents = OLD. Scripts d'écriture jetables (*.tmp.mjs) : ils lisent .env.db.local, n'affichent jamais de valeur, sont supprimés après usage.

7. Catalogue

7.1 Taxonomie

2 catégories, 3 sous-catégories chacune (6 au total). Libellés dans CATEGORY_LABELS / SUBCATEGORY_LABELS (src/lib/products.ts). Déployer un nouveau libellé avant d'insérer des produits, sinon le slug brut s'affiche. Patounes : chiens → promenade, jouets-chiens, couchage-chiens ; chats → jouets-chats, griffoirs, couchage-chats.

7.2 Format d'une fiche (parsé par le gabarit de page)

Accroche d'une phrase.

Ce que vous obtenez :
• 4 puces factuelles (matière, taille, contenu, particularité visible sur la photo)

Phrase d'usage.

Règles : français soigné, uniquement des faits (fiche CJ ou photo) ; sinon « selon la fiche du fournisseur » ; aucune allégation de santé ; aucune marque ; une puce « Vendu à l'unité (modèle X ; les autres coloris visibles ne sont pas inclus) » quand les photos montrent d'autres variantes ; nom court avec matière ou format entre parenthèses ; slug kebab-case sans accents, unique.

7.3 Photos

image_url = photo de la variante vendue ; images = 1 à 4 photos de la même variante. Rejeter : texte publicitaire ou cotes sur la photo principale, filigrane, logo d'une autre marque, variantes côte à côte, rendu IA différent du produit, photos d'un autre article que celui vendu (ex. pièce seule vs set complet). Une photo avec cotes n'est acceptable qu'en dernière position de la galerie.

8. Sourcing CJdropshipping

8.1 Authentification (piège majeur)

La clé API CJ (forme xxxx@api@xxxx) n'est pas le jeton d'accès. L'échanger : POST /v1/authentication/getAccessToken {"apiKey": "..."} → accessToken (valable environ 6 mois) + refreshToken. Renouvellement : POST /v1/authentication/refreshAccessToken. Limite : 1 échange toutes les 5 minutes. Le jeton se met aussi dans Vercel (CJ_ACCESS_TOKEN) : la tâche de commandes l'utilise. Noter la date d'expiration.

8.2 API (base https://developers.cjdropshipping.com/api2.0, en-tête CJ-Access-Token)

UsageAppel
RechercheGET /v1/product/listV2?keyWord=<anglais>&size=20 → data.content[0].productList
DétailGET /v1/product/query?pid= → variantes (vid, variantKey, variantSellPrice, variantImage, variantStandard), productImage (chaîne JSON), description
LivraisonPOST /v1/logistic/freightCalculate {startCountryCode:"CN", endCountryCode:"FR", products:[{quantity:1, vid}]}
CommandePOST /v1/shopping/order/createOrderV3 (isSandbox 1/0, iossType: 3, iossNumber: "CJ-IOSS")
PayerPOST /v1/shopping/pay/payBalance · solde : GET /v1/shopping/pay/getBalance
My ProductsPOST /v1/product/addToMyProduct {productId} (code 100002 = déjà ajouté)
1 appel par seconde (code 1600200) : espacer de 1,3 à 1,5 s et réessayer. Les commandes sandbox ne se paient pas.

8.3 Pipeline d'une vague de produits (reproductible)

  1. Recherche : 40 à 50 mots-clés en anglais répartis par sous-catégorie ; garder les 4 premiers par listedNum avec warehouseInventoryNum > 100 ; exclure ce qui est déjà en base (cj_product_id) et le bruit (regex : vêtements, médical/vétérinaire, électronique, piles, LED, laser, GPS, caméra, distributeur automatique, cage, marque, adulte…).
  2. Détail + livraison de chaque candidat (variante la moins chère) ; route au totalPostageFee le plus bas dont le délai maximal est ≤ 15 jours ; calcul du prix et de la marge (section 9) ; écarter au-delà de 34,90 € (couchages 44,90 €).
  3. Planches de photos numérotées (Python + Pillow, 8 produits par planche, 1re vignette = variante vendue) : regarder toutes les planches. Taux de rejet observé : environ 40 % (texte sur la photo, mauvaise variante, produit différent, marque, parodie de marque, produit électronique).
  4. Rédiger les fiches (7.2) dans un fichier wave*.json : slug, name, description, price_cents, category, subcategory, cj_product_id, cj_variant_id, cj_logistic_name, wholesale_usd, postage_usd, net_margin_eur, delivery_days, images[].
  5. Valider sans écrire : doublons en base, prix en ,90 ≥ 12,90 €, marge ≥ seuil, 4 puces, pas d'allégation, hôtes d'images.
  6. Présenter le lot et attendre l'accord, puis insérer, écrire la trace SQL, ajouter à « My Products », vérifier en ligne (page 200, image via /_next/image, flux, sitemap). Rendement observé : vague 2 = 23 produits retenus sur 58 candidats ; vague 3 = 28 retenus sur 115 candidats (67 passés en revue visuelle). Arrêter plutôt que de forcer un produit médiocre.

9. Prix et marges

net = P / 1,2  −  (0,015 × P + 0,25)  −  (prix_gros_USD + totalPostageFee_USD) × 0,86

P = prix TTC en euros ; toujours totalPostageFee (jamais logisticPrice, qui sous-estime) ; en franchise de TVA remplacer P / 1,2 par P. Prix en ,90, minimum 12,90 € ; livraison offerte (son coût est dans le prix). Fonctions de référence : netMargin et priceFor (annexe 18.1).

Ordres de grandeur observés : prix moyen 21,5 €, marge nette moyenne 7,8 € (35-38 %). Baisser un prix de 1 € TTC retire environ 0,8 € de marge.

Gamme d'appel (décision du 2026-10-10) : 10 produits d'entrée à 28 % de marge plancher (au lieu de 35 %) pour obtenir les premières commandes et les premiers avis : prix moyen 17,70 € → 15,60 €, marge moyenne 6,45 € → 4,73 € (-27 %), soit +36 % de ventes nécessaires pour gagner autant. Produits d'entrée = articles courants, comparables dans Google Shopping, hors saison. Ne pas baisser globalement ; mesurer 3 semaines (scripts/bilan-gamme.mjs), puis garder, étendre ou revenir. Tant qu'il y a peu de visites, le prix n'est pas le problème : trafic et confiance d'abord.

10. Paiement, commande fournisseur, suivi

  • Checkout (/api/checkout) : reçoit {slug, quantity}, relit prix et stock en base, crée la session avec collecte d'adresse (pays livrés) et téléphone obligatoire (exigé par CJ).
  • Webhook (/api/webhooks/stripe) : signature vérifiée sur le corps brut ; commande + lignes insérées en une requête ; mode = livemode ? "live" : "test" ; erreur → alerte + réponse 500 (Stripe rejoue).
  • Fulfillment : regrouper par route logistique, numéro de commande stable (PAT-<id> ou -N), createOrderV3 (sandbox si mode test), paiement sur le solde ; solde insuffisant → statut « Paiement CJ en attente » + une alerte.
  • Cron quotidien : relance des commandes non transmises, paiements en attente, numéros de suivi.
  • Admin : /admin/avis (modération), /admin/commandes (bouton « Payer maintenant ») ; cookie httpOnly, 8 h, comparaison à temps constant ; fermé tant que ADMIN_PASSWORD n'est pas défini et déployé.
  • Suivi : /suivi-commande (numéro et e-mail doivent correspondre).

Stripe : test et réel sont deux mondes séparés

Clé, webhook et secret de webhook doivent être du même mode. Un webhook de test ne reçoit rien des paiements réels. La CLI Stripe travaille dans le bac à sable ; pour agir en réel, lui fournir la clé réelle (variable STRIPE_API_KEY) et obtenir l'accord explicite avant. Contrôle sans payer : créer une session via /api/checkout et lire le préfixe de l'URL (cs_test_ ou cs_live_). Test du webhook sans carte : envoyer un événement checkout.session.completed signé (HMAC-SHA256 de t.payload avec le secret) pour une vraie session ; vérifier signature fausse = 400, rejeu = pas de doublon ; puis supprimer la commande fictive (sinon le cron la relance).

11. Pages et gabarits

Fiche produit V2 : galerie, titre, prix, accroche, cartes « Ce que vous obtenez », encadré de livraison estimée (dates calculées, jamais une promesse), bouton d'achat, barre d'achat fixe sur mobile, sections dépliables, avis, produits associés. Accueil : bannière compacte, deux cartes de catégories animées (RotatingImage), thèmes, nouveautés, catalogue groupé, guides, garanties. Pages légales : reprendre l'éditeur (entreprise individuelle, SIRET, adresse, e-mail) depuis src/lib/site.ts ; hébergeur Vercel ; CGV 7 articles ; confidentialité (Stripe, CJ, Vercel, RGPD, 10 ans). Règles uniques (faq.ts) : livraison offerte FR/BE/CH/LU, 7 à 20 jours ouvrés (moyenne), rétractation 14 jours, retour par envoi postal, frais à la charge du client sauf défaut, pas d'échange, remboursement sous 14 jours, réponse sous 48 h ouvrées. Ne jamais inventer une règle (ex. hygiène) qui n'est pas partout identique.

12. SEO, données structurées et flux

12.1 Métadonnées

Un <title> avec mot-clé par page, description de 120 à 160 caractères, URL canonique, Open Graph, un seul <h1>.

12.2 JSON-LD

Accueil : Organization, WebSite · Fiche : Product + Offer avec OfferShippingDetails (0 €, pays livrés) et MerchantReturnPolicy (14 jours, par envoi postal, ReturnShippingFees) · Avis : AggregateRating seulement s'il existe de vrais avis publiés · FAQ : FAQPage · Guides : Article · Fil d'Ariane : BreadcrumbList.

12.3 Flux produits (/flux/produits.xml)

RSS 2.0 espace g: (accepté par Google, Meta, Pinterest) : g:id (slug), title, description (accroche + puces ponctuées), link, g:image_link, g:additional_image_link (≤ 10), g:availability, g:price (12.90 EUR), g:condition, g:brand, g:identifier_exists = no, g:google_product_category (chemin en texte, ex. Animals & Pet Supplies > Pet Supplies > Dog Supplies), g:product_type. Cache s-maxage=300 : un changement de prix n'apparaît qu'après 5 minutes. Livraison et TVA se règlent dans chaque compte plateforme.

12.4 À faire par vous dans chaque plateforme (non automatisable)

  • Google Merchant Center : source = le flux (récupération planifiée) ; pays ; livraison (offerte, 1-3 j de traitement + 6-17 j d'acheminement, corriger le fuseau horaire) ; retours (échanges : Non ; neufs et légèrement utilisés ; à la charge du client) ; service client (page contact, cocher le chatbot). Statut « limité » = normal sans publicité.
  • Meta : catalogue alimenté par le flux ; URL de paiement /commande/meta?products=slug:qty,….
  • Pinterest (fait sur Patounes) : 1) Paramètres → Lien vers Pinterest → Sites Web → Revendiquer vos contenus ; la balise p:domain_verify affichée est propre au compte Pinterest, pas au domaine : la même sert pour tous vos sites ; l'ajouter dans metadata.other de layout.tsx, déployer, puis valider (méthode « balise HTML »). 2) Catalogues → Ajouter une source de données → Fournissez un lien URL : nom, adresse du flux, format XML, pays France, langue Français, devise EUR (par défaut : CSV, États-Unis, English, USD), ingestion toutes les 24 h, puis Importer et Continuer (validation par e-mail sous 24 h). Le catalogue de Maison Bien-Être peut recevoir plusieurs sources (une par boutique). Pièges : le navigateur automatisé fige souvent (attendre 10 s avant chaque capture), les listes se règlent avec form_input, et un clic hors du panneau déclenche « fermer cette page ? ».
  • Google Search Console : soumettre https://<domaine>/sitemap.xml. Un nouveau magasin n'apparaît qu'après plusieurs semaines : zéro clic au début est normal.

12.5 Contenu

3 guides de fond liés aux produits (choix de l'équipement, occuper l'animal, aménager un coin repos), sans allégation de santé. Le contenu met des mois à produire du trafic : le faire tôt.

13. Automatisation

13.1 Routine quotidienne de produits (tâche planifiée Claude Code)

  • 3 scripts à noms constants dans scripts/routine/ : cj.mjs (search, detail, freight, image, mine ; renouvelle le jeton si besoin), q.mjs (lectures select : products, counts, next, exists), ins.mjs (--dry puis insertion + trace). Chaque forme de commande nouvelle déclenche une demande d'autorisation : n'utiliser que ces formes, avec chemins absolus, et passer les paramètres du jour par scripts/routine/jour.json (écrit avec l'outil de fichiers).
  • Garde-fous dans ins.mjs : 3 produits au plus par jour, 1 par sous-catégorie, sous-catégories connues seulement, prix en ,90 ≥ 12,90 €, marge ≥ 35 % avec totalPostageFee, format de fiche, pas d'allégation, hôtes d'images CJ.
  • Rotation : q.mjs next choisit les 3 sous-catégories les moins fournies, puis celles où l'ajout est le plus ancien.
  • Interdits explicites : Stripe, commandes, achats, secrets affichés, modification de produits existants, nouvelles catégories, fichiers du site, vercel/npm/git push/reset/checkout, navigateur.
  • Horaire décalé de celles des autres boutiques (limite CJ de 1 appel par seconde partagée) ; 8 h 30 ici.
  • Le prompt doit être entièrement autonome (contexte, chemins, règles, format du compte rendu).

13.2 Fonctionnement des tâches planifiées

Elles ne s'exécutent que si l'application est ouverte (sinon au prochain lancement). « Run now » une première fois pour préapprouver les outils. Une exécution peut être lancée à la demande. Un rappel unique utilise fireAt (ex. bilan de la gamme d'appel à 3 semaines, en lecture seule, qui recommande sans rien modifier).

14. Claude Code : permissions et sécurité

  • Le contrôle automatique refuse : lire un dossier de secrets (~/.claude/secrets), vercel deploy --prod, toute action en mode réel non autorisée. Ne pas contourner : demander l'accord, ou ajouter une règle dans .claude/settings.local.json (personnel, ignoré par Git), ex. {"permissions":{"allow":["Bash(vercel deploy --prod:*)"]}} (peut nécessiter une nouvelle session pour être lue).
  • Secrets : fichiers .env*.local créés par vous ; Claude les lit via des scripts, ne les affiche jamais, ne les colle pas dans le chat, n'entre pas de clés ou de cartes dans un formulaire d'une page tierce (même une carte de test sur Stripe).
  • Mode réel (Stripe, base de production, déploiement, DNS) : toujours un « oui » explicite, par action.
  • Bash sous Windows : vercel curl /chemin est déformé par Git Bash (préfixer MSYS_NO_PATHCONV=1) ; éviter les heredocs contenant des apostrophes (utiliser l'outil de création de fichier) ; sleep long refusé → boucle until.
  • Navigateur intégré : fenêtre étroite = version mobile des sites ; fermer les fenêtres d'accueil ; préférer lire le texte de la page et la ligne de commande aux captures.

15. Pièges et leçons (par ordre d'importance)

  1. Stripe : clé réelle + webhook de test = paiements encaissés mais commandes perdues. Vérifier le mode avant tout.
  2. totalPostageFee, jamais logisticPrice : sinon marges fausses.
  3. La clé API CJ n'est pas le jeton ; noter l'expiration ; reporter le jeton renouvelé dans Vercel.
  4. Solde CJ à 0 = commande créée mais non expédiée : alerte + bouton « Payer maintenant » ; premières ventes retardées.
  5. Libellé de sous-catégorie à déployer avant les produits.
  6. Une variable Vercel ne s'applique qu'au déploiement suivant ; copie locale ≠ valeur Vercel.
  7. Photos CJ : 40 % de rejet ; toujours regarder ; la photo de la variante vendue doit montrer le produit vendu.
  8. Produits à éviter : électronique/piles, médical/vétérinaire, marques et parodies de marques, produits à texte personnalisé, doublons de modèles, articles lourds et fragiles.
  9. Page pré-générée sans base = « catalogue indisponible » figé ; sitemap doit être dynamique.
  10. source .env casse les URL Neon (&) ; CRLF casse les remplacements ; shell et apostrophes.
  11. Sous-domaine ≠ nouveau domaine ; DNS en « DNS uniquement » ; émettre le certificat si besoin.
  12. Commande fictive de test : toujours la supprimer (le cron la relance sinon).
  13. Baisser les prix n'attire pas de trafic ; mesurer avant ; gamme d'appel limitée et réversible.
  14. Les valeurs par défaut de Merchant Center sont fausses pour vous (fuseau horaire, échanges, état).
  15. Deux routines partagent la limite CJ : décaler les horaires.
  16. Une règle inventée (hygiène, etc.) crée une incohérence avec Merchant Center et la FAQ : ne jamais en ajouter.
  17. Un changement invisible (SEO, flux) ne se voit pas : le grouper avec un changement visible.

16. Checklist de lancement

Phase 0 — Cadrage : niche, 2 catégories, 6 sous-catégories, nom, sous-domaine, e-mail, pays, délai ; vérifier 60+ produits CJ éligibles. Phase 1 — Fondations : projet Next ; Vercel lié ; Neon créé et schéma rejoué ; DNS ; certificat ; secrets locaux ; variables Vercel. Phase 2 — Catalogue : libellés de taxonomie ; vague 1 (3 à 5 produits, pour valider le circuit) puis vagues de 25 ; traces SQL. Phase 3 — Tunnel en TEST : clé de test, webhook de test, commande sandbox CJ, événement signé, suppression de la commande fictive. Phase 4 — Confiance et légal : pages d'information, éditeur, FAQ unique, CGV, confidentialité, avis, admin (ADMIN_PASSWORD). Phase 5 — SEO : métadonnées, JSON-LD, sitemap dynamique, flux, 3 guides. Phase 6 — Passage en réel (accord explicite) : clé réelle et webhook réel (secret en production) dans le même déploiement ; solde CJ ; un vrai petit achat remboursé pour valider le circuit. Phase 7 — Visibilité : Merchant Center, Meta, Pinterest, Search Console. Phase 8 — Pilotage : routine quotidienne, gamme d'appel, bilan à 3 semaines.

  • Clé Stripe et webhook du même mode · [ ] ADMIN_PASSWORD, CRON_SECRET définis et déployés · [ ] solde CJ vérifié
  • pages légales relues · [ ] commande réelle de test réussie · [ ] sitemap soumis · [ ] flux importé · [ ] routine « Run now »

17. Consignes prêtes à copier pour Claude

Lancement d'une boutique

Crée une boutique de dropshipping sur la niche : {{THEME}}, en suivant GUIDE-CONSTRUCTION-BOUTIQUE.md. Nom : {{NOM}},
domaine : {{DOMAINE}}, pays : {{PAYS}}. Reprends les fichiers génériques de la boutique Patounes (section 5.2). Aucune action
en mode réel ni écriture en base de production sans mon « oui » explicite ; n'affiche jamais un secret ; demande-moi seulement
ce que toi seul ne peux pas faire (comptes, clés Stripe, solde CJ, DNS).

Vague de produits

Prépare environ {{N}} produits : {{X}} pour {{CATEGORIE_A}} et {{Y}} pour {{CATEGORIE_B}}. Méthode 8.3 : 40 à 50 mots-clés en
anglais, détail et livraison (totalPostageFee, ≤ 15 j), planches de photos que tu regardes toutes, fiches au format 7.2,
validation sans écriture, puis présente le lot. Insère seulement après mon accord (trace SQL, My Products, vérification en ligne).

Gamme d'appel : « Propose 10 produits d'entrée à 28 % de marge, montre avant/après, applique après accord, ajoute un rappel de bilan à 3 semaines. » Routine : « Crée la routine quotidienne sur le modèle de patounes-routine-quotidienne (scripts à noms constants, garde-fous, rotation). »

18. Annexes

18.1 Fonctions de prix

export function netMargin(price: number, wholesaleUsd: number, postageUsd: number): number {
  return price / 1.2 - (0.015 * price + 0.25) - (wholesaleUsd + postageUsd) * 0.86;
}
export function priceFor(wholesaleUsd: number, postageUsd: number, minMargin = 0.35): number {
  let p = 12.9;
  while (netMargin(p, wholesaleUsd, postageUsd) < minMargin * p) p = Math.round((p + 0.5) * 100) / 100;
  const cand = Math.ceil(p) - 0.1;
  return cand >= p ? cand : cand + 1;
}

18.2 Aide-mémoire de commandes

vercel deploy --prod --yes | vercel env ls production | vercel domains inspect <d> | vercel certs issue <d>
stripe webhook_endpoints list --limit 20            # bac à sable par défaut
STRIPE_API_KEY=<clé réelle> stripe webhook_endpoints create --url <url> -d "enabled_events[]=checkout.session.completed"
npx neon@latest projects list --org-id <org>
node scripts/routine/q.mjs next | counts | products     node scripts/routine/ins.mjs --dry
node scripts/bilan-gamme.mjs                        # lecture seule
npx tsc --noEmit && npx eslint && npm run build     # avant tout déploiement

18.3 Glossaire

Variante (vid) déclinaison précise d'un produit · totalPostageFee frais de livraison réellement facturés par CJ · Sandbox commande fictive sans argent · Webhook appel automatique de Stripe vers le site · Idempotent rejouable sans effet double · IOSS régime de TVA à l'import des petits colis · Gamme d'appel produits d'entrée à marge réduite.

19. Adapter à une nouvelle niche : où changer quoi

FichierÀ adapter
src/lib/site.tsnom, sous-titre, thème, URL, e-mail, pays, délais, éditeur
src/lib/products.tsCATEGORY_LABELS, CATEGORY_ORDER, SUBCATEGORY_LABELS, URL par défaut
src/lib/chat/catalog.tsdictionnaire SYNONYMS (vocabulaire de la niche) ; suggestions dans engine.ts et ChatWidget.tsx
src/lib/guides.ts3 guides (slugs, textes, productSlugs)
src/components/CategoryCards.tsx, src/app/page.tsxtextes d'accueil, titre, description, JSON-LD
src/app/layout.tsxtitre, description, retirer toute balise de vérification d'un autre domaine
src/app/flux/produits.xml/route.tsmarque, catégorie Google (texte) par catégorie
src/components/SiteLogo.tsx, icon.svg, favicon.ico, apple-icon.pnglogo et icônes
src/lib/cart-context.tsxclé localStorage (<nom>.cart)
scripts/routine/*.mjsarbre TREE, liste des sous-catégories de q.mjs next, plafonds de prix
scripts/gamme-appel.json, bilan-gamme.mjsproduits de la gamme d'appel de la nouvelle boutique
Tâche planifiéeprompt : nom, domaine, chemins, sous-catégories, critères d'éligibilité propres à la niche

Critères d'éligibilité à réécrire pour la niche : exclusions (réglementées, électroniques, de marque), articles saisonniers et leurs dates, plafonds de prix par sous-catégorie, vocabulaire des mots-clés anglais.

20. Reste à faire sur Patounes (au 2026-10-10)

Premier achat réel de validation (puis remboursement) · alimenter le solde CJ · Merchant Center, Meta, Pinterest, Search Console · balise Pinterest du domaine · ALERT_WEBHOOK_URL (facultatif) · bilan de la gamme d'appel le 2026-10-31 · jeton CJ à renouveler avant le 2027-04-06 · relire les fiches les plus chères ajoutées par la routine.