refactor(docs): réorganiser la documentation selon principes DDD

Réorganise la documentation du projet selon les principes du Domain-Driven Design (DDD) pour améliorer la cohésion, la maintenabilité et l'alignement avec l'architecture modulaire du backend.

**Structure cible:**
```
docs/domains/
├── README.md (Context Map)
├── _shared/ (Core Domain)
├── recommendation/ (Supporting Subdomain)
├── content/ (Supporting Subdomain)
├── moderation/ (Supporting Subdomain)
├── advertising/ (Generic Subdomain)
├── premium/ (Generic Subdomain)
└── monetization/ (Generic Subdomain)
```

**Changements effectués:**

Phase 1: Création de l'arborescence des 7 bounded contexts
Phase 2: Déplacement des règles métier (01-19) vers domains/*/rules/
Phase 3: Déplacement des diagrammes d'entités vers domains/*/entities/
Phase 4: Déplacement des diagrammes flux/états/séquences vers domains/*/
Phase 5: Création des README.md pour chaque domaine
Phase 6: Déplacement des features Gherkin vers domains/*/features/
Phase 7: Création du Context Map (domains/README.md)
Phase 8: Mise à jour de mkdocs.yml pour la nouvelle navigation
Phase 9: Correction automatique des liens internes (script fix-markdown-links.sh)
Phase 10: Nettoyage de l'ancienne structure (regles-metier/, diagrammes/, features/)

**Configuration des tests:**
- Makefile: godog run docs/domains/*/features/
- scripts/generate-bdd-docs.py: features_dir → docs/domains

**Avantages:**
 Cohésion forte: toute la doc d'un domaine au même endroit
 Couplage faible: domaines indépendants, dépendances explicites
 Navigabilité améliorée: README par domaine = entrée claire
 Alignement code/docs: miroir de backend/internal/
 Onboarding facilité: exploration domaine par domaine
 Tests BDD intégrés: features au plus près des règles métier

Voir docs/REFACTOR-DDD.md pour le plan complet.
This commit is contained in:
jpgiannetti
2026-02-07 17:15:02 +01:00
parent 78422bb2c0
commit 5e5fcf4714
227 changed files with 1413 additions and 1967 deletions

View File

@@ -0,0 +1,90 @@
# language: fr
@api @profile @verification @mvp
Fonctionnalité: Badge compte vérifié pour créateurs authentiques
En tant que créateur officiel
Je veux obtenir un badge vérifié
Afin de prouver mon authenticité et gagner la confiance
Scénario: Demande de vérification par un créateur
Étant donné un créateur "MuseeDuLouvre" avec 1000+ abonnés
Quand il demande la vérification via "Paramètres > Demander la vérification"
Alors un formulaire de demande s'affiche:
| Champ requis | Exemple |
| Nom officiel | Musée du Louvre |
| Type d'organisation | Institution culturelle |
| Document officiel | KBIS / Statuts |
| Preuve d'identité | Carte d'identité |
| Site web officiel | louvre.fr |
| Compte social officiel | @MuseeLouvre (Twitter) |
Et la demande est soumise pour review
Et un événement "VERIFICATION_REQUEST_SUBMITTED" est enregistré
Scénario: Vérification par l'équipe RoadWave
Étant donné une demande de vérification reçue
Quand un modérateur examine le dossier
Alors il vérifie:
| Critère | Validation |
| Documents officiels | Authentiques |
| Correspondance identité | Confirmée |
| Site web officiel | Vérifié (DNS) |
| Réseaux sociaux | Cross-vérifiés |
| Activité sur RoadWave | Régulière (3+ mois) |
Et prend une décision dans les 7 jours
Et un événement "VERIFICATION_REVIEWED" est enregistré
Scénario: Attribution du badge vérifié
Étant donné une demande acceptée
Quand le badge est attribué
Alors un badge bleu " Vérifié" s'affiche:
| Emplacement | Affichage |
| À côté du nom de profil | Musée du Louvre |
| Dans les résultats | Badge visible |
| Dans les commentaires | Badge visible |
Et une notification est envoyée: "Félicitations ! Votre compte est maintenant vérifié"
Et un événement "VERIFICATION_BADGE_GRANTED" est enregistré
Scénario: Avantages du compte vérifié
Étant donné un créateur vérifié
Alors il bénéficie de:
| Avantage | Détail |
| Badge bleu visible | Crédibilité accrue |
| Priorité dans les recherches | Meilleur ranking SEO |
| Statistiques avancées | Analytics détaillées |
| Support prioritaire | Réponse < 24h |
| Contenu mis en avant | Page "Créateurs vérifiés" |
Et un événement "VERIFIED_BENEFITS_DISPLAYED" est enregistré
Scénario: Révocation du badge pour violation
Étant donné un créateur vérifié "InstitutionX"
Quand il viole les CGU (contenu inapproprié)
Alors le badge est révoqué immédiatement
Et un email explique la raison
Et il peut faire appel de la décision
Et un événement "VERIFICATION_BADGE_REVOKED" est enregistré
Scénario: Renouvellement annuel de la vérification
Étant donné un créateur vérifié depuis 12 mois
Quand l'anniversaire de la vérification arrive
Alors une review automatique est lancée
Et des documents à jour peuvent être demandés
Et le badge reste actif pendant la review
Et un événement "VERIFICATION_RENEWAL_STARTED" est enregistré
Scénario: Badge spécial pour partenaires officiels
Étant donné un partenaire stratégique (Offices du Tourisme, Musées nationaux)
Alors un badge or " Partenaire Officiel" est attribué
Et des privilèges supplémentaires sont accordés
Et un événement "OFFICIAL_PARTNER_BADGE_GRANTED" est enregistré
Scénario: Statistiques des comptes vérifiés
Étant donné que 150 comptes sont vérifiés
Alors les indicateurs suivants sont disponibles:
| Métrique | Valeur |
| Comptes vérifiés | 150 |
| % de la base créateurs | 1.5% |
| Demandes en attente | 45 |
| Taux d'acceptation | 65% |
| Temps moyen de vérification | 5 jours |
Et les métriques sont exportées vers le monitoring

View File

@@ -0,0 +1,293 @@
# language: fr
Fonctionnalité: Profil créateur
En tant qu'utilisateur de RoadWave
Je veux consulter les profils des créateurs
Afin de découvrir leur contenu et décider de m'abonner
Contexte:
Étant donné que l'application RoadWave est démarrée
# 15.2.1 - Structure de la page profil
Scénario: URL du profil créateur
Étant donné un créateur avec le pseudo "paris_stories"
Quand l'utilisateur accède au profil
Alors l'URL est "https://roadwave.fr/@paris_stories"
Scénario: Informations principales du profil
Étant donné un créateur "@paris_stories" avec les informations suivantes:
| champ | valeur |
| photo | avatar_120x120.jpg |
| pseudo | paris_stories |
| badge_vérifié | true |
| bio | Histoires et anecdotes de Paris |
| abonnés | 1200 |
| contenus | 42 |
| durée_totale | 18h |
| écoutes_totales | 54000 |
Quand le profil est affiché
Alors les éléments suivants sont visibles:
| élément | valeur affichée |
| Photo profil | 120×120 px |
| @pseudo | @paris_stories |
| Badge vérifié | |
| Bio | Histoires et... |
| Nombre abonnés | 1.2K abonnés |
| Nombre contenus | 42 contenus |
| Durée totale | 18h de contenu créé |
| Écoutes totales | 54K écoutes totales |
Plan du Scénario: Arrondi des statistiques publiques
Étant donné un créateur avec <valeur_exacte> <métrique>
Quand le profil est affiché
Alors la valeur affichée est "<valeur_affichée>"
Exemples:
| métrique | valeur_exacte | valeur_affichée |
| abonnés | 342 | 342 |
| abonnés | 1200 | 1.2K |
| abonnés | 54000 | 54K |
| abonnés | 1200000 | 1.2M |
| écoutes | 842 | 842 |
| écoutes | 5400 | 5.4K |
| écoutes | 142000 | 142K |
| écoutes | 2100000 | 2.1M |
| durée (heures) | 18 | 18h |
| durée (heures) | 142 | 142h |
Scénario: Bio avec markdown basique
Étant donné un créateur avec la bio suivante en markdown:
"""
**Histoires de Paris** - Découvrez la capitale
*Nouveau contenu chaque semaine*
https://paris-stories.fr
"""
Quand le profil est affiché
Alors le texte en gras "Histoires de Paris" est formaté
Et le texte en italique "Nouveau contenu chaque semaine" est formaté
Et le lien "https://paris-stories.fr" est cliquable
Scénario: Limitation de la bio à 300 caractères
Étant donné un créateur qui entre une bio de 350 caractères
Quand la bio est sauvegardée
Alors seuls les 300 premiers caractères sont conservés
Et un message "Maximum 300 caractères" s'affiche
Scénario: Boutons d'action principaux
Étant donné que l'utilisateur consulte un profil créateur
Quand la page est chargée
Alors les boutons suivants sont visibles:
| bouton | action |
| S'abonner | Abonnement au créateur |
| Partager profil | Menu de partage |
| | Menu contextuel |
Scénario: Menu contextuel du profil [•••]
Étant donné que l'utilisateur clique sur le bouton []
Quand le menu s'ouvre
Alors les options suivantes sont disponibles:
| option | description |
| Partager profil | Partager le lien du profil |
| Signaler profil | Signaler spam ou usurpation d'identité |
| Bloquer créateur | Masquer tous les contenus du créateur |
Scénario: Liste des contenus du créateur
Étant donné un créateur avec 3 contenus publiés
Quand le profil est affiché
Alors chaque contenu affiche:
| élément | exemple |
| Cover image | Image 16:9 |
| Titre | Balade à Paris |
| Durée et écoutes | 12 min · 🎧 2.3K |
| Localisation | 📍 Paris |
| Bouton lecture | |
Plan du Scénario: Options de tri des contenus
Étant donné un créateur avec 10 contenus publiés
Quand l'utilisateur sélectionne le tri "<option_tri>"
Alors les contenus sont triés par <critère>
Exemples:
| option_tri | critère |
| Plus récents | Date publication DESC (défaut) |
| Plus populaires | Écoutes × facteur temporel (90 jours) |
| Plus anciens | Date publication ASC |
Scénario: Filtrage des contenus par tag
Étant donné un créateur avec des contenus taggés "Voyage", "Histoire", "Gastronomie"
Quand l'utilisateur filtre par tags "Voyage, Histoire"
Alors seuls les contenus avec ces tags sont affichés
Et le nombre de résultats est indiqué "12 contenus"
Scénario: Recherche locale dans le profil
Étant donné que l'utilisateur consulte le profil de "@paris_stories"
Et que le créateur a publié 50 contenus
Quand l'utilisateur entre "Montmartre" dans la barre de recherche
Alors la recherche s'effectue sur les titres et descriptions
Et seuls les contenus correspondants sont affichés
Et le placeholder indique "Rechercher dans les contenus de @paris_stories"
Scénario: Chargement paginé des contenus
Étant donné un créateur avec 100 contenus publiés
Quand le profil est affiché
Alors 20 contenus sont chargés initialement
Et un bouton "Charger plus" est visible en bas de page
Quand l'utilisateur clique sur "Charger plus"
Alors 20 contenus supplémentaires sont chargés
# 15.2.2 - Statistiques publiques
Scénario: Informations publiques visibles par tous
Étant donné que l'utilisateur consulte un profil créateur
Alors les informations suivantes sont publiques:
| information | visible |
| Photo et pseudo | |
| Badge vérifié | |
| Bio | |
| Nombre abonnés | |
| Nombre contenus | |
| Durée totale créée | |
| Écoutes totales | |
Scénario: Informations privées non visibles
Étant donné que l'utilisateur consulte un profil créateur
Alors les informations suivantes sont privées:
| information | visible |
| Liste des abonnés | |
| Revenus | |
| Localisation précise | |
| Email | |
Scénario: Dashboard créateur avec métriques privées
Étant donné que le créateur "@paris_stories" consulte son propre dashboard
Quand la page statistiques est affichée
Alors les métriques suivantes sont accessibles:
| métrique | type |
| Taux complétion moyen | 78% |
| Évolution abonnés | Graphique |
| Écoutes par contenu | Tableau |
| Revenus | Dashboard |
| Taux conversion Premium | Pourcentage |
| Démographie (âge/zone) | Agrégée |
Scénario: Graphique d'évolution des abonnés
Étant donné que le créateur consulte son dashboard
Quand il sélectionne la période "30 jours"
Alors un graphique d'évolution des abonnés est affiché
Et les périodes disponibles sont:
| période |
| 30j |
| 90j |
| 1 an |
Scénario: Tableau détaillé des écoutes par contenu
Étant donné un créateur avec 10 contenus publiés
Quand il consulte le tableau des performances
Alors chaque contenu affiche:
| métrique | exemple |
| Titre | Balade |
| Écoutes totales | 2300 |
| Écoutes complètes >80% | 1840 |
| Taux complétion | 80% |
| Likes | 420 |
| Partages | 56 |
# 15.2.3 - Badge vérifié
Scénario: Affichage du badge vérifié
Étant donné un créateur vérifié "@paris_stories"
Quand son profil est affiché
Alors le badge bleu "" est accolé au pseudo
Et un tooltip "Compte vérifié" s'affiche au survol
Scénario: Badge vérifié visible partout
Étant donné un créateur vérifié "@paris_stories"
Alors le badge "" est affiché dans:
| emplacement |
| Page profil |
| Player en lecture |
| Résultats de recherche|
| Notifications |
Plan du Scénario: Attribution automatique du badge selon critères
Étant donné un créateur avec <critère>
Quand les conditions sont validées
Alors le badge vérifié est attribué <automatique>
Exemples:
| critère | automatique |
| KYC Mangopay validé | Oui |
| 10K abonnés + compte >6 mois | Oui |
| Célébrité / Média officiel | Manuel |
Scénario: Attribution automatique via KYC
Étant donné un créateur qui complète son KYC Mangopay
Quand les documents sont validés
Alors le badge vérifié est attribué automatiquement
Et une notification "Votre compte est maintenant vérifié " est envoyée
Scénario: Attribution automatique à 10K abonnés
Étant donné un créateur avec 9999 abonnés et un compte de 7 mois
Quand il atteint 10000 abonnés
Alors le badge vérifié est attribué automatiquement
Et une notification de félicitations est envoyée
Scénario: Demande manuelle de vérification (célébrité)
Étant donné un créateur reconnu publiquement
Quand il soumet le formulaire de demande de vérification
Alors une requête est créée pour l'équipe RoadWave
Et l'équipe vérifie l'identité sous 48-72h
Et le badge est attribué si validation réussie
Scénario: Retrait du badge en cas de suspension
Étant donné un créateur vérifié avec le badge ""
Quand sa monétisation est suspendue
Alors le badge vérifié est retiré temporairement
Et le badge est restauré après levée de la suspension
Scénario: Retrait définitif du badge pour strikes multiples
Étant donné un créateur vérifié avec 3 strikes actifs
Quand un 4ème strike est appliqué (ban)
Alors le badge vérifié est retiré définitivement
Et le compte est banni
Scénario: Retrait du badge pour usurpation d'identité
Étant donné un créateur vérifié qui usurpe l'identité d'une célébrité
Quand la fraude est détectée
Alors le badge est retiré immédiatement
Et le compte est banni
Et une enquête est ouverte
# Cas d'erreur et limites
Scénario: Profil créateur supprimé
Étant donné qu'un utilisateur tente d'accéder à "@deleted_user"
Quand la page est chargée
Alors un message "Ce profil n'existe pas ou a été supprimé" s'affiche
Scénario: Blocage d'un créateur
Étant donné que l'utilisateur bloque le créateur "@spam_account"
Quand l'utilisateur consulte son flux de recommandations
Alors aucun contenu de "@spam_account" n'est affiché
Et le créateur n'apparaît plus dans les recherches
Scénario: Déblocage d'un créateur
Étant donné que l'utilisateur a bloqué "@paris_stories"
Quand il accède à ses paramètres "Comptes bloqués"
Et qu'il débloque "@paris_stories"
Alors les contenus du créateur réapparaissent dans les recommandations
Scénario: Signalement d'un profil pour spam
Étant donné que l'utilisateur signale le profil "@spam_account"
Quand il sélectionne la raison "Spam"
Alors le signalement est envoyé à la modération
Et un message de confirmation s'affiche
Et le profil reste visible jusqu'à décision de modération
Scénario: Signalement pour usurpation d'identité
Étant donné que l'utilisateur signale le profil "@fake_celebrity"
Quand il sélectionne "Usurpation d'identité"
Et qu'il fournit une preuve
Alors le signalement est priorisé (priorité HAUTE)
Et l'équipe modération traite sous 24h

View File

@@ -0,0 +1,70 @@
# language: fr
@ui @profile @privacy @mvp
Fonctionnalité: Statistiques arrondies pour protection de la vie privée
En tant qu'utilisateur
Je veux que mes statistiques publiques soient arrondies
Afin de protéger ma vie privée et éviter le tracking précis
Scénario: Arrondi du nombre d'écoutes publiques
Étant donné un créateur avec 1,234 écoutes exactes
Quand son profil public est affiché
Alors le nombre affiché est: "1.2k écoutes"
Et non pas "1,234"
Et un événement "STATS_ROUNDED_DISPLAYED" est enregistré
Scénario: Règles d'arrondi selon les volumes
Étant donné différents volumes d'écoutes
Alors l'arrondi appliqué est:
| Écoutes exactes | Affiché publiquement |
| 42 | 40 |
| 157 | 150+ |
| 1,234 | 1.2k |
| 15,678 | 15k |
| 123,456 | 120k |
| 1,234,567 | 1.2M |
Et un événement "ROUNDING_RULES_APPLIED" est enregistré
Scénario: Statistiques précises pour le créateur seulement
Étant donné un créateur "alice@roadwave.fr"
Quand elle consulte son propre dashboard
Alors elle voit les chiffres exacts: 1,234
Mais les visiteurs externes voient: 1.2k
Et un événement "PRECISE_STATS_CREATOR_VIEW" est enregistré
Scénario: Arrondi des revenus publics
Étant donné un créateur avec 1,567 de revenus
Quand ses stats publiques sont affichées
Alors le montant est arrondi: "1.5k"
Et les décimales exactes sont masquées
Et un événement "REVENUE_ROUNDED_PUBLIC" est enregistré
Scénario: Arrondi du nombre d'abonnés
Étant donné un créateur avec 8,743 abonnés
Alors le profil public affiche: "8.7k abonnés"
Et évite le tracking précis de croissance
Et un événement "FOLLOWERS_ROUNDED_DISPLAYED" est enregistré
Scénario: Protection contre le scraping de données
Étant donné un bot qui scrape les profils
Quand il collecte les statistiques arrondies
Alors il ne peut pas obtenir de données précises
Et le tracking temporel est rendu imprécis
Et un événement "SCRAPING_PROTECTION_ACTIVE" est enregistré
Scénario: Option de désactivation de l'arrondi pour créateurs vérifiés
Étant donné un créateur vérifié "MuseeDuLouvre"
Quand il active "Afficher statistiques exactes"
Alors les chiffres précis sont publics
Et cela renforce la transparence
Et un événement "PRECISE_STATS_PUBLIC_ENABLED" est enregistré
Scénario: Métriques d'impact de l'arrondi sur la vie privée
Étant donné que 10 000 profils affichent des stats arrondies
Alors l'impact est mesuré:
| Métrique | Valeur |
| Tentatives de tracking bloquées | 1,234 |
| Précision moyenne du scraping | -70% |
| Satisfaction utilisateurs | 4.5/5 |
Et les métriques sont exportées vers le monitoring