diff --git a/.gitignore b/.gitignore index a7aa401..4353b08 100644 --- a/.gitignore +++ b/.gitignore @@ -1,143 +1,143 @@ -# ==================================== -# GITIGNORE POUR UNIONFLOW SERVER API -# ==================================== - -# ===== MAVEN ===== -target/ -pom.xml.tag -pom.xml.releaseBackup -pom.xml.versionsBackup -pom.xml.next -release.properties -dependency-reduced-pom.xml -buildNumber.properties -.mvn/timing.properties -.mvn/wrapper/maven-wrapper.jar -.flattened-pom.xml - -# ===== QUARKUS ===== -.quarkus/ -quarkus.log -hs_err_pid* - -# ===== JAVA COMPILED FILES ===== -*.class -*.jar -*.war -*.ear -*.nar -*.zip -*.tar.gz -*.rar - -# ===== IDE - ECLIPSE ===== -.project -.classpath -.settings/ -.factorypath -.metadata/ -bin/ -.apt_generated -.springBeans -.sts4-cache - -# ===== IDE - INTELLIJ IDEA ===== -.idea/ -*.iml -*.ipr -*.iws -out/ - -# ===== IDE - NETBEANS ===== -nbproject/ -nbbuild/ -nbdist/ -.nb-gradle/ -nb-configuration.xml -nbactions.xml - -# ===== IDE - VS CODE ===== -.vscode/ -*.code-workspace - -# ===== OS SPECIFIC ===== -# Mac -.DS_Store - -# Windows -Thumbs.db -ehthumbs.db -Desktop.ini -$RECYCLE.BIN/ - -# Linux -*~ - -# ===== LOGS ===== -*.log -*.log.* -logs/ -log/ - -# ===== TEMPORARY FILES ===== -*.tmp -*.temp -*.bak -*.backup -*.old -*.swp -*.swo -*.orig -*.rej -*~ - -# ===== ENVIRONMENT & CONFIGURATION ===== -.env -.env.local -.env.* -*.local -application-local.properties - -# ===== SECURITY - KEYS & CERTIFICATES ===== -*.key -*.pem -*.crt -*.p12 -*.jks -*.keystore -.certs/ -.certificates/ - -# ===== TEST COVERAGE ===== -.jacoco/ -jacoco.exec -coverage/ -.nyc_output/ - -# ===== GENERATED SOURCES ===== -src/gen/ -generated-sources/ -generated-test-sources/ - -# ===== BUILD ARTIFACTS ===== -dist/ -build/ -out/ - -# ===== NODE (if used for build tools) ===== -node_modules/ -npm-debug.log* -yarn-debug.log* -yarn-error.log* -pnpm-debug.log* -lerna-debug.log* - -# ===== DOCKER ===== -.dockerignore - -# ===== MAVEN WRAPPER (if not using project wrapper) ===== -# Uncomment if you don't want to commit Maven wrapper -# .mvn/ -# mvnw -# mvnw.cmd - +# ==================================== +# GITIGNORE POUR UNIONFLOW SERVER API +# ==================================== + +# ===== MAVEN ===== +target/ +pom.xml.tag +pom.xml.releaseBackup +pom.xml.versionsBackup +pom.xml.next +release.properties +dependency-reduced-pom.xml +buildNumber.properties +.mvn/timing.properties +.mvn/wrapper/maven-wrapper.jar +.flattened-pom.xml + +# ===== QUARKUS ===== +.quarkus/ +quarkus.log +hs_err_pid* + +# ===== JAVA COMPILED FILES ===== +*.class +*.jar +*.war +*.ear +*.nar +*.zip +*.tar.gz +*.rar + +# ===== IDE - ECLIPSE ===== +.project +.classpath +.settings/ +.factorypath +.metadata/ +bin/ +.apt_generated +.springBeans +.sts4-cache + +# ===== IDE - INTELLIJ IDEA ===== +.idea/ +*.iml +*.ipr +*.iws +out/ + +# ===== IDE - NETBEANS ===== +nbproject/ +nbbuild/ +nbdist/ +.nb-gradle/ +nb-configuration.xml +nbactions.xml + +# ===== IDE - VS CODE ===== +.vscode/ +*.code-workspace + +# ===== OS SPECIFIC ===== +# Mac +.DS_Store + +# Windows +Thumbs.db +ehthumbs.db +Desktop.ini +$RECYCLE.BIN/ + +# Linux +*~ + +# ===== LOGS ===== +*.log +*.log.* +logs/ +log/ + +# ===== TEMPORARY FILES ===== +*.tmp +*.temp +*.bak +*.backup +*.old +*.swp +*.swo +*.orig +*.rej +*~ + +# ===== ENVIRONMENT & CONFIGURATION ===== +.env +.env.local +.env.* +*.local +application-local.properties + +# ===== SECURITY - KEYS & CERTIFICATES ===== +*.key +*.pem +*.crt +*.p12 +*.jks +*.keystore +.certs/ +.certificates/ + +# ===== TEST COVERAGE ===== +.jacoco/ +jacoco.exec +coverage/ +.nyc_output/ + +# ===== GENERATED SOURCES ===== +src/gen/ +generated-sources/ +generated-test-sources/ + +# ===== BUILD ARTIFACTS ===== +dist/ +build/ +out/ + +# ===== NODE (if used for build tools) ===== +node_modules/ +npm-debug.log* +yarn-debug.log* +yarn-error.log* +pnpm-debug.log* +lerna-debug.log* + +# ===== DOCKER ===== +.dockerignore + +# ===== MAVEN WRAPPER (if not using project wrapper) ===== +# Uncomment if you don't want to commit Maven wrapper +# .mvn/ +# mvnw +# mvnw.cmd + diff --git a/CLASSES_SANS_TESTS.md b/CLASSES_SANS_TESTS.md index 860d606..c31b078 100644 --- a/CLASSES_SANS_TESTS.md +++ b/CLASSES_SANS_TESTS.md @@ -1,276 +1,276 @@ -# Classes sans Tests - UnionFlow Server API - -**Date d'analyse**: 2026-03-15 -**Couverture globale**: 72% (4635 instructions manquées sur 16697) -**Classes sans tests**: 91 classes (0% de couverture) - ---- - -## 1. DTOs REQUEST (dev.lions.unionflow.server.api.dto) - -### 1.1 Solidarité (8 classes - 0%) -- `dev.lions.unionflow.server.api.dto.solidarite.request.CreateCommentaireAideRequest` -- `dev.lions.unionflow.server.api.dto.solidarite.request.CreateDemandeAideRequest` -- `dev.lions.unionflow.server.api.dto.solidarite.request.CreateEvaluationAideRequest` -- `dev.lions.unionflow.server.api.dto.solidarite.request.CreatePropositionAideRequest` -- `dev.lions.unionflow.server.api.dto.solidarite.request.UpdateCommentaireAideRequest` -- `dev.lions.unionflow.server.api.dto.solidarite.request.UpdateDemandeAideRequest` -- `dev.lions.unionflow.server.api.dto.solidarite.request.UpdateEvaluationAideRequest` -- `dev.lions.unionflow.server.api.dto.solidarite.request.UpdatePropositionAideRequest` - -### 1.2 Comptabilité (8 classes - 0%) -- `dev.lions.unionflow.server.api.dto.comptabilite.request.CreateCompteComptableRequest` -- `dev.lions.unionflow.server.api.dto.comptabilite.request.CreateEcritureComptableRequest` -- `dev.lions.unionflow.server.api.dto.comptabilite.request.CreateJournalComptableRequest` -- `dev.lions.unionflow.server.api.dto.comptabilite.request.CreateLigneEcritureRequest` -- `dev.lions.unionflow.server.api.dto.comptabilite.request.UpdateCompteComptableRequest` -- `dev.lions.unionflow.server.api.dto.comptabilite.request.UpdateEcritureComptableRequest` -- `dev.lions.unionflow.server.api.dto.comptabilite.request.UpdateJournalComptableRequest` -- `dev.lions.unionflow.server.api.dto.comptabilite.request.UpdateLigneEcritureRequest` - -### 1.3 Paiement (4 classes - 0%) -- `dev.lions.unionflow.server.api.dto.paiement.request.CreatePaiementRequest` -- `dev.lions.unionflow.server.api.dto.paiement.request.DeclarerPaiementManuelRequest` -- `dev.lions.unionflow.server.api.dto.paiement.request.InitierDepotEpargneRequest` -- `dev.lions.unionflow.server.api.dto.paiement.request.InitierPaiementEnLigneRequest` - -### 1.4 Notification (4 classes - 0%) -- `dev.lions.unionflow.server.api.dto.notification.request.CreateNotificationRequest` -- `dev.lions.unionflow.server.api.dto.notification.request.CreateTemplateNotificationRequest` -- `dev.lions.unionflow.server.api.dto.notification.request.UpdateNotificationRequest` -- `dev.lions.unionflow.server.api.dto.notification.request.UpdateTemplateNotificationRequest` - -### 1.5 Document (4 classes - 0%) -- `dev.lions.unionflow.server.api.dto.document.request.CreateDocumentRequest` -- `dev.lions.unionflow.server.api.dto.document.request.CreatePieceJointeRequest` -- `dev.lions.unionflow.server.api.dto.document.request.UpdateDocumentRequest` -- `dev.lions.unionflow.server.api.dto.document.request.UpdatePieceJointeRequest` - -### 1.6 Abonnement (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.abonnement.request.CreateAbonnementRequest` -- `dev.lions.unionflow.server.api.dto.abonnement.request.UpdateAbonnementRequest` - -### 1.7 Événement (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.evenement.request.CreateEvenementRequest` -- `dev.lions.unionflow.server.api.dto.evenement.request.UpdateEvenementRequest` - -### 1.8 Formule Abonnement (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.formuleabonnement.request.CreateFormuleAbonnementRequest` -- `dev.lions.unionflow.server.api.dto.formuleabonnement.request.UpdateFormuleAbonnementRequest` - -### 1.9 Organisation (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.organisation.request.CreateOrganisationRequest` -- `dev.lions.unionflow.server.api.dto.organisation.request.UpdateOrganisationRequest` - -### 1.10 Adresse (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.adresse.request.CreateAdresseRequest` -- `dev.lions.unionflow.server.api.dto.adresse.request.UpdateAdresseRequest` - -### 1.11 Membre (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.membre.request.CreateMembreRequest` -- `dev.lions.unionflow.server.api.dto.membre.request.UpdateMembreRequest` - -### 1.12 Cotisation (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.cotisation.request.CreateCotisationRequest` -- `dev.lions.unionflow.server.api.dto.cotisation.request.UpdateCotisationRequest` - -### 1.13 Référence (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.reference.request.CreateTypeReferenceRequest` -- `dev.lions.unionflow.server.api.dto.reference.request.UpdateTypeReferenceRequest` - -### 1.14 Suggestion (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.suggestion.request.CreateSuggestionRequest` -- `dev.lions.unionflow.server.api.dto.suggestion.request.UpdateSuggestionRequest` - -### 1.15 Finance (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.finance.request.CreateAdhesionRequest` -- `dev.lions.unionflow.server.api.dto.finance.request.UpdateAdhesionRequest` - -### 1.16 User (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.user.request.CreateUserRequest` -- `dev.lions.unionflow.server.api.dto.user.request.UpdateUserRequest` - -### 1.17 Configuration (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.config.request.CreateConfigurationRequest` -- `dev.lions.unionflow.server.api.dto.config.request.UpdateConfigurationRequest` - -### 1.18 Ticket (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.ticket.request.CreateTicketRequest` -- `dev.lions.unionflow.server.api.dto.ticket.request.UpdateTicketRequest` - -### 1.19 Rôle (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.role.request.CreateRoleRequest` -- `dev.lions.unionflow.server.api.dto.role.request.UpdateRoleRequest` - -### 1.20 Admin (1 classe - 0%) -- `dev.lions.unionflow.server.api.dto.admin.request.CreateAdminRequest` - -### 1.21 Favoris (1 classe - 0%) -- `dev.lions.unionflow.server.api.dto.favoris.request.CreateFavoriRequest` - ---- - -## 2. DTOs RESPONSE (dev.lions.unionflow.server.api.dto) - -### 2.1 Paiement (1 classe - 0%) -- `dev.lions.unionflow.server.api.dto.paiement.response.PaiementGatewayResponse` - -### 2.2 Cotisation (1 classe - 0%) -- `dev.lions.unionflow.server.api.dto.cotisation.response.CotisationSummaryResponse` - -### 2.3 Adresse (1 classe - 0%) -- `dev.lions.unionflow.server.api.dto.adresse.response.AdresseResponse` - -### 2.4 Admin (1 classe - 0%) -- `dev.lions.unionflow.server.api.dto.admin.response.AdminResponse` - ---- - -## 3. AUTRES DTOs - -### 3.1 Wave (2 classes - 0%) -- `dev.lions.unionflow.server.api.dto.wave.CompteWaveDTO` -- `dev.lions.unionflow.server.api.dto.wave.TransactionWaveDTO` - ---- - -## 4. ENUMS (dev.lions.unionflow.server.api.enums) - -### 4.1 Mutuelle - Crédit (4 classes - 0%) -- `dev.lions.unionflow.server.api.enums.mutuelle.credit.StatutDemandeCredit` -- `dev.lions.unionflow.server.api.enums.mutuelle.credit.StatutEcheanceCredit` -- `dev.lions.unionflow.server.api.enums.mutuelle.credit.TypeCredit` -- `dev.lions.unionflow.server.api.enums.mutuelle.credit.TypeGarantie` - -### 4.2 Mutuelle - Épargne (3 classes - 0%) -- `dev.lions.unionflow.server.api.enums.mutuelle.epargne.StatutCompteEpargne` -- `dev.lions.unionflow.server.api.enums.mutuelle.epargne.TypeCompteEpargne` -- `dev.lions.unionflow.server.api.enums.mutuelle.epargne.TypeTransactionEpargne` - -### 4.3 Vote (3 classes - 0%) -- `dev.lions.unionflow.server.api.enums.vote.ModeScrutin` -- `dev.lions.unionflow.server.api.enums.vote.StatutVote` -- `dev.lions.unionflow.server.api.enums.vote.TypeVote` - -### 4.4 Tontine (3 classes - 0%) -- `dev.lions.unionflow.server.api.enums.tontine.FrequenceTour` -- `dev.lions.unionflow.server.api.enums.tontine.StatutTontine` -- `dev.lions.unionflow.server.api.enums.tontine.TypeTontine` - -### 4.5 Ayant Droit (2 classes - 0%) -- `dev.lions.unionflow.server.api.enums.ayantdroit.StatutAyantDroit` -- `dev.lions.unionflow.server.api.enums.ayantdroit.TypeAyantDroit` - -### 4.6 Agricole (1 classe - 0%) -- `dev.lions.unionflow.server.api.enums.agricole.StatutCampagneAgricole` - -### 4.7 Collecte de Fonds (1 classe - 0%) -- `dev.lions.unionflow.server.api.enums.collectefonds.StatutCampagneCollecte` - -### 4.8 Culte (1 classe - 0%) -- `dev.lions.unionflow.server.api.enums.culte.TypeDonReligieux` - -### 4.9 ONG (1 classe - 0%) -- `dev.lions.unionflow.server.api.enums.ong.StatutProjetOng` - -### 4.10 Gouvernance (1 classe - 0%) -- `dev.lions.unionflow.server.api.enums.gouvernance.NiveauEchelon` - -### 4.11 Registre (1 classe - 0%) -- `dev.lions.unionflow.server.api.enums.registre.StatutAgrement` - ---- - -## RÉCAPITULATIF PAR CATÉGORIE - -| Catégorie | Nombre de classes | % du total | -|-----------|-------------------|------------| -| **DTO Requests** | **62 classes** | **68%** | -| **Enums** | **21 classes** | **23%** | -| **DTO Responses** | **4 classes** | **4%** | -| **Autres DTOs** | **2 classes** | **2%** | -| **Autres** | **2 classes** | **2%** | -| **TOTAL** | **91 classes** | **100%** | - ---- - -## PRIORITÉS DE TEST - -### P0 - Haute Priorité (Core Business) -1. **Solidarité** (8 requests) - Module métier principal -2. **Comptabilité** (8 requests) - Gestion financière critique -3. **Paiement** (4 requests + 1 response) - Transactions financières -4. **Mutuelle Crédit** (4 enums) - Microfinance core -5. **Mutuelle Épargne** (3 enums) - Microfinance core - -### P1 - Priorité Moyenne (Features importantes) -6. **Notification** (4 requests) - Communication système -7. **Document** (4 requests) - Gestion documentaire -8. **Événement** (2 requests) - Gestion événementielle -9. **Organisation** (2 requests) - Structure organisationnelle -10. **Membre** (2 requests) - Gestion des utilisateurs - -### P2 - Priorité Basse (Features secondaires) -11. **Abonnement** (2 requests) - Gestion des abonnements -12. **Tontine** (3 enums) - Feature spécifique -13. **Vote** (3 enums) - Feature spécifique -14. **Autres requests** (20 requests restants) -15. **Enums divers** (11 enums restants) - ---- - -## PLAN D'ACTION - -### Étape 1: Tests DTOs Request (62 classes) -- Tester getters/setters -- Tester validations Jakarta Bean Validation -- Tester méthodes equals/hashCode/toString si présentes - -### Étape 2: Tests DTOs Response (4 classes) -- Tester constructeurs et builders -- Tester sérialisation JSON - -### Étape 3: Tests Enums (21 classes) -- Tester valueOf() et values() -- Tester getters de valeurs -- Tester méthodes utilitaires (fromString, etc.) - -### Étape 4: Tests Autres (4 classes) -- Tests spécifiques selon le type de classe - ---- - -## TEMPLATES DE TEST RECOMMANDÉS - -### Pour DTOs Request: -```java -@Test -void testCreateXxxRequest_AllFields() { - var request = new CreateXxxRequest(); - // Set all fields - // Assert all fields -} - -@Test -void testCreateXxxRequest_Validation() { - var request = new CreateXxxRequest(); - // Test @NotNull, @Size, etc. -} -``` - -### Pour Enums: -```java -@Test -void testEnumValues() { - assertEquals(3, TypeXxx.values().length); -} - -@Test -void testEnumValueOf() { - assertEquals(TypeXxx.VALUE1, TypeXxx.valueOf("VALUE1")); -} -``` - ---- - -**Objectif**: Atteindre **100% de couverture** sur le module unionflow-server-api. +# Classes sans Tests - UnionFlow Server API + +**Date d'analyse**: 2026-03-15 +**Couverture globale**: 72% (4635 instructions manquées sur 16697) +**Classes sans tests**: 91 classes (0% de couverture) + +--- + +## 1. DTOs REQUEST (dev.lions.unionflow.server.api.dto) + +### 1.1 Solidarité (8 classes - 0%) +- `dev.lions.unionflow.server.api.dto.solidarite.request.CreateCommentaireAideRequest` +- `dev.lions.unionflow.server.api.dto.solidarite.request.CreateDemandeAideRequest` +- `dev.lions.unionflow.server.api.dto.solidarite.request.CreateEvaluationAideRequest` +- `dev.lions.unionflow.server.api.dto.solidarite.request.CreatePropositionAideRequest` +- `dev.lions.unionflow.server.api.dto.solidarite.request.UpdateCommentaireAideRequest` +- `dev.lions.unionflow.server.api.dto.solidarite.request.UpdateDemandeAideRequest` +- `dev.lions.unionflow.server.api.dto.solidarite.request.UpdateEvaluationAideRequest` +- `dev.lions.unionflow.server.api.dto.solidarite.request.UpdatePropositionAideRequest` + +### 1.2 Comptabilité (8 classes - 0%) +- `dev.lions.unionflow.server.api.dto.comptabilite.request.CreateCompteComptableRequest` +- `dev.lions.unionflow.server.api.dto.comptabilite.request.CreateEcritureComptableRequest` +- `dev.lions.unionflow.server.api.dto.comptabilite.request.CreateJournalComptableRequest` +- `dev.lions.unionflow.server.api.dto.comptabilite.request.CreateLigneEcritureRequest` +- `dev.lions.unionflow.server.api.dto.comptabilite.request.UpdateCompteComptableRequest` +- `dev.lions.unionflow.server.api.dto.comptabilite.request.UpdateEcritureComptableRequest` +- `dev.lions.unionflow.server.api.dto.comptabilite.request.UpdateJournalComptableRequest` +- `dev.lions.unionflow.server.api.dto.comptabilite.request.UpdateLigneEcritureRequest` + +### 1.3 Paiement (4 classes - 0%) +- `dev.lions.unionflow.server.api.dto.paiement.request.CreatePaiementRequest` +- `dev.lions.unionflow.server.api.dto.paiement.request.DeclarerPaiementManuelRequest` +- `dev.lions.unionflow.server.api.dto.paiement.request.InitierDepotEpargneRequest` +- `dev.lions.unionflow.server.api.dto.paiement.request.InitierPaiementEnLigneRequest` + +### 1.4 Notification (4 classes - 0%) +- `dev.lions.unionflow.server.api.dto.notification.request.CreateNotificationRequest` +- `dev.lions.unionflow.server.api.dto.notification.request.CreateTemplateNotificationRequest` +- `dev.lions.unionflow.server.api.dto.notification.request.UpdateNotificationRequest` +- `dev.lions.unionflow.server.api.dto.notification.request.UpdateTemplateNotificationRequest` + +### 1.5 Document (4 classes - 0%) +- `dev.lions.unionflow.server.api.dto.document.request.CreateDocumentRequest` +- `dev.lions.unionflow.server.api.dto.document.request.CreatePieceJointeRequest` +- `dev.lions.unionflow.server.api.dto.document.request.UpdateDocumentRequest` +- `dev.lions.unionflow.server.api.dto.document.request.UpdatePieceJointeRequest` + +### 1.6 Abonnement (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.abonnement.request.CreateAbonnementRequest` +- `dev.lions.unionflow.server.api.dto.abonnement.request.UpdateAbonnementRequest` + +### 1.7 Événement (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.evenement.request.CreateEvenementRequest` +- `dev.lions.unionflow.server.api.dto.evenement.request.UpdateEvenementRequest` + +### 1.8 Formule Abonnement (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.formuleabonnement.request.CreateFormuleAbonnementRequest` +- `dev.lions.unionflow.server.api.dto.formuleabonnement.request.UpdateFormuleAbonnementRequest` + +### 1.9 Organisation (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.organisation.request.CreateOrganisationRequest` +- `dev.lions.unionflow.server.api.dto.organisation.request.UpdateOrganisationRequest` + +### 1.10 Adresse (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.adresse.request.CreateAdresseRequest` +- `dev.lions.unionflow.server.api.dto.adresse.request.UpdateAdresseRequest` + +### 1.11 Membre (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.membre.request.CreateMembreRequest` +- `dev.lions.unionflow.server.api.dto.membre.request.UpdateMembreRequest` + +### 1.12 Cotisation (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.cotisation.request.CreateCotisationRequest` +- `dev.lions.unionflow.server.api.dto.cotisation.request.UpdateCotisationRequest` + +### 1.13 Référence (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.reference.request.CreateTypeReferenceRequest` +- `dev.lions.unionflow.server.api.dto.reference.request.UpdateTypeReferenceRequest` + +### 1.14 Suggestion (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.suggestion.request.CreateSuggestionRequest` +- `dev.lions.unionflow.server.api.dto.suggestion.request.UpdateSuggestionRequest` + +### 1.15 Finance (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.finance.request.CreateAdhesionRequest` +- `dev.lions.unionflow.server.api.dto.finance.request.UpdateAdhesionRequest` + +### 1.16 User (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.user.request.CreateUserRequest` +- `dev.lions.unionflow.server.api.dto.user.request.UpdateUserRequest` + +### 1.17 Configuration (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.config.request.CreateConfigurationRequest` +- `dev.lions.unionflow.server.api.dto.config.request.UpdateConfigurationRequest` + +### 1.18 Ticket (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.ticket.request.CreateTicketRequest` +- `dev.lions.unionflow.server.api.dto.ticket.request.UpdateTicketRequest` + +### 1.19 Rôle (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.role.request.CreateRoleRequest` +- `dev.lions.unionflow.server.api.dto.role.request.UpdateRoleRequest` + +### 1.20 Admin (1 classe - 0%) +- `dev.lions.unionflow.server.api.dto.admin.request.CreateAdminRequest` + +### 1.21 Favoris (1 classe - 0%) +- `dev.lions.unionflow.server.api.dto.favoris.request.CreateFavoriRequest` + +--- + +## 2. DTOs RESPONSE (dev.lions.unionflow.server.api.dto) + +### 2.1 Paiement (1 classe - 0%) +- `dev.lions.unionflow.server.api.dto.paiement.response.PaiementGatewayResponse` + +### 2.2 Cotisation (1 classe - 0%) +- `dev.lions.unionflow.server.api.dto.cotisation.response.CotisationSummaryResponse` + +### 2.3 Adresse (1 classe - 0%) +- `dev.lions.unionflow.server.api.dto.adresse.response.AdresseResponse` + +### 2.4 Admin (1 classe - 0%) +- `dev.lions.unionflow.server.api.dto.admin.response.AdminResponse` + +--- + +## 3. AUTRES DTOs + +### 3.1 Wave (2 classes - 0%) +- `dev.lions.unionflow.server.api.dto.wave.CompteWaveDTO` +- `dev.lions.unionflow.server.api.dto.wave.TransactionWaveDTO` + +--- + +## 4. ENUMS (dev.lions.unionflow.server.api.enums) + +### 4.1 Mutuelle - Crédit (4 classes - 0%) +- `dev.lions.unionflow.server.api.enums.mutuelle.credit.StatutDemandeCredit` +- `dev.lions.unionflow.server.api.enums.mutuelle.credit.StatutEcheanceCredit` +- `dev.lions.unionflow.server.api.enums.mutuelle.credit.TypeCredit` +- `dev.lions.unionflow.server.api.enums.mutuelle.credit.TypeGarantie` + +### 4.2 Mutuelle - Épargne (3 classes - 0%) +- `dev.lions.unionflow.server.api.enums.mutuelle.epargne.StatutCompteEpargne` +- `dev.lions.unionflow.server.api.enums.mutuelle.epargne.TypeCompteEpargne` +- `dev.lions.unionflow.server.api.enums.mutuelle.epargne.TypeTransactionEpargne` + +### 4.3 Vote (3 classes - 0%) +- `dev.lions.unionflow.server.api.enums.vote.ModeScrutin` +- `dev.lions.unionflow.server.api.enums.vote.StatutVote` +- `dev.lions.unionflow.server.api.enums.vote.TypeVote` + +### 4.4 Tontine (3 classes - 0%) +- `dev.lions.unionflow.server.api.enums.tontine.FrequenceTour` +- `dev.lions.unionflow.server.api.enums.tontine.StatutTontine` +- `dev.lions.unionflow.server.api.enums.tontine.TypeTontine` + +### 4.5 Ayant Droit (2 classes - 0%) +- `dev.lions.unionflow.server.api.enums.ayantdroit.StatutAyantDroit` +- `dev.lions.unionflow.server.api.enums.ayantdroit.TypeAyantDroit` + +### 4.6 Agricole (1 classe - 0%) +- `dev.lions.unionflow.server.api.enums.agricole.StatutCampagneAgricole` + +### 4.7 Collecte de Fonds (1 classe - 0%) +- `dev.lions.unionflow.server.api.enums.collectefonds.StatutCampagneCollecte` + +### 4.8 Culte (1 classe - 0%) +- `dev.lions.unionflow.server.api.enums.culte.TypeDonReligieux` + +### 4.9 ONG (1 classe - 0%) +- `dev.lions.unionflow.server.api.enums.ong.StatutProjetOng` + +### 4.10 Gouvernance (1 classe - 0%) +- `dev.lions.unionflow.server.api.enums.gouvernance.NiveauEchelon` + +### 4.11 Registre (1 classe - 0%) +- `dev.lions.unionflow.server.api.enums.registre.StatutAgrement` + +--- + +## RÉCAPITULATIF PAR CATÉGORIE + +| Catégorie | Nombre de classes | % du total | +|-----------|-------------------|------------| +| **DTO Requests** | **62 classes** | **68%** | +| **Enums** | **21 classes** | **23%** | +| **DTO Responses** | **4 classes** | **4%** | +| **Autres DTOs** | **2 classes** | **2%** | +| **Autres** | **2 classes** | **2%** | +| **TOTAL** | **91 classes** | **100%** | + +--- + +## PRIORITÉS DE TEST + +### P0 - Haute Priorité (Core Business) +1. **Solidarité** (8 requests) - Module métier principal +2. **Comptabilité** (8 requests) - Gestion financière critique +3. **Paiement** (4 requests + 1 response) - Transactions financières +4. **Mutuelle Crédit** (4 enums) - Microfinance core +5. **Mutuelle Épargne** (3 enums) - Microfinance core + +### P1 - Priorité Moyenne (Features importantes) +6. **Notification** (4 requests) - Communication système +7. **Document** (4 requests) - Gestion documentaire +8. **Événement** (2 requests) - Gestion événementielle +9. **Organisation** (2 requests) - Structure organisationnelle +10. **Membre** (2 requests) - Gestion des utilisateurs + +### P2 - Priorité Basse (Features secondaires) +11. **Abonnement** (2 requests) - Gestion des abonnements +12. **Tontine** (3 enums) - Feature spécifique +13. **Vote** (3 enums) - Feature spécifique +14. **Autres requests** (20 requests restants) +15. **Enums divers** (11 enums restants) + +--- + +## PLAN D'ACTION + +### Étape 1: Tests DTOs Request (62 classes) +- Tester getters/setters +- Tester validations Jakarta Bean Validation +- Tester méthodes equals/hashCode/toString si présentes + +### Étape 2: Tests DTOs Response (4 classes) +- Tester constructeurs et builders +- Tester sérialisation JSON + +### Étape 3: Tests Enums (21 classes) +- Tester valueOf() et values() +- Tester getters de valeurs +- Tester méthodes utilitaires (fromString, etc.) + +### Étape 4: Tests Autres (4 classes) +- Tests spécifiques selon le type de classe + +--- + +## TEMPLATES DE TEST RECOMMANDÉS + +### Pour DTOs Request: +```java +@Test +void testCreateXxxRequest_AllFields() { + var request = new CreateXxxRequest(); + // Set all fields + // Assert all fields +} + +@Test +void testCreateXxxRequest_Validation() { + var request = new CreateXxxRequest(); + // Test @NotNull, @Size, etc. +} +``` + +### Pour Enums: +```java +@Test +void testEnumValues() { + assertEquals(3, TypeXxx.values().length); +} + +@Test +void testEnumValueOf() { + assertEquals(TypeXxx.VALUE1, TypeXxx.valueOf("VALUE1")); +} +``` + +--- + +**Objectif**: Atteindre **100% de couverture** sur le module unionflow-server-api. diff --git a/README.md b/README.md index 3a70c40..5a6cb8c 100644 --- a/README.md +++ b/README.md @@ -1,548 +1,548 @@ -# UnionFlow Server API - DTOs et Contrats - -![Java](https://img.shields.io/badge/Java-17-blue) -![Maven](https://img.shields.io/badge/Maven-Central-green) -![License](https://img.shields.io/badge/License-Proprietary-red) - -Module API partagé UnionFlow - DTOs, Request/Response, Validation, Enums. - ---- - -## 📋 Vue d'ensemble - -Ce module contient les **contrats d'API** partagés entre : -- **Backend Quarkus** (unionflow-server-impl-quarkus) -- **Frontend Web** (unionflow-client-quarkus-primefaces-freya) -- **Mobile Flutter** (unionflow-mobile-apps) - via génération TypeScript/JSON - -### Avantages - -✅ **Type-safety** : Contrats Java typés -✅ **Validation centralisée** : Contraintes Jakarta Bean Validation -✅ **DRY** : Zéro duplication entre projets -✅ **Versioning** : Maven semantic versioning -✅ **Documentation** : Javadoc complète - ---- - -## 🏗️ Structure - -``` -src/main/java/dev/lions/unionflow/server/api/ -├── dto/ # Data Transfer Objects -│ ├── base/ # DTOs de base -│ │ ├── BaseRequest.java -│ │ └── BaseResponse.java -│ ├── dashboard/ # Dashboard -│ │ ├── DashboardStatsResponse.java -│ │ ├── MembreDashboardSyntheseResponse.java -│ │ └── UpcomingEventResponse.java -│ ├── membre/ # Membres -│ │ ├── request/ -│ │ │ └── CreateMembreRequest.java -│ │ └── response/ -│ │ ├── MembreResponse.java -│ └── MembreSummaryResponse.java -│ ├── finance/ # Finance Workflow -│ │ ├── request/ -│ │ │ ├── ApproveTransactionRequest.java -│ │ │ └── RejectTransactionRequest.java -│ │ └── response/ -│ │ ├── AdhesionResponse.java -│ │ ├── TransactionApprovalResponse.java -│ │ └── BudgetResponse.java -│ ├── cotisation/ # Cotisations -│ ├── evenement/ # Événements -│ ├── solidarite/ # Demandes d'aide -│ └── notification/ # Notifications -├── enums/ # Énumérations -│ ├── membre/ -│ │ ├── StatutMembre.java -│ │ └── TypeMembre.java -│ ├── finance/ -│ │ ├── StatutApprobation.java -│ │ ├── TypeTransaction.java -│ │ └── BudgetPeriod.java -│ ├── paiement/ -│ │ ├── StatutPaiement.java -│ │ └── ModePaiement.java -│ └── notification/ -│ └── TypeNotification.java -├── validation/ # Validateurs custom -│ ├── annotations/ # Annotations validation -│ │ ├── @ValidEmail -│ │ ├── @ValidPhoneNumber -│ │ └── @ValidAmount -│ ├── validators/ # Implémentations -│ │ ├── EmailValidator.java -│ │ └── AmountValidator.java -│ └── ValidationConstants.java # Constantes (regex, limites) -└── exception/ # Exceptions API - ├── ApiException.java - ├── ValidationException.java - └── ErrorResponse.java -``` - ---- - -## 📦 Installation - -### Maven Dependency - -Ajouter à votre `pom.xml` : - -```xml - - dev.lions.unionflow - unionflow-server-api - 2.0.0 - -``` - -### Repository Gitea (Maven Registry) - -Configurer `~/.m2/settings.xml` : - -```xml - - - - gitea-lionsdev - ${env.GITEA_USERNAME} - ${env.GITEA_TOKEN} - - - - - - gitea-lionsdev - https://git.lions.dev/api/packages/lionsdev/maven - - - -``` - -### Variables d'environnement - -```bash -export GITEA_USERNAME=lionsdev -export GITEA_TOKEN=your-gitea-token -``` - ---- - -## 🎯 Utilisation - -### 1. DTOs Request/Response - -#### Exemple : Créer un membre - -**Request DTO** : - -```java -@Data -@NoArgsConstructor -@AllArgsConstructor -public class CreateMembreRequest { - - @NotBlank(message = "Le nom est requis") - @Size(min = 2, max = 100) - private String nom; - - @NotBlank(message = "Le prénom est requis") - @Size(min = 2, max = 100) - private String prenom; - - @ValidEmail - private String email; - - @ValidPhoneNumber - private String telephone; - - @NotNull - private UUID organisationId; - - private TypeMembre typeMembre = TypeMembre.MEMBRE; -} -``` - -**Response DTO** : - -```java -@Data -@NoArgsConstructor -@AllArgsConstructor -public class MembreResponse extends BaseResponse { - - private UUID id; - private String nom; - private String prenom; - private String email; - private String telephone; - private StatutMembre statut; - private TypeMembre type; - private String numeroMembre; - private LocalDate dateAdhesion; - private UUID organisationId; - private String organisationNom; -} -``` - -**Usage Backend** : - -```java -@POST -@Path("/membres") -@Consumes(MediaType.APPLICATION_JSON) -@Produces(MediaType.APPLICATION_JSON) -public Response createMembre(@Valid CreateMembreRequest request) { - MembreResponse response = membreService.create(request); - return Response.status(201).entity(response).build(); -} -``` - -**Usage Frontend (REST Client)** : - -```java -@Path("/api/v1/membres") -@RegisterRestClient(configKey = "unionflow-backend") -public interface MembreRestClient { - - @POST - @Consumes(MediaType.APPLICATION_JSON) - @Produces(MediaType.APPLICATION_JSON) - MembreResponse createMembre(@Valid CreateMembreRequest request); -} -``` - -### 2. Validation - -#### Annotations standard (Jakarta Bean Validation) - -```java -@NotNull // Non null -@NotBlank // Non vide (String) -@Size(min, max) // Taille min/max -@Min(value) // Valeur minimale (nombres) -@Max(value) // Valeur maximale (nombres) -@Email // Format email -@Pattern(regex) // Regex custom -@Positive // > 0 -@PositiveOrZero // >= 0 -``` - -#### Annotations custom UnionFlow - -```java -@ValidEmail // Email avec domaines autorisés -@ValidPhoneNumber // Téléphone international (+225, +33, etc.) -@ValidAmount // Montant positif, max 2 décimales -@ValidNumeroMembre // Format: ORG-YYYY-NNNN -@ValidPeriodeCotisation // Format: YYYY-MM -``` - -**Exemple d'utilisation** : - -```java -public class PaiementRequest { - - @ValidAmount(min = 100.0, max = 10_000_000.0) - private BigDecimal montant; - - @ValidPhoneNumber - private String telephonePaiement; - - @NotNull - @Pattern(regexp = "^\\d{4}-\\d{2}$") - private String periode; // Ex: "2026-03" -} -``` - -#### Validators custom - Implémentation - -**Annotation** : - -```java -@Target({ElementType.FIELD, ElementType.PARAMETER}) -@Retention(RetentionPolicy.RUNTIME) -@Constraint(validatedBy = AmountValidator.class) -public @interface ValidAmount { - String message() default "Montant invalide"; - double min() default 0.0; - double max() default Double.MAX_VALUE; - Class[] groups() default {}; - Class[] payload() default {}; -} -``` - -**Validator** : - -```java -public class AmountValidator implements ConstraintValidator { - - private double min; - private double max; - - @Override - public void initialize(ValidAmount annotation) { - this.min = annotation.min(); - this.max = annotation.max(); - } - - @Override - public boolean isValid(BigDecimal value, ConstraintValidatorContext context) { - if (value == null) return true; // Use @NotNull separately - - double amount = value.doubleValue(); - - // Check positive - if (amount <= 0) { - context.disableDefaultConstraintViolation(); - context.buildConstraintViolationWithTemplate("Le montant doit être positif") - .addConstraintViolation(); - return false; - } - - // Check range - if (amount < min || amount > max) { - context.disableDefaultConstraintViolation(); - context.buildConstraintViolationWithTemplate( - String.format("Le montant doit être entre %.2f et %.2f", min, max) - ).addConstraintViolation(); - return false; - } - - // Check max 2 decimals - if (value.scale() > 2) { - context.disableDefaultConstraintViolation(); - context.buildConstraintViolationWithTemplate("Maximum 2 décimales autorisées") - .addConstraintViolation(); - return false; - } - - return true; - } -} -``` - -### 3. Enums - -#### Exemple : StatutApprobation - -```java -public enum StatutApprobation { - PENDING("En attente"), - APPROVED("Approuvée"), - REJECTED("Rejetée"), - CANCELLED("Annulée"); - - private final String libelle; - - StatutApprobation(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } - - public static StatutApprobation fromString(String str) { - return Arrays.stream(values()) - .filter(s -> s.name().equalsIgnoreCase(str)) - .findFirst() - .orElseThrow(() -> new IllegalArgumentException("Statut invalide: " + str)); - } -} -``` - -**Usage** : - -```java -StatutApprobation statut = StatutApprobation.APPROVED; -System.out.println(statut.getLibelle()); // "Approuvée" - -StatutApprobation parsed = StatutApprobation.fromString("PENDING"); -``` - -### 4. BaseResponse - Héritage commun - -Tous les Response DTOs étendent `BaseResponse` : - -```java -@Data -@NoArgsConstructor -public abstract class BaseResponse implements Serializable { - - private static final long serialVersionUID = 1L; - - // Audit fields (si nécessaire côté client) - private LocalDateTime dateCreation; - private LocalDateTime dateModification; - private Boolean actif; -} -``` - -**Avantages** : -- Champs audit automatiques -- Serializable pour cache/sessions -- Type-safe avec génériques - ---- - -## 🧪 Tests - -### Tests de validation - -**Fichier** : `src/test/java/dev/lions/unionflow/server/api/validation/AmountValidatorTest.java` - -```java -@Test -void shouldRejectNegativeAmount() { - CreatePaiementRequest request = new CreatePaiementRequest(); - request.setMontant(BigDecimal.valueOf(-100)); - - Set> violations = validator.validate(request); - - assertFalse(violations.isEmpty()); - assertTrue(violations.stream() - .anyMatch(v -> v.getMessage().contains("positif"))); -} - -@Test -void shouldRejectTooManyDecimals() { - CreatePaiementRequest request = new CreatePaiementRequest(); - request.setMontant(BigDecimal.valueOf(100.123)); - - Set> violations = validator.validate(request); - - assertFalse(violations.isEmpty()); - assertTrue(violations.stream() - .anyMatch(v -> v.getMessage().contains("2 décimales"))); -} -``` - -### Lancer les tests - -```bash -mvn test -``` - ---- - -## 📊 DTOs par Feature - -### Dashboard - -- `DashboardStatsResponse` - Stats organisation (membres, cotisations, events) -- `MembreDashboardSyntheseResponse` - Synthèse membre (solde, cotisations) -- `UpcomingEventResponse` - Événements à venir - -### Finance Workflow - -- `TransactionApprovalResponse` - Approbation de transaction -- `BudgetResponse` - Budget avec lignes budgétaires -- `AdhesionResponse` - Adhésion membre - -### Membres - -- `MembreResponse` - Détails membre complets -- `MembreSummaryResponse` - Résumé membre (liste) -- `CreateMembreRequest` - Création membre -- `UpdateMembreRequest` - Modification membre - -### Cotisations - -- `CotisationResponse` - Cotisation avec détails -- `CreateCotisationRequest` - Enregistrement cotisation -- `CotisationStatisticsResponse` - Statistiques cotisations - -### Notifications - -- `NotificationResponse` - Notification utilisateur -- `MarkAsReadRequest` - Marquer comme lue - ---- - -## 🔄 Publication Maven (Développeurs seulement) - -### Publier une nouvelle version - -```bash -# 1. Mettre à jour la version dans pom.xml -2.1.0 - -# 2. Compiler et publier -mvn clean deploy - -# Les artifacts sont publiés sur: -# https://git.lions.dev/api/packages/lionsdev/maven -``` - -### Versioning Semantic - -- **Major** (2.0.0) : Breaking changes -- **Minor** (2.1.0) : Nouvelles features (backward compatible) -- **Patch** (2.0.1) : Bugfixes - ---- - -## 📝 Changelog - -### v2.0.0 (2026-03-14) - -✅ **Nouveau** : -- DTOs Finance Workflow complets -- Validation `@ValidAmount` avec min/max -- Enums `BudgetPeriod`, `BudgetCategory` -- `TransactionApprovalResponse` avec tous les champs - -✅ **Améliorations** : -- BaseResponse avec audit fields -- ValidationConstants centralisées -- Javadoc complète pour tous les DTOs - -### v1.0.0 (2026-01-04) - -- Version initiale -- 20+ DTOs principaux -- 10+ validators custom - ---- - -## 📚 Documentation - -### Javadoc - -```bash -# Générer Javadoc -mvn javadoc:javadoc - -# Ouvrir -open target/site/apidocs/index.html -``` - -### Ressources - -- **Jakarta Bean Validation**: https://jakarta.ee/specifications/bean-validation/ -- **Maven Repository**: https://git.lions.dev/lionsdev/unionflow-server-api - ---- - -## 🤝 Contribution - -1. Créer une branche feature -2. Ajouter DTOs/Validators avec tests -3. Documenter avec Javadoc -4. Pull Request avec description - ---- - -## 📄 Licence - -Propriétaire - © 2026 Lions Club Côte d'Ivoire - ---- - -**Version** : 2.0.0 -**Dernière mise à jour** : 2026-03-14 -**Auteur** : Équipe UnionFlow +# UnionFlow Server API - DTOs et Contrats + +![Java](https://img.shields.io/badge/Java-17-blue) +![Maven](https://img.shields.io/badge/Maven-Central-green) +![License](https://img.shields.io/badge/License-Proprietary-red) + +Module API partagé UnionFlow - DTOs, Request/Response, Validation, Enums. + +--- + +## 📋 Vue d'ensemble + +Ce module contient les **contrats d'API** partagés entre : +- **Backend Quarkus** (unionflow-server-impl-quarkus) +- **Frontend Web** (unionflow-client-quarkus-primefaces-freya) +- **Mobile Flutter** (unionflow-mobile-apps) - via génération TypeScript/JSON + +### Avantages + +✅ **Type-safety** : Contrats Java typés +✅ **Validation centralisée** : Contraintes Jakarta Bean Validation +✅ **DRY** : Zéro duplication entre projets +✅ **Versioning** : Maven semantic versioning +✅ **Documentation** : Javadoc complète + +--- + +## 🏗️ Structure + +``` +src/main/java/dev/lions/unionflow/server/api/ +├── dto/ # Data Transfer Objects +│ ├── base/ # DTOs de base +│ │ ├── BaseRequest.java +│ │ └── BaseResponse.java +│ ├── dashboard/ # Dashboard +│ │ ├── DashboardStatsResponse.java +│ │ ├── MembreDashboardSyntheseResponse.java +│ │ └── UpcomingEventResponse.java +│ ├── membre/ # Membres +│ │ ├── request/ +│ │ │ └── CreateMembreRequest.java +│ │ └── response/ +│ │ ├── MembreResponse.java +│ └── MembreSummaryResponse.java +│ ├── finance/ # Finance Workflow +│ │ ├── request/ +│ │ │ ├── ApproveTransactionRequest.java +│ │ │ └── RejectTransactionRequest.java +│ │ └── response/ +│ │ ├── AdhesionResponse.java +│ │ ├── TransactionApprovalResponse.java +│ │ └── BudgetResponse.java +│ ├── cotisation/ # Cotisations +│ ├── evenement/ # Événements +│ ├── solidarite/ # Demandes d'aide +│ └── notification/ # Notifications +├── enums/ # Énumérations +│ ├── membre/ +│ │ ├── StatutMembre.java +│ │ └── TypeMembre.java +│ ├── finance/ +│ │ ├── StatutApprobation.java +│ │ ├── TypeTransaction.java +│ │ └── BudgetPeriod.java +│ ├── paiement/ +│ │ ├── StatutPaiement.java +│ │ └── ModePaiement.java +│ └── notification/ +│ └── TypeNotification.java +├── validation/ # Validateurs custom +│ ├── annotations/ # Annotations validation +│ │ ├── @ValidEmail +│ │ ├── @ValidPhoneNumber +│ │ └── @ValidAmount +│ ├── validators/ # Implémentations +│ │ ├── EmailValidator.java +│ │ └── AmountValidator.java +│ └── ValidationConstants.java # Constantes (regex, limites) +└── exception/ # Exceptions API + ├── ApiException.java + ├── ValidationException.java + └── ErrorResponse.java +``` + +--- + +## 📦 Installation + +### Maven Dependency + +Ajouter à votre `pom.xml` : + +```xml + + dev.lions.unionflow + unionflow-server-api + 2.0.0 + +``` + +### Repository Gitea (Maven Registry) + +Configurer `~/.m2/settings.xml` : + +```xml + + + + gitea-lionsdev + ${env.GITEA_USERNAME} + ${env.GITEA_TOKEN} + + + + + + gitea-lionsdev + https://git.lions.dev/api/packages/lionsdev/maven + + + +``` + +### Variables d'environnement + +```bash +export GITEA_USERNAME=lionsdev +export GITEA_TOKEN=your-gitea-token +``` + +--- + +## 🎯 Utilisation + +### 1. DTOs Request/Response + +#### Exemple : Créer un membre + +**Request DTO** : + +```java +@Data +@NoArgsConstructor +@AllArgsConstructor +public class CreateMembreRequest { + + @NotBlank(message = "Le nom est requis") + @Size(min = 2, max = 100) + private String nom; + + @NotBlank(message = "Le prénom est requis") + @Size(min = 2, max = 100) + private String prenom; + + @ValidEmail + private String email; + + @ValidPhoneNumber + private String telephone; + + @NotNull + private UUID organisationId; + + private TypeMembre typeMembre = TypeMembre.MEMBRE; +} +``` + +**Response DTO** : + +```java +@Data +@NoArgsConstructor +@AllArgsConstructor +public class MembreResponse extends BaseResponse { + + private UUID id; + private String nom; + private String prenom; + private String email; + private String telephone; + private StatutMembre statut; + private TypeMembre type; + private String numeroMembre; + private LocalDate dateAdhesion; + private UUID organisationId; + private String organisationNom; +} +``` + +**Usage Backend** : + +```java +@POST +@Path("/membres") +@Consumes(MediaType.APPLICATION_JSON) +@Produces(MediaType.APPLICATION_JSON) +public Response createMembre(@Valid CreateMembreRequest request) { + MembreResponse response = membreService.create(request); + return Response.status(201).entity(response).build(); +} +``` + +**Usage Frontend (REST Client)** : + +```java +@Path("/api/v1/membres") +@RegisterRestClient(configKey = "unionflow-backend") +public interface MembreRestClient { + + @POST + @Consumes(MediaType.APPLICATION_JSON) + @Produces(MediaType.APPLICATION_JSON) + MembreResponse createMembre(@Valid CreateMembreRequest request); +} +``` + +### 2. Validation + +#### Annotations standard (Jakarta Bean Validation) + +```java +@NotNull // Non null +@NotBlank // Non vide (String) +@Size(min, max) // Taille min/max +@Min(value) // Valeur minimale (nombres) +@Max(value) // Valeur maximale (nombres) +@Email // Format email +@Pattern(regex) // Regex custom +@Positive // > 0 +@PositiveOrZero // >= 0 +``` + +#### Annotations custom UnionFlow + +```java +@ValidEmail // Email avec domaines autorisés +@ValidPhoneNumber // Téléphone international (+225, +33, etc.) +@ValidAmount // Montant positif, max 2 décimales +@ValidNumeroMembre // Format: ORG-YYYY-NNNN +@ValidPeriodeCotisation // Format: YYYY-MM +``` + +**Exemple d'utilisation** : + +```java +public class PaiementRequest { + + @ValidAmount(min = 100.0, max = 10_000_000.0) + private BigDecimal montant; + + @ValidPhoneNumber + private String telephonePaiement; + + @NotNull + @Pattern(regexp = "^\\d{4}-\\d{2}$") + private String periode; // Ex: "2026-03" +} +``` + +#### Validators custom - Implémentation + +**Annotation** : + +```java +@Target({ElementType.FIELD, ElementType.PARAMETER}) +@Retention(RetentionPolicy.RUNTIME) +@Constraint(validatedBy = AmountValidator.class) +public @interface ValidAmount { + String message() default "Montant invalide"; + double min() default 0.0; + double max() default Double.MAX_VALUE; + Class[] groups() default {}; + Class[] payload() default {}; +} +``` + +**Validator** : + +```java +public class AmountValidator implements ConstraintValidator { + + private double min; + private double max; + + @Override + public void initialize(ValidAmount annotation) { + this.min = annotation.min(); + this.max = annotation.max(); + } + + @Override + public boolean isValid(BigDecimal value, ConstraintValidatorContext context) { + if (value == null) return true; // Use @NotNull separately + + double amount = value.doubleValue(); + + // Check positive + if (amount <= 0) { + context.disableDefaultConstraintViolation(); + context.buildConstraintViolationWithTemplate("Le montant doit être positif") + .addConstraintViolation(); + return false; + } + + // Check range + if (amount < min || amount > max) { + context.disableDefaultConstraintViolation(); + context.buildConstraintViolationWithTemplate( + String.format("Le montant doit être entre %.2f et %.2f", min, max) + ).addConstraintViolation(); + return false; + } + + // Check max 2 decimals + if (value.scale() > 2) { + context.disableDefaultConstraintViolation(); + context.buildConstraintViolationWithTemplate("Maximum 2 décimales autorisées") + .addConstraintViolation(); + return false; + } + + return true; + } +} +``` + +### 3. Enums + +#### Exemple : StatutApprobation + +```java +public enum StatutApprobation { + PENDING("En attente"), + APPROVED("Approuvée"), + REJECTED("Rejetée"), + CANCELLED("Annulée"); + + private final String libelle; + + StatutApprobation(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } + + public static StatutApprobation fromString(String str) { + return Arrays.stream(values()) + .filter(s -> s.name().equalsIgnoreCase(str)) + .findFirst() + .orElseThrow(() -> new IllegalArgumentException("Statut invalide: " + str)); + } +} +``` + +**Usage** : + +```java +StatutApprobation statut = StatutApprobation.APPROVED; +System.out.println(statut.getLibelle()); // "Approuvée" + +StatutApprobation parsed = StatutApprobation.fromString("PENDING"); +``` + +### 4. BaseResponse - Héritage commun + +Tous les Response DTOs étendent `BaseResponse` : + +```java +@Data +@NoArgsConstructor +public abstract class BaseResponse implements Serializable { + + private static final long serialVersionUID = 1L; + + // Audit fields (si nécessaire côté client) + private LocalDateTime dateCreation; + private LocalDateTime dateModification; + private Boolean actif; +} +``` + +**Avantages** : +- Champs audit automatiques +- Serializable pour cache/sessions +- Type-safe avec génériques + +--- + +## 🧪 Tests + +### Tests de validation + +**Fichier** : `src/test/java/dev/lions/unionflow/server/api/validation/AmountValidatorTest.java` + +```java +@Test +void shouldRejectNegativeAmount() { + CreatePaiementRequest request = new CreatePaiementRequest(); + request.setMontant(BigDecimal.valueOf(-100)); + + Set> violations = validator.validate(request); + + assertFalse(violations.isEmpty()); + assertTrue(violations.stream() + .anyMatch(v -> v.getMessage().contains("positif"))); +} + +@Test +void shouldRejectTooManyDecimals() { + CreatePaiementRequest request = new CreatePaiementRequest(); + request.setMontant(BigDecimal.valueOf(100.123)); + + Set> violations = validator.validate(request); + + assertFalse(violations.isEmpty()); + assertTrue(violations.stream() + .anyMatch(v -> v.getMessage().contains("2 décimales"))); +} +``` + +### Lancer les tests + +```bash +mvn test +``` + +--- + +## 📊 DTOs par Feature + +### Dashboard + +- `DashboardStatsResponse` - Stats organisation (membres, cotisations, events) +- `MembreDashboardSyntheseResponse` - Synthèse membre (solde, cotisations) +- `UpcomingEventResponse` - Événements à venir + +### Finance Workflow + +- `TransactionApprovalResponse` - Approbation de transaction +- `BudgetResponse` - Budget avec lignes budgétaires +- `AdhesionResponse` - Adhésion membre + +### Membres + +- `MembreResponse` - Détails membre complets +- `MembreSummaryResponse` - Résumé membre (liste) +- `CreateMembreRequest` - Création membre +- `UpdateMembreRequest` - Modification membre + +### Cotisations + +- `CotisationResponse` - Cotisation avec détails +- `CreateCotisationRequest` - Enregistrement cotisation +- `CotisationStatisticsResponse` - Statistiques cotisations + +### Notifications + +- `NotificationResponse` - Notification utilisateur +- `MarkAsReadRequest` - Marquer comme lue + +--- + +## 🔄 Publication Maven (Développeurs seulement) + +### Publier une nouvelle version + +```bash +# 1. Mettre à jour la version dans pom.xml +2.1.0 + +# 2. Compiler et publier +mvn clean deploy + +# Les artifacts sont publiés sur: +# https://git.lions.dev/api/packages/lionsdev/maven +``` + +### Versioning Semantic + +- **Major** (2.0.0) : Breaking changes +- **Minor** (2.1.0) : Nouvelles features (backward compatible) +- **Patch** (2.0.1) : Bugfixes + +--- + +## 📝 Changelog + +### v2.0.0 (2026-03-14) + +✅ **Nouveau** : +- DTOs Finance Workflow complets +- Validation `@ValidAmount` avec min/max +- Enums `BudgetPeriod`, `BudgetCategory` +- `TransactionApprovalResponse` avec tous les champs + +✅ **Améliorations** : +- BaseResponse avec audit fields +- ValidationConstants centralisées +- Javadoc complète pour tous les DTOs + +### v1.0.0 (2026-01-04) + +- Version initiale +- 20+ DTOs principaux +- 10+ validators custom + +--- + +## 📚 Documentation + +### Javadoc + +```bash +# Générer Javadoc +mvn javadoc:javadoc + +# Ouvrir +open target/site/apidocs/index.html +``` + +### Ressources + +- **Jakarta Bean Validation**: https://jakarta.ee/specifications/bean-validation/ +- **Maven Repository**: https://git.lions.dev/lionsdev/unionflow-server-api + +--- + +## 🤝 Contribution + +1. Créer une branche feature +2. Ajouter DTOs/Validators avec tests +3. Documenter avec Javadoc +4. Pull Request avec description + +--- + +## 📄 Licence + +Propriétaire - © 2026 Lions Club Côte d'Ivoire + +--- + +**Version** : 2.0.0 +**Dernière mise à jour** : 2026-03-14 +**Auteur** : Équipe UnionFlow diff --git a/analyze_jacoco.py b/analyze_jacoco.py index cb7dc4b..69627d7 100644 --- a/analyze_jacoco.py +++ b/analyze_jacoco.py @@ -1,169 +1,169 @@ -#!/usr/bin/env python3 -"""Script pour analyser le rapport JaCoCo et extraire les classes sans tests.""" - -import os -import re -from pathlib import Path -from html.parser import HTMLParser - -class JaCoCoParser(HTMLParser): - def __init__(self): - super().__init__() - self.current_package = "" - self.classes = [] - self.in_tbody = False - self.current_row = {} - self.current_cell = "" - self.cell_index = 0 - - def handle_starttag(self, tag, attrs): - if tag == "tbody": - self.in_tbody = True - elif tag == "tr" and self.in_tbody: - self.current_row = {} - self.cell_index = 0 - elif tag == "td" and self.in_tbody: - self.current_cell = "" - elif tag == "a" and self.in_tbody: - for attr, value in attrs: - if attr == "href" and value.endswith(".html"): - self.current_row["href"] = value - - def handle_endtag(self, tag): - if tag == "tbody": - self.in_tbody = False - elif tag == "tr" and self.in_tbody and self.current_row: - if "coverage" in self.current_row and self.current_row["coverage"] == "0 %": - self.classes.append(self.current_row.copy()) - elif tag == "td" and self.in_tbody: - self.cell_index += 1 - - def handle_data(self, data): - if self.in_tbody: - data = data.strip() - if data and self.cell_index == 0: - self.current_row["name"] = data - elif data and "%" in data: - self.current_row["coverage"] = data - -def analyze_package(package_path, package_name): - """Analyse un fichier index.html de package.""" - index_file = os.path.join(package_path, "index.html") - if not os.path.exists(index_file): - return [] - - with open(index_file, 'r', encoding='utf-8') as f: - content = f.read() - - parser = JaCoCoParser() - parser.current_package = package_name - parser.feed(content) - - classes = [] - for row in parser.classes: - if "name" in row: - classes.append({ - "package": package_name, - "class": row["name"], - "coverage": row.get("coverage", "0 %") - }) - - return classes - -def main(): - jacoco_dir = Path("target/site/jacoco") - - if not jacoco_dir.exists(): - print(f"Erreur: Le répertoire {jacoco_dir} n'existe pas.") - print("Veuillez exécuter 'mvn clean test' pour générer le rapport JaCoCo.") - return - - # Collecter tous les packages - all_classes = [] - - for package_dir in jacoco_dir.iterdir(): - if package_dir.is_dir() and not package_dir.name.startswith("."): - package_name = package_dir.name.replace("/", ".") - classes = analyze_package(package_dir, package_name) - all_classes.extend(classes) - - # Trier par package et type - dto_requests = [] - dto_responses = [] - dto_other = [] - enums = [] - others = [] - - for cls in all_classes: - pkg = cls["package"] - name = cls["class"] - - if "enums" in pkg: - enums.append(cls) - elif "dto" in pkg: - if ".request" in pkg: - dto_requests.append(cls) - elif ".response" in pkg: - dto_responses.append(cls) - else: - dto_other.append(cls) - else: - others.append(cls) - - # Afficher les résultats - print("=" * 80) - print("CLASSES SANS TESTS (0% de couverture)") - print("=" * 80) - print() - - if dto_requests: - print("1. DTOs REQUEST (dev.lions.unionflow.server.api.dto)") - print("-" * 80) - for cls in sorted(dto_requests, key=lambda x: (x["package"], x["class"])): - print(f" {cls['package']}.{cls['class']}") - print(f" Type: DTO Request | Couverture: {cls['coverage']}") - print() - - if dto_responses: - print("2. DTOs RESPONSE (dev.lions.unionflow.server.api.dto)") - print("-" * 80) - for cls in sorted(dto_responses, key=lambda x: (x["package"], x["class"])): - print(f" {cls['package']}.{cls['class']}") - print(f" Type: DTO Response | Couverture: {cls['coverage']}") - print() - - if dto_other: - print("3. AUTRES DTOs") - print("-" * 80) - for cls in sorted(dto_other, key=lambda x: (x["package"], x["class"])): - print(f" {cls['package']}.{cls['class']}") - print(f" Type: DTO | Couverture: {cls['coverage']}") - print() - - if enums: - print("4. ENUMS (dev.lions.unionflow.server.api.enums)") - print("-" * 80) - for cls in sorted(enums, key=lambda x: (x["package"], x["class"])): - print(f" {cls['package']}.{cls['class']}") - print(f" Type: Enum | Couverture: {cls['coverage']}") - print() - - if others: - print("5. AUTRES") - print("-" * 80) - for cls in sorted(others, key=lambda x: (x["package"], x["class"])): - print(f" {cls['package']}.{cls['class']}") - print(f" Type: Autre | Couverture: {cls['coverage']}") - print() - - print("=" * 80) - print(f"TOTAL: {len(all_classes)} classes sans tests") - print(f" - DTO Requests: {len(dto_requests)}") - print(f" - DTO Responses: {len(dto_responses)}") - print(f" - Autres DTOs: {len(dto_other)}") - print(f" - Enums: {len(enums)}") - print(f" - Autres: {len(others)}") - print("=" * 80) - -if __name__ == "__main__": - main() +#!/usr/bin/env python3 +"""Script pour analyser le rapport JaCoCo et extraire les classes sans tests.""" + +import os +import re +from pathlib import Path +from html.parser import HTMLParser + +class JaCoCoParser(HTMLParser): + def __init__(self): + super().__init__() + self.current_package = "" + self.classes = [] + self.in_tbody = False + self.current_row = {} + self.current_cell = "" + self.cell_index = 0 + + def handle_starttag(self, tag, attrs): + if tag == "tbody": + self.in_tbody = True + elif tag == "tr" and self.in_tbody: + self.current_row = {} + self.cell_index = 0 + elif tag == "td" and self.in_tbody: + self.current_cell = "" + elif tag == "a" and self.in_tbody: + for attr, value in attrs: + if attr == "href" and value.endswith(".html"): + self.current_row["href"] = value + + def handle_endtag(self, tag): + if tag == "tbody": + self.in_tbody = False + elif tag == "tr" and self.in_tbody and self.current_row: + if "coverage" in self.current_row and self.current_row["coverage"] == "0 %": + self.classes.append(self.current_row.copy()) + elif tag == "td" and self.in_tbody: + self.cell_index += 1 + + def handle_data(self, data): + if self.in_tbody: + data = data.strip() + if data and self.cell_index == 0: + self.current_row["name"] = data + elif data and "%" in data: + self.current_row["coverage"] = data + +def analyze_package(package_path, package_name): + """Analyse un fichier index.html de package.""" + index_file = os.path.join(package_path, "index.html") + if not os.path.exists(index_file): + return [] + + with open(index_file, 'r', encoding='utf-8') as f: + content = f.read() + + parser = JaCoCoParser() + parser.current_package = package_name + parser.feed(content) + + classes = [] + for row in parser.classes: + if "name" in row: + classes.append({ + "package": package_name, + "class": row["name"], + "coverage": row.get("coverage", "0 %") + }) + + return classes + +def main(): + jacoco_dir = Path("target/site/jacoco") + + if not jacoco_dir.exists(): + print(f"Erreur: Le répertoire {jacoco_dir} n'existe pas.") + print("Veuillez exécuter 'mvn clean test' pour générer le rapport JaCoCo.") + return + + # Collecter tous les packages + all_classes = [] + + for package_dir in jacoco_dir.iterdir(): + if package_dir.is_dir() and not package_dir.name.startswith("."): + package_name = package_dir.name.replace("/", ".") + classes = analyze_package(package_dir, package_name) + all_classes.extend(classes) + + # Trier par package et type + dto_requests = [] + dto_responses = [] + dto_other = [] + enums = [] + others = [] + + for cls in all_classes: + pkg = cls["package"] + name = cls["class"] + + if "enums" in pkg: + enums.append(cls) + elif "dto" in pkg: + if ".request" in pkg: + dto_requests.append(cls) + elif ".response" in pkg: + dto_responses.append(cls) + else: + dto_other.append(cls) + else: + others.append(cls) + + # Afficher les résultats + print("=" * 80) + print("CLASSES SANS TESTS (0% de couverture)") + print("=" * 80) + print() + + if dto_requests: + print("1. DTOs REQUEST (dev.lions.unionflow.server.api.dto)") + print("-" * 80) + for cls in sorted(dto_requests, key=lambda x: (x["package"], x["class"])): + print(f" {cls['package']}.{cls['class']}") + print(f" Type: DTO Request | Couverture: {cls['coverage']}") + print() + + if dto_responses: + print("2. DTOs RESPONSE (dev.lions.unionflow.server.api.dto)") + print("-" * 80) + for cls in sorted(dto_responses, key=lambda x: (x["package"], x["class"])): + print(f" {cls['package']}.{cls['class']}") + print(f" Type: DTO Response | Couverture: {cls['coverage']}") + print() + + if dto_other: + print("3. AUTRES DTOs") + print("-" * 80) + for cls in sorted(dto_other, key=lambda x: (x["package"], x["class"])): + print(f" {cls['package']}.{cls['class']}") + print(f" Type: DTO | Couverture: {cls['coverage']}") + print() + + if enums: + print("4. ENUMS (dev.lions.unionflow.server.api.enums)") + print("-" * 80) + for cls in sorted(enums, key=lambda x: (x["package"], x["class"])): + print(f" {cls['package']}.{cls['class']}") + print(f" Type: Enum | Couverture: {cls['coverage']}") + print() + + if others: + print("5. AUTRES") + print("-" * 80) + for cls in sorted(others, key=lambda x: (x["package"], x["class"])): + print(f" {cls['package']}.{cls['class']}") + print(f" Type: Autre | Couverture: {cls['coverage']}") + print() + + print("=" * 80) + print(f"TOTAL: {len(all_classes)} classes sans tests") + print(f" - DTO Requests: {len(dto_requests)}") + print(f" - DTO Responses: {len(dto_responses)}") + print(f" - Autres DTOs: {len(dto_other)}") + print(f" - Enums: {len(enums)}") + print(f" - Autres: {len(others)}") + print("=" * 80) + +if __name__ == "__main__": + main() diff --git a/checkstyle-unionflow.xml b/checkstyle-unionflow.xml index 8d7953c..5427f91 100644 --- a/checkstyle-unionflow.xml +++ b/checkstyle-unionflow.xml @@ -1,359 +1,359 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/lombok.config b/lombok.config index df71bb6..9d3ccb6 100644 --- a/lombok.config +++ b/lombok.config @@ -1,2 +1,2 @@ -config.stopBubbling = true -lombok.addLombokGeneratedAnnotation = true +config.stopBubbling = true +lombok.addLombokGeneratedAnnotation = true diff --git a/parent-pom.xml b/parent-pom.xml index 723b615..31f3912 100644 --- a/parent-pom.xml +++ b/parent-pom.xml @@ -6,7 +6,7 @@ dev.lions.unionflow unionflow-parent - 1.0.5 + 1.0.6 pom UnionFlow - Parent diff --git a/pom.xml b/pom.xml index 3297490..ec85c0c 100644 --- a/pom.xml +++ b/pom.xml @@ -4,23 +4,39 @@ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> 4.0.0 - - dev.lions.unionflow - unionflow-parent - 1.0.5 - parent-pom.xml - - + dev.lions.unionflow unionflow-server-api + 1.0.7 jar UnionFlow Server API API définitions pour le serveur UnionFlow + + + gitea-lionsdev + https://git.lions.dev/api/packages/lionsdev/maven + + + + + + gitea-lionsdev + https://git.lions.dev/api/packages/lionsdev/maven + true + true + + + + 21 + ${java.version} + ${java.version} + ${java.version} UTF-8 - 3.20.0 + 3.27.3 + 1.18.38 2.18.2 3.0.2 3.1.1 diff --git a/script/publish-api.bat b/script/publish-api.bat index e8f77fc..a07f728 100644 --- a/script/publish-api.bat +++ b/script/publish-api.bat @@ -1,30 +1,30 @@ -@echo off -REM Publie le parent pom + server-api sur le Gitea Package Registry -REM Usage : script\publish-api.bat -REM Depuis : n'importe où dans le repo server-api -REM Prérequis: credentials dans %USERPROFILE%\.m2\settings.xml (server id: gitea-lionsdev) - -set REGISTRY_URL=https://git.lions.dev/api/packages/lionsdev/maven -set REGISTRY_ID=gitea-lionsdev - -cd /d "%~dp0\.." - -echo. -echo [1/2] Publication du parent pom... -call mvn deploy:deploy-file ^ - -DgroupId=dev.lions.unionflow ^ - -DartifactId=unionflow-parent ^ - -Dversion=1.0.0 ^ - -Dpackaging=pom ^ - -Dfile=parent-pom.xml ^ - -DrepositoryId=%REGISTRY_ID% ^ - -Durl=%REGISTRY_URL% -if errorlevel 409 echo [WARN] Parent pom deja publie pour cette version, on continue. - -echo. -echo [2/2] Publication du server-api... -call mvn deploy -DskipTests -if errorlevel 409 echo [WARN] Server-api deja publie - incrementer la version pour republier. - -echo. -echo Done -- https://git.lions.dev/lionsdev/-/packages +@echo off +REM Publie le parent pom + server-api sur le Gitea Package Registry +REM Usage : script\publish-api.bat +REM Depuis : n'importe où dans le repo server-api +REM Prérequis: credentials dans %USERPROFILE%\.m2\settings.xml (server id: gitea-lionsdev) + +set REGISTRY_URL=https://git.lions.dev/api/packages/lionsdev/maven +set REGISTRY_ID=gitea-lionsdev + +cd /d "%~dp0\.." + +echo. +echo [1/2] Publication du parent pom... +call mvn deploy:deploy-file ^ + -DgroupId=dev.lions.unionflow ^ + -DartifactId=unionflow-parent ^ + -Dversion=1.0.0 ^ + -Dpackaging=pom ^ + -Dfile=parent-pom.xml ^ + -DrepositoryId=%REGISTRY_ID% ^ + -Durl=%REGISTRY_URL% +if errorlevel 409 echo [WARN] Parent pom deja publie pour cette version, on continue. + +echo. +echo [2/2] Publication du server-api... +call mvn deploy -DskipTests +if errorlevel 409 echo [WARN] Server-api deja publie - incrementer la version pour republier. + +echo. +echo Done -- https://git.lions.dev/lionsdev/-/packages diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/abonnement/request/CreateAbonnementRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/abonnement/request/CreateAbonnementRequest.java index 996d745..3cc4123 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/abonnement/request/CreateAbonnementRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/abonnement/request/CreateAbonnementRequest.java @@ -1,82 +1,82 @@ -package dev.lions.unionflow.server.api.dto.abonnement.request; - -import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; -import dev.lions.unionflow.server.api.enums.abonnement.TypePeriodeAbonnement; -import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.Future; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Pattern; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'un abonnement. - */ -@Builder -public record CreateAbonnementRequest( - @NotBlank(message = "Le numéro de référence est obligatoire") @Pattern(regexp = "^ABO-\\d{4}-[A-Z0-9]{8}$", message = "Format de référence invalide (ABO-YYYY-XXXXXXXX)") String numeroReference, - - @NotNull(message = "L'identifiant de l'organisation est obligatoire") UUID organisationId, - - String nomOrganisation, - - @NotNull(message = "L'identifiant de la formule est obligatoire") UUID formulaireId, - - String codeFormule, - String nomFormule, - TypeFormule typeFormule, - - @NotNull(message = "Le statut est obligatoire") StatutAbonnement statut, - - @NotNull(message = "Le type d'abonnement est obligatoire") TypePeriodeAbonnement typeAbonnement, - - @NotNull(message = "La date de début est obligatoire") LocalDate dateDebut, - - @Future(message = "La date de fin doit être dans le futur") LocalDate dateFin, - - LocalDate dateProchainePeriode, - - @NotNull(message = "Le montant est obligatoire") @DecimalMin(value = "0.0", inclusive = false, message = "Le montant doit être positif") @Digits(integer = 10, fraction = 2, message = "Le montant ne peut avoir plus de 10 chiffres entiers et 2 décimales") BigDecimal montant, - - @NotBlank(message = "La devise est obligatoire") @Pattern(regexp = "^[A-Z]{3}$", message = "La devise doit être un code ISO à 3 lettres") String devise, - - @DecimalMin(value = "0.0", message = "La remise doit être positive") @DecimalMin(value = "100.0", message = "La remise ne peut pas dépasser 100%") BigDecimal remise, - - @DecimalMin(value = "0.0", message = "Le montant final doit être positif") @Digits(integer = 10, fraction = 2, message = "Le montant ne peut avoir plus de 10 chiffres entiers et 2 décimales") BigDecimal montantFinal, - - Boolean renouvellementAutomatique, - Boolean periodeEssaiUtilisee, - LocalDate dateFinEssai, - Integer maxMembres, - Integer nombreMembresActuels, - BigDecimal espaceStockageGB, - BigDecimal espaceStockageUtilise, - Boolean supportTechnique, - String niveauSupport, - Boolean fonctionnalitesAvancees, - Boolean apiAccess, - Boolean rapportsPersonnalises, - Boolean integrationsTierces, - UUID responsableId, - String nomResponsable, - String emailResponsable, - String telephoneResponsable, - - @Pattern(regexp = "^(WAVE_MONEY|ORANGE_MONEY|FREE_MONEY|VIREMENT|CHEQUE|AUTRE)$", message = "Mode de paiement invalide") String modePaiementPrefere, - - @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Format de numéro de téléphone invalide") String numeroPaiementMobile, - - @Size(max = 5000, message = "L'historique ne peut pas dépasser 5000 caractères") String historiquePaiements, - - @Size(max = 1000, message = "Les notes ne peuvent pas dépasser 1000 caractères") String notes, - - Boolean alertesActivees, - Boolean notificationsEmail, - Boolean notificationsSMS) { -} +package dev.lions.unionflow.server.api.dto.abonnement.request; + +import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; +import dev.lions.unionflow.server.api.enums.abonnement.TypePeriodeAbonnement; +import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.Future; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Pattern; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'un abonnement. + */ +@Builder +public record CreateAbonnementRequest( + @NotBlank(message = "Le numéro de référence est obligatoire") @Pattern(regexp = "^ABO-\\d{4}-[A-Z0-9]{8}$", message = "Format de référence invalide (ABO-YYYY-XXXXXXXX)") String numeroReference, + + @NotNull(message = "L'identifiant de l'organisation est obligatoire") UUID organisationId, + + String nomOrganisation, + + @NotNull(message = "L'identifiant de la formule est obligatoire") UUID formulaireId, + + String codeFormule, + String nomFormule, + TypeFormule typeFormule, + + @NotNull(message = "Le statut est obligatoire") StatutAbonnement statut, + + @NotNull(message = "Le type d'abonnement est obligatoire") TypePeriodeAbonnement typeAbonnement, + + @NotNull(message = "La date de début est obligatoire") LocalDate dateDebut, + + @Future(message = "La date de fin doit être dans le futur") LocalDate dateFin, + + LocalDate dateProchainePeriode, + + @NotNull(message = "Le montant est obligatoire") @DecimalMin(value = "0.0", inclusive = false, message = "Le montant doit être positif") @Digits(integer = 10, fraction = 2, message = "Le montant ne peut avoir plus de 10 chiffres entiers et 2 décimales") BigDecimal montant, + + @NotBlank(message = "La devise est obligatoire") @Pattern(regexp = "^[A-Z]{3}$", message = "La devise doit être un code ISO à 3 lettres") String devise, + + @DecimalMin(value = "0.0", message = "La remise doit être positive") @DecimalMin(value = "100.0", message = "La remise ne peut pas dépasser 100%") BigDecimal remise, + + @DecimalMin(value = "0.0", message = "Le montant final doit être positif") @Digits(integer = 10, fraction = 2, message = "Le montant ne peut avoir plus de 10 chiffres entiers et 2 décimales") BigDecimal montantFinal, + + Boolean renouvellementAutomatique, + Boolean periodeEssaiUtilisee, + LocalDate dateFinEssai, + Integer maxMembres, + Integer nombreMembresActuels, + BigDecimal espaceStockageGB, + BigDecimal espaceStockageUtilise, + Boolean supportTechnique, + String niveauSupport, + Boolean fonctionnalitesAvancees, + Boolean apiAccess, + Boolean rapportsPersonnalises, + Boolean integrationsTierces, + UUID responsableId, + String nomResponsable, + String emailResponsable, + String telephoneResponsable, + + @Pattern(regexp = "^(WAVE_MONEY|ORANGE_MONEY|FREE_MONEY|VIREMENT|CHEQUE|AUTRE)$", message = "Mode de paiement invalide") String modePaiementPrefere, + + @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Format de numéro de téléphone invalide") String numeroPaiementMobile, + + @Size(max = 5000, message = "L'historique ne peut pas dépasser 5000 caractères") String historiquePaiements, + + @Size(max = 1000, message = "Les notes ne peuvent pas dépasser 1000 caractères") String notes, + + Boolean alertesActivees, + Boolean notificationsEmail, + Boolean notificationsSMS) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/abonnement/request/UpdateAbonnementRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/abonnement/request/UpdateAbonnementRequest.java index a959b81..14046c2 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/abonnement/request/UpdateAbonnementRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/abonnement/request/UpdateAbonnementRequest.java @@ -1,77 +1,77 @@ -package dev.lions.unionflow.server.api.dto.abonnement.request; - -import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; -import dev.lions.unionflow.server.api.enums.abonnement.TypePeriodeAbonnement; -import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.Future; -import jakarta.validation.constraints.Pattern; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de mise à jour d'un abonnement. - */ -@Builder -public record UpdateAbonnementRequest( - @Pattern(regexp = "^ABO-\\d{4}-[A-Z0-9]{8}$", message = "Format de référence invalide (ABO-YYYY-XXXXXXXX)") String numeroReference, - - UUID organisationId, - String nomOrganisation, - UUID formulaireId, - - String codeFormule, - String nomFormule, - TypeFormule typeFormule, - - StatutAbonnement statut, - TypePeriodeAbonnement typeAbonnement, - - LocalDate dateDebut, - - @Future(message = "La date de fin doit être dans le futur") LocalDate dateFin, - - LocalDate dateProchainePeriode, - - @DecimalMin(value = "0.0", inclusive = false, message = "Le montant doit être positif") @Digits(integer = 10, fraction = 2, message = "Le montant ne peut avoir plus de 10 chiffres entiers et 2 décimales") BigDecimal montant, - - @Pattern(regexp = "^[A-Z]{3}$", message = "La devise doit être un code ISO à 3 lettres") String devise, - - @DecimalMin(value = "0.0", message = "La remise doit être positive") @DecimalMin(value = "100.0", message = "La remise ne peut pas dépasser 100%") BigDecimal remise, - - @DecimalMin(value = "0.0", message = "Le montant final doit être positif") @Digits(integer = 10, fraction = 2, message = "Le montant ne peut avoir plus de 10 chiffres entiers et 2 décimales") BigDecimal montantFinal, - - Boolean renouvellementAutomatique, - Boolean periodeEssaiUtilisee, - LocalDate dateFinEssai, - Integer maxMembres, - Integer nombreMembresActuels, - BigDecimal espaceStockageGB, - BigDecimal espaceStockageUtilise, - Boolean supportTechnique, - String niveauSupport, - Boolean fonctionnalitesAvancees, - Boolean apiAccess, - Boolean rapportsPersonnalises, - Boolean integrationsTierces, - UUID responsableId, - String nomResponsable, - String emailResponsable, - String telephoneResponsable, - - @Pattern(regexp = "^(WAVE_MONEY|ORANGE_MONEY|FREE_MONEY|VIREMENT|CHEQUE|AUTRE)$", message = "Mode de paiement invalide") String modePaiementPrefere, - - @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Format de numéro de téléphone invalide") String numeroPaiementMobile, - - @Size(max = 5000, message = "L'historique ne peut pas dépasser 5000 caractères") String historiquePaiements, - - @Size(max = 1000, message = "Les notes ne peuvent pas dépasser 1000 caractères") String notes, - - Boolean alertesActivees, - Boolean notificationsEmail, - Boolean notificationsSMS) { -} +package dev.lions.unionflow.server.api.dto.abonnement.request; + +import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; +import dev.lions.unionflow.server.api.enums.abonnement.TypePeriodeAbonnement; +import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.Future; +import jakarta.validation.constraints.Pattern; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de mise à jour d'un abonnement. + */ +@Builder +public record UpdateAbonnementRequest( + @Pattern(regexp = "^ABO-\\d{4}-[A-Z0-9]{8}$", message = "Format de référence invalide (ABO-YYYY-XXXXXXXX)") String numeroReference, + + UUID organisationId, + String nomOrganisation, + UUID formulaireId, + + String codeFormule, + String nomFormule, + TypeFormule typeFormule, + + StatutAbonnement statut, + TypePeriodeAbonnement typeAbonnement, + + LocalDate dateDebut, + + @Future(message = "La date de fin doit être dans le futur") LocalDate dateFin, + + LocalDate dateProchainePeriode, + + @DecimalMin(value = "0.0", inclusive = false, message = "Le montant doit être positif") @Digits(integer = 10, fraction = 2, message = "Le montant ne peut avoir plus de 10 chiffres entiers et 2 décimales") BigDecimal montant, + + @Pattern(regexp = "^[A-Z]{3}$", message = "La devise doit être un code ISO à 3 lettres") String devise, + + @DecimalMin(value = "0.0", message = "La remise doit être positive") @DecimalMin(value = "100.0", message = "La remise ne peut pas dépasser 100%") BigDecimal remise, + + @DecimalMin(value = "0.0", message = "Le montant final doit être positif") @Digits(integer = 10, fraction = 2, message = "Le montant ne peut avoir plus de 10 chiffres entiers et 2 décimales") BigDecimal montantFinal, + + Boolean renouvellementAutomatique, + Boolean periodeEssaiUtilisee, + LocalDate dateFinEssai, + Integer maxMembres, + Integer nombreMembresActuels, + BigDecimal espaceStockageGB, + BigDecimal espaceStockageUtilise, + Boolean supportTechnique, + String niveauSupport, + Boolean fonctionnalitesAvancees, + Boolean apiAccess, + Boolean rapportsPersonnalises, + Boolean integrationsTierces, + UUID responsableId, + String nomResponsable, + String emailResponsable, + String telephoneResponsable, + + @Pattern(regexp = "^(WAVE_MONEY|ORANGE_MONEY|FREE_MONEY|VIREMENT|CHEQUE|AUTRE)$", message = "Mode de paiement invalide") String modePaiementPrefere, + + @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Format de numéro de téléphone invalide") String numeroPaiementMobile, + + @Size(max = 5000, message = "L'historique ne peut pas dépasser 5000 caractères") String historiquePaiements, + + @Size(max = 1000, message = "Les notes ne peuvent pas dépasser 1000 caractères") String notes, + + Boolean alertesActivees, + Boolean notificationsEmail, + Boolean notificationsSMS) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/abonnement/response/AbonnementResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/abonnement/response/AbonnementResponse.java index 3381980..9d9b7a4 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/abonnement/response/AbonnementResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/abonnement/response/AbonnementResponse.java @@ -1,133 +1,133 @@ -package dev.lions.unionflow.server.api.dto.abonnement.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; -import dev.lions.unionflow.server.api.enums.abonnement.TypePeriodeAbonnement; -import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalDateTime; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée pour un abonnement. - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class AbonnementResponse extends BaseResponse { - - private String numeroReference; - private UUID organisationId; - private String nomOrganisation; - private UUID formulaireId; - private String codeFormule; - private String nomFormule; - private TypeFormule typeFormule; - private StatutAbonnement statut; - private TypePeriodeAbonnement typeAbonnement; - private LocalDate dateDebut; - private LocalDate dateFin; - private LocalDate dateProchainePeriode; - private BigDecimal montant; - private String devise; - private BigDecimal remise; - private BigDecimal montantFinal; - private Boolean renouvellementAutomatique; - private Boolean periodeEssaiUtilisee; - private LocalDate dateFinEssai; - private Integer maxMembres; - private Integer nombreMembresActuels; - private BigDecimal espaceStockageGB; - private BigDecimal espaceStockageUtilise; - private Boolean supportTechnique; - private String niveauSupport; - private Boolean fonctionnalitesAvancees; - private Boolean apiAccess; - private Boolean rapportsPersonnalises; - private Boolean integrationsTierces; - private LocalDateTime dateDerniereUtilisation; - private Integer connexionsCeMois; - private UUID responsableId; - private String nomResponsable; - private String emailResponsable; - private String telephoneResponsable; - - private String modePaiementPrefere; - private String numeroPaiementMobile; - private String historiquePaiements; - private String notes; - - private Boolean alertesActivees; - private Boolean notificationsEmail; - private Boolean notificationsSMS; - - private LocalDateTime dateSuspension; - - private String raisonSuspension; - - private LocalDateTime dateAnnulation; - - private String raisonAnnulation; - - // === MÉTHODES UTILITAIRES === - - public boolean isActive() { - return StatutAbonnement.ACTIF.equals(statut); - } - - public boolean isExpire() { - return StatutAbonnement.EXPIRE.equals(statut) || - (dateFin != null && dateFin.isBefore(LocalDate.now())); - } - - public boolean isSuspendu() { - return StatutAbonnement.SUSPENDU.equals(statut); - } - - public int getMembresRestants() { - if (maxMembres == null) return 0; - int actuels = nombreMembresActuels != null ? nombreMembresActuels : 0; - return Math.max(0, maxMembres - actuels); - } - - public boolean isQuotaAtteint() { - if (maxMembres == null) return false; - int actuels = nombreMembresActuels != null ? nombreMembresActuels : 0; - return actuels >= maxMembres; - } - - public int getPourcentageUtilisation() { - if (maxMembres == null || maxMembres == 0) return 0; - int actuels = nombreMembresActuels != null ? nombreMembresActuels : 0; - return (actuels * 100) / maxMembres; - } - - public long getJoursRestants() { - if (dateFin == null) return -1; - LocalDate maintenant = LocalDate.now(); - if (maintenant.isAfter(dateFin)) return 0; - return java.time.temporal.ChronoUnit.DAYS.between(maintenant, dateFin); - } - - public boolean isExpirationProche() { - long joursRestants = getJoursRestants(); - return joursRestants >= 0 && joursRestants <= 30; - } - - public boolean peutEtreRenouvele() { - return Boolean.TRUE.equals(renouvellementAutomatique) && !isExpire(); - } - - public String getStatutLibelle() { - return statut != null ? statut.name() : "INCONNU"; - } -} +package dev.lions.unionflow.server.api.dto.abonnement.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; +import dev.lions.unionflow.server.api.enums.abonnement.TypePeriodeAbonnement; +import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée pour un abonnement. + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class AbonnementResponse extends BaseResponse { + + private String numeroReference; + private UUID organisationId; + private String nomOrganisation; + private UUID formulaireId; + private String codeFormule; + private String nomFormule; + private TypeFormule typeFormule; + private StatutAbonnement statut; + private TypePeriodeAbonnement typeAbonnement; + private LocalDate dateDebut; + private LocalDate dateFin; + private LocalDate dateProchainePeriode; + private BigDecimal montant; + private String devise; + private BigDecimal remise; + private BigDecimal montantFinal; + private Boolean renouvellementAutomatique; + private Boolean periodeEssaiUtilisee; + private LocalDate dateFinEssai; + private Integer maxMembres; + private Integer nombreMembresActuels; + private BigDecimal espaceStockageGB; + private BigDecimal espaceStockageUtilise; + private Boolean supportTechnique; + private String niveauSupport; + private Boolean fonctionnalitesAvancees; + private Boolean apiAccess; + private Boolean rapportsPersonnalises; + private Boolean integrationsTierces; + private LocalDateTime dateDerniereUtilisation; + private Integer connexionsCeMois; + private UUID responsableId; + private String nomResponsable; + private String emailResponsable; + private String telephoneResponsable; + + private String modePaiementPrefere; + private String numeroPaiementMobile; + private String historiquePaiements; + private String notes; + + private Boolean alertesActivees; + private Boolean notificationsEmail; + private Boolean notificationsSMS; + + private LocalDateTime dateSuspension; + + private String raisonSuspension; + + private LocalDateTime dateAnnulation; + + private String raisonAnnulation; + + // === MÉTHODES UTILITAIRES === + + public boolean isActive() { + return StatutAbonnement.ACTIF.equals(statut); + } + + public boolean isExpire() { + return StatutAbonnement.EXPIRE.equals(statut) || + (dateFin != null && dateFin.isBefore(LocalDate.now())); + } + + public boolean isSuspendu() { + return StatutAbonnement.SUSPENDU.equals(statut); + } + + public int getMembresRestants() { + if (maxMembres == null) return 0; + int actuels = nombreMembresActuels != null ? nombreMembresActuels : 0; + return Math.max(0, maxMembres - actuels); + } + + public boolean isQuotaAtteint() { + if (maxMembres == null) return false; + int actuels = nombreMembresActuels != null ? nombreMembresActuels : 0; + return actuels >= maxMembres; + } + + public int getPourcentageUtilisation() { + if (maxMembres == null || maxMembres == 0) return 0; + int actuels = nombreMembresActuels != null ? nombreMembresActuels : 0; + return (actuels * 100) / maxMembres; + } + + public long getJoursRestants() { + if (dateFin == null) return -1; + LocalDate maintenant = LocalDate.now(); + if (maintenant.isAfter(dateFin)) return 0; + return java.time.temporal.ChronoUnit.DAYS.between(maintenant, dateFin); + } + + public boolean isExpirationProche() { + long joursRestants = getJoursRestants(); + return joursRestants >= 0 && joursRestants <= 30; + } + + public boolean peutEtreRenouvele() { + return Boolean.TRUE.equals(renouvellementAutomatique) && !isExpire(); + } + + public String getStatutLibelle() { + return statut != null ? statut.name() : "INCONNU"; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/admin/request/CreateAuditLogRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/admin/request/CreateAuditLogRequest.java index 4393028..abd6b8a 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/admin/request/CreateAuditLogRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/admin/request/CreateAuditLogRequest.java @@ -1,29 +1,29 @@ -package dev.lions.unionflow.server.api.dto.admin.request; - -import java.time.LocalDateTime; -import lombok.Builder; - -/** - * Requête de création d'un log d'audit. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreateAuditLogRequest( - String typeAction, - String severite, - String utilisateur, - String role, - String module, - String description, - String details, - String ipAddress, - String userAgent, - String sessionId, - LocalDateTime dateHeure, - String donneesAvant, - String donneesApres, - String entiteId, - String entiteType) { -} +package dev.lions.unionflow.server.api.dto.admin.request; + +import java.time.LocalDateTime; +import lombok.Builder; + +/** + * Requête de création d'un log d'audit. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreateAuditLogRequest( + String typeAction, + String severite, + String utilisateur, + String role, + String module, + String description, + String details, + String ipAddress, + String userAgent, + String sessionId, + LocalDateTime dateHeure, + String donneesAvant, + String donneesApres, + String entiteId, + String entiteType) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/admin/response/AuditLogResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/admin/response/AuditLogResponse.java index a1b9248..15c95d3 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/admin/response/AuditLogResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/admin/response/AuditLogResponse.java @@ -1,33 +1,33 @@ -package dev.lions.unionflow.server.api.dto.admin.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.time.LocalDateTime; -import lombok.Getter; -import lombok.Setter; - -/** - * Réponse pour les logs d'audit. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -public class AuditLogResponse extends BaseResponse { - - private String typeAction; - private String severite; - private String utilisateur; - private String role; - private String module; - private String description; - private String details; - private String ipAddress; - private String userAgent; - private String sessionId; - private LocalDateTime dateHeure; - private String donneesAvant; - private String donneesApres; - private String entiteId; - private String entiteType; -} +package dev.lions.unionflow.server.api.dto.admin.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.time.LocalDateTime; +import lombok.Getter; +import lombok.Setter; + +/** + * Réponse pour les logs d'audit. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +public class AuditLogResponse extends BaseResponse { + + private String typeAction; + private String severite; + private String utilisateur; + private String role; + private String module; + private String description; + private String details; + private String ipAddress; + private String userAgent; + private String sessionId; + private LocalDateTime dateHeure; + private String donneesAvant; + private String donneesApres; + private String entiteId; + private String entiteType; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/adresse/request/CreateAdresseRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/adresse/request/CreateAdresseRequest.java index d774aec..ef88245 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/adresse/request/CreateAdresseRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/adresse/request/CreateAdresseRequest.java @@ -1,43 +1,43 @@ -package dev.lions.unionflow.server.api.dto.adresse.request; - -import jakarta.validation.constraints.DecimalMax; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import java.math.BigDecimal; -import java.util.UUID; - -/** - * Requete de création d'une adresse. - * - * @author UnionFlow Team - * @version 3.0 - */ -public record CreateAdresseRequest( - @NotBlank(message = "Le type d'adresse est obligatoire") String typeAdresse, // Code depuis types_reference - - @NotBlank(message = "L'adresse est obligatoire") String adresse, - - String complementAdresse, - String codePostal, - - @NotBlank(message = "La ville est obligatoire") String ville, - - String region, - - @NotBlank(message = "Le pays est obligatoire") String pays, - - @DecimalMin(value = "-90.0", message = "La latitude doit être comprise entre -90 et 90") @DecimalMax(value = "90.0", message = "La latitude doit être comprise entre -90 et 90") @Digits(integer = 3, fraction = 6) BigDecimal latitude, // Optionnel - - @DecimalMin(value = "-180.0", message = "La longitude doit être comprise entre -180 et 180") @DecimalMax(value = "180.0", message = "La longitude doit être comprise entre -180 et 180") @Digits(integer = 3, fraction = 6) BigDecimal longitude, // Optionnel - - @NotNull(message = "L'indicateur principale est obligatoire") Boolean principale, - - String libelle, - String notes, - - UUID organisationId, // Exclusive: soit organisationId, soit membreId, soit evenementId - UUID membreId, - UUID evenementId) { -} +package dev.lions.unionflow.server.api.dto.adresse.request; + +import jakarta.validation.constraints.DecimalMax; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import java.math.BigDecimal; +import java.util.UUID; + +/** + * Requete de création d'une adresse. + * + * @author UnionFlow Team + * @version 3.0 + */ +public record CreateAdresseRequest( + @NotBlank(message = "Le type d'adresse est obligatoire") String typeAdresse, // Code depuis types_reference + + @NotBlank(message = "L'adresse est obligatoire") String adresse, + + String complementAdresse, + String codePostal, + + @NotBlank(message = "La ville est obligatoire") String ville, + + String region, + + @NotBlank(message = "Le pays est obligatoire") String pays, + + @DecimalMin(value = "-90.0", message = "La latitude doit être comprise entre -90 et 90") @DecimalMax(value = "90.0", message = "La latitude doit être comprise entre -90 et 90") @Digits(integer = 3, fraction = 6) BigDecimal latitude, // Optionnel + + @DecimalMin(value = "-180.0", message = "La longitude doit être comprise entre -180 et 180") @DecimalMax(value = "180.0", message = "La longitude doit être comprise entre -180 et 180") @Digits(integer = 3, fraction = 6) BigDecimal longitude, // Optionnel + + @NotNull(message = "L'indicateur principale est obligatoire") Boolean principale, + + String libelle, + String notes, + + UUID organisationId, // Exclusive: soit organisationId, soit membreId, soit evenementId + UUID membreId, + UUID evenementId) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/adresse/request/UpdateAdresseRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/adresse/request/UpdateAdresseRequest.java index 7460e5a..af39fec 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/adresse/request/UpdateAdresseRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/adresse/request/UpdateAdresseRequest.java @@ -1,36 +1,36 @@ -package dev.lions.unionflow.server.api.dto.adresse.request; - -import jakarta.validation.constraints.DecimalMax; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import java.math.BigDecimal; -import java.util.UUID; - -/** - * Requete de mise à jour d'une adresse. - * Tous les champs sont optionnels pour permettre des mises à jour partielles. - * - * @author UnionFlow Team - * @version 3.0 - */ -public record UpdateAdresseRequest( - String typeAdresse, // Code depuis types_reference - String adresse, - String complementAdresse, - String codePostal, - String ville, - String region, - String pays, - - @DecimalMin(value = "-90.0", message = "La latitude doit être comprise entre -90 et 90") @DecimalMax(value = "90.0", message = "La latitude doit être comprise entre -90 et 90") @Digits(integer = 3, fraction = 6) BigDecimal latitude, - - @DecimalMin(value = "-180.0", message = "La longitude doit être comprise entre -180 et 180") @DecimalMax(value = "180.0", message = "La longitude doit être comprise entre -180 et 180") @Digits(integer = 3, fraction = 6) BigDecimal longitude, - - Boolean principale, - String libelle, - String notes, - - UUID organisationId, - UUID membreId, - UUID evenementId) { -} +package dev.lions.unionflow.server.api.dto.adresse.request; + +import jakarta.validation.constraints.DecimalMax; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import java.math.BigDecimal; +import java.util.UUID; + +/** + * Requete de mise à jour d'une adresse. + * Tous les champs sont optionnels pour permettre des mises à jour partielles. + * + * @author UnionFlow Team + * @version 3.0 + */ +public record UpdateAdresseRequest( + String typeAdresse, // Code depuis types_reference + String adresse, + String complementAdresse, + String codePostal, + String ville, + String region, + String pays, + + @DecimalMin(value = "-90.0", message = "La latitude doit être comprise entre -90 et 90") @DecimalMax(value = "90.0", message = "La latitude doit être comprise entre -90 et 90") @Digits(integer = 3, fraction = 6) BigDecimal latitude, + + @DecimalMin(value = "-180.0", message = "La longitude doit être comprise entre -180 et 180") @DecimalMax(value = "180.0", message = "La longitude doit être comprise entre -180 et 180") @Digits(integer = 3, fraction = 6) BigDecimal longitude, + + Boolean principale, + String libelle, + String notes, + + UUID organisationId, + UUID membreId, + UUID evenementId) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/adresse/response/AdresseResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/adresse/response/AdresseResponse.java index eef7bf8..0cc0ac0 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/adresse/response/AdresseResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/adresse/response/AdresseResponse.java @@ -1,42 +1,42 @@ -package dev.lions.unionflow.server.api.dto.adresse.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.math.BigDecimal; -import java.util.UUID; -import lombok.Getter; -import lombok.Setter; - -/** - * DTO de réponse détaillée pour une adresse. - * - * @author UnionFlow Team - * @version 3.0 - */ -@Getter -@Setter -public class AdresseResponse extends BaseResponse { - - private String typeAdresse; // Code - private String typeAdresseLibelle; // Depuis types_reference - private String typeAdresseIcone; - - private String adresse; - private String complementAdresse; - private String codePostal; - private String ville; - private String region; - private String pays; - - private BigDecimal latitude; - private BigDecimal longitude; - - private Boolean principale; - private String libelle; - private String notes; - - private UUID organisationId; - private UUID membreId; - private UUID evenementId; - - private String adresseComplete; -} +package dev.lions.unionflow.server.api.dto.adresse.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.math.BigDecimal; +import java.util.UUID; +import lombok.Getter; +import lombok.Setter; + +/** + * DTO de réponse détaillée pour une adresse. + * + * @author UnionFlow Team + * @version 3.0 + */ +@Getter +@Setter +public class AdresseResponse extends BaseResponse { + + private String typeAdresse; // Code + private String typeAdresseLibelle; // Depuis types_reference + private String typeAdresseIcone; + + private String adresse; + private String complementAdresse; + private String codePostal; + private String ville; + private String region; + private String pays; + + private BigDecimal latitude; + private BigDecimal longitude; + + private Boolean principale; + private String libelle; + private String notes; + + private UUID organisationId; + private UUID membreId; + private UUID evenementId; + + private String adresseComplete; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/agricole/CampagneAgricoleDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/agricole/CampagneAgricoleDTO.java index c889af6..5985a51 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/agricole/CampagneAgricoleDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/agricole/CampagneAgricoleDTO.java @@ -1,35 +1,35 @@ -package dev.lions.unionflow.server.api.dto.agricole; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.agricole.StatutCampagneAgricole; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; - -import java.math.BigDecimal; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class CampagneAgricoleDTO extends BaseDTO { - - private String organisationCoopId; - - // Exemple : "Campagne d'Arachide 2025/2026" - private String designation; - - private String typeCulturePrincipale; - - // Nombre d'hectares au total couvert par les membres de la coop - private BigDecimal surfaceTotaleEstimeeHectares; - - // Tonnes récoltées attendues vs réelles - private BigDecimal volumePrevisionnelTonnes; - private BigDecimal volumeReelTonnes; - - private StatutCampagneAgricole statut; -} +package dev.lions.unionflow.server.api.dto.agricole; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.agricole.StatutCampagneAgricole; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; + +import java.math.BigDecimal; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class CampagneAgricoleDTO extends BaseDTO { + + private String organisationCoopId; + + // Exemple : "Campagne d'Arachide 2025/2026" + private String designation; + + private String typeCulturePrincipale; + + // Nombre d'hectares au total couvert par les membres de la coop + private BigDecimal surfaceTotaleEstimeeHectares; + + // Tonnes récoltées attendues vs réelles + private BigDecimal volumePrevisionnelTonnes; + private BigDecimal volumeReelTonnes; + + private StatutCampagneAgricole statut; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/analytics/AnalyticsDataResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/analytics/AnalyticsDataResponse.java index d90f17e..b12801d 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/analytics/AnalyticsDataResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/analytics/AnalyticsDataResponse.java @@ -1,265 +1,265 @@ -package dev.lions.unionflow.server.api.dto.analytics; - -import com.fasterxml.jackson.annotation.JsonFormat; -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; -import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; -import jakarta.validation.constraints.DecimalMax; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDateTime; -import java.util.List; -import java.util.Map; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * DTO pour les données analytics UnionFlow - * - *

- * Représente une donnée analytique avec sa valeur, sa métrique associée, sa - * période d'analyse et - * ses métadonnées. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class AnalyticsDataResponse extends BaseDTO { - - private static final long serialVersionUID = 1L; - - /** Type de métrique analysée */ - @NotNull(message = "Le type de métrique est obligatoire") - private TypeMetrique typeMetrique; - - /** Période d'analyse */ - @NotNull(message = "La période d'analyse est obligatoire") - private PeriodeAnalyse periodeAnalyse; - - /** Valeur numérique de la métrique */ - @NotNull(message = "La valeur est obligatoire") - @DecimalMin(value = "0.0", message = "La valeur doit être positive ou nulle") - @Digits(integer = 15, fraction = 4, message = "Format de valeur invalide") - private BigDecimal valeur; - - /** Valeur précédente pour comparaison */ - @DecimalMin(value = "0.0", message = "La valeur précédente doit être positive ou nulle") - @Digits(integer = 15, fraction = 4, message = "Format de valeur précédente invalide") - private BigDecimal valeurPrecedente; - - /** Pourcentage d'évolution par rapport à la période précédente */ - @Digits(integer = 6, fraction = 2, message = "Format de pourcentage d'évolution invalide") - private BigDecimal pourcentageEvolution; - - /** Date de début de la période analysée */ - @NotNull(message = "La date de début est obligatoire") - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateDebut; - - /** Date de fin de la période analysée */ - @NotNull(message = "La date de fin est obligatoire") - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateFin; - - /** Date de calcul de la métrique */ - @NotNull(message = "La date de calcul est obligatoire") - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateCalcul; - - /** Identifiant de l'organisation (optionnel pour filtrage) */ - private UUID organisationId; - - /** Nom de l'organisation */ - @Size(max = 200, message = "Le nom de l'organisation ne peut pas dépasser 200 caractères") - private String nomOrganisation; - - /** Identifiant de l'utilisateur qui a demandé le calcul */ - private UUID utilisateurId; - - /** Nom de l'utilisateur qui a demandé le calcul */ - @Size(max = 200, message = "Le nom de l'utilisateur ne peut pas dépasser 200 caractères") - private String nomUtilisateur; - - /** Libellé personnalisé de la métrique */ - @Size(max = 300, message = "Le libellé personnalisé ne peut pas dépasser 300 caractères") - private String libellePersonnalise; - - /** Description ou commentaire sur la métrique */ - @Size(max = 1000, message = "La description ne peut pas dépasser 1000 caractères") - private String description; - - /** Données détaillées pour les graphiques (format JSON) */ - @Size(max = 10000, message = "Les données détaillées ne peuvent pas dépasser 10000 caractères") - private String donneesDetaillees; - - /** Configuration du graphique (couleurs, type, etc.) */ - @Size(max = 2000, message = "La configuration graphique ne peut pas dépasser 2000 caractères") - private String configurationGraphique; - - /** Métadonnées additionnelles */ - private Map metadonnees; - - /** Indicateur de fiabilité des données (0-100) */ - @DecimalMin(value = "0.0", message = "L'indicateur de fiabilité doit être positif") - @DecimalMax(value = "100.0", message = "L'indicateur de fiabilité ne peut pas dépasser 100") - @Digits(integer = 3, fraction = 1, message = "Format d'indicateur de fiabilité invalide") - private BigDecimal indicateurFiabilite; - - /** Nombre d'éléments analysés pour calculer cette métrique */ - @DecimalMin(value = "0", message = "Le nombre d'éléments doit être positif") - private Integer nombreElementsAnalyses; - - /** Temps de calcul en millisecondes */ - @DecimalMin(value = "0", message = "Le temps de calcul doit être positif") - private Long tempsCalculMs; - - /** Indicateur si la métrique est en temps réel */ - @Builder.Default - private Boolean tempsReel = false; - - /** Indicateur si la métrique nécessite une mise à jour */ - @Builder.Default - private Boolean necessiteMiseAJour = false; - - /** Niveau de priorité de la métrique (1=faible, 5=critique) */ - @DecimalMin(value = "1", message = "Le niveau de priorité minimum est 1") - @DecimalMax(value = "5", message = "Le niveau de priorité maximum est 5") - private Integer niveauPriorite; - - /** Tags pour catégoriser la métrique */ - private List tags; - - // === MÉTHODES UTILITAIRES === - - /** - * Retourne le libellé à afficher (personnalisé ou par défaut) - * - * @return Le libellé à afficher - */ - public String getLibelleAffichage() { - return libellePersonnalise != null && !libellePersonnalise.trim().isEmpty() - ? libellePersonnalise - : typeMetrique.getLibelle(); - } - - /** - * Retourne l'unité de mesure de la métrique - * - * @return L'unité de mesure - */ - public String getUnite() { - return typeMetrique.getUnite(); - } - - /** - * Retourne l'icône de la métrique - * - * @return L'icône Material Design - */ - public String getIcone() { - return typeMetrique.getIcone(); - } - - /** - * Retourne la couleur de la métrique - * - * @return Le code couleur hexadécimal - */ - public String getCouleur() { - return typeMetrique.getCouleur(); - } - - /** - * Vérifie si la métrique a évolué positivement - * - * @return true si l'évolution est positive - */ - public boolean hasEvolutionPositive() { - return pourcentageEvolution != null && pourcentageEvolution.compareTo(BigDecimal.ZERO) > 0; - } - - /** - * Vérifie si la métrique a évolué négativement - * - * @return true si l'évolution est négative - */ - public boolean hasEvolutionNegative() { - return pourcentageEvolution != null && pourcentageEvolution.compareTo(BigDecimal.ZERO) < 0; - } - - /** - * Vérifie si la métrique est stable (pas d'évolution) - * - * @return true si l'évolution est nulle - */ - public boolean isStable() { - return pourcentageEvolution != null && pourcentageEvolution.compareTo(BigDecimal.ZERO) == 0; - } - - /** - * Retourne la tendance sous forme de texte - * - * @return "hausse", "baisse" ou "stable" - */ - public String getTendance() { - if (hasEvolutionPositive()) - return "hausse"; - if (hasEvolutionNegative()) - return "baisse"; - return "stable"; - } - - /** - * Vérifie si les données sont fiables (indicateur > 80) - * - * @return true si les données sont considérées comme fiables - */ - public boolean isDonneesFiables() { - return indicateurFiabilite != null - && indicateurFiabilite.compareTo(new BigDecimal("80.0")) >= 0; - } - - /** - * Vérifie si la métrique est critique (priorité >= 4) - * - * @return true si la métrique est critique - */ - public boolean isCritique() { - return niveauPriorite != null && niveauPriorite >= 4; - } - - /** - * Constructeur avec les champs essentiels - * - * @param typeMetrique Le type de métrique - * @param periodeAnalyse La période d'analyse - * @param valeur La valeur de la métrique - */ - public AnalyticsDataResponse( - TypeMetrique typeMetrique, PeriodeAnalyse periodeAnalyse, BigDecimal valeur) { - super(); - this.typeMetrique = typeMetrique; - this.periodeAnalyse = periodeAnalyse; - this.valeur = valeur; - this.dateCalcul = LocalDateTime.now(); - this.dateDebut = periodeAnalyse.getDateDebut(); - this.dateFin = periodeAnalyse.getDateFin(); - this.tempsReel = false; - this.necessiteMiseAJour = false; - this.niveauPriorite = 3; // Priorité normale par défaut - this.indicateurFiabilite = new BigDecimal("95.0"); // Fiabilité élevée par défaut - } -} +package dev.lions.unionflow.server.api.dto.analytics; + +import com.fasterxml.jackson.annotation.JsonFormat; +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; +import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; +import jakarta.validation.constraints.DecimalMax; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDateTime; +import java.util.List; +import java.util.Map; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * DTO pour les données analytics UnionFlow + * + *

+ * Représente une donnée analytique avec sa valeur, sa métrique associée, sa + * période d'analyse et + * ses métadonnées. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class AnalyticsDataResponse extends BaseDTO { + + private static final long serialVersionUID = 1L; + + /** Type de métrique analysée */ + @NotNull(message = "Le type de métrique est obligatoire") + private TypeMetrique typeMetrique; + + /** Période d'analyse */ + @NotNull(message = "La période d'analyse est obligatoire") + private PeriodeAnalyse periodeAnalyse; + + /** Valeur numérique de la métrique */ + @NotNull(message = "La valeur est obligatoire") + @DecimalMin(value = "0.0", message = "La valeur doit être positive ou nulle") + @Digits(integer = 15, fraction = 4, message = "Format de valeur invalide") + private BigDecimal valeur; + + /** Valeur précédente pour comparaison */ + @DecimalMin(value = "0.0", message = "La valeur précédente doit être positive ou nulle") + @Digits(integer = 15, fraction = 4, message = "Format de valeur précédente invalide") + private BigDecimal valeurPrecedente; + + /** Pourcentage d'évolution par rapport à la période précédente */ + @Digits(integer = 6, fraction = 2, message = "Format de pourcentage d'évolution invalide") + private BigDecimal pourcentageEvolution; + + /** Date de début de la période analysée */ + @NotNull(message = "La date de début est obligatoire") + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateDebut; + + /** Date de fin de la période analysée */ + @NotNull(message = "La date de fin est obligatoire") + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateFin; + + /** Date de calcul de la métrique */ + @NotNull(message = "La date de calcul est obligatoire") + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateCalcul; + + /** Identifiant de l'organisation (optionnel pour filtrage) */ + private UUID organisationId; + + /** Nom de l'organisation */ + @Size(max = 200, message = "Le nom de l'organisation ne peut pas dépasser 200 caractères") + private String nomOrganisation; + + /** Identifiant de l'utilisateur qui a demandé le calcul */ + private UUID utilisateurId; + + /** Nom de l'utilisateur qui a demandé le calcul */ + @Size(max = 200, message = "Le nom de l'utilisateur ne peut pas dépasser 200 caractères") + private String nomUtilisateur; + + /** Libellé personnalisé de la métrique */ + @Size(max = 300, message = "Le libellé personnalisé ne peut pas dépasser 300 caractères") + private String libellePersonnalise; + + /** Description ou commentaire sur la métrique */ + @Size(max = 1000, message = "La description ne peut pas dépasser 1000 caractères") + private String description; + + /** Données détaillées pour les graphiques (format JSON) */ + @Size(max = 10000, message = "Les données détaillées ne peuvent pas dépasser 10000 caractères") + private String donneesDetaillees; + + /** Configuration du graphique (couleurs, type, etc.) */ + @Size(max = 2000, message = "La configuration graphique ne peut pas dépasser 2000 caractères") + private String configurationGraphique; + + /** Métadonnées additionnelles */ + private Map metadonnees; + + /** Indicateur de fiabilité des données (0-100) */ + @DecimalMin(value = "0.0", message = "L'indicateur de fiabilité doit être positif") + @DecimalMax(value = "100.0", message = "L'indicateur de fiabilité ne peut pas dépasser 100") + @Digits(integer = 3, fraction = 1, message = "Format d'indicateur de fiabilité invalide") + private BigDecimal indicateurFiabilite; + + /** Nombre d'éléments analysés pour calculer cette métrique */ + @DecimalMin(value = "0", message = "Le nombre d'éléments doit être positif") + private Integer nombreElementsAnalyses; + + /** Temps de calcul en millisecondes */ + @DecimalMin(value = "0", message = "Le temps de calcul doit être positif") + private Long tempsCalculMs; + + /** Indicateur si la métrique est en temps réel */ + @Builder.Default + private Boolean tempsReel = false; + + /** Indicateur si la métrique nécessite une mise à jour */ + @Builder.Default + private Boolean necessiteMiseAJour = false; + + /** Niveau de priorité de la métrique (1=faible, 5=critique) */ + @DecimalMin(value = "1", message = "Le niveau de priorité minimum est 1") + @DecimalMax(value = "5", message = "Le niveau de priorité maximum est 5") + private Integer niveauPriorite; + + /** Tags pour catégoriser la métrique */ + private List tags; + + // === MÉTHODES UTILITAIRES === + + /** + * Retourne le libellé à afficher (personnalisé ou par défaut) + * + * @return Le libellé à afficher + */ + public String getLibelleAffichage() { + return libellePersonnalise != null && !libellePersonnalise.trim().isEmpty() + ? libellePersonnalise + : typeMetrique.getLibelle(); + } + + /** + * Retourne l'unité de mesure de la métrique + * + * @return L'unité de mesure + */ + public String getUnite() { + return typeMetrique.getUnite(); + } + + /** + * Retourne l'icône de la métrique + * + * @return L'icône Material Design + */ + public String getIcone() { + return typeMetrique.getIcone(); + } + + /** + * Retourne la couleur de la métrique + * + * @return Le code couleur hexadécimal + */ + public String getCouleur() { + return typeMetrique.getCouleur(); + } + + /** + * Vérifie si la métrique a évolué positivement + * + * @return true si l'évolution est positive + */ + public boolean hasEvolutionPositive() { + return pourcentageEvolution != null && pourcentageEvolution.compareTo(BigDecimal.ZERO) > 0; + } + + /** + * Vérifie si la métrique a évolué négativement + * + * @return true si l'évolution est négative + */ + public boolean hasEvolutionNegative() { + return pourcentageEvolution != null && pourcentageEvolution.compareTo(BigDecimal.ZERO) < 0; + } + + /** + * Vérifie si la métrique est stable (pas d'évolution) + * + * @return true si l'évolution est nulle + */ + public boolean isStable() { + return pourcentageEvolution != null && pourcentageEvolution.compareTo(BigDecimal.ZERO) == 0; + } + + /** + * Retourne la tendance sous forme de texte + * + * @return "hausse", "baisse" ou "stable" + */ + public String getTendance() { + if (hasEvolutionPositive()) + return "hausse"; + if (hasEvolutionNegative()) + return "baisse"; + return "stable"; + } + + /** + * Vérifie si les données sont fiables (indicateur > 80) + * + * @return true si les données sont considérées comme fiables + */ + public boolean isDonneesFiables() { + return indicateurFiabilite != null + && indicateurFiabilite.compareTo(new BigDecimal("80.0")) >= 0; + } + + /** + * Vérifie si la métrique est critique (priorité >= 4) + * + * @return true si la métrique est critique + */ + public boolean isCritique() { + return niveauPriorite != null && niveauPriorite >= 4; + } + + /** + * Constructeur avec les champs essentiels + * + * @param typeMetrique Le type de métrique + * @param periodeAnalyse La période d'analyse + * @param valeur La valeur de la métrique + */ + public AnalyticsDataResponse( + TypeMetrique typeMetrique, PeriodeAnalyse periodeAnalyse, BigDecimal valeur) { + super(); + this.typeMetrique = typeMetrique; + this.periodeAnalyse = periodeAnalyse; + this.valeur = valeur; + this.dateCalcul = LocalDateTime.now(); + this.dateDebut = periodeAnalyse.getDateDebut(); + this.dateFin = periodeAnalyse.getDateFin(); + this.tempsReel = false; + this.necessiteMiseAJour = false; + this.niveauPriorite = 3; // Priorité normale par défaut + this.indicateurFiabilite = new BigDecimal("95.0"); // Fiabilité élevée par défaut + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/analytics/DashboardWidgetResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/analytics/DashboardWidgetResponse.java index 528989d..6dfe8e3 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/analytics/DashboardWidgetResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/analytics/DashboardWidgetResponse.java @@ -1,350 +1,350 @@ -package dev.lions.unionflow.server.api.dto.analytics; - -import com.fasterxml.jackson.annotation.JsonFormat; -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; -import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; -import jakarta.validation.constraints.DecimalMax; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import java.time.LocalDateTime; -import java.util.Map; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * DTO pour les widgets de tableau de bord analytics UnionFlow - * - *

Représente un widget personnalisable affiché sur le tableau de bord avec sa configuration, sa - * position et ses données. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class DashboardWidgetResponse extends BaseDTO { - - private static final long serialVersionUID = 1L; - - /** Titre du widget */ - @NotBlank(message = "Le titre du widget est obligatoire") - @Size(min = 3, max = 200, message = "Le titre du widget doit contenir entre 3 et 200 caractères") - private String titre; - - /** Description du widget */ - @Size(max = 500, message = "La description ne peut pas dépasser 500 caractères") - private String description; - - /** Type de widget (kpi, chart, table, gauge, progress, text) */ - @NotBlank(message = "Le type de widget est obligatoire") - @Size(max = 50, message = "Le type de widget ne peut pas dépasser 50 caractères") - private String typeWidget; - - /** Type de métrique affiché */ - private TypeMetrique typeMetrique; - - /** Période d'analyse */ - private PeriodeAnalyse periodeAnalyse; - - /** Identifiant de l'organisation (optionnel pour filtrage) */ - private UUID organisationId; - - /** Nom de l'organisation */ - @Size(max = 200, message = "Le nom de l'organisation ne peut pas dépasser 200 caractères") - private String nomOrganisation; - - /** Identifiant de l'utilisateur propriétaire */ - @NotNull(message = "L'identifiant de l'utilisateur propriétaire est obligatoire") - private UUID utilisateurProprietaireId; - - /** Nom de l'utilisateur propriétaire */ - @Size( - max = 200, - message = "Le nom de l'utilisateur propriétaire ne peut pas dépasser 200 caractères") - private String nomUtilisateurProprietaire; - - /** Position X du widget sur la grille */ - @NotNull(message = "La position X est obligatoire") - @DecimalMin(value = "0", message = "La position X doit être positive ou nulle") - private Integer positionX; - - /** Position Y du widget sur la grille */ - @NotNull(message = "La position Y est obligatoire") - @DecimalMin(value = "0", message = "La position Y doit être positive ou nulle") - private Integer positionY; - - /** Largeur du widget (en unités de grille) */ - @NotNull(message = "La largeur est obligatoire") - @DecimalMin(value = "1", message = "La largeur minimum est 1") - @DecimalMax(value = "12", message = "La largeur maximum est 12") - private Integer largeur; - - /** Hauteur du widget (en unités de grille) */ - @NotNull(message = "La hauteur est obligatoire") - @DecimalMin(value = "1", message = "La hauteur minimum est 1") - @DecimalMax(value = "12", message = "La hauteur maximum est 12") - private Integer hauteur; - - /** Ordre d'affichage (z-index) */ - @DecimalMin(value = "0", message = "L'ordre d'affichage doit être positif ou nul") - @Builder.Default - private Integer ordreAffichage = 0; - - /** Configuration visuelle du widget */ - @Size(max = 5000, message = "La configuration visuelle ne peut pas dépasser 5000 caractères") - private String configurationVisuelle; - - /** Couleur principale du widget */ - @Size(max = 7, message = "La couleur doit être au format #RRGGBB") - private String couleurPrincipale; - - /** Couleur secondaire du widget */ - @Size(max = 7, message = "La couleur secondaire doit être au format #RRGGBB") - private String couleurSecondaire; - - /** Icône du widget */ - @Size(max = 50, message = "L'icône ne peut pas dépasser 50 caractères") - private String icone; - - /** Indicateur si le widget est visible */ - @Builder.Default private Boolean visible = true; - - /** Indicateur si le widget est redimensionnable */ - @Builder.Default private Boolean redimensionnable = true; - - /** Indicateur si le widget est déplaçable */ - @Builder.Default private Boolean deplacable = true; - - /** Indicateur si le widget peut être supprimé */ - @Builder.Default private Boolean supprimable = true; - - /** Indicateur si le widget se met à jour automatiquement */ - @Builder.Default private Boolean miseAJourAutomatique = true; - - /** Fréquence de mise à jour en secondes */ - @DecimalMin(value = "30", message = "La fréquence minimum est 30 secondes") - @Builder.Default - private Integer frequenceMiseAJourSecondes = 300; // 5 minutes par défaut - - /** Date de dernière mise à jour des données */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateDerniereMiseAJour; - - /** Prochaine mise à jour programmée */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime prochaineMiseAJour; - - /** Données du widget (format JSON) */ - @Size(max = 50000, message = "Les données du widget ne peuvent pas dépasser 50000 caractères") - private String donneesWidget; - - /** Configuration des filtres */ - private Map configurationFiltres; - - /** Configuration des alertes */ - private Map configurationAlertes; - - /** Seuil d'alerte bas */ - private Double seuilAlerteBas; - - /** Seuil d'alerte haut */ - private Double seuilAlerteHaut; - - /** Indicateur si une alerte est active */ - @Builder.Default private Boolean alerteActive = false; - - /** Message d'alerte actuel */ - @Size(max = 500, message = "Le message d'alerte ne peut pas dépasser 500 caractères") - private String messageAlerte; - - /** Type d'alerte (info, warning, error, success) */ - @Size(max = 20, message = "Le type d'alerte ne peut pas dépasser 20 caractères") - private String typeAlerte; - - /** Permissions d'accès au widget */ - @Size(max = 1000, message = "Les permissions ne peuvent pas dépasser 1000 caractères") - private String permissions; - - /** Rôles autorisés à voir le widget */ - @Size(max = 500, message = "Les rôles autorisés ne peuvent pas dépasser 500 caractères") - private String rolesAutorises; - - /** Template personnalisé du widget */ - @Size(max = 10000, message = "Le template personnalisé ne peut pas dépasser 10000 caractères") - private String templatePersonnalise; - - /** CSS personnalisé du widget */ - @Size(max = 5000, message = "Le CSS personnalisé ne peut pas dépasser 5000 caractères") - private String cssPersonnalise; - - /** JavaScript personnalisé du widget */ - @Size(max = 10000, message = "Le JavaScript personnalisé ne peut pas dépasser 10000 caractères") - private String javascriptPersonnalise; - - /** Métadonnées additionnelles */ - private Map metadonnees; - - /** Nombre de vues du widget */ - @DecimalMin(value = "0", message = "Le nombre de vues doit être positif") - @Builder.Default - private Long nombreVues = 0L; - - /** Nombre d'interactions avec le widget */ - @DecimalMin(value = "0", message = "Le nombre d'interactions doit être positif") - @Builder.Default - private Long nombreInteractions = 0L; - - /** Temps moyen passé sur le widget (en secondes) */ - @DecimalMin(value = "0", message = "Le temps moyen doit être positif") - private Integer tempsMoyenSecondes; - - /** Taux d'erreur du widget (en pourcentage) */ - @DecimalMin(value = "0.0", message = "Le taux d'erreur doit être positif") - @DecimalMax(value = "100.0", message = "Le taux d'erreur ne peut pas dépasser 100%") - @Builder.Default - private Double tauxErreur = 0.0; - - /** Date de dernière erreur */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateDerniereErreur; - - /** Message de dernière erreur */ - @Size(max = 1000, message = "Le message d'erreur ne peut pas dépasser 1000 caractères") - private String messageDerniereErreur; - - // === MÉTHODES UTILITAIRES === - - /** - * Retourne le libellé de la métrique si définie - * - * @return Le libellé de la métrique ou null - */ - public String getLibelleMetrique() { - return typeMetrique != null ? typeMetrique.getLibelle() : null; - } - - /** - * Retourne l'unité de mesure si métrique définie - * - * @return L'unité de mesure ou chaîne vide - */ - public String getUnite() { - return typeMetrique != null ? typeMetrique.getUnite() : ""; - } - - /** - * Retourne l'icône de la métrique ou l'icône personnalisée - * - * @return L'icône à afficher - */ - public String getIconeAffichage() { - if (icone != null && !icone.trim().isEmpty()) { - return icone; - } - return typeMetrique != null ? typeMetrique.getIcone() : "dashboard"; - } - - /** - * Retourne la couleur de la métrique ou la couleur personnalisée - * - * @return La couleur à utiliser - */ - public String getCouleurAffichage() { - if (couleurPrincipale != null && !couleurPrincipale.trim().isEmpty()) { - return couleurPrincipale; - } - return typeMetrique != null ? typeMetrique.getCouleur() : "#757575"; - } - - /** - * Vérifie si le widget nécessite une mise à jour - * - * @return true si une mise à jour est nécessaire - */ - public boolean necessiteMiseAJour() { - return miseAJourAutomatique - && prochaineMiseAJour != null - && prochaineMiseAJour.isBefore(LocalDateTime.now()); - } - - /** - * Vérifie si le widget est interactif - * - * @return true si le widget permet des interactions - */ - public boolean isInteractif() { - return "chart".equals(typeWidget) || "table".equals(typeWidget) || "gauge".equals(typeWidget); - } - - /** - * Vérifie si le widget affiche des données temps réel - * - * @return true si le widget est en temps réel - */ - /** Indique si la fréquence est en temps réel (pour couverture branches). */ - private boolean isFrequenceTempsReel() { - if (frequenceMiseAJourSecondes == null) return false; - return frequenceMiseAJourSecondes <= 60; - } - - public boolean isTempsReel() { - return isFrequenceTempsReel(); - } - - /** - * Retourne la taille du widget (surface occupée) - * - * @return La surface en unités de grille - */ - public int getTailleWidget() { - return largeur * hauteur; - } - - /** - * Vérifie si le widget est grand (surface > 6) - * - * @return true si le widget est considéré comme grand - */ - public boolean isWidgetGrand() { - return getTailleWidget() > 6; - } - - /** - * Vérifie si le widget a des erreurs récentes (< 24h) - * - * @return true si des erreurs récentes sont détectées - */ - public boolean hasErreursRecentes() { - return dateDerniereErreur != null - && dateDerniereErreur.isAfter(LocalDateTime.now().minusHours(24)); - } - - /** - * Retourne le statut du widget - * - * @return "actif", "erreur", "inactif" ou "maintenance" - */ - /** Indique si le taux d'erreur déclenche le statut maintenance (pour couverture branches). */ - private boolean isTauxErreurMaintenance() { - if (tauxErreur == null) return false; - return tauxErreur > 10.0; - } - - public String getStatutWidget() { - if (hasErreursRecentes()) return "erreur"; - if (!visible) return "inactif"; - if (isTauxErreurMaintenance()) return "maintenance"; - return "actif"; - } -} +package dev.lions.unionflow.server.api.dto.analytics; + +import com.fasterxml.jackson.annotation.JsonFormat; +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; +import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; +import jakarta.validation.constraints.DecimalMax; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import java.time.LocalDateTime; +import java.util.Map; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * DTO pour les widgets de tableau de bord analytics UnionFlow + * + *

Représente un widget personnalisable affiché sur le tableau de bord avec sa configuration, sa + * position et ses données. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class DashboardWidgetResponse extends BaseDTO { + + private static final long serialVersionUID = 1L; + + /** Titre du widget */ + @NotBlank(message = "Le titre du widget est obligatoire") + @Size(min = 3, max = 200, message = "Le titre du widget doit contenir entre 3 et 200 caractères") + private String titre; + + /** Description du widget */ + @Size(max = 500, message = "La description ne peut pas dépasser 500 caractères") + private String description; + + /** Type de widget (kpi, chart, table, gauge, progress, text) */ + @NotBlank(message = "Le type de widget est obligatoire") + @Size(max = 50, message = "Le type de widget ne peut pas dépasser 50 caractères") + private String typeWidget; + + /** Type de métrique affiché */ + private TypeMetrique typeMetrique; + + /** Période d'analyse */ + private PeriodeAnalyse periodeAnalyse; + + /** Identifiant de l'organisation (optionnel pour filtrage) */ + private UUID organisationId; + + /** Nom de l'organisation */ + @Size(max = 200, message = "Le nom de l'organisation ne peut pas dépasser 200 caractères") + private String nomOrganisation; + + /** Identifiant de l'utilisateur propriétaire */ + @NotNull(message = "L'identifiant de l'utilisateur propriétaire est obligatoire") + private UUID utilisateurProprietaireId; + + /** Nom de l'utilisateur propriétaire */ + @Size( + max = 200, + message = "Le nom de l'utilisateur propriétaire ne peut pas dépasser 200 caractères") + private String nomUtilisateurProprietaire; + + /** Position X du widget sur la grille */ + @NotNull(message = "La position X est obligatoire") + @DecimalMin(value = "0", message = "La position X doit être positive ou nulle") + private Integer positionX; + + /** Position Y du widget sur la grille */ + @NotNull(message = "La position Y est obligatoire") + @DecimalMin(value = "0", message = "La position Y doit être positive ou nulle") + private Integer positionY; + + /** Largeur du widget (en unités de grille) */ + @NotNull(message = "La largeur est obligatoire") + @DecimalMin(value = "1", message = "La largeur minimum est 1") + @DecimalMax(value = "12", message = "La largeur maximum est 12") + private Integer largeur; + + /** Hauteur du widget (en unités de grille) */ + @NotNull(message = "La hauteur est obligatoire") + @DecimalMin(value = "1", message = "La hauteur minimum est 1") + @DecimalMax(value = "12", message = "La hauteur maximum est 12") + private Integer hauteur; + + /** Ordre d'affichage (z-index) */ + @DecimalMin(value = "0", message = "L'ordre d'affichage doit être positif ou nul") + @Builder.Default + private Integer ordreAffichage = 0; + + /** Configuration visuelle du widget */ + @Size(max = 5000, message = "La configuration visuelle ne peut pas dépasser 5000 caractères") + private String configurationVisuelle; + + /** Couleur principale du widget */ + @Size(max = 7, message = "La couleur doit être au format #RRGGBB") + private String couleurPrincipale; + + /** Couleur secondaire du widget */ + @Size(max = 7, message = "La couleur secondaire doit être au format #RRGGBB") + private String couleurSecondaire; + + /** Icône du widget */ + @Size(max = 50, message = "L'icône ne peut pas dépasser 50 caractères") + private String icone; + + /** Indicateur si le widget est visible */ + @Builder.Default private Boolean visible = true; + + /** Indicateur si le widget est redimensionnable */ + @Builder.Default private Boolean redimensionnable = true; + + /** Indicateur si le widget est déplaçable */ + @Builder.Default private Boolean deplacable = true; + + /** Indicateur si le widget peut être supprimé */ + @Builder.Default private Boolean supprimable = true; + + /** Indicateur si le widget se met à jour automatiquement */ + @Builder.Default private Boolean miseAJourAutomatique = true; + + /** Fréquence de mise à jour en secondes */ + @DecimalMin(value = "30", message = "La fréquence minimum est 30 secondes") + @Builder.Default + private Integer frequenceMiseAJourSecondes = 300; // 5 minutes par défaut + + /** Date de dernière mise à jour des données */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateDerniereMiseAJour; + + /** Prochaine mise à jour programmée */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime prochaineMiseAJour; + + /** Données du widget (format JSON) */ + @Size(max = 50000, message = "Les données du widget ne peuvent pas dépasser 50000 caractères") + private String donneesWidget; + + /** Configuration des filtres */ + private Map configurationFiltres; + + /** Configuration des alertes */ + private Map configurationAlertes; + + /** Seuil d'alerte bas */ + private Double seuilAlerteBas; + + /** Seuil d'alerte haut */ + private Double seuilAlerteHaut; + + /** Indicateur si une alerte est active */ + @Builder.Default private Boolean alerteActive = false; + + /** Message d'alerte actuel */ + @Size(max = 500, message = "Le message d'alerte ne peut pas dépasser 500 caractères") + private String messageAlerte; + + /** Type d'alerte (info, warning, error, success) */ + @Size(max = 20, message = "Le type d'alerte ne peut pas dépasser 20 caractères") + private String typeAlerte; + + /** Permissions d'accès au widget */ + @Size(max = 1000, message = "Les permissions ne peuvent pas dépasser 1000 caractères") + private String permissions; + + /** Rôles autorisés à voir le widget */ + @Size(max = 500, message = "Les rôles autorisés ne peuvent pas dépasser 500 caractères") + private String rolesAutorises; + + /** Template personnalisé du widget */ + @Size(max = 10000, message = "Le template personnalisé ne peut pas dépasser 10000 caractères") + private String templatePersonnalise; + + /** CSS personnalisé du widget */ + @Size(max = 5000, message = "Le CSS personnalisé ne peut pas dépasser 5000 caractères") + private String cssPersonnalise; + + /** JavaScript personnalisé du widget */ + @Size(max = 10000, message = "Le JavaScript personnalisé ne peut pas dépasser 10000 caractères") + private String javascriptPersonnalise; + + /** Métadonnées additionnelles */ + private Map metadonnees; + + /** Nombre de vues du widget */ + @DecimalMin(value = "0", message = "Le nombre de vues doit être positif") + @Builder.Default + private Long nombreVues = 0L; + + /** Nombre d'interactions avec le widget */ + @DecimalMin(value = "0", message = "Le nombre d'interactions doit être positif") + @Builder.Default + private Long nombreInteractions = 0L; + + /** Temps moyen passé sur le widget (en secondes) */ + @DecimalMin(value = "0", message = "Le temps moyen doit être positif") + private Integer tempsMoyenSecondes; + + /** Taux d'erreur du widget (en pourcentage) */ + @DecimalMin(value = "0.0", message = "Le taux d'erreur doit être positif") + @DecimalMax(value = "100.0", message = "Le taux d'erreur ne peut pas dépasser 100%") + @Builder.Default + private Double tauxErreur = 0.0; + + /** Date de dernière erreur */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateDerniereErreur; + + /** Message de dernière erreur */ + @Size(max = 1000, message = "Le message d'erreur ne peut pas dépasser 1000 caractères") + private String messageDerniereErreur; + + // === MÉTHODES UTILITAIRES === + + /** + * Retourne le libellé de la métrique si définie + * + * @return Le libellé de la métrique ou null + */ + public String getLibelleMetrique() { + return typeMetrique != null ? typeMetrique.getLibelle() : null; + } + + /** + * Retourne l'unité de mesure si métrique définie + * + * @return L'unité de mesure ou chaîne vide + */ + public String getUnite() { + return typeMetrique != null ? typeMetrique.getUnite() : ""; + } + + /** + * Retourne l'icône de la métrique ou l'icône personnalisée + * + * @return L'icône à afficher + */ + public String getIconeAffichage() { + if (icone != null && !icone.trim().isEmpty()) { + return icone; + } + return typeMetrique != null ? typeMetrique.getIcone() : "dashboard"; + } + + /** + * Retourne la couleur de la métrique ou la couleur personnalisée + * + * @return La couleur à utiliser + */ + public String getCouleurAffichage() { + if (couleurPrincipale != null && !couleurPrincipale.trim().isEmpty()) { + return couleurPrincipale; + } + return typeMetrique != null ? typeMetrique.getCouleur() : "#757575"; + } + + /** + * Vérifie si le widget nécessite une mise à jour + * + * @return true si une mise à jour est nécessaire + */ + public boolean necessiteMiseAJour() { + return miseAJourAutomatique + && prochaineMiseAJour != null + && prochaineMiseAJour.isBefore(LocalDateTime.now()); + } + + /** + * Vérifie si le widget est interactif + * + * @return true si le widget permet des interactions + */ + public boolean isInteractif() { + return "chart".equals(typeWidget) || "table".equals(typeWidget) || "gauge".equals(typeWidget); + } + + /** + * Vérifie si le widget affiche des données temps réel + * + * @return true si le widget est en temps réel + */ + /** Indique si la fréquence est en temps réel (pour couverture branches). */ + private boolean isFrequenceTempsReel() { + if (frequenceMiseAJourSecondes == null) return false; + return frequenceMiseAJourSecondes <= 60; + } + + public boolean isTempsReel() { + return isFrequenceTempsReel(); + } + + /** + * Retourne la taille du widget (surface occupée) + * + * @return La surface en unités de grille + */ + public int getTailleWidget() { + return largeur * hauteur; + } + + /** + * Vérifie si le widget est grand (surface > 6) + * + * @return true si le widget est considéré comme grand + */ + public boolean isWidgetGrand() { + return getTailleWidget() > 6; + } + + /** + * Vérifie si le widget a des erreurs récentes (< 24h) + * + * @return true si des erreurs récentes sont détectées + */ + public boolean hasErreursRecentes() { + return dateDerniereErreur != null + && dateDerniereErreur.isAfter(LocalDateTime.now().minusHours(24)); + } + + /** + * Retourne le statut du widget + * + * @return "actif", "erreur", "inactif" ou "maintenance" + */ + /** Indique si le taux d'erreur déclenche le statut maintenance (pour couverture branches). */ + private boolean isTauxErreurMaintenance() { + if (tauxErreur == null) return false; + return tauxErreur > 10.0; + } + + public String getStatutWidget() { + if (hasErreursRecentes()) return "erreur"; + if (!visible) return "inactif"; + if (isTauxErreurMaintenance()) return "maintenance"; + return "actif"; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/analytics/KPITrendResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/analytics/KPITrendResponse.java index a0b2c6b..358f426 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/analytics/KPITrendResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/analytics/KPITrendResponse.java @@ -1,309 +1,309 @@ -package dev.lions.unionflow.server.api.dto.analytics; - -import com.fasterxml.jackson.annotation.JsonFormat; -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; -import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; -import jakarta.validation.constraints.DecimalMax; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDateTime; -import java.util.List; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * DTO pour les tendances et évolutions des KPI UnionFlow - * - *

Représente l'évolution d'un KPI dans le temps avec les points de données historiques pour - * générer des graphiques de tendance. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class KPITrendResponse extends BaseDTO { - - private static final long serialVersionUID = 1L; - - /** Type de métrique pour cette tendance */ - @NotNull(message = "Le type de métrique est obligatoire") - private TypeMetrique typeMetrique; - - /** Période d'analyse globale */ - @NotNull(message = "La période d'analyse est obligatoire") - private PeriodeAnalyse periodeAnalyse; - - /** Identifiant de l'organisation (optionnel) */ - private UUID organisationId; - - /** Nom de l'organisation */ - @Size(max = 200, message = "Le nom de l'organisation ne peut pas dépasser 200 caractères") - private String nomOrganisation; - - /** Date de début de la période analysée */ - @NotNull(message = "La date de début est obligatoire") - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateDebut; - - /** Date de fin de la période analysée */ - @NotNull(message = "La date de fin est obligatoire") - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateFin; - - /** Points de données pour la tendance */ - @NotNull(message = "Les points de données sont obligatoires") - private List pointsDonnees; - - /** Valeur actuelle du KPI */ - @NotNull(message = "La valeur actuelle est obligatoire") - @DecimalMin(value = "0.0", message = "La valeur actuelle doit être positive ou nulle") - @Digits(integer = 15, fraction = 4, message = "Format de valeur actuelle invalide") - private BigDecimal valeurActuelle; - - /** Valeur minimale sur la période */ - @DecimalMin(value = "0.0", message = "La valeur minimale doit être positive ou nulle") - @Digits(integer = 15, fraction = 4, message = "Format de valeur minimale invalide") - private BigDecimal valeurMinimale; - - /** Valeur maximale sur la période */ - @DecimalMin(value = "0.0", message = "La valeur maximale doit être positive ou nulle") - @Digits(integer = 15, fraction = 4, message = "Format de valeur maximale invalide") - private BigDecimal valeurMaximale; - - /** Valeur moyenne sur la période */ - @DecimalMin(value = "0.0", message = "La valeur moyenne doit être positive ou nulle") - @Digits(integer = 15, fraction = 4, message = "Format de valeur moyenne invalide") - private BigDecimal valeurMoyenne; - - /** Écart-type des valeurs */ - @DecimalMin(value = "0.0", message = "L'écart-type doit être positif ou nul") - @Digits(integer = 15, fraction = 4, message = "Format d'écart-type invalide") - private BigDecimal ecartType; - - /** Coefficient de variation (écart-type / moyenne) */ - @DecimalMin(value = "0.0", message = "Le coefficient de variation doit être positif ou nul") - @Digits(integer = 6, fraction = 4, message = "Format de coefficient de variation invalide") - private BigDecimal coefficientVariation; - - /** Tendance générale (pente de la régression linéaire) */ - @Digits(integer = 10, fraction = 6, message = "Format de tendance invalide") - private BigDecimal tendanceGenerale; - - /** Coefficient de corrélation R² */ - @DecimalMin(value = "0.0", message = "Le coefficient de corrélation doit être positif ou nul") - @DecimalMax(value = "1.0", message = "Le coefficient de corrélation ne peut pas dépasser 1") - @Digits(integer = 1, fraction = 6, message = "Format de coefficient de corrélation invalide") - private BigDecimal coefficientCorrelation; - - /** Pourcentage d'évolution depuis le début de la période */ - @Digits(integer = 6, fraction = 2, message = "Format de pourcentage d'évolution invalide") - private BigDecimal pourcentageEvolutionGlobale; - - /** Prédiction pour la prochaine période */ - @DecimalMin(value = "0.0", message = "La prédiction doit être positive ou nulle") - @Digits(integer = 15, fraction = 4, message = "Format de prédiction invalide") - private BigDecimal predictionProchainePeriode; - - /** Marge d'erreur de la prédiction (en pourcentage) */ - @DecimalMin(value = "0.0", message = "La marge d'erreur doit être positive ou nulle") - @DecimalMax(value = "100.0", message = "La marge d'erreur ne peut pas dépasser 100%") - @Digits(integer = 3, fraction = 2, message = "Format de marge d'erreur invalide") - private BigDecimal margeErreurPrediction; - - /** Seuil d'alerte bas */ - @DecimalMin(value = "0.0", message = "Le seuil d'alerte bas doit être positif ou nul") - @Digits(integer = 15, fraction = 4, message = "Format de seuil d'alerte bas invalide") - private BigDecimal seuilAlerteBas; - - /** Seuil d'alerte haut */ - @DecimalMin(value = "0.0", message = "Le seuil d'alerte haut doit être positif ou nul") - @Digits(integer = 15, fraction = 4, message = "Format de seuil d'alerte haut invalide") - private BigDecimal seuilAlerteHaut; - - /** Indicateur si une alerte est active */ - @Builder.Default private Boolean alerteActive = false; - - /** Type d'alerte (bas, haut, anomalie) */ - @Size(max = 50, message = "Le type d'alerte ne peut pas dépasser 50 caractères") - private String typeAlerte; - - /** Message d'alerte */ - @Size(max = 500, message = "Le message d'alerte ne peut pas dépasser 500 caractères") - private String messageAlerte; - - /** Configuration du graphique (couleurs, style, etc.) */ - @Size(max = 2000, message = "La configuration graphique ne peut pas dépasser 2000 caractères") - private String configurationGraphique; - - /** Intervalle de regroupement des données */ - @Size(max = 20, message = "L'intervalle de regroupement ne peut pas dépasser 20 caractères") - private String intervalleRegroupement; - - /** Format d'affichage des dates */ - @Size(max = 20, message = "Le format de date ne peut pas dépasser 20 caractères") - private String formatDate; - - /** Date de dernière mise à jour */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateDerniereMiseAJour; - - /** Fréquence de mise à jour en minutes */ - @DecimalMin(value = "1", message = "La fréquence de mise à jour minimum est 1 minute") - private Integer frequenceMiseAJourMinutes; - - // === CLASSES INTERNES === - - /** Classe interne représentant un point de données dans la tendance */ - @Getter - @Setter - @Builder - @NoArgsConstructor - @AllArgsConstructor - public static class PointDonneeDTO { - - /** Date du point de données */ - @NotNull(message = "La date du point de données est obligatoire") - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime date; - - /** Valeur du point de données */ - @NotNull(message = "La valeur du point de données est obligatoire") - @DecimalMin(value = "0.0", message = "La valeur du point doit être positive ou nulle") - @Digits(integer = 15, fraction = 4, message = "Format de valeur du point invalide") - private BigDecimal valeur; - - /** Libellé du point (optionnel) */ - @Size(max = 100, message = "Le libellé du point ne peut pas dépasser 100 caractères") - private String libelle; - - /** Indicateur si le point est une anomalie */ - @Builder.Default private Boolean anomalie = false; - - /** Indicateur si le point est une prédiction */ - @Builder.Default private Boolean prediction = false; - - /** Métadonnées additionnelles du point */ - private String metadonnees; - } - - // === MÉTHODES UTILITAIRES === - - /** - * Retourne le libellé de la métrique - * - * @return Le libellé de la métrique - */ - public String getLibelleMetrique() { - return typeMetrique.getLibelle(); - } - - /** - * Retourne l'unité de mesure - * - * @return L'unité de mesure - */ - public String getUnite() { - return typeMetrique.getUnite(); - } - - /** - * Retourne l'icône de la métrique - * - * @return L'icône Material Design - */ - public String getIcone() { - return typeMetrique.getIcone(); - } - - /** - * Retourne la couleur de la métrique - * - * @return Le code couleur hexadécimal - */ - public String getCouleur() { - return typeMetrique.getCouleur(); - } - - /** - * Vérifie si la tendance est positive - * - * @return true si la tendance générale est positive - */ - public boolean isTendancePositive() { - return tendanceGenerale != null && tendanceGenerale.compareTo(BigDecimal.ZERO) > 0; - } - - /** - * Vérifie si la tendance est négative - * - * @return true si la tendance générale est négative - */ - public boolean isTendanceNegative() { - return tendanceGenerale != null && tendanceGenerale.compareTo(BigDecimal.ZERO) < 0; - } - - /** - * Vérifie si la tendance est stable - * - * @return true si la tendance générale est stable - */ - public boolean isTendanceStable() { - return tendanceGenerale != null && tendanceGenerale.compareTo(BigDecimal.ZERO) == 0; - } - - /** - * Retourne la volatilité du KPI (basée sur le coefficient de variation) - * - * @return "faible", "moyenne" ou "élevée" - */ - public String getVolatilite() { - if (coefficientVariation == null) return "inconnue"; - - BigDecimal cv = coefficientVariation; - if (cv.compareTo(new BigDecimal("0.1")) <= 0) return "faible"; - if (cv.compareTo(new BigDecimal("0.3")) <= 0) return "moyenne"; - return "élevée"; - } - - /** - * Vérifie si la prédiction est fiable (R² > 0.7) - * - * @return true si la prédiction est considérée comme fiable - */ - public boolean isPredictionFiable() { - return coefficientCorrelation != null - && coefficientCorrelation.compareTo(new BigDecimal("0.7")) >= 0; - } - - /** - * Retourne le nombre de points de données - * - * @return Le nombre de points de données - */ - public int getNombrePointsDonnees() { - return pointsDonnees != null ? pointsDonnees.size() : 0; - } - - /** - * Vérifie si des anomalies ont été détectées - * - * @return true si au moins un point est marqué comme anomalie - */ - public boolean hasAnomalies() { - return pointsDonnees != null - && pointsDonnees.stream().anyMatch(point -> Boolean.TRUE.equals(point.getAnomalie())); - } -} +package dev.lions.unionflow.server.api.dto.analytics; + +import com.fasterxml.jackson.annotation.JsonFormat; +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; +import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; +import jakarta.validation.constraints.DecimalMax; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDateTime; +import java.util.List; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * DTO pour les tendances et évolutions des KPI UnionFlow + * + *

Représente l'évolution d'un KPI dans le temps avec les points de données historiques pour + * générer des graphiques de tendance. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class KPITrendResponse extends BaseDTO { + + private static final long serialVersionUID = 1L; + + /** Type de métrique pour cette tendance */ + @NotNull(message = "Le type de métrique est obligatoire") + private TypeMetrique typeMetrique; + + /** Période d'analyse globale */ + @NotNull(message = "La période d'analyse est obligatoire") + private PeriodeAnalyse periodeAnalyse; + + /** Identifiant de l'organisation (optionnel) */ + private UUID organisationId; + + /** Nom de l'organisation */ + @Size(max = 200, message = "Le nom de l'organisation ne peut pas dépasser 200 caractères") + private String nomOrganisation; + + /** Date de début de la période analysée */ + @NotNull(message = "La date de début est obligatoire") + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateDebut; + + /** Date de fin de la période analysée */ + @NotNull(message = "La date de fin est obligatoire") + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateFin; + + /** Points de données pour la tendance */ + @NotNull(message = "Les points de données sont obligatoires") + private List pointsDonnees; + + /** Valeur actuelle du KPI */ + @NotNull(message = "La valeur actuelle est obligatoire") + @DecimalMin(value = "0.0", message = "La valeur actuelle doit être positive ou nulle") + @Digits(integer = 15, fraction = 4, message = "Format de valeur actuelle invalide") + private BigDecimal valeurActuelle; + + /** Valeur minimale sur la période */ + @DecimalMin(value = "0.0", message = "La valeur minimale doit être positive ou nulle") + @Digits(integer = 15, fraction = 4, message = "Format de valeur minimale invalide") + private BigDecimal valeurMinimale; + + /** Valeur maximale sur la période */ + @DecimalMin(value = "0.0", message = "La valeur maximale doit être positive ou nulle") + @Digits(integer = 15, fraction = 4, message = "Format de valeur maximale invalide") + private BigDecimal valeurMaximale; + + /** Valeur moyenne sur la période */ + @DecimalMin(value = "0.0", message = "La valeur moyenne doit être positive ou nulle") + @Digits(integer = 15, fraction = 4, message = "Format de valeur moyenne invalide") + private BigDecimal valeurMoyenne; + + /** Écart-type des valeurs */ + @DecimalMin(value = "0.0", message = "L'écart-type doit être positif ou nul") + @Digits(integer = 15, fraction = 4, message = "Format d'écart-type invalide") + private BigDecimal ecartType; + + /** Coefficient de variation (écart-type / moyenne) */ + @DecimalMin(value = "0.0", message = "Le coefficient de variation doit être positif ou nul") + @Digits(integer = 6, fraction = 4, message = "Format de coefficient de variation invalide") + private BigDecimal coefficientVariation; + + /** Tendance générale (pente de la régression linéaire) */ + @Digits(integer = 10, fraction = 6, message = "Format de tendance invalide") + private BigDecimal tendanceGenerale; + + /** Coefficient de corrélation R² */ + @DecimalMin(value = "0.0", message = "Le coefficient de corrélation doit être positif ou nul") + @DecimalMax(value = "1.0", message = "Le coefficient de corrélation ne peut pas dépasser 1") + @Digits(integer = 1, fraction = 6, message = "Format de coefficient de corrélation invalide") + private BigDecimal coefficientCorrelation; + + /** Pourcentage d'évolution depuis le début de la période */ + @Digits(integer = 6, fraction = 2, message = "Format de pourcentage d'évolution invalide") + private BigDecimal pourcentageEvolutionGlobale; + + /** Prédiction pour la prochaine période */ + @DecimalMin(value = "0.0", message = "La prédiction doit être positive ou nulle") + @Digits(integer = 15, fraction = 4, message = "Format de prédiction invalide") + private BigDecimal predictionProchainePeriode; + + /** Marge d'erreur de la prédiction (en pourcentage) */ + @DecimalMin(value = "0.0", message = "La marge d'erreur doit être positive ou nulle") + @DecimalMax(value = "100.0", message = "La marge d'erreur ne peut pas dépasser 100%") + @Digits(integer = 3, fraction = 2, message = "Format de marge d'erreur invalide") + private BigDecimal margeErreurPrediction; + + /** Seuil d'alerte bas */ + @DecimalMin(value = "0.0", message = "Le seuil d'alerte bas doit être positif ou nul") + @Digits(integer = 15, fraction = 4, message = "Format de seuil d'alerte bas invalide") + private BigDecimal seuilAlerteBas; + + /** Seuil d'alerte haut */ + @DecimalMin(value = "0.0", message = "Le seuil d'alerte haut doit être positif ou nul") + @Digits(integer = 15, fraction = 4, message = "Format de seuil d'alerte haut invalide") + private BigDecimal seuilAlerteHaut; + + /** Indicateur si une alerte est active */ + @Builder.Default private Boolean alerteActive = false; + + /** Type d'alerte (bas, haut, anomalie) */ + @Size(max = 50, message = "Le type d'alerte ne peut pas dépasser 50 caractères") + private String typeAlerte; + + /** Message d'alerte */ + @Size(max = 500, message = "Le message d'alerte ne peut pas dépasser 500 caractères") + private String messageAlerte; + + /** Configuration du graphique (couleurs, style, etc.) */ + @Size(max = 2000, message = "La configuration graphique ne peut pas dépasser 2000 caractères") + private String configurationGraphique; + + /** Intervalle de regroupement des données */ + @Size(max = 20, message = "L'intervalle de regroupement ne peut pas dépasser 20 caractères") + private String intervalleRegroupement; + + /** Format d'affichage des dates */ + @Size(max = 20, message = "Le format de date ne peut pas dépasser 20 caractères") + private String formatDate; + + /** Date de dernière mise à jour */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateDerniereMiseAJour; + + /** Fréquence de mise à jour en minutes */ + @DecimalMin(value = "1", message = "La fréquence de mise à jour minimum est 1 minute") + private Integer frequenceMiseAJourMinutes; + + // === CLASSES INTERNES === + + /** Classe interne représentant un point de données dans la tendance */ + @Getter + @Setter + @Builder + @NoArgsConstructor + @AllArgsConstructor + public static class PointDonneeDTO { + + /** Date du point de données */ + @NotNull(message = "La date du point de données est obligatoire") + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime date; + + /** Valeur du point de données */ + @NotNull(message = "La valeur du point de données est obligatoire") + @DecimalMin(value = "0.0", message = "La valeur du point doit être positive ou nulle") + @Digits(integer = 15, fraction = 4, message = "Format de valeur du point invalide") + private BigDecimal valeur; + + /** Libellé du point (optionnel) */ + @Size(max = 100, message = "Le libellé du point ne peut pas dépasser 100 caractères") + private String libelle; + + /** Indicateur si le point est une anomalie */ + @Builder.Default private Boolean anomalie = false; + + /** Indicateur si le point est une prédiction */ + @Builder.Default private Boolean prediction = false; + + /** Métadonnées additionnelles du point */ + private String metadonnees; + } + + // === MÉTHODES UTILITAIRES === + + /** + * Retourne le libellé de la métrique + * + * @return Le libellé de la métrique + */ + public String getLibelleMetrique() { + return typeMetrique.getLibelle(); + } + + /** + * Retourne l'unité de mesure + * + * @return L'unité de mesure + */ + public String getUnite() { + return typeMetrique.getUnite(); + } + + /** + * Retourne l'icône de la métrique + * + * @return L'icône Material Design + */ + public String getIcone() { + return typeMetrique.getIcone(); + } + + /** + * Retourne la couleur de la métrique + * + * @return Le code couleur hexadécimal + */ + public String getCouleur() { + return typeMetrique.getCouleur(); + } + + /** + * Vérifie si la tendance est positive + * + * @return true si la tendance générale est positive + */ + public boolean isTendancePositive() { + return tendanceGenerale != null && tendanceGenerale.compareTo(BigDecimal.ZERO) > 0; + } + + /** + * Vérifie si la tendance est négative + * + * @return true si la tendance générale est négative + */ + public boolean isTendanceNegative() { + return tendanceGenerale != null && tendanceGenerale.compareTo(BigDecimal.ZERO) < 0; + } + + /** + * Vérifie si la tendance est stable + * + * @return true si la tendance générale est stable + */ + public boolean isTendanceStable() { + return tendanceGenerale != null && tendanceGenerale.compareTo(BigDecimal.ZERO) == 0; + } + + /** + * Retourne la volatilité du KPI (basée sur le coefficient de variation) + * + * @return "faible", "moyenne" ou "élevée" + */ + public String getVolatilite() { + if (coefficientVariation == null) return "inconnue"; + + BigDecimal cv = coefficientVariation; + if (cv.compareTo(new BigDecimal("0.1")) <= 0) return "faible"; + if (cv.compareTo(new BigDecimal("0.3")) <= 0) return "moyenne"; + return "élevée"; + } + + /** + * Vérifie si la prédiction est fiable (R² > 0.7) + * + * @return true si la prédiction est considérée comme fiable + */ + public boolean isPredictionFiable() { + return coefficientCorrelation != null + && coefficientCorrelation.compareTo(new BigDecimal("0.7")) >= 0; + } + + /** + * Retourne le nombre de points de données + * + * @return Le nombre de points de données + */ + public int getNombrePointsDonnees() { + return pointsDonnees != null ? pointsDonnees.size() : 0; + } + + /** + * Vérifie si des anomalies ont été détectées + * + * @return true si au moins un point est marqué comme anomalie + */ + public boolean hasAnomalies() { + return pointsDonnees != null + && pointsDonnees.stream().anyMatch(point -> Boolean.TRUE.equals(point.getAnomalie())); + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/analytics/ReportConfigDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/analytics/ReportConfigDTO.java index cdc2060..01598ba 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/analytics/ReportConfigDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/analytics/ReportConfigDTO.java @@ -1,333 +1,333 @@ -package dev.lions.unionflow.server.api.dto.analytics; - -import com.fasterxml.jackson.annotation.JsonFormat; -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.analytics.FormatExport; -import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; -import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; -import jakarta.validation.Valid; -import jakarta.validation.constraints.DecimalMax; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import java.time.LocalDateTime; -import java.util.List; -import java.util.Map; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * DTO pour la configuration des rapports analytics UnionFlow - * - *

Représente la configuration d'un rapport personnalisé avec ses métriques, sa mise en forme et - * ses paramètres d'export. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class ReportConfigDTO extends BaseDTO { - - private static final long serialVersionUID = 1L; - - /** Nom du rapport */ - @NotBlank(message = "Le nom du rapport est obligatoire") - @Size(min = 3, max = 200, message = "Le nom du rapport doit contenir entre 3 et 200 caractères") - private String nom; - - /** Description du rapport */ - @Size(max = 1000, message = "La description ne peut pas dépasser 1000 caractères") - private String description; - - /** Type de rapport (executif, analytique, technique, operationnel) */ - @NotBlank(message = "Le type de rapport est obligatoire") - @Size(max = 50, message = "Le type de rapport ne peut pas dépasser 50 caractères") - private String typeRapport; - - /** Période d'analyse par défaut */ - @NotNull(message = "La période d'analyse est obligatoire") - private PeriodeAnalyse periodeAnalyse; - - /** Date de début personnalisée (si période personnalisée) */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateDebutPersonnalisee; - - /** Date de fin personnalisée (si période personnalisée) */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateFinPersonnalisee; - - /** Identifiant de l'organisation (optionnel pour filtrage) */ - private UUID organisationId; - - /** Nom de l'organisation */ - @Size(max = 200, message = "Le nom de l'organisation ne peut pas dépasser 200 caractères") - private String nomOrganisation; - - /** Identifiant de l'utilisateur créateur */ - @NotNull(message = "L'identifiant de l'utilisateur créateur est obligatoire") - private UUID utilisateurCreateurId; - - /** Nom de l'utilisateur créateur */ - @Size(max = 200, message = "Le nom de l'utilisateur créateur ne peut pas dépasser 200 caractères") - private String nomUtilisateurCreateur; - - /** Métriques incluses dans le rapport */ - @NotNull(message = "Les métriques sont obligatoires") - @Valid - private List metriques; - - /** Sections du rapport */ - @Valid private List sections; - - /** Format d'export par défaut */ - @NotNull(message = "Le format d'export est obligatoire") - private FormatExport formatExport; - - /** Formats d'export autorisés */ - private List formatsExportAutorises; - - /** Modèle de rapport à utiliser */ - @Size(max = 100, message = "Le modèle de rapport ne peut pas dépasser 100 caractères") - private String modeleRapport; - - /** Configuration de la mise en page */ - @Size( - max = 2000, - message = "La configuration de mise en page ne peut pas dépasser 2000 caractères") - private String configurationMiseEnPage; - - /** Logo personnalisé (URL ou base64) */ - @Size(max = 5000, message = "Le logo personnalisé ne peut pas dépasser 5000 caractères") - private String logoPersonnalise; - - /** Couleurs personnalisées du rapport */ - private Map couleursPersonnalisees; - - /** Indicateur si le rapport est public */ - @Builder.Default private Boolean rapportPublic = false; - - /** Indicateur si le rapport est automatique */ - @Builder.Default private Boolean rapportAutomatique = false; - - /** Fréquence de génération automatique (en heures) */ - @DecimalMin(value = "1", message = "La fréquence minimum est 1 heure") - private Integer frequenceGenerationHeures; - - /** Prochaine génération automatique */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime prochaineGeneration; - - /** Liste des destinataires pour l'envoi automatique */ - private List destinatairesEmail; - - /** Objet de l'email pour l'envoi automatique */ - @Size(max = 200, message = "L'objet de l'email ne peut pas dépasser 200 caractères") - private String objetEmail; - - /** Corps de l'email pour l'envoi automatique */ - @Size(max = 2000, message = "Le corps de l'email ne peut pas dépasser 2000 caractères") - private String corpsEmail; - - /** Paramètres de filtrage avancé */ - private Map parametresFiltrage; - - /** Tags pour catégoriser le rapport */ - private List tags; - - /** Niveau de confidentialité (1=public, 5=confidentiel) */ - @DecimalMin(value = "1", message = "Le niveau de confidentialité minimum est 1") - @DecimalMax(value = "5", message = "Le niveau de confidentialité maximum est 5") - @Builder.Default - private Integer niveauConfidentialite = 1; - - /** Date de dernière génération */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateDerniereGeneration; - - /** Nombre de générations effectuées */ - @DecimalMin(value = "0", message = "Le nombre de générations doit être positif") - @Builder.Default - private Integer nombreGenerations = 0; - - /** Taille moyenne des rapports générés (en KB) */ - @DecimalMin(value = "0", message = "La taille moyenne doit être positive") - private Long tailleMoyenneKB; - - /** Temps moyen de génération (en secondes) */ - @DecimalMin(value = "0", message = "Le temps moyen de génération doit être positif") - private Integer tempsMoyenGenerationSecondes; - - // === CLASSES INTERNES === - - /** Configuration d'une métrique dans le rapport */ - @Getter - @Setter - @Builder - @NoArgsConstructor - @AllArgsConstructor - public static class MetriqueConfigDTO { - - /** Type de métrique */ - @NotNull(message = "Le type de métrique est obligatoire") - private TypeMetrique typeMetrique; - - /** Libellé personnalisé */ - @Size(max = 200, message = "Le libellé personnalisé ne peut pas dépasser 200 caractères") - private String libellePersonnalise; - - /** Position dans le rapport (ordre d'affichage) */ - @DecimalMin(value = "1", message = "La position minimum est 1") - private Integer position; - - /** Taille d'affichage (1=petit, 2=moyen, 3=grand) */ - @DecimalMin(value = "1", message = "La taille minimum est 1") - @DecimalMax(value = "3", message = "La taille maximum est 3") - @Builder.Default - private Integer tailleAffichage = 2; - - /** Couleur personnalisée */ - @Size(max = 7, message = "La couleur doit être au format #RRGGBB") - private String couleurPersonnalisee; - - /** Indicateur si la métrique inclut un graphique */ - @Builder.Default private Boolean inclureGraphique = true; - - /** Type de graphique (line, bar, pie, area) */ - @Size(max = 20, message = "Le type de graphique ne peut pas dépasser 20 caractères") - @Builder.Default - private String typeGraphique = "line"; - - /** Indicateur si la métrique inclut la tendance */ - @Builder.Default private Boolean inclureTendance = true; - - /** Indicateur si la métrique inclut la comparaison */ - @Builder.Default private Boolean inclureComparaison = true; - - /** Seuils d'alerte personnalisés */ - private Map seuilsAlerte; - - /** Filtres spécifiques à cette métrique */ - private Map filtresSpecifiques; - } - - /** Configuration d'une section du rapport */ - @Getter - @Setter - @Builder - @NoArgsConstructor - @AllArgsConstructor - public static class SectionRapportDTO { - - /** Nom de la section */ - @NotBlank(message = "Le nom de la section est obligatoire") - @Size(max = 200, message = "Le nom de la section ne peut pas dépasser 200 caractères") - private String nom; - - /** Description de la section */ - @Size(max = 500, message = "La description de la section ne peut pas dépasser 500 caractères") - private String description; - - /** Position de la section dans le rapport */ - @DecimalMin(value = "1", message = "La position minimum est 1") - private Integer position; - - /** Type de section (resume, metriques, graphiques, tableaux, analyse) */ - @NotBlank(message = "Le type de section est obligatoire") - @Size(max = 50, message = "Le type de section ne peut pas dépasser 50 caractères") - private String typeSection; - - /** Métriques incluses dans cette section */ - private List metriquesIncluses; - - /** Configuration spécifique de la section */ - private Map configurationSection; - - /** Indicateur si la section est visible */ - @Builder.Default private Boolean visible = true; - - /** Indicateur si la section peut être réduite */ - @Builder.Default private Boolean pliable = false; - } - - // === MÉTHODES UTILITAIRES === - - /** - * Retourne le nombre de métriques configurées - * - * @return Le nombre de métriques - */ - public int getNombreMetriques() { - return metriques != null ? metriques.size() : 0; - } - - /** - * Retourne le nombre de sections configurées - * - * @return Le nombre de sections - */ - public int getNombreSections() { - return sections != null ? sections.size() : 0; - } - - /** - * Vérifie si le rapport utilise une période personnalisée - * - * @return true si la période est personnalisée - */ - public boolean isPeriodePersonnalisee() { - return periodeAnalyse == PeriodeAnalyse.PERIODE_PERSONNALISEE; - } - - /** - * Vérifie si le rapport est confidentiel (niveau >= 4) - * - * @return true si le rapport est confidentiel - */ - /** Indique si le niveau de confidentialité est élevé (pour couverture branches). */ - private boolean isNiveauConfidentiel() { - if (niveauConfidentialite == null) return false; - return niveauConfidentialite >= 4; - } - - public boolean isConfidentiel() { - return isNiveauConfidentiel(); - } - - /** - * Vérifie si le rapport nécessite une génération - * - * @return true si la prochaine génération est due - */ - public boolean necessiteGeneration() { - return rapportAutomatique - && prochaineGeneration != null - && prochaineGeneration.isBefore(LocalDateTime.now()); - } - - /** - * Retourne la fréquence de génération en texte - * - * @return La fréquence sous forme de texte - */ - public String getFrequenceTexte() { - if (frequenceGenerationHeures == null) return "Manuelle"; - - return switch (frequenceGenerationHeures) { - case 1 -> "Toutes les heures"; - case 24 -> "Quotidienne"; - case 168 -> "Hebdomadaire"; // 24 * 7 - case 720 -> "Mensuelle"; // 24 * 30 - default -> "Toutes les " + frequenceGenerationHeures + " heures"; - }; - } -} +package dev.lions.unionflow.server.api.dto.analytics; + +import com.fasterxml.jackson.annotation.JsonFormat; +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.analytics.FormatExport; +import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; +import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; +import jakarta.validation.Valid; +import jakarta.validation.constraints.DecimalMax; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import java.time.LocalDateTime; +import java.util.List; +import java.util.Map; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * DTO pour la configuration des rapports analytics UnionFlow + * + *

Représente la configuration d'un rapport personnalisé avec ses métriques, sa mise en forme et + * ses paramètres d'export. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class ReportConfigDTO extends BaseDTO { + + private static final long serialVersionUID = 1L; + + /** Nom du rapport */ + @NotBlank(message = "Le nom du rapport est obligatoire") + @Size(min = 3, max = 200, message = "Le nom du rapport doit contenir entre 3 et 200 caractères") + private String nom; + + /** Description du rapport */ + @Size(max = 1000, message = "La description ne peut pas dépasser 1000 caractères") + private String description; + + /** Type de rapport (executif, analytique, technique, operationnel) */ + @NotBlank(message = "Le type de rapport est obligatoire") + @Size(max = 50, message = "Le type de rapport ne peut pas dépasser 50 caractères") + private String typeRapport; + + /** Période d'analyse par défaut */ + @NotNull(message = "La période d'analyse est obligatoire") + private PeriodeAnalyse periodeAnalyse; + + /** Date de début personnalisée (si période personnalisée) */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateDebutPersonnalisee; + + /** Date de fin personnalisée (si période personnalisée) */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateFinPersonnalisee; + + /** Identifiant de l'organisation (optionnel pour filtrage) */ + private UUID organisationId; + + /** Nom de l'organisation */ + @Size(max = 200, message = "Le nom de l'organisation ne peut pas dépasser 200 caractères") + private String nomOrganisation; + + /** Identifiant de l'utilisateur créateur */ + @NotNull(message = "L'identifiant de l'utilisateur créateur est obligatoire") + private UUID utilisateurCreateurId; + + /** Nom de l'utilisateur créateur */ + @Size(max = 200, message = "Le nom de l'utilisateur créateur ne peut pas dépasser 200 caractères") + private String nomUtilisateurCreateur; + + /** Métriques incluses dans le rapport */ + @NotNull(message = "Les métriques sont obligatoires") + @Valid + private List metriques; + + /** Sections du rapport */ + @Valid private List sections; + + /** Format d'export par défaut */ + @NotNull(message = "Le format d'export est obligatoire") + private FormatExport formatExport; + + /** Formats d'export autorisés */ + private List formatsExportAutorises; + + /** Modèle de rapport à utiliser */ + @Size(max = 100, message = "Le modèle de rapport ne peut pas dépasser 100 caractères") + private String modeleRapport; + + /** Configuration de la mise en page */ + @Size( + max = 2000, + message = "La configuration de mise en page ne peut pas dépasser 2000 caractères") + private String configurationMiseEnPage; + + /** Logo personnalisé (URL ou base64) */ + @Size(max = 5000, message = "Le logo personnalisé ne peut pas dépasser 5000 caractères") + private String logoPersonnalise; + + /** Couleurs personnalisées du rapport */ + private Map couleursPersonnalisees; + + /** Indicateur si le rapport est public */ + @Builder.Default private Boolean rapportPublic = false; + + /** Indicateur si le rapport est automatique */ + @Builder.Default private Boolean rapportAutomatique = false; + + /** Fréquence de génération automatique (en heures) */ + @DecimalMin(value = "1", message = "La fréquence minimum est 1 heure") + private Integer frequenceGenerationHeures; + + /** Prochaine génération automatique */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime prochaineGeneration; + + /** Liste des destinataires pour l'envoi automatique */ + private List destinatairesEmail; + + /** Objet de l'email pour l'envoi automatique */ + @Size(max = 200, message = "L'objet de l'email ne peut pas dépasser 200 caractères") + private String objetEmail; + + /** Corps de l'email pour l'envoi automatique */ + @Size(max = 2000, message = "Le corps de l'email ne peut pas dépasser 2000 caractères") + private String corpsEmail; + + /** Paramètres de filtrage avancé */ + private Map parametresFiltrage; + + /** Tags pour catégoriser le rapport */ + private List tags; + + /** Niveau de confidentialité (1=public, 5=confidentiel) */ + @DecimalMin(value = "1", message = "Le niveau de confidentialité minimum est 1") + @DecimalMax(value = "5", message = "Le niveau de confidentialité maximum est 5") + @Builder.Default + private Integer niveauConfidentialite = 1; + + /** Date de dernière génération */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateDerniereGeneration; + + /** Nombre de générations effectuées */ + @DecimalMin(value = "0", message = "Le nombre de générations doit être positif") + @Builder.Default + private Integer nombreGenerations = 0; + + /** Taille moyenne des rapports générés (en KB) */ + @DecimalMin(value = "0", message = "La taille moyenne doit être positive") + private Long tailleMoyenneKB; + + /** Temps moyen de génération (en secondes) */ + @DecimalMin(value = "0", message = "Le temps moyen de génération doit être positif") + private Integer tempsMoyenGenerationSecondes; + + // === CLASSES INTERNES === + + /** Configuration d'une métrique dans le rapport */ + @Getter + @Setter + @Builder + @NoArgsConstructor + @AllArgsConstructor + public static class MetriqueConfigDTO { + + /** Type de métrique */ + @NotNull(message = "Le type de métrique est obligatoire") + private TypeMetrique typeMetrique; + + /** Libellé personnalisé */ + @Size(max = 200, message = "Le libellé personnalisé ne peut pas dépasser 200 caractères") + private String libellePersonnalise; + + /** Position dans le rapport (ordre d'affichage) */ + @DecimalMin(value = "1", message = "La position minimum est 1") + private Integer position; + + /** Taille d'affichage (1=petit, 2=moyen, 3=grand) */ + @DecimalMin(value = "1", message = "La taille minimum est 1") + @DecimalMax(value = "3", message = "La taille maximum est 3") + @Builder.Default + private Integer tailleAffichage = 2; + + /** Couleur personnalisée */ + @Size(max = 7, message = "La couleur doit être au format #RRGGBB") + private String couleurPersonnalisee; + + /** Indicateur si la métrique inclut un graphique */ + @Builder.Default private Boolean inclureGraphique = true; + + /** Type de graphique (line, bar, pie, area) */ + @Size(max = 20, message = "Le type de graphique ne peut pas dépasser 20 caractères") + @Builder.Default + private String typeGraphique = "line"; + + /** Indicateur si la métrique inclut la tendance */ + @Builder.Default private Boolean inclureTendance = true; + + /** Indicateur si la métrique inclut la comparaison */ + @Builder.Default private Boolean inclureComparaison = true; + + /** Seuils d'alerte personnalisés */ + private Map seuilsAlerte; + + /** Filtres spécifiques à cette métrique */ + private Map filtresSpecifiques; + } + + /** Configuration d'une section du rapport */ + @Getter + @Setter + @Builder + @NoArgsConstructor + @AllArgsConstructor + public static class SectionRapportDTO { + + /** Nom de la section */ + @NotBlank(message = "Le nom de la section est obligatoire") + @Size(max = 200, message = "Le nom de la section ne peut pas dépasser 200 caractères") + private String nom; + + /** Description de la section */ + @Size(max = 500, message = "La description de la section ne peut pas dépasser 500 caractères") + private String description; + + /** Position de la section dans le rapport */ + @DecimalMin(value = "1", message = "La position minimum est 1") + private Integer position; + + /** Type de section (resume, metriques, graphiques, tableaux, analyse) */ + @NotBlank(message = "Le type de section est obligatoire") + @Size(max = 50, message = "Le type de section ne peut pas dépasser 50 caractères") + private String typeSection; + + /** Métriques incluses dans cette section */ + private List metriquesIncluses; + + /** Configuration spécifique de la section */ + private Map configurationSection; + + /** Indicateur si la section est visible */ + @Builder.Default private Boolean visible = true; + + /** Indicateur si la section peut être réduite */ + @Builder.Default private Boolean pliable = false; + } + + // === MÉTHODES UTILITAIRES === + + /** + * Retourne le nombre de métriques configurées + * + * @return Le nombre de métriques + */ + public int getNombreMetriques() { + return metriques != null ? metriques.size() : 0; + } + + /** + * Retourne le nombre de sections configurées + * + * @return Le nombre de sections + */ + public int getNombreSections() { + return sections != null ? sections.size() : 0; + } + + /** + * Vérifie si le rapport utilise une période personnalisée + * + * @return true si la période est personnalisée + */ + public boolean isPeriodePersonnalisee() { + return periodeAnalyse == PeriodeAnalyse.PERIODE_PERSONNALISEE; + } + + /** + * Vérifie si le rapport est confidentiel (niveau >= 4) + * + * @return true si le rapport est confidentiel + */ + /** Indique si le niveau de confidentialité est élevé (pour couverture branches). */ + private boolean isNiveauConfidentiel() { + if (niveauConfidentialite == null) return false; + return niveauConfidentialite >= 4; + } + + public boolean isConfidentiel() { + return isNiveauConfidentiel(); + } + + /** + * Vérifie si le rapport nécessite une génération + * + * @return true si la prochaine génération est due + */ + public boolean necessiteGeneration() { + return rapportAutomatique + && prochaineGeneration != null + && prochaineGeneration.isBefore(LocalDateTime.now()); + } + + /** + * Retourne la fréquence de génération en texte + * + * @return La fréquence sous forme de texte + */ + public String getFrequenceTexte() { + if (frequenceGenerationHeures == null) return "Manuelle"; + + return switch (frequenceGenerationHeures) { + case 1 -> "Toutes les heures"; + case 24 -> "Quotidienne"; + case 168 -> "Hebdomadaire"; // 24 * 7 + case 720 -> "Mensuelle"; // 24 * 30 + default -> "Toutes les " + frequenceGenerationHeures + " heures"; + }; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/auth/request/LoginRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/auth/request/LoginRequest.java index 0f64271..b6cc298 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/auth/request/LoginRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/auth/request/LoginRequest.java @@ -1,32 +1,32 @@ -package dev.lions.unionflow.server.api.dto.auth.request; - -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.Size; -import lombok.Builder; - -/** - * Requête d'authentification utilisateur. - * - * @param username Email ou nom d'utilisateur - * @param password Mot de passe - * @param typeCompte Type de compte (MEMBRE, ADMIN, etc.) - * @param rememberMe Se souvenir de moi - * @author UnionFlow Team - * @version 2.0 - * @since 2026-02-28 - */ -@Builder -public record LoginRequest( - @NotBlank(message = "L'email ou nom d'utilisateur est requis") - @Size(min = 3, max = 100, message = "L'email ou nom d'utilisateur doit contenir entre 3 et 100 caractères") - String username, - - @NotBlank(message = "Le mot de passe est requis") - @Size(min = 6, message = "Le mot de passe doit contenir au moins 6 caractères") - String password, - - @NotBlank(message = "Le type de compte est requis") - String typeCompte, - - Boolean rememberMe) { -} +package dev.lions.unionflow.server.api.dto.auth.request; + +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.Size; +import lombok.Builder; + +/** + * Requête d'authentification utilisateur. + * + * @param username Email ou nom d'utilisateur + * @param password Mot de passe + * @param typeCompte Type de compte (MEMBRE, ADMIN, etc.) + * @param rememberMe Se souvenir de moi + * @author UnionFlow Team + * @version 2.0 + * @since 2026-02-28 + */ +@Builder +public record LoginRequest( + @NotBlank(message = "L'email ou nom d'utilisateur est requis") + @Size(min = 3, max = 100, message = "L'email ou nom d'utilisateur doit contenir entre 3 et 100 caractères") + String username, + + @NotBlank(message = "Le mot de passe est requis") + @Size(min = 6, message = "Le mot de passe doit contenir au moins 6 caractères") + String password, + + @NotBlank(message = "Le type de compte est requis") + String typeCompte, + + Boolean rememberMe) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/auth/response/LoginResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/auth/response/LoginResponse.java index e23e6f4..d1b048a 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/auth/response/LoginResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/auth/response/LoginResponse.java @@ -1,90 +1,90 @@ -package dev.lions.unionflow.server.api.dto.auth.response; - -import java.time.LocalDateTime; -import java.util.List; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse d'authentification contenant le token JWT et les informations utilisateur. - * - * @author UnionFlow Team - * @version 2.0 - * @since 2026-02-28 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class LoginResponse { - - private String accessToken; - private String refreshToken; - @Builder.Default - private String tokenType = "Bearer"; - private Long expiresIn; - private LocalDateTime expirationDate; - private UserInfo user; - - /** - * Vérifie si le token est expiré. - * - * @return true si le token est expiré - */ - public boolean isExpired() { - return expirationDate != null && LocalDateTime.now().isAfter(expirationDate); - } - - /** - * Informations de l'utilisateur connecté. - */ - @Getter - @Setter - @Builder - @NoArgsConstructor - @AllArgsConstructor - public static class UserInfo { - private UUID id; - private String nom; - private String prenom; - private String email; - private String username; - private String typeCompte; - private List roles; - private List permissions; - private EntiteInfo entite; - - /** - * Retourne le nom complet de l'utilisateur. - * - * @return Prénom + Nom ou nom d'utilisateur si absent - */ - public String getNomComplet() { - if (prenom != null && nom != null) { - return prenom + " " + nom; - } - return nom != null ? nom : username; - } - } - - /** - * Informations sur l'entité (organisation/membre) de l'utilisateur. - */ - @Getter - @Setter - @Builder - @NoArgsConstructor - @AllArgsConstructor - public static class EntiteInfo { - private UUID id; - private String nom; - private String type; - private String pays; - private String ville; - } -} +package dev.lions.unionflow.server.api.dto.auth.response; + +import java.time.LocalDateTime; +import java.util.List; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse d'authentification contenant le token JWT et les informations utilisateur. + * + * @author UnionFlow Team + * @version 2.0 + * @since 2026-02-28 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class LoginResponse { + + private String accessToken; + private String refreshToken; + @Builder.Default + private String tokenType = "Bearer"; + private Long expiresIn; + private LocalDateTime expirationDate; + private UserInfo user; + + /** + * Vérifie si le token est expiré. + * + * @return true si le token est expiré + */ + public boolean isExpired() { + return expirationDate != null && LocalDateTime.now().isAfter(expirationDate); + } + + /** + * Informations de l'utilisateur connecté. + */ + @Getter + @Setter + @Builder + @NoArgsConstructor + @AllArgsConstructor + public static class UserInfo { + private UUID id; + private String nom; + private String prenom; + private String email; + private String username; + private String typeCompte; + private List roles; + private List permissions; + private EntiteInfo entite; + + /** + * Retourne le nom complet de l'utilisateur. + * + * @return Prénom + Nom ou nom d'utilisateur si absent + */ + public String getNomComplet() { + if (prenom != null && nom != null) { + return prenom + " " + nom; + } + return nom != null ? nom : username; + } + } + + /** + * Informations sur l'entité (organisation/membre) de l'utilisateur. + */ + @Getter + @Setter + @Builder + @NoArgsConstructor + @AllArgsConstructor + public static class EntiteInfo { + private UUID id; + private String nom; + private String type; + private String pays; + private String ville; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/ayantdroit/AyantDroitRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/ayantdroit/AyantDroitRequest.java index a13ee1b..96eaf7e 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/ayantdroit/AyantDroitRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/ayantdroit/AyantDroitRequest.java @@ -1,42 +1,42 @@ -package dev.lions.unionflow.server.api.dto.ayantdroit; - -import dev.lions.unionflow.server.api.enums.ayantdroit.LienParente; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Past; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.time.LocalDate; - -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class AyantDroitRequest { - - @NotBlank(message = "L'Id du membre principal rattaché est obligatoire") - private String membrePrincipalId; - - @NotBlank(message = "Le prénom est obligatoire") - private String prenom; - - @NotBlank(message = "Le nom est obligatoire") - private String nom; - - @NotNull(message = "La date de naissance est obligatoire pour l'âge limite") - @Past(message = "La date de naissance doit être dans le passé") - private LocalDate dateNaissance; - - private String sexe; - - private String pieceIdentite; - - @NotNull(message = "Le lien de parenté / bénéfice est requis") - private LienParente lienParente; - - // Id document du livret de famille ou certificat médical / scolaire - private String justificatifLienId; -} +package dev.lions.unionflow.server.api.dto.ayantdroit; + +import dev.lions.unionflow.server.api.enums.ayantdroit.LienParente; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Past; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.time.LocalDate; + +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class AyantDroitRequest { + + @NotBlank(message = "L'Id du membre principal rattaché est obligatoire") + private String membrePrincipalId; + + @NotBlank(message = "Le prénom est obligatoire") + private String prenom; + + @NotBlank(message = "Le nom est obligatoire") + private String nom; + + @NotNull(message = "La date de naissance est obligatoire pour l'âge limite") + @Past(message = "La date de naissance doit être dans le passé") + private LocalDate dateNaissance; + + private String sexe; + + private String pieceIdentite; + + @NotNull(message = "Le lien de parenté / bénéfice est requis") + private LienParente lienParente; + + // Id document du livret de famille ou certificat médical / scolaire + private String justificatifLienId; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/ayantdroit/AyantDroitResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/ayantdroit/AyantDroitResponse.java index 6f5feb7..30654a9 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/ayantdroit/AyantDroitResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/ayantdroit/AyantDroitResponse.java @@ -1,40 +1,40 @@ -package dev.lions.unionflow.server.api.dto.ayantdroit; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.ayantdroit.LienParente; -import dev.lions.unionflow.server.api.enums.ayantdroit.StatutAyantDroit; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; - -import java.time.LocalDate; -import java.math.BigDecimal; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class AyantDroitResponse extends BaseDTO { - - private String membrePrincipalId; - - private String numeroCarteBeneficiaire; - - private String prenom; - private String nom; - - private LocalDate dateNaissance; - private Integer ageActuel; - private String sexe; - private String pieceIdentite; - - private LienParente lienParente; - - // Prise en charge (%) par rapport à la couverture du Membre Principal - private BigDecimal pourcentageCouvertureSante; - - private StatutAyantDroit statut; -} +package dev.lions.unionflow.server.api.dto.ayantdroit; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.ayantdroit.LienParente; +import dev.lions.unionflow.server.api.enums.ayantdroit.StatutAyantDroit; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; + +import java.time.LocalDate; +import java.math.BigDecimal; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class AyantDroitResponse extends BaseDTO { + + private String membrePrincipalId; + + private String numeroCarteBeneficiaire; + + private String prenom; + private String nom; + + private LocalDate dateNaissance; + private Integer ageActuel; + private String sexe; + private String pieceIdentite; + + private LienParente lienParente; + + // Prise en charge (%) par rapport à la couverture du Membre Principal + private BigDecimal pourcentageCouvertureSante; + + private StatutAyantDroit statut; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/backup/request/CreateBackupRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/backup/request/CreateBackupRequest.java index b73f7d7..05f3539 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/backup/request/CreateBackupRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/backup/request/CreateBackupRequest.java @@ -1,28 +1,28 @@ -package dev.lions.unionflow.server.api.dto.backup.request; - -import jakarta.validation.constraints.NotBlank; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * Request pour créer une sauvegarde - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class CreateBackupRequest { - - @NotBlank(message = "Le nom de la sauvegarde est requis") - private String name; - - private String description; - - private String type; // AUTO, MANUAL, RESTORE_POINT - - private Boolean includeDatabase; - private Boolean includeFiles; - private Boolean includeConfiguration; -} +package dev.lions.unionflow.server.api.dto.backup.request; + +import jakarta.validation.constraints.NotBlank; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * Request pour créer une sauvegarde + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class CreateBackupRequest { + + @NotBlank(message = "Le nom de la sauvegarde est requis") + private String name; + + private String description; + + private String type; // AUTO, MANUAL, RESTORE_POINT + + private Boolean includeDatabase; + private Boolean includeFiles; + private Boolean includeConfiguration; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/backup/request/RestoreBackupRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/backup/request/RestoreBackupRequest.java index 910df17..914c059 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/backup/request/RestoreBackupRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/backup/request/RestoreBackupRequest.java @@ -1,28 +1,28 @@ -package dev.lions.unionflow.server.api.dto.backup.request; - -import jakarta.validation.constraints.NotNull; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.util.UUID; - -/** - * Request pour restaurer une sauvegarde - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class RestoreBackupRequest { - - @NotNull(message = "L'ID de la sauvegarde est requis") - private UUID backupId; - - private Boolean restoreDatabase; - private Boolean restoreFiles; - private Boolean restoreConfiguration; - - private Boolean createRestorePoint; // Créer un point de restauration avant -} +package dev.lions.unionflow.server.api.dto.backup.request; + +import jakarta.validation.constraints.NotNull; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.util.UUID; + +/** + * Request pour restaurer une sauvegarde + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class RestoreBackupRequest { + + @NotNull(message = "L'ID de la sauvegarde est requis") + private UUID backupId; + + private Boolean restoreDatabase; + private Boolean restoreFiles; + private Boolean restoreConfiguration; + + private Boolean createRestorePoint; // Créer un point de restauration avant +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/backup/request/UpdateBackupConfigRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/backup/request/UpdateBackupConfigRequest.java index 69770e6..c7e3b35 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/backup/request/UpdateBackupConfigRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/backup/request/UpdateBackupConfigRequest.java @@ -1,25 +1,25 @@ -package dev.lions.unionflow.server.api.dto.backup.request; - -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * Request pour mettre à jour la configuration des sauvegardes automatiques - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class UpdateBackupConfigRequest { - - private Boolean autoBackupEnabled; - private String frequency; // HOURLY, DAILY, WEEKLY - private String retention; // "7 jours", "30 jours", "90 jours", "1 an" - private Integer retentionDays; - private String backupTime; // Format HH:mm pour sauvegarde quotidienne - private Boolean includeDatabase; - private Boolean includeFiles; - private Boolean includeConfiguration; -} +package dev.lions.unionflow.server.api.dto.backup.request; + +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * Request pour mettre à jour la configuration des sauvegardes automatiques + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class UpdateBackupConfigRequest { + + private Boolean autoBackupEnabled; + private String frequency; // HOURLY, DAILY, WEEKLY + private String retention; // "7 jours", "30 jours", "90 jours", "1 an" + private Integer retentionDays; + private String backupTime; // Format HH:mm pour sauvegarde quotidienne + private Boolean includeDatabase; + private Boolean includeFiles; + private Boolean includeConfiguration; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/backup/response/BackupConfigResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/backup/response/BackupConfigResponse.java index 3a5ab98..424acb7 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/backup/response/BackupConfigResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/backup/response/BackupConfigResponse.java @@ -1,33 +1,33 @@ -package dev.lions.unionflow.server.api.dto.backup.response; - -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.time.LocalDateTime; - -/** - * Response contenant la configuration des sauvegardes automatiques - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class BackupConfigResponse { - - private Boolean autoBackupEnabled; - private String frequency; // HOURLY, DAILY, WEEKLY - private String retention; // "7 jours", "30 jours", etc. - private Integer retentionDays; - private String backupTime; // HH:mm - private Boolean includeDatabase; - private Boolean includeFiles; - private Boolean includeConfiguration; - - private LocalDateTime lastBackup; - private LocalDateTime nextScheduledBackup; - private Integer totalBackups; - private Long totalSizeBytes; - private String totalSizeFormatted; -} +package dev.lions.unionflow.server.api.dto.backup.response; + +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.time.LocalDateTime; + +/** + * Response contenant la configuration des sauvegardes automatiques + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class BackupConfigResponse { + + private Boolean autoBackupEnabled; + private String frequency; // HOURLY, DAILY, WEEKLY + private String retention; // "7 jours", "30 jours", etc. + private Integer retentionDays; + private String backupTime; // HH:mm + private Boolean includeDatabase; + private Boolean includeFiles; + private Boolean includeConfiguration; + + private LocalDateTime lastBackup; + private LocalDateTime nextScheduledBackup; + private Integer totalBackups; + private Long totalSizeBytes; + private String totalSizeFormatted; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/backup/response/BackupResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/backup/response/BackupResponse.java index 44d8d2c..98ba4f7 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/backup/response/BackupResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/backup/response/BackupResponse.java @@ -1,37 +1,37 @@ -package dev.lions.unionflow.server.api.dto.backup.response; - -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.time.LocalDateTime; -import java.util.UUID; - -/** - * Response représentant une sauvegarde - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class BackupResponse { - - private UUID id; - private String name; - private String description; - private String type; // AUTO, MANUAL, RESTORE_POINT - private Long sizeBytes; - private String sizeFormatted; // ex: "2.3 GB" - private String status; // PENDING, IN_PROGRESS, COMPLETED, FAILED - private LocalDateTime createdAt; - private LocalDateTime completedAt; - private String createdBy; - - private Boolean includesDatabase; - private Boolean includesFiles; - private Boolean includesConfiguration; - - private String filePath; - private String errorMessage; // Si status = FAILED -} +package dev.lions.unionflow.server.api.dto.backup.response; + +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.time.LocalDateTime; +import java.util.UUID; + +/** + * Response représentant une sauvegarde + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class BackupResponse { + + private UUID id; + private String name; + private String description; + private String type; // AUTO, MANUAL, RESTORE_POINT + private Long sizeBytes; + private String sizeFormatted; // ex: "2.3 GB" + private String status; // PENDING, IN_PROGRESS, COMPLETED, FAILED + private LocalDateTime createdAt; + private LocalDateTime completedAt; + private String createdBy; + + private Boolean includesDatabase; + private Boolean includesFiles; + private Boolean includesConfiguration; + + private String filePath; + private String errorMessage; // Si status = FAILED +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/base/BaseDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/base/BaseDTO.java index 8741e88..f72a6ff 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/base/BaseDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/base/BaseDTO.java @@ -1,164 +1,164 @@ -package dev.lions.unionflow.server.api.dto.base; - -import com.fasterxml.jackson.annotation.JsonFormat; -import java.io.Serial; -import java.io.Serializable; -import java.time.LocalDateTime; -import java.util.UUID; -import lombok.Getter; -import lombok.Setter; - -/** - * Classe de base pour tous les DTOs UnionFlow Fournit les propriétés communes - * d'audit et de gestion - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -@Getter -@Setter -public abstract class BaseDTO implements Serializable { - - @Serial - private static final long serialVersionUID = 1L; - - /** Identifiant unique UUID */ - private UUID id; - - /** Date de création de l'enregistrement */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - public LocalDateTime dateCreation; - - /** Date de dernière modification */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - public LocalDateTime dateModification; - - /** Utilisateur qui a créé l'enregistrement */ - private String creePar; - - /** Utilisateur qui a modifié l'enregistrement en dernier */ - private String modifiePar; - - /** Version pour gestion de la concurrence optimiste */ - private Long version; - - /** Indicateur si l'enregistrement est actif */ - private Boolean actif; - - // Constructeur par défaut - public BaseDTO() { - this.dateCreation = LocalDateTime.now(); - this.actif = true; - this.version = 0L; - } - - // Getters et Setters générés automatiquement par Lombok @Getter/@Setter - - // Méthodes utilitaires - - /** - * Marque l'entité comme nouvellement créée - * - * @param utilisateur L'utilisateur qui crée l'entité - */ - public void marquerCommeNouveau(String utilisateur) { - LocalDateTime maintenant = LocalDateTime.now(); - this.dateCreation = maintenant; - this.dateModification = maintenant; - this.creePar = utilisateur; - this.modifiePar = utilisateur; - this.version = 0L; - this.actif = true; - } - - /** - * Marque l'entité comme modifiée - * - * @param utilisateur L'utilisateur qui modifie l'entité - */ - public void marquerCommeModifie(String utilisateur) { - this.dateModification = LocalDateTime.now(); - this.modifiePar = utilisateur; - if (this.version != null) { - this.version++; - } - } - - /** - * Désactive l'entité (soft delete) - * - * @param utilisateur L'utilisateur qui désactive l'entité - */ - public void desactiver(String utilisateur) { - this.actif = false; - marquerCommeModifie(utilisateur); - } - - /** - * Réactive l'entité - * - * @param utilisateur L'utilisateur qui réactive l'entité - */ - public void reactiver(String utilisateur) { - this.actif = true; - marquerCommeModifie(utilisateur); - } - - /** - * Vérifie si l'entité est nouvelle (pas encore persistée) - * - * @return true si l'entité est nouvelle - */ - public boolean isNouveau() { - return id == null; - } - - /** - * Vérifie si l'entité est active - * - * @return true si l'entité est active - */ - public boolean isActif() { - return Boolean.TRUE.equals(actif); - } - - @Override - public boolean equals(Object obj) { - if (this == obj) - return true; - if (obj == null || getClass() != obj.getClass()) - return false; - - BaseDTO baseDTO = (BaseDTO) obj; - return id != null && id.equals(baseDTO.id); - } - - @Override - public int hashCode() { - return id != null ? id.hashCode() : 0; - } - - @Override - public String toString() { - return getClass().getSimpleName() - + "{" - + "id=" - + id - + ", dateCreation=" - + dateCreation - + ", dateModification=" - + dateModification - + ", creePar='" - + creePar - + '\'' - + ", modifiePar='" - + modifiePar - + '\'' - + ", version=" - + version - + ", actif=" - + actif - + '}'; - } -} +package dev.lions.unionflow.server.api.dto.base; + +import com.fasterxml.jackson.annotation.JsonFormat; +import java.io.Serial; +import java.io.Serializable; +import java.time.LocalDateTime; +import java.util.UUID; +import lombok.Getter; +import lombok.Setter; + +/** + * Classe de base pour tous les DTOs UnionFlow Fournit les propriétés communes + * d'audit et de gestion + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +@Getter +@Setter +public abstract class BaseDTO implements Serializable { + + @Serial + private static final long serialVersionUID = 1L; + + /** Identifiant unique UUID */ + private UUID id; + + /** Date de création de l'enregistrement */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + public LocalDateTime dateCreation; + + /** Date de dernière modification */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + public LocalDateTime dateModification; + + /** Utilisateur qui a créé l'enregistrement */ + private String creePar; + + /** Utilisateur qui a modifié l'enregistrement en dernier */ + private String modifiePar; + + /** Version pour gestion de la concurrence optimiste */ + private Long version; + + /** Indicateur si l'enregistrement est actif */ + private Boolean actif; + + // Constructeur par défaut + public BaseDTO() { + this.dateCreation = LocalDateTime.now(); + this.actif = true; + this.version = 0L; + } + + // Getters et Setters générés automatiquement par Lombok @Getter/@Setter + + // Méthodes utilitaires + + /** + * Marque l'entité comme nouvellement créée + * + * @param utilisateur L'utilisateur qui crée l'entité + */ + public void marquerCommeNouveau(String utilisateur) { + LocalDateTime maintenant = LocalDateTime.now(); + this.dateCreation = maintenant; + this.dateModification = maintenant; + this.creePar = utilisateur; + this.modifiePar = utilisateur; + this.version = 0L; + this.actif = true; + } + + /** + * Marque l'entité comme modifiée + * + * @param utilisateur L'utilisateur qui modifie l'entité + */ + public void marquerCommeModifie(String utilisateur) { + this.dateModification = LocalDateTime.now(); + this.modifiePar = utilisateur; + if (this.version != null) { + this.version++; + } + } + + /** + * Désactive l'entité (soft delete) + * + * @param utilisateur L'utilisateur qui désactive l'entité + */ + public void desactiver(String utilisateur) { + this.actif = false; + marquerCommeModifie(utilisateur); + } + + /** + * Réactive l'entité + * + * @param utilisateur L'utilisateur qui réactive l'entité + */ + public void reactiver(String utilisateur) { + this.actif = true; + marquerCommeModifie(utilisateur); + } + + /** + * Vérifie si l'entité est nouvelle (pas encore persistée) + * + * @return true si l'entité est nouvelle + */ + public boolean isNouveau() { + return id == null; + } + + /** + * Vérifie si l'entité est active + * + * @return true si l'entité est active + */ + public boolean isActif() { + return Boolean.TRUE.equals(actif); + } + + @Override + public boolean equals(Object obj) { + if (this == obj) + return true; + if (obj == null || getClass() != obj.getClass()) + return false; + + BaseDTO baseDTO = (BaseDTO) obj; + return id != null && id.equals(baseDTO.id); + } + + @Override + public int hashCode() { + return id != null ? id.hashCode() : 0; + } + + @Override + public String toString() { + return getClass().getSimpleName() + + "{" + + "id=" + + id + + ", dateCreation=" + + dateCreation + + ", dateModification=" + + dateModification + + ", creePar='" + + creePar + + '\'' + + ", modifiePar='" + + modifiePar + + '\'' + + ", version=" + + version + + ", actif=" + + actif + + '}'; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/base/BaseResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/base/BaseResponse.java index 8a58f95..c3e8306 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/base/BaseResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/base/BaseResponse.java @@ -1,79 +1,79 @@ -package dev.lions.unionflow.server.api.dto.base; - -import java.time.LocalDateTime; -import java.util.UUID; -import lombok.Getter; -import lombok.Setter; - -/** - * Classe de base pour les DTOs de réponse. - * - *

- * Contient les champs d'audit communs à toutes - * les réponses : identifiant, dates de - * création/modification, créateur, et version. - * - *

- * Les DTOs de type Request ne doivent - * pas hériter de cette classe (utiliser - * des {@code record} sans héritage). - * - * @author UnionFlow Team - * @version 3.0 - * @since 2026-02-21 - */ -@Getter -@Setter -public abstract class BaseResponse { - - /** Identifiant unique de l'entité. */ - private UUID id; - - /** Date de création de l'entité. */ - private LocalDateTime dateCreation; - - /** Date de dernière modification. */ - private LocalDateTime dateModification; - - /** Email du créateur. */ - private String creePar; - - /** Email du dernier modificateur. */ - private String modifiePar; - - /** Version pour l'optimistic locking. */ - private Long version; - - /** État actif/inactif (soft-delete). */ - private Boolean actif; - - /** - * Comparaison basée sur l'ID. - * Deux BaseResponse sont égaux si leurs IDs sont égaux et non null. - * - * @param obj Objet à comparer - * @return true si les objets ont le même ID - */ - @Override - public boolean equals(Object obj) { - if (this == obj) { - return true; - } - if (obj == null || getClass() != obj.getClass()) { - return false; - } - - BaseResponse that = (BaseResponse) obj; - return id != null && id.equals(that.id); - } - - /** - * Hash code basé sur l'ID. - * - * @return Hash code de l'ID, ou 0 si ID null - */ - @Override - public int hashCode() { - return id != null ? id.hashCode() : 0; - } -} +package dev.lions.unionflow.server.api.dto.base; + +import java.time.LocalDateTime; +import java.util.UUID; +import lombok.Getter; +import lombok.Setter; + +/** + * Classe de base pour les DTOs de réponse. + * + *

+ * Contient les champs d'audit communs à toutes + * les réponses : identifiant, dates de + * création/modification, créateur, et version. + * + *

+ * Les DTOs de type Request ne doivent + * pas hériter de cette classe (utiliser + * des {@code record} sans héritage). + * + * @author UnionFlow Team + * @version 3.0 + * @since 2026-02-21 + */ +@Getter +@Setter +public abstract class BaseResponse { + + /** Identifiant unique de l'entité. */ + private UUID id; + + /** Date de création de l'entité. */ + private LocalDateTime dateCreation; + + /** Date de dernière modification. */ + private LocalDateTime dateModification; + + /** Email du créateur. */ + private String creePar; + + /** Email du dernier modificateur. */ + private String modifiePar; + + /** Version pour l'optimistic locking. */ + private Long version; + + /** État actif/inactif (soft-delete). */ + private Boolean actif; + + /** + * Comparaison basée sur l'ID. + * Deux BaseResponse sont égaux si leurs IDs sont égaux et non null. + * + * @param obj Objet à comparer + * @return true si les objets ont le même ID + */ + @Override + public boolean equals(Object obj) { + if (this == obj) { + return true; + } + if (obj == null || getClass() != obj.getClass()) { + return false; + } + + BaseResponse that = (BaseResponse) obj; + return id != null && id.equals(that.id); + } + + /** + * Hash code basé sur l'ID. + * + * @return Hash code de l'ID, ou 0 si ID null + */ + @Override + public int hashCode() { + return id != null ? id.hashCode() : 0; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/base/PageResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/base/PageResponse.java index f676656..01cc98b 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/base/PageResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/base/PageResponse.java @@ -1,59 +1,59 @@ -package dev.lions.unionflow.server.api.dto.base; - -import java.util.List; -import lombok.AllArgsConstructor; -import lombok.Getter; - -/** - * Réponse paginée générique. - * - *

- * Encapsule une liste d'éléments avec les - * métadonnées de pagination (page, taille, - * total). Utilisable pour tout type de réponse - * paginée. - * - * @param type des éléments de la page - * @author UnionFlow Team - * @version 3.0 - * @since 2026-02-21 - */ -@Getter -@AllArgsConstructor -public class PageResponse { - - /** Éléments de la page courante. */ - private final List contenu; - - /** Numéro de page courant (0-indexed). */ - private final int page; - - /** Taille de la page demandée. */ - private final int taille; - - /** Nombre total d'éléments. */ - private final long totalElements; - - /** Nombre total de pages. */ - private final int totalPages; - - /** - * Indique s'il existe une page suivante. - * - * @return {@code true} si une page suivante - * existe - */ - public boolean hasNext() { - return page < totalPages - 1; - } - - /** - * Indique s'il existe une page précédente. - * - * @return {@code true} si une page précédente - * existe - */ - public boolean hasPrevious() { - return page > 0; - } -} +package dev.lions.unionflow.server.api.dto.base; + +import java.util.List; +import lombok.AllArgsConstructor; +import lombok.Getter; + +/** + * Réponse paginée générique. + * + *

+ * Encapsule une liste d'éléments avec les + * métadonnées de pagination (page, taille, + * total). Utilisable pour tout type de réponse + * paginée. + * + * @param type des éléments de la page + * @author UnionFlow Team + * @version 3.0 + * @since 2026-02-21 + */ +@Getter +@AllArgsConstructor +public class PageResponse { + + /** Éléments de la page courante. */ + private final List contenu; + + /** Numéro de page courant (0-indexed). */ + private final int page; + + /** Taille de la page demandée. */ + private final int taille; + + /** Nombre total d'éléments. */ + private final long totalElements; + + /** Nombre total de pages. */ + private final int totalPages; + + /** + * Indique s'il existe une page suivante. + * + * @return {@code true} si une page suivante + * existe + */ + public boolean hasNext() { + return page < totalPages - 1; + } + + /** + * Indique s'il existe une page précédente. + * + * @return {@code true} si une page précédente + * existe + */ + public boolean hasPrevious() { + return page > 0; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/collectefonds/CampagneCollecteResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/collectefonds/CampagneCollecteResponse.java index 99b32a7..297f7f0 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/collectefonds/CampagneCollecteResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/collectefonds/CampagneCollecteResponse.java @@ -1,45 +1,45 @@ -package dev.lions.unionflow.server.api.dto.collectefonds; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.collectefonds.StatutCampagneCollecte; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -import java.math.BigDecimal; -import java.time.LocalDateTime; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Campagne de levée de fonds (Crowdfunding / ONG)") -public class CampagneCollecteResponse extends BaseDTO { - - private String organisationId; - - private String titre; - private String courteDescription; - private String htmlDescriptionComplete; - private String imageBanniereUrl; - - @Schema(description = "Objectif monétaire escompté") - private BigDecimal objectifFinancier; - - @Schema(description = "Somme totale déjà récoltée sur cette campagne") - private BigDecimal montantCollecteActuel; - - private Integer nombreDonateurs; - - private StatutCampagneCollecte statut; - - private LocalDateTime dateOuverture; - private LocalDateTime dateCloturePrevue; - - // Si la page est visible pour les non-membres (donateurs externes) - private Boolean estPublique; -} +package dev.lions.unionflow.server.api.dto.collectefonds; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.collectefonds.StatutCampagneCollecte; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +import java.math.BigDecimal; +import java.time.LocalDateTime; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Campagne de levée de fonds (Crowdfunding / ONG)") +public class CampagneCollecteResponse extends BaseDTO { + + private String organisationId; + + private String titre; + private String courteDescription; + private String htmlDescriptionComplete; + private String imageBanniereUrl; + + @Schema(description = "Objectif monétaire escompté") + private BigDecimal objectifFinancier; + + @Schema(description = "Somme totale déjà récoltée sur cette campagne") + private BigDecimal montantCollecteActuel; + + private Integer nombreDonateurs; + + private StatutCampagneCollecte statut; + + private LocalDateTime dateOuverture; + private LocalDateTime dateCloturePrevue; + + // Si la page est visible pour les non-membres (donateurs externes) + private Boolean estPublique; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/collectefonds/ContributionCollecteDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/collectefonds/ContributionCollecteDTO.java index 7d2989f..41a973b 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/collectefonds/ContributionCollecteDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/collectefonds/ContributionCollecteDTO.java @@ -1,42 +1,42 @@ -package dev.lions.unionflow.server.api.dto.collectefonds; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.wave.StatutTransactionWave; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -import java.math.BigDecimal; -import java.time.LocalDateTime; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Don transactionnel reçu pour une campagne de collecte") -public class ContributionCollecteDTO extends BaseDTO { - - private String campagneId; - - @Schema(description = "Id du membre (Null si le don est public/externe)") - private String membreDonateurId; - - @Schema(description = "Nom affiché si don public ou pour le mur de contributeurs") - private String aliasDonateur; - - private Boolean estAnonyme; - - private BigDecimal montantSoutien; - - private String messageSoutien; - - private LocalDateTime dateContribution; - - // Lien avec la passerelle de paiement - private String transactionPaiementId; - private StatutTransactionWave statutPaiement; -} +package dev.lions.unionflow.server.api.dto.collectefonds; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.wave.StatutTransactionWave; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +import java.math.BigDecimal; +import java.time.LocalDateTime; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Don transactionnel reçu pour une campagne de collecte") +public class ContributionCollecteDTO extends BaseDTO { + + private String campagneId; + + @Schema(description = "Id du membre (Null si le don est public/externe)") + private String membreDonateurId; + + @Schema(description = "Nom affiché si don public ou pour le mur de contributeurs") + private String aliasDonateur; + + private Boolean estAnonyme; + + private BigDecimal montantSoutien; + + private String messageSoutien; + + private LocalDateTime dateContribution; + + // Lien avec la passerelle de paiement + private String transactionPaiementId; + private StatutTransactionWave statutPaiement; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/common/PagedResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/common/PagedResponse.java index c6f2b17..1f5c77f 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/common/PagedResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/common/PagedResponse.java @@ -1,125 +1,125 @@ -package dev.lions.unionflow.server.api.dto.common; - -import com.fasterxml.jackson.annotation.JsonProperty; -import java.util.List; - -/** - * DTO générique pour les réponses paginées de l'API. - * Utilisé par tous les endpoints REST qui renvoient des données paginées. - * - * @param Type des éléments dans la liste - * @author UnionFlow Team - * @version 2.0 - */ -public class PagedResponse { - - @JsonProperty("data") - private List data; - - @JsonProperty("total") - private Long total; - - @JsonProperty("page") - private Integer page; - - @JsonProperty("size") - private Integer size; - - @JsonProperty("totalPages") - private Integer totalPages; - - // Constructeurs - public PagedResponse() { - } - - public PagedResponse(List data, Long total, Integer page, Integer size) { - this.data = data; - this.total = total; - this.page = page; - this.size = size; - this.totalPages = calculateTotalPages(total, size); - } - - public PagedResponse(List data, Long total, Integer page, Integer size, Integer totalPages) { - this.data = data; - this.total = total; - this.page = page; - this.size = size; - this.totalPages = totalPages; - } - - // Méthode utilitaire pour calculer le nombre de pages - private Integer calculateTotalPages(Long total, Integer size) { - if (size == null || size == 0 || total == null) { - return 0; - } - return (int) Math.ceil((double) total / size); - } - - // Getters et setters - public List getData() { - return data; - } - - public void setData(List data) { - this.data = data; - } - - public Long getTotal() { - return total; - } - - public void setTotal(Long total) { - this.total = total; - this.totalPages = calculateTotalPages(total, this.size); - } - - public Integer getPage() { - return page; - } - - public void setPage(Integer page) { - this.page = page; - } - - public Integer getSize() { - return size; - } - - public void setSize(Integer size) { - this.size = size; - this.totalPages = calculateTotalPages(this.total, size); - } - - public Integer getTotalPages() { - return totalPages; - } - - public void setTotalPages(Integer totalPages) { - this.totalPages = totalPages; - } - - // Méthodes utilitaires - public boolean hasNext() { - return page != null && totalPages != null && page < totalPages - 1; - } - - public boolean hasPrevious() { - return page != null && page > 0; - } - - public boolean isEmpty() { - return data == null || data.isEmpty(); - } - - @Override - public String toString() { - return "PagedResponse{" + - "total=" + total + - ", page=" + page + - ", size=" + size + - ", totalPages=" + totalPages + - ", itemsCount=" + (data != null ? data.size() : 0) + - '}'; - } -} +package dev.lions.unionflow.server.api.dto.common; + +import com.fasterxml.jackson.annotation.JsonProperty; +import java.util.List; + +/** + * DTO générique pour les réponses paginées de l'API. + * Utilisé par tous les endpoints REST qui renvoient des données paginées. + * + * @param Type des éléments dans la liste + * @author UnionFlow Team + * @version 2.0 + */ +public class PagedResponse { + + @JsonProperty("data") + private List data; + + @JsonProperty("total") + private Long total; + + @JsonProperty("page") + private Integer page; + + @JsonProperty("size") + private Integer size; + + @JsonProperty("totalPages") + private Integer totalPages; + + // Constructeurs + public PagedResponse() { + } + + public PagedResponse(List data, Long total, Integer page, Integer size) { + this.data = data; + this.total = total; + this.page = page; + this.size = size; + this.totalPages = calculateTotalPages(total, size); + } + + public PagedResponse(List data, Long total, Integer page, Integer size, Integer totalPages) { + this.data = data; + this.total = total; + this.page = page; + this.size = size; + this.totalPages = totalPages; + } + + // Méthode utilitaire pour calculer le nombre de pages + private Integer calculateTotalPages(Long total, Integer size) { + if (size == null || size == 0 || total == null) { + return 0; + } + return (int) Math.ceil((double) total / size); + } + + // Getters et setters + public List getData() { + return data; + } + + public void setData(List data) { + this.data = data; + } + + public Long getTotal() { + return total; + } + + public void setTotal(Long total) { + this.total = total; + this.totalPages = calculateTotalPages(total, this.size); + } + + public Integer getPage() { + return page; + } + + public void setPage(Integer page) { + this.page = page; + } + + public Integer getSize() { + return size; + } + + public void setSize(Integer size) { + this.size = size; + this.totalPages = calculateTotalPages(this.total, size); + } + + public Integer getTotalPages() { + return totalPages; + } + + public void setTotalPages(Integer totalPages) { + this.totalPages = totalPages; + } + + // Méthodes utilitaires + public boolean hasNext() { + return page != null && totalPages != null && page < totalPages - 1; + } + + public boolean hasPrevious() { + return page != null && page > 0; + } + + public boolean isEmpty() { + return data == null || data.isEmpty(); + } + + @Override + public String toString() { + return "PagedResponse{" + + "total=" + total + + ", page=" + page + + ", size=" + size + + ", totalPages=" + totalPages + + ", itemsCount=" + (data != null ? data.size() : 0) + + '}'; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/communication/request/CreateConversationRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/communication/request/CreateConversationRequest.java index 7dabd92..a67dd5d 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/communication/request/CreateConversationRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/communication/request/CreateConversationRequest.java @@ -1,27 +1,27 @@ -package dev.lions.unionflow.server.api.dto.communication.request; - -import dev.lions.unionflow.server.api.enums.communication.ConversationType; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotEmpty; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import lombok.Builder; - -import java.util.List; -import java.util.UUID; - -/** - * Request DTO pour créer une conversation - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-16 - */ -@Builder -public record CreateConversationRequest( - @NotBlank @Size(max = 255) String name, - @Size(max = 1000) String description, - @NotNull ConversationType type, - @NotEmpty List participantIds, - UUID organisationId -) {} +package dev.lions.unionflow.server.api.dto.communication.request; + +import dev.lions.unionflow.server.api.enums.communication.ConversationType; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotEmpty; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import lombok.Builder; + +import java.util.List; +import java.util.UUID; + +/** + * Request DTO pour créer une conversation + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-16 + */ +@Builder +public record CreateConversationRequest( + @NotBlank @Size(max = 255) String name, + @Size(max = 1000) String description, + @NotNull ConversationType type, + @NotEmpty List participantIds, + UUID organisationId +) {} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/communication/request/SendMessageRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/communication/request/SendMessageRequest.java index c98f7f5..c25094a 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/communication/request/SendMessageRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/communication/request/SendMessageRequest.java @@ -1,29 +1,29 @@ -package dev.lions.unionflow.server.api.dto.communication.request; - -import dev.lions.unionflow.server.api.enums.communication.MessagePriority; -import dev.lions.unionflow.server.api.enums.communication.MessageType; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import lombok.Builder; - -import java.util.List; -import java.util.UUID; - -/** - * Request DTO pour envoyer un message - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-16 - */ -@Builder -public record SendMessageRequest( - @NotNull UUID conversationId, - @NotBlank @Size(max = 10000) String content, - MessageType type, - MessagePriority priority, - List recipientIds, - List recipientRoles, - List attachments -) {} +package dev.lions.unionflow.server.api.dto.communication.request; + +import dev.lions.unionflow.server.api.enums.communication.MessagePriority; +import dev.lions.unionflow.server.api.enums.communication.MessageType; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import lombok.Builder; + +import java.util.List; +import java.util.UUID; + +/** + * Request DTO pour envoyer un message + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-16 + */ +@Builder +public record SendMessageRequest( + @NotNull UUID conversationId, + @NotBlank @Size(max = 10000) String content, + MessageType type, + MessagePriority priority, + List recipientIds, + List recipientRoles, + List attachments +) {} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateCompteComptableRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateCompteComptableRequest.java index 7cb68b2..45f4782 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateCompteComptableRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateCompteComptableRequest.java @@ -1,28 +1,28 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import dev.lions.unionflow.server.api.enums.comptabilite.TypeCompteComptable; -import jakarta.validation.constraints.Max; -import jakarta.validation.constraints.Min; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import java.math.BigDecimal; -import lombok.Builder; - -/** - * Requête de création d'un compte comptable. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreateCompteComptableRequest( - @NotBlank(message = "Le numéro de compte est obligatoire") String numeroCompte, - @NotBlank(message = "Le libellé est obligatoire") String libelle, - @NotNull(message = "Le type de compte est obligatoire") TypeCompteComptable typeCompte, - @NotNull(message = "La classe comptable est obligatoire") @Min(value = 1, message = "La classe comptable doit être entre 1 et 7") @Max(value = 7, message = "La classe comptable doit être entre 1 et 7") Integer classeComptable, - BigDecimal soldeInitial, - BigDecimal soldeActuel, - Boolean compteCollectif, - Boolean compteAnalytique, - String description) { -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import dev.lions.unionflow.server.api.enums.comptabilite.TypeCompteComptable; +import jakarta.validation.constraints.Max; +import jakarta.validation.constraints.Min; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import java.math.BigDecimal; +import lombok.Builder; + +/** + * Requête de création d'un compte comptable. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreateCompteComptableRequest( + @NotBlank(message = "Le numéro de compte est obligatoire") String numeroCompte, + @NotBlank(message = "Le libellé est obligatoire") String libelle, + @NotNull(message = "Le type de compte est obligatoire") TypeCompteComptable typeCompte, + @NotNull(message = "La classe comptable est obligatoire") @Min(value = 1, message = "La classe comptable doit être entre 1 et 7") @Max(value = 7, message = "La classe comptable doit être entre 1 et 7") Integer classeComptable, + BigDecimal soldeInitial, + BigDecimal soldeActuel, + Boolean compteCollectif, + Boolean compteAnalytique, + String description) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateEcritureComptableRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateEcritureComptableRequest.java index ddd15cc..1575c7d 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateEcritureComptableRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateEcritureComptableRequest.java @@ -1,41 +1,41 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.List; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'une écriture comptable. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreateEcritureComptableRequest( - @NotBlank(message = "Le numéro de pièce est obligatoire") String numeroPiece, - - @NotNull(message = "La date de l'écriture est obligatoire") LocalDate dateEcriture, - - @NotBlank(message = "Le libellé est obligatoire") String libelle, - - String reference, - String lettrage, - Boolean pointe, - - @DecimalMin(value = "0.0") @Digits(integer = 12, fraction = 2) BigDecimal montantDebit, - @DecimalMin(value = "0.0") @Digits(integer = 12, fraction = 2) BigDecimal montantCredit, - - String commentaire, - - @NotNull(message = "Le journal est obligatoire") UUID journalId, - UUID organisationId, - UUID paiementId, - - List lignes) { -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.List; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'une écriture comptable. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreateEcritureComptableRequest( + @NotBlank(message = "Le numéro de pièce est obligatoire") String numeroPiece, + + @NotNull(message = "La date de l'écriture est obligatoire") LocalDate dateEcriture, + + @NotBlank(message = "Le libellé est obligatoire") String libelle, + + String reference, + String lettrage, + Boolean pointe, + + @DecimalMin(value = "0.0") @Digits(integer = 12, fraction = 2) BigDecimal montantDebit, + @DecimalMin(value = "0.0") @Digits(integer = 12, fraction = 2) BigDecimal montantCredit, + + String commentaire, + + @NotNull(message = "Le journal est obligatoire") UUID journalId, + UUID organisationId, + UUID paiementId, + + List lignes) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateJournalComptableRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateJournalComptableRequest.java index 5bef23d..b23dd59 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateJournalComptableRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateJournalComptableRequest.java @@ -1,24 +1,24 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import dev.lions.unionflow.server.api.enums.comptabilite.TypeJournalComptable; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import java.time.LocalDate; -import lombok.Builder; - -/** - * Requête de création d'un journal comptable. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreateJournalComptableRequest( - @NotBlank(message = "Le code du journal est obligatoire") String code, - @NotBlank(message = "Le libellé est obligatoire") String libelle, - @NotNull(message = "Le type de journal est obligatoire") TypeJournalComptable typeJournal, - LocalDate dateDebut, - LocalDate dateFin, - String statut, - String description) { -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import dev.lions.unionflow.server.api.enums.comptabilite.TypeJournalComptable; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import java.time.LocalDate; +import lombok.Builder; + +/** + * Requête de création d'un journal comptable. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreateJournalComptableRequest( + @NotBlank(message = "Le code du journal est obligatoire") String code, + @NotBlank(message = "Le libellé est obligatoire") String libelle, + @NotNull(message = "Le type de journal est obligatoire") TypeJournalComptable typeJournal, + LocalDate dateDebut, + LocalDate dateFin, + String statut, + String description) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateLigneEcritureRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateLigneEcritureRequest.java index f097a19..376c073 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateLigneEcritureRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateLigneEcritureRequest.java @@ -1,30 +1,30 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.Min; -import jakarta.validation.constraints.NotNull; -import java.math.BigDecimal; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'une ligne d'écriture comptable. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreateLigneEcritureRequest( - @NotNull(message = "Le numéro de ligne est obligatoire") @Min(value = 1, message = "Le numéro de ligne doit être positif") Integer numeroLigne, - - @DecimalMin(value = "0.0", message = "Le montant débit doit être positif ou nul") @Digits(integer = 12, fraction = 2) BigDecimal montantDebit, - - @DecimalMin(value = "0.0", message = "Le montant crédit doit être positif ou nul") @Digits(integer = 12, fraction = 2) BigDecimal montantCredit, - - String libelle, - String reference, - - @NotNull(message = "L'écriture est obligatoire") UUID ecritureId, - @NotNull(message = "Le compte comptable est obligatoire") UUID compteComptableId) { -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.Min; +import jakarta.validation.constraints.NotNull; +import java.math.BigDecimal; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'une ligne d'écriture comptable. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreateLigneEcritureRequest( + @NotNull(message = "Le numéro de ligne est obligatoire") @Min(value = 1, message = "Le numéro de ligne doit être positif") Integer numeroLigne, + + @DecimalMin(value = "0.0", message = "Le montant débit doit être positif ou nul") @Digits(integer = 12, fraction = 2) BigDecimal montantDebit, + + @DecimalMin(value = "0.0", message = "Le montant crédit doit être positif ou nul") @Digits(integer = 12, fraction = 2) BigDecimal montantCredit, + + String libelle, + String reference, + + @NotNull(message = "L'écriture est obligatoire") UUID ecritureId, + @NotNull(message = "Le compte comptable est obligatoire") UUID compteComptableId) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateCompteComptableRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateCompteComptableRequest.java index 0ecc684..3f271fc 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateCompteComptableRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateCompteComptableRequest.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import dev.lions.unionflow.server.api.enums.comptabilite.TypeCompteComptable; -import jakarta.validation.constraints.Max; -import jakarta.validation.constraints.Min; -import java.math.BigDecimal; -import lombok.Builder; - -/** - * Requête de mise à jour d'un compte comptable. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record UpdateCompteComptableRequest( - String numeroCompte, - String libelle, - TypeCompteComptable typeCompte, - @Min(value = 1, message = "La classe comptable doit être entre 1 et 7") @Max(value = 7, message = "La classe comptable doit être entre 1 et 7") Integer classeComptable, - BigDecimal soldeInitial, - BigDecimal soldeActuel, - Boolean compteCollectif, - Boolean compteAnalytique, - String description) { -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import dev.lions.unionflow.server.api.enums.comptabilite.TypeCompteComptable; +import jakarta.validation.constraints.Max; +import jakarta.validation.constraints.Min; +import java.math.BigDecimal; +import lombok.Builder; + +/** + * Requête de mise à jour d'un compte comptable. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record UpdateCompteComptableRequest( + String numeroCompte, + String libelle, + TypeCompteComptable typeCompte, + @Min(value = 1, message = "La classe comptable doit être entre 1 et 7") @Max(value = 7, message = "La classe comptable doit être entre 1 et 7") Integer classeComptable, + BigDecimal soldeInitial, + BigDecimal soldeActuel, + Boolean compteCollectif, + Boolean compteAnalytique, + String description) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateEcritureComptableRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateEcritureComptableRequest.java index 322a388..e572bed 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateEcritureComptableRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateEcritureComptableRequest.java @@ -1,34 +1,34 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.List; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de mise à jour d'une écriture comptable. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record UpdateEcritureComptableRequest( - String numeroPiece, - LocalDate dateEcriture, - String libelle, - String reference, - String lettrage, - Boolean pointe, - - @DecimalMin(value = "0.0") @Digits(integer = 12, fraction = 2) BigDecimal montantDebit, - @DecimalMin(value = "0.0") @Digits(integer = 12, fraction = 2) BigDecimal montantCredit, - - String commentaire, - UUID journalId, - UUID paiementId, - - List lignes) { -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.List; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de mise à jour d'une écriture comptable. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record UpdateEcritureComptableRequest( + String numeroPiece, + LocalDate dateEcriture, + String libelle, + String reference, + String lettrage, + Boolean pointe, + + @DecimalMin(value = "0.0") @Digits(integer = 12, fraction = 2) BigDecimal montantDebit, + @DecimalMin(value = "0.0") @Digits(integer = 12, fraction = 2) BigDecimal montantCredit, + + String commentaire, + UUID journalId, + UUID paiementId, + + List lignes) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateJournalComptableRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateJournalComptableRequest.java index ea96aaf..4c16c41 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateJournalComptableRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateJournalComptableRequest.java @@ -1,21 +1,21 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import dev.lions.unionflow.server.api.enums.comptabilite.TypeJournalComptable; -import java.time.LocalDate; -import lombok.Builder; - -/** - * Requête de mise à jour d'un journal comptable. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record UpdateJournalComptableRequest( - String libelle, - TypeJournalComptable typeJournal, - LocalDate dateDebut, - LocalDate dateFin, - String statut, - String description) { -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import dev.lions.unionflow.server.api.enums.comptabilite.TypeJournalComptable; +import java.time.LocalDate; +import lombok.Builder; + +/** + * Requête de mise à jour d'un journal comptable. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record UpdateJournalComptableRequest( + String libelle, + TypeJournalComptable typeJournal, + LocalDate dateDebut, + LocalDate dateFin, + String statut, + String description) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateLigneEcritureRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateLigneEcritureRequest.java index 8d74a42..78c2df3 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateLigneEcritureRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateLigneEcritureRequest.java @@ -1,24 +1,24 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.Min; -import java.math.BigDecimal; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de mise à jour d'une ligne d'écriture comptable. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record UpdateLigneEcritureRequest( - @Min(value = 1, message = "Le numéro de ligne doit être positif") Integer numeroLigne, - @DecimalMin(value = "0.0", message = "Le montant débit doit être positif ou nul") @Digits(integer = 12, fraction = 2) BigDecimal montantDebit, - @DecimalMin(value = "0.0", message = "Le montant crédit doit être positif ou nul") @Digits(integer = 12, fraction = 2) BigDecimal montantCredit, - String libelle, - String reference, - UUID compteComptableId) { -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.Min; +import java.math.BigDecimal; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de mise à jour d'une ligne d'écriture comptable. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record UpdateLigneEcritureRequest( + @Min(value = 1, message = "Le numéro de ligne doit être positif") Integer numeroLigne, + @DecimalMin(value = "0.0", message = "Le montant débit doit être positif ou nul") @Digits(integer = 12, fraction = 2) BigDecimal montantDebit, + @DecimalMin(value = "0.0", message = "Le montant crédit doit être positif ou nul") @Digits(integer = 12, fraction = 2) BigDecimal montantCredit, + String libelle, + String reference, + UUID compteComptableId) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/CompteComptableResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/CompteComptableResponse.java index a7aa558..9ce1ff6 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/CompteComptableResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/CompteComptableResponse.java @@ -1,35 +1,35 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import dev.lions.unionflow.server.api.enums.comptabilite.TypeCompteComptable; -import java.math.BigDecimal; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée d'un compte comptable. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class CompteComptableResponse extends BaseResponse { - - private String numeroCompte; - private String libelle; - private TypeCompteComptable typeCompte; - private Integer classeComptable; - private BigDecimal soldeInitial; - private BigDecimal soldeActuel; - private Boolean compteCollectif; - private Boolean compteAnalytique; - private String description; -} +package dev.lions.unionflow.server.api.dto.comptabilite.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import dev.lions.unionflow.server.api.enums.comptabilite.TypeCompteComptable; +import java.math.BigDecimal; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée d'un compte comptable. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class CompteComptableResponse extends BaseResponse { + + private String numeroCompte; + private String libelle; + private TypeCompteComptable typeCompte; + private Integer classeComptable; + private BigDecimal soldeInitial; + private BigDecimal soldeActuel; + private Boolean compteCollectif; + private Boolean compteAnalytique; + private String description; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/EcritureComptableResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/EcritureComptableResponse.java index df50568..0cf7fb9 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/EcritureComptableResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/EcritureComptableResponse.java @@ -1,41 +1,41 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.List; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée d'une écriture comptable. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class EcritureComptableResponse extends BaseResponse { - - private String numeroPiece; - private LocalDate dateEcriture; - private String libelle; - private String reference; - private String lettrage; - private Boolean pointe; - private BigDecimal montantDebit; - private BigDecimal montantCredit; - private String commentaire; - private UUID journalId; - private UUID organisationId; - private UUID paiementId; - private List lignes; -} +package dev.lions.unionflow.server.api.dto.comptabilite.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.List; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée d'une écriture comptable. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class EcritureComptableResponse extends BaseResponse { + + private String numeroPiece; + private LocalDate dateEcriture; + private String libelle; + private String reference; + private String lettrage; + private Boolean pointe; + private BigDecimal montantDebit; + private BigDecimal montantCredit; + private String commentaire; + private UUID journalId; + private UUID organisationId; + private UUID paiementId; + private List lignes; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/JournalComptableResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/JournalComptableResponse.java index c075576..24ca32a 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/JournalComptableResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/JournalComptableResponse.java @@ -1,33 +1,33 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import dev.lions.unionflow.server.api.enums.comptabilite.TypeJournalComptable; -import java.time.LocalDate; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée d'un journal comptable. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class JournalComptableResponse extends BaseResponse { - - private String code; - private String libelle; - private TypeJournalComptable typeJournal; - private LocalDate dateDebut; - private LocalDate dateFin; - private String statut; - private String description; -} +package dev.lions.unionflow.server.api.dto.comptabilite.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import dev.lions.unionflow.server.api.enums.comptabilite.TypeJournalComptable; +import java.time.LocalDate; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée d'un journal comptable. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class JournalComptableResponse extends BaseResponse { + + private String code; + private String libelle; + private TypeJournalComptable typeJournal; + private LocalDate dateDebut; + private LocalDate dateFin; + private String statut; + private String description; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/LigneEcritureResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/LigneEcritureResponse.java index e6bab58..33175bf 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/LigneEcritureResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/comptabilite/response/LigneEcritureResponse.java @@ -1,33 +1,33 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.math.BigDecimal; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée d'une ligne d'écriture comptable. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class LigneEcritureResponse extends BaseResponse { - - private Integer numeroLigne; - private BigDecimal montantDebit; - private BigDecimal montantCredit; - private String libelle; - private String reference; - private UUID ecritureId; - private UUID compteComptableId; -} +package dev.lions.unionflow.server.api.dto.comptabilite.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.math.BigDecimal; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée d'une ligne d'écriture comptable. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class LigneEcritureResponse extends BaseResponse { + + private Integer numeroLigne; + private BigDecimal montantDebit; + private BigDecimal montantCredit; + private String libelle; + private String reference; + private UUID ecritureId; + private UUID compteComptableId; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/config/request/CreateConfigurationRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/config/request/CreateConfigurationRequest.java index cd71862..8375d44 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/config/request/CreateConfigurationRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/config/request/CreateConfigurationRequest.java @@ -1,22 +1,22 @@ -package dev.lions.unionflow.server.api.dto.config.request; - -import java.util.Map; -import lombok.Builder; - -/** - * Requête de création d'une configuration. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreateConfigurationRequest( - String cle, - String valeur, - String type, - String categorie, - String description, - Boolean modifiable, - Boolean visible, - Map metadonnees) { -} +package dev.lions.unionflow.server.api.dto.config.request; + +import java.util.Map; +import lombok.Builder; + +/** + * Requête de création d'une configuration. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreateConfigurationRequest( + String cle, + String valeur, + String type, + String categorie, + String description, + Boolean modifiable, + Boolean visible, + Map metadonnees) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/config/request/ParametresLcbFtRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/config/request/ParametresLcbFtRequest.java index 3df99f5..a59335b 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/config/request/ParametresLcbFtRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/config/request/ParametresLcbFtRequest.java @@ -1,50 +1,50 @@ -package dev.lions.unionflow.server.api.dto.config.request; - -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -import java.math.BigDecimal; - -/** - * Requête de création/mise à jour des paramètres LCB-FT (Lutte contre le Blanchiment et le Financement du Terrorisme). - * Définit les seuils au-dessus desquels les justifications d'origine des fonds sont obligatoires. - * - * @author lions dev Team - * @version 1.0 - * @since 2026-03-13 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Paramètres LCB-FT (seuils de vigilance)") -public class ParametresLcbFtRequest { - - @Schema(description = "ID de l'organisation (null pour paramètres plateforme)") - private String organisationId; - - @NotNull(message = "Le montant seuil de justification est obligatoire") - @DecimalMin(value = "0", message = "Le montant doit être positif ou nul") - @Schema(description = "Montant au-dessus duquel l'origine des fonds est obligatoire (ex. 500000 XOF)", example = "500000") - private BigDecimal montantSeuilJustification; - - @NotNull(message = "Le montant seuil de validation manuelle est obligatoire") - @DecimalMin(value = "0", message = "Le montant doit être positif ou nul") - @Schema(description = "Montant au-dessus duquel une validation manuelle est requise (ex. 1000000 XOF)", example = "1000000") - private BigDecimal montantSeuilValidationManuelle; - - @NotBlank(message = "Le code devise est obligatoire") - @Size(max = 3, message = "Le code devise doit faire 3 caractères (ISO 4217)") - @Schema(description = "Code devise ISO 4217 (ex. XOF, EUR, USD)", example = "XOF") - private String codeDevise; - - @Schema(description = "Notes ou commentaires sur la configuration") - private String notes; -} +package dev.lions.unionflow.server.api.dto.config.request; + +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +import java.math.BigDecimal; + +/** + * Requête de création/mise à jour des paramètres LCB-FT (Lutte contre le Blanchiment et le Financement du Terrorisme). + * Définit les seuils au-dessus desquels les justifications d'origine des fonds sont obligatoires. + * + * @author lions dev Team + * @version 1.0 + * @since 2026-03-13 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Paramètres LCB-FT (seuils de vigilance)") +public class ParametresLcbFtRequest { + + @Schema(description = "ID de l'organisation (null pour paramètres plateforme)") + private String organisationId; + + @NotNull(message = "Le montant seuil de justification est obligatoire") + @DecimalMin(value = "0", message = "Le montant doit être positif ou nul") + @Schema(description = "Montant au-dessus duquel l'origine des fonds est obligatoire (ex. 500000 XOF)", example = "500000") + private BigDecimal montantSeuilJustification; + + @NotNull(message = "Le montant seuil de validation manuelle est obligatoire") + @DecimalMin(value = "0", message = "Le montant doit être positif ou nul") + @Schema(description = "Montant au-dessus duquel une validation manuelle est requise (ex. 1000000 XOF)", example = "1000000") + private BigDecimal montantSeuilValidationManuelle; + + @NotBlank(message = "Le code devise est obligatoire") + @Size(max = 3, message = "Le code devise doit faire 3 caractères (ISO 4217)") + @Schema(description = "Code devise ISO 4217 (ex. XOF, EUR, USD)", example = "XOF") + private String codeDevise; + + @Schema(description = "Notes ou commentaires sur la configuration") + private String notes; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/config/request/UpdateConfigurationRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/config/request/UpdateConfigurationRequest.java index 5c89627..cb7d6a2 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/config/request/UpdateConfigurationRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/config/request/UpdateConfigurationRequest.java @@ -1,22 +1,22 @@ -package dev.lions.unionflow.server.api.dto.config.request; - -import java.util.Map; -import lombok.Builder; - -/** - * Requête de mise à jour d'une configuration. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record UpdateConfigurationRequest( - String cle, - String valeur, - String type, - String categorie, - String description, - Boolean modifiable, - Boolean visible, - Map metadonnees) { -} +package dev.lions.unionflow.server.api.dto.config.request; + +import java.util.Map; +import lombok.Builder; + +/** + * Requête de mise à jour d'une configuration. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record UpdateConfigurationRequest( + String cle, + String valeur, + String type, + String categorie, + String description, + Boolean modifiable, + Boolean visible, + Map metadonnees) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/config/response/ConfigurationResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/config/response/ConfigurationResponse.java index 70805c1..46305d2 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/config/response/ConfigurationResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/config/response/ConfigurationResponse.java @@ -1,33 +1,33 @@ -package dev.lions.unionflow.server.api.dto.config.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.util.Map; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse contenant les données d'une configuration. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class ConfigurationResponse extends BaseResponse { - - private String cle; - private String valeur; - private String type; - private String categorie; - private String description; - private Boolean modifiable; - private Boolean visible; - private Map metadonnees; -} +package dev.lions.unionflow.server.api.dto.config.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.util.Map; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse contenant les données d'une configuration. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class ConfigurationResponse extends BaseResponse { + + private String cle; + private String valeur; + private String type; + private String categorie; + private String description; + private Boolean modifiable; + private Boolean visible; + private Map metadonnees; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/config/response/ParametresLcbFtResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/config/response/ParametresLcbFtResponse.java index 96adda7..04d4cd6 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/config/response/ParametresLcbFtResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/config/response/ParametresLcbFtResponse.java @@ -1,49 +1,49 @@ -package dev.lions.unionflow.server.api.dto.config.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -import java.math.BigDecimal; - -/** - * Réponse contenant les paramètres LCB-FT (Lutte contre le Blanchiment et le Financement du Terrorisme). - * Retourne les seuils configurés pour une organisation ou la plateforme. - * - * @author lions dev Team - * @version 1.0 - * @since 2026-03-13 - */ -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Paramètres LCB-FT avec seuils de vigilance") -public class ParametresLcbFtResponse extends BaseResponse { - - @Schema(description = "ID de l'organisation (null si paramètres plateforme)") - private String organisationId; - - @Schema(description = "Nom de l'organisation (null si paramètres plateforme)") - private String organisationNom; - - @Schema(description = "Montant au-dessus duquel l'origine des fonds est obligatoire", example = "500000") - private BigDecimal montantSeuilJustification; - - @Schema(description = "Montant au-dessus duquel une validation manuelle est requise", example = "1000000") - private BigDecimal montantSeuilValidationManuelle; - - @Schema(description = "Code devise ISO 4217", example = "XOF") - private String codeDevise; - - @Schema(description = "Notes ou commentaires sur la configuration") - private String notes; - - @Schema(description = "Indique si ces paramètres s'appliquent à toute la plateforme") - private Boolean estParametrePlateforme; -} +package dev.lions.unionflow.server.api.dto.config.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +import java.math.BigDecimal; + +/** + * Réponse contenant les paramètres LCB-FT (Lutte contre le Blanchiment et le Financement du Terrorisme). + * Retourne les seuils configurés pour une organisation ou la plateforme. + * + * @author lions dev Team + * @version 1.0 + * @since 2026-03-13 + */ +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Paramètres LCB-FT avec seuils de vigilance") +public class ParametresLcbFtResponse extends BaseResponse { + + @Schema(description = "ID de l'organisation (null si paramètres plateforme)") + private String organisationId; + + @Schema(description = "Nom de l'organisation (null si paramètres plateforme)") + private String organisationNom; + + @Schema(description = "Montant au-dessus duquel l'origine des fonds est obligatoire", example = "500000") + private BigDecimal montantSeuilJustification; + + @Schema(description = "Montant au-dessus duquel une validation manuelle est requise", example = "1000000") + private BigDecimal montantSeuilValidationManuelle; + + @Schema(description = "Code devise ISO 4217", example = "XOF") + private String codeDevise; + + @Schema(description = "Notes ou commentaires sur la configuration") + private String notes; + + @Schema(description = "Indique si ces paramètres s'appliquent à toute la plateforme") + private Boolean estParametrePlateforme; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/cotisation/request/CreateCotisationRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/cotisation/request/CreateCotisationRequest.java index 9a161d1..c7eae8b 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/cotisation/request/CreateCotisationRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/cotisation/request/CreateCotisationRequest.java @@ -1,62 +1,62 @@ -package dev.lions.unionflow.server.api.dto.cotisation.request; - -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.Max; -import jakarta.validation.constraints.Min; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.UUID; - -import lombok.Builder; - -/** - * Requête de création d'une nouvelle cotisation. - * - * @param membreId Identifiant du membre concerné. - * @param typeCotisation Type de cotisation (MENSUELLE, etc.). - * @param libelle Libellé de la cotisation. - * @param description Description détaillée. - * @param montantDu Montant total à payer. - * @param codeDevise Code ISO de la devise (par défaut XOF). - * @param dateEcheance Date limite de paiement. - * @param periode Période concernée (ex: Janvier 2025). - * @param annee Année de référence. - * @param mois Mois de référence (1-12, optionnel). - * @param recurrente Indique si la cotisation est récurrente. - * @param observations Commentaires libres. - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-22 - */ -@Builder -public record CreateCotisationRequest( - @NotNull(message = "L'identifiant du membre est obligatoire") UUID membreId, - - @NotNull(message = "L'identifiant de l'organisation est obligatoire") UUID organisationId, - - @NotBlank(message = "Le type de cotisation est obligatoire") String typeCotisation, - - @NotBlank(message = "Le libellé est obligatoire") @Size(max = 100) String libelle, - - @Size(max = 500) String description, - - @NotNull(message = "Le montant dû est obligatoire") @DecimalMin(value = "0.0", inclusive = false) @Digits(integer = 10, fraction = 2) BigDecimal montantDu, - - @Size(min = 3, max = 3) String codeDevise, - - @NotNull(message = "La date d'échéance est obligatoire") LocalDate dateEcheance, - - @Size(max = 50) String periode, - - @Min(2020) @Max(2100) Integer annee, - - @Min(1) @Max(12) Integer mois, - - Boolean recurrente, - - @Size(max = 1000) String observations) { -} +package dev.lions.unionflow.server.api.dto.cotisation.request; + +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.Max; +import jakarta.validation.constraints.Min; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.UUID; + +import lombok.Builder; + +/** + * Requête de création d'une nouvelle cotisation. + * + * @param membreId Identifiant du membre concerné. + * @param typeCotisation Type de cotisation (MENSUELLE, etc.). + * @param libelle Libellé de la cotisation. + * @param description Description détaillée. + * @param montantDu Montant total à payer. + * @param codeDevise Code ISO de la devise (par défaut XOF). + * @param dateEcheance Date limite de paiement. + * @param periode Période concernée (ex: Janvier 2025). + * @param annee Année de référence. + * @param mois Mois de référence (1-12, optionnel). + * @param recurrente Indique si la cotisation est récurrente. + * @param observations Commentaires libres. + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-22 + */ +@Builder +public record CreateCotisationRequest( + @NotNull(message = "L'identifiant du membre est obligatoire") UUID membreId, + + @NotNull(message = "L'identifiant de l'organisation est obligatoire") UUID organisationId, + + @NotBlank(message = "Le type de cotisation est obligatoire") String typeCotisation, + + @NotBlank(message = "Le libellé est obligatoire") @Size(max = 100) String libelle, + + @Size(max = 500) String description, + + @NotNull(message = "Le montant dû est obligatoire") @DecimalMin(value = "0.0", inclusive = false) @Digits(integer = 10, fraction = 2) BigDecimal montantDu, + + @Size(min = 3, max = 3) String codeDevise, + + @NotNull(message = "La date d'échéance est obligatoire") LocalDate dateEcheance, + + @Size(max = 50) String periode, + + @Min(2020) @Max(2100) Integer annee, + + @Min(1) @Max(12) Integer mois, + + Boolean recurrente, + + @Size(max = 1000) String observations) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/cotisation/request/UpdateCotisationRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/cotisation/request/UpdateCotisationRequest.java index a3cfbd1..00627db 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/cotisation/request/UpdateCotisationRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/cotisation/request/UpdateCotisationRequest.java @@ -1,48 +1,48 @@ -package dev.lions.unionflow.server.api.dto.cotisation.request; - -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.Max; -import jakarta.validation.constraints.Min; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; - -import lombok.Builder; - -/** - * Requête de mise à jour d'une cotisation existante. - * - * @param libelle Nouveau libellé. - * @param description Nouvelle description. - * @param montantDu Nouveau montant dû (si non payé). - * @param dateEcheance Nouvelle date d'échéance. - * @param observations Nouvelles observations. - * @param statut Nouveau statut (validation métier requise). - * @param annee Année de référence. - * @param mois Mois de référence. - * @param recurrente État de récurrence. - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-22 - */ -@Builder -public record UpdateCotisationRequest( - @Size(max = 100) String libelle, - - @Size(max = 500) String description, - - @DecimalMin(value = "0.0", inclusive = false) @Digits(integer = 10, fraction = 2) BigDecimal montantDu, - - LocalDate dateEcheance, - - @Size(max = 1000) String observations, - - String statut, - - @Min(2020) @Max(2100) Integer annee, - - @Min(1) @Max(12) Integer mois, - - Boolean recurrente) { -} +package dev.lions.unionflow.server.api.dto.cotisation.request; + +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.Max; +import jakarta.validation.constraints.Min; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; + +import lombok.Builder; + +/** + * Requête de mise à jour d'une cotisation existante. + * + * @param libelle Nouveau libellé. + * @param description Nouvelle description. + * @param montantDu Nouveau montant dû (si non payé). + * @param dateEcheance Nouvelle date d'échéance. + * @param observations Nouvelles observations. + * @param statut Nouveau statut (validation métier requise). + * @param annee Année de référence. + * @param mois Mois de référence. + * @param recurrente État de récurrence. + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-22 + */ +@Builder +public record UpdateCotisationRequest( + @Size(max = 100) String libelle, + + @Size(max = 500) String description, + + @DecimalMin(value = "0.0", inclusive = false) @Digits(integer = 10, fraction = 2) BigDecimal montantDu, + + LocalDate dateEcheance, + + @Size(max = 1000) String observations, + + String statut, + + @Min(2020) @Max(2100) Integer annee, + + @Min(1) @Max(12) Integer mois, + + Boolean recurrente) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/cotisation/response/CotisationResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/cotisation/response/CotisationResponse.java index 4e55c55..49220e4 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/cotisation/response/CotisationResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/cotisation/response/CotisationResponse.java @@ -1,129 +1,129 @@ -package dev.lions.unionflow.server.api.dto.cotisation.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalDateTime; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée pour une cotisation. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-22 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class CotisationResponse extends BaseResponse { - - private String numeroReference; - private UUID membreId; - private String nomMembre; - /** Nom complet (prénom + nom) pour affichage */ - private String nomCompletMembre; - private String numeroMembre; - /** Initiales du membre (ex: JD pour Jean Dupont) */ - private String initialesMembre; - /** Type / statut du membre (ex: Actif, En attente) */ - private String typeMembre; - private UUID organisationId; - private String nomOrganisation; - /** Région de l'organisation (affichage liste) */ - private String regionOrganisation; - /** Classe CSS icône PrimeFaces pour l'organisation (ex: pi-building) */ - private String iconeOrganisation; - private String typeCotisation; - /** Alias pour tri/filtre (type de cotisation) */ - private String type; - private String typeCotisationLibelle; - /** Libellé du type pour affichage (alias typeCotisationLibelle) */ - private String typeLibelle; - /** Sévérité PrimeFaces pour le tag type (info, success, warn, error, secondary) */ - private String typeSeverity; - /** Classe icône PrimeFaces pour le type (ex: pi-calendar) */ - private String typeIcon; - private String libelle; - private String description; - private BigDecimal montantDu; - /** Alias pour tri/filtre (montant du) */ - private BigDecimal montant; - /** Montant formaté pour affichage (ex: "5 000") */ - private String montantFormatte; - private BigDecimal montantPaye; - private BigDecimal montantRestant; - private String codeDevise; - private String statut; - private String statutLibelle; - /** Sévérité PrimeFaces pour le tag statut */ - private String statutSeverity; - /** Classe icône PrimeFaces pour le statut (ex: pi-check) */ - private String statutIcon; - private LocalDate dateEcheance; - /** Date d'échéance formatée pour affichage */ - private String dateEcheanceFormattee; - /** Classe CSS couleur pour le retard (ex: text-red-500) */ - private String retardCouleur; - /** Texte affiché pour le retard (ex: "X jours de retard") */ - private String retardTexte; - /** Date de paiement formatée pour affichage */ - private String datePaiementFormattee; - /** Icône PrimeFaces pour le mode de paiement */ - private String modePaiementIcon; - /** Libellé du mode de paiement */ - private String modePaiementLibelle; - private LocalDateTime datePaiement; - private String periode; - private Integer annee; - private Integer mois; - private String observations; - private Boolean recurrente; - private Integer nombreRappels; - private LocalDateTime dateDernierRappel; - private UUID valideParId; - private String nomValidateur; - private LocalDateTime dateValidation; - private Integer pourcentagePaiement; - private Long joursRetard; - private Boolean enRetard; - - // === MÉTHODES DE FORMATAGE === - - public String getMontantDuFormatte() { - if (montantDu == null) return "0 FCFA"; - return String.format(java.util.Locale.US, "%,.0f %s", montantDu, codeDevise != null ? codeDevise : "FCFA"); - } - - public String getMontantPayeFormatte() { - if (montantPaye == null) return "0 FCFA"; - return String.format(java.util.Locale.US, "%,.0f %s", montantPaye, codeDevise != null ? codeDevise : "FCFA"); - } - - public String getMontantRestantFormatte() { - if (montantRestant == null) return "0 FCFA"; - return String.format(java.util.Locale.US, "%,.0f %s", montantRestant, codeDevise != null ? codeDevise : "FCFA"); - } - - public boolean isMontantRestantPositif() { - return montantRestant != null && montantRestant.signum() > 0; - } - - /** Alias de {@link #modePaiementLibelle} pour #{cotisation.methodePaiementLibelle}. */ - public String getMethodePaiementLibelle() { - return modePaiementLibelle; - } - - // Informations de paiement - private String methodePaiement; // WAVE_MONEY, VIREMENT, ESPECES, CARTE, MOBILE_MONEY - private String referencePaiement; // Référence externe du paiement - private String waveSessionId; // ID de session Wave Money pour prélèvements -} +package dev.lions.unionflow.server.api.dto.cotisation.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée pour une cotisation. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-22 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class CotisationResponse extends BaseResponse { + + private String numeroReference; + private UUID membreId; + private String nomMembre; + /** Nom complet (prénom + nom) pour affichage */ + private String nomCompletMembre; + private String numeroMembre; + /** Initiales du membre (ex: JD pour Jean Dupont) */ + private String initialesMembre; + /** Type / statut du membre (ex: Actif, En attente) */ + private String typeMembre; + private UUID organisationId; + private String nomOrganisation; + /** Région de l'organisation (affichage liste) */ + private String regionOrganisation; + /** Classe CSS icône PrimeFaces pour l'organisation (ex: pi-building) */ + private String iconeOrganisation; + private String typeCotisation; + /** Alias pour tri/filtre (type de cotisation) */ + private String type; + private String typeCotisationLibelle; + /** Libellé du type pour affichage (alias typeCotisationLibelle) */ + private String typeLibelle; + /** Sévérité PrimeFaces pour le tag type (info, success, warn, error, secondary) */ + private String typeSeverity; + /** Classe icône PrimeFaces pour le type (ex: pi-calendar) */ + private String typeIcon; + private String libelle; + private String description; + private BigDecimal montantDu; + /** Alias pour tri/filtre (montant du) */ + private BigDecimal montant; + /** Montant formaté pour affichage (ex: "5 000") */ + private String montantFormatte; + private BigDecimal montantPaye; + private BigDecimal montantRestant; + private String codeDevise; + private String statut; + private String statutLibelle; + /** Sévérité PrimeFaces pour le tag statut */ + private String statutSeverity; + /** Classe icône PrimeFaces pour le statut (ex: pi-check) */ + private String statutIcon; + private LocalDate dateEcheance; + /** Date d'échéance formatée pour affichage */ + private String dateEcheanceFormattee; + /** Classe CSS couleur pour le retard (ex: text-red-500) */ + private String retardCouleur; + /** Texte affiché pour le retard (ex: "X jours de retard") */ + private String retardTexte; + /** Date de paiement formatée pour affichage */ + private String datePaiementFormattee; + /** Icône PrimeFaces pour le mode de paiement */ + private String modePaiementIcon; + /** Libellé du mode de paiement */ + private String modePaiementLibelle; + private LocalDateTime datePaiement; + private String periode; + private Integer annee; + private Integer mois; + private String observations; + private Boolean recurrente; + private Integer nombreRappels; + private LocalDateTime dateDernierRappel; + private UUID valideParId; + private String nomValidateur; + private LocalDateTime dateValidation; + private Integer pourcentagePaiement; + private Long joursRetard; + private Boolean enRetard; + + // === MÉTHODES DE FORMATAGE === + + public String getMontantDuFormatte() { + if (montantDu == null) return "0 FCFA"; + return String.format(java.util.Locale.US, "%,.0f %s", montantDu, codeDevise != null ? codeDevise : "FCFA"); + } + + public String getMontantPayeFormatte() { + if (montantPaye == null) return "0 FCFA"; + return String.format(java.util.Locale.US, "%,.0f %s", montantPaye, codeDevise != null ? codeDevise : "FCFA"); + } + + public String getMontantRestantFormatte() { + if (montantRestant == null) return "0 FCFA"; + return String.format(java.util.Locale.US, "%,.0f %s", montantRestant, codeDevise != null ? codeDevise : "FCFA"); + } + + public boolean isMontantRestantPositif() { + return montantRestant != null && montantRestant.signum() > 0; + } + + /** Alias de {@link #modePaiementLibelle} pour #{cotisation.methodePaiementLibelle}. */ + public String getMethodePaiementLibelle() { + return modePaiementLibelle; + } + + // Informations de paiement + private String methodePaiement; // WAVE_MONEY, VIREMENT, ESPECES, CARTE, MOBILE_MONEY + private String referencePaiement; // Référence externe du paiement + private String waveSessionId; // ID de session Wave Money pour prélèvements +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/culte/DonReligieuxDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/culte/DonReligieuxDTO.java index 897482a..593faff 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/culte/DonReligieuxDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/culte/DonReligieuxDTO.java @@ -1,33 +1,33 @@ -package dev.lions.unionflow.server.api.dto.culte; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.culte.TypeDonReligieux; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; - -import java.math.BigDecimal; -import java.time.LocalDateTime; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class DonReligieuxDTO extends BaseDTO { - - private String institutionId; // Mosquée, Église, Paroisse... - - // Si relié spécifiquement à un fidèle enregistré - private String fideleId; - - private TypeDonReligieux typeDon; - - private BigDecimal montant; - private LocalDateTime dateEncaissement; - - // Utile pour la zakat (Nissab de l'année concernée) ou la dîme périodique - private String periodeOuNatureAssociee; -} +package dev.lions.unionflow.server.api.dto.culte; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.culte.TypeDonReligieux; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; + +import java.math.BigDecimal; +import java.time.LocalDateTime; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class DonReligieuxDTO extends BaseDTO { + + private String institutionId; // Mosquée, Église, Paroisse... + + // Si relié spécifiquement à un fidèle enregistré + private String fideleId; + + private TypeDonReligieux typeDon; + + private BigDecimal montant; + private LocalDateTime dateEncaissement; + + // Utile pour la zakat (Nissab de l'année concernée) ou la dîme périodique + private String periodeOuNatureAssociee; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardDataResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardDataResponse.java index 427b8e9..5cf4d09 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardDataResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardDataResponse.java @@ -1,122 +1,122 @@ -package dev.lions.unionflow.server.api.dto.dashboard; - -import com.fasterxml.jackson.annotation.JsonProperty; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.util.List; -import java.util.Map; - -/** - * DTO principal pour toutes les données du dashboard - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class DashboardDataResponse { - - @JsonProperty("stats") - private DashboardStatsResponse stats; - - @JsonProperty("recentActivities") - private List recentActivities; - - @JsonProperty("upcomingEvents") - private List upcomingEvents; - - @JsonProperty("userPreferences") - private Map userPreferences; - - @JsonProperty("organizationId") - private String organizationId; - - @JsonProperty("userId") - private String userId; - - // Méthodes utilitaires - public Integer getTodayEventsCount() { - if (upcomingEvents == null) { - return 0; - } - - return (int) upcomingEvents.stream() - .filter(event -> event.getIsToday() != null && event.getIsToday()) - .count(); - } - - public Integer getTomorrowEventsCount() { - if (upcomingEvents == null) { - return 0; - } - - return (int) upcomingEvents.stream() - .filter(event -> event.getIsTomorrow() != null && event.getIsTomorrow()) - .count(); - } - - public Integer getRecentActivitiesCount() { - if (recentActivities == null) { - return 0; - } - - return (int) recentActivities.stream() - .filter(activity -> activity.getIsRecent() != null && activity.getIsRecent()) - .count(); - } - - public Integer getTodayActivitiesCount() { - if (recentActivities == null) { - return 0; - } - - return (int) recentActivities.stream() - .filter(activity -> activity.getIsToday() != null && activity.getIsToday()) - .count(); - } - - public Boolean getHasUpcomingEvents() { - return upcomingEvents != null && !upcomingEvents.isEmpty(); - } - - public Boolean getHasRecentActivities() { - return recentActivities != null && !recentActivities.isEmpty(); - } - - public String getThemePreference() { - if (userPreferences == null) { - return "royal_teal"; - } - return (String) userPreferences.getOrDefault("theme", "royal_teal"); - } - - public String getLanguagePreference() { - if (userPreferences == null) { - return "fr"; - } - return (String) userPreferences.getOrDefault("language", "fr"); - } - - public Boolean getNotificationsEnabled() { - if (userPreferences == null) { - return true; - } - return (Boolean) userPreferences.getOrDefault("notifications", true); - } - - public Boolean getAutoRefreshEnabled() { - if (userPreferences == null) { - return true; - } - return (Boolean) userPreferences.getOrDefault("autoRefresh", true); - } - - public Integer getRefreshInterval() { - if (userPreferences == null) { - return 300; // 5 minutes par défaut - } - return (Integer) userPreferences.getOrDefault("refreshInterval", 300); - } -} +package dev.lions.unionflow.server.api.dto.dashboard; + +import com.fasterxml.jackson.annotation.JsonProperty; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.util.List; +import java.util.Map; + +/** + * DTO principal pour toutes les données du dashboard + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class DashboardDataResponse { + + @JsonProperty("stats") + private DashboardStatsResponse stats; + + @JsonProperty("recentActivities") + private List recentActivities; + + @JsonProperty("upcomingEvents") + private List upcomingEvents; + + @JsonProperty("userPreferences") + private Map userPreferences; + + @JsonProperty("organizationId") + private String organizationId; + + @JsonProperty("userId") + private String userId; + + // Méthodes utilitaires + public Integer getTodayEventsCount() { + if (upcomingEvents == null) { + return 0; + } + + return (int) upcomingEvents.stream() + .filter(event -> event.getIsToday() != null && event.getIsToday()) + .count(); + } + + public Integer getTomorrowEventsCount() { + if (upcomingEvents == null) { + return 0; + } + + return (int) upcomingEvents.stream() + .filter(event -> event.getIsTomorrow() != null && event.getIsTomorrow()) + .count(); + } + + public Integer getRecentActivitiesCount() { + if (recentActivities == null) { + return 0; + } + + return (int) recentActivities.stream() + .filter(activity -> activity.getIsRecent() != null && activity.getIsRecent()) + .count(); + } + + public Integer getTodayActivitiesCount() { + if (recentActivities == null) { + return 0; + } + + return (int) recentActivities.stream() + .filter(activity -> activity.getIsToday() != null && activity.getIsToday()) + .count(); + } + + public Boolean getHasUpcomingEvents() { + return upcomingEvents != null && !upcomingEvents.isEmpty(); + } + + public Boolean getHasRecentActivities() { + return recentActivities != null && !recentActivities.isEmpty(); + } + + public String getThemePreference() { + if (userPreferences == null) { + return "royal_teal"; + } + return (String) userPreferences.getOrDefault("theme", "royal_teal"); + } + + public String getLanguagePreference() { + if (userPreferences == null) { + return "fr"; + } + return (String) userPreferences.getOrDefault("language", "fr"); + } + + public Boolean getNotificationsEnabled() { + if (userPreferences == null) { + return true; + } + return (Boolean) userPreferences.getOrDefault("notifications", true); + } + + public Boolean getAutoRefreshEnabled() { + if (userPreferences == null) { + return true; + } + return (Boolean) userPreferences.getOrDefault("autoRefresh", true); + } + + public Integer getRefreshInterval() { + if (userPreferences == null) { + return 300; // 5 minutes par défaut + } + return (Integer) userPreferences.getOrDefault("refreshInterval", 300); + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardStatsResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardStatsResponse.java index 3bfbe3d..904e1e6 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardStatsResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardStatsResponse.java @@ -1,119 +1,119 @@ -package dev.lions.unionflow.server.api.dto.dashboard; - -import com.fasterxml.jackson.annotation.JsonFormat; -import com.fasterxml.jackson.annotation.JsonProperty; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.time.LocalDateTime; -import java.util.List; -import java.util.Map; - -/** - * DTO pour les statistiques du dashboard - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class DashboardStatsResponse { - - @JsonProperty("totalMembers") - private Integer totalMembers; - - @JsonProperty("activeMembers") - private Integer activeMembers; - - @JsonProperty("totalEvents") - private Integer totalEvents; - - @JsonProperty("upcomingEvents") - private Integer upcomingEvents; - - @JsonProperty("totalContributions") - private Integer totalContributions; - - @JsonProperty("totalContributionAmount") - private Double totalContributionAmount; - - @JsonProperty("pendingRequests") - private Integer pendingRequests; - - @JsonProperty("completedProjects") - private Integer completedProjects; - - @JsonProperty("monthlyGrowth") - private Double monthlyGrowth; - - @JsonProperty("engagementRate") - private Double engagementRate; - - @JsonProperty("lastUpdated") - @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") - private LocalDateTime lastUpdated; - - /** - * Nombre total d'organisations dans le système (SuperAdmin uniquement) - */ - @JsonProperty("totalOrganizations") - private Integer totalOrganizations; - - /** - * Répartition des organisations par type - * Exemple: {"Mutuelle": 15, "Coopérative": 8, "Tontine": 5, "Autre": 3} - */ - @JsonProperty("organizationTypeDistribution") - private Map organizationTypeDistribution; - - /** - * Données historiques mensuelles pour les graphiques (12 derniers mois) - */ - @JsonProperty("monthlyHistoricalData") - private List monthlyHistoricalData; - - // Méthodes utilitaires - public String getFormattedContributionAmount() { - if (totalContributionAmount == null) { - return "0"; - } - - if (totalContributionAmount >= 1_000_000) { - return String.format("%.1fM", totalContributionAmount / 1_000_000); - } else if (totalContributionAmount >= 1_000) { - return String.format("%.0fK", totalContributionAmount / 1_000); - } else { - return String.format("%.0f", totalContributionAmount); - } - } - - public Boolean getHasGrowth() { - return monthlyGrowth != null && monthlyGrowth > 0; - } - - public Boolean getIsHighEngagement() { - return engagementRate != null && engagementRate > 0.7; - } - - public Double getInactiveMembers() { - if (totalMembers == null || activeMembers == null) { - return 0.0; - } - return (double) (totalMembers - activeMembers); - } - - public Double getActiveMemberPercentage() { - if (totalMembers == null || activeMembers == null || totalMembers == 0) { - return 0.0; - } - return (double) activeMembers / totalMembers * 100; - } - - public Double getEngagementPercentage() { - if (engagementRate == null) { - return 0.0; - } - return engagementRate * 100; - } -} +package dev.lions.unionflow.server.api.dto.dashboard; + +import com.fasterxml.jackson.annotation.JsonFormat; +import com.fasterxml.jackson.annotation.JsonProperty; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.time.LocalDateTime; +import java.util.List; +import java.util.Map; + +/** + * DTO pour les statistiques du dashboard + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class DashboardStatsResponse { + + @JsonProperty("totalMembers") + private Integer totalMembers; + + @JsonProperty("activeMembers") + private Integer activeMembers; + + @JsonProperty("totalEvents") + private Integer totalEvents; + + @JsonProperty("upcomingEvents") + private Integer upcomingEvents; + + @JsonProperty("totalContributions") + private Integer totalContributions; + + @JsonProperty("totalContributionAmount") + private Double totalContributionAmount; + + @JsonProperty("pendingRequests") + private Integer pendingRequests; + + @JsonProperty("completedProjects") + private Integer completedProjects; + + @JsonProperty("monthlyGrowth") + private Double monthlyGrowth; + + @JsonProperty("engagementRate") + private Double engagementRate; + + @JsonProperty("lastUpdated") + @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") + private LocalDateTime lastUpdated; + + /** + * Nombre total d'organisations dans le système (SuperAdmin uniquement) + */ + @JsonProperty("totalOrganizations") + private Integer totalOrganizations; + + /** + * Répartition des organisations par type + * Exemple: {"Mutuelle": 15, "Coopérative": 8, "Tontine": 5, "Autre": 3} + */ + @JsonProperty("organizationTypeDistribution") + private Map organizationTypeDistribution; + + /** + * Données historiques mensuelles pour les graphiques (12 derniers mois) + */ + @JsonProperty("monthlyHistoricalData") + private List monthlyHistoricalData; + + // Méthodes utilitaires + public String getFormattedContributionAmount() { + if (totalContributionAmount == null) { + return "0"; + } + + if (totalContributionAmount >= 1_000_000) { + return String.format("%.1fM", totalContributionAmount / 1_000_000); + } else if (totalContributionAmount >= 1_000) { + return String.format("%.0fK", totalContributionAmount / 1_000); + } else { + return String.format("%.0f", totalContributionAmount); + } + } + + public Boolean getHasGrowth() { + return monthlyGrowth != null && monthlyGrowth > 0; + } + + public Boolean getIsHighEngagement() { + return engagementRate != null && engagementRate > 0.7; + } + + public Double getInactiveMembers() { + if (totalMembers == null || activeMembers == null) { + return 0.0; + } + return (double) (totalMembers - activeMembers); + } + + public Double getActiveMemberPercentage() { + if (totalMembers == null || activeMembers == null || totalMembers == 0) { + return 0.0; + } + return (double) activeMembers / totalMembers * 100; + } + + public Double getEngagementPercentage() { + if (engagementRate == null) { + return 0.0; + } + return engagementRate * 100; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/MonthlyStatDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/MonthlyStatDTO.java index 5681248..7002f2b 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/MonthlyStatDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/MonthlyStatDTO.java @@ -1,70 +1,70 @@ -package dev.lions.unionflow.server.api.dto.dashboard; - -import com.fasterxml.jackson.annotation.JsonProperty; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO pour les statistiques mensuelles historiques - * Utilisé pour générer des graphiques de croissance sur 12 mois - * - * @author UnionFlow Team - * @version 2.0 - * @since 2026-03-07 - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class MonthlyStatDTO { - - /** - * Mois au format "2026-01", "2026-02", etc. - */ - @JsonProperty("month") - private String month; - - /** - * Nombre de membres ce mois-là - */ - @JsonProperty("totalMembers") - private Integer totalMembers; - - /** - * Nombre de membres actifs ce mois-là - */ - @JsonProperty("activeMembers") - private Integer activeMembers; - - /** - * Montant total des contributions ce mois-là - */ - @JsonProperty("contributionAmount") - private Double contributionAmount; - - /** - * Nombre d'événements organisés ce mois-là - */ - @JsonProperty("eventsCount") - private Integer eventsCount; - - /** - * Taux d'engagement ce mois-là - */ - @JsonProperty("engagementRate") - private Double engagementRate; - - /** - * Nombre de nouveaux membres ce mois-là - */ - @JsonProperty("newMembers") - private Integer newMembers; - - /** - * Nombre de cotisations payées ce mois-là - */ - @JsonProperty("contributionsCount") - private Integer contributionsCount; -} +package dev.lions.unionflow.server.api.dto.dashboard; + +import com.fasterxml.jackson.annotation.JsonProperty; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO pour les statistiques mensuelles historiques + * Utilisé pour générer des graphiques de croissance sur 12 mois + * + * @author UnionFlow Team + * @version 2.0 + * @since 2026-03-07 + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class MonthlyStatDTO { + + /** + * Mois au format "2026-01", "2026-02", etc. + */ + @JsonProperty("month") + private String month; + + /** + * Nombre de membres ce mois-là + */ + @JsonProperty("totalMembers") + private Integer totalMembers; + + /** + * Nombre de membres actifs ce mois-là + */ + @JsonProperty("activeMembers") + private Integer activeMembers; + + /** + * Montant total des contributions ce mois-là + */ + @JsonProperty("contributionAmount") + private Double contributionAmount; + + /** + * Nombre d'événements organisés ce mois-là + */ + @JsonProperty("eventsCount") + private Integer eventsCount; + + /** + * Taux d'engagement ce mois-là + */ + @JsonProperty("engagementRate") + private Double engagementRate; + + /** + * Nombre de nouveaux membres ce mois-là + */ + @JsonProperty("newMembers") + private Integer newMembers; + + /** + * Nombre de cotisations payées ce mois-là + */ + @JsonProperty("contributionsCount") + private Integer contributionsCount; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/RecentActivityResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/RecentActivityResponse.java index ddf2296..63152c3 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/RecentActivityResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/RecentActivityResponse.java @@ -1,130 +1,130 @@ -package dev.lions.unionflow.server.api.dto.dashboard; - -import com.fasterxml.jackson.annotation.JsonFormat; -import com.fasterxml.jackson.annotation.JsonProperty; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.time.LocalDateTime; -import java.time.temporal.ChronoUnit; - -/** - * DTO pour les activités récentes du dashboard - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class RecentActivityResponse { - - @JsonProperty("id") - private String id; - - @JsonProperty("type") - private String type; - - @JsonProperty("title") - private String title; - - @JsonProperty("description") - private String description; - - @JsonProperty("userName") - private String userName; - - @JsonProperty("timestamp") - @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") - private LocalDateTime timestamp; - - @JsonProperty("userAvatar") - private String userAvatar; - - @JsonProperty("actionUrl") - private String actionUrl; - - // Méthodes utilitaires - public String getTimeAgo() { - if (timestamp == null) { - return ""; - } - - LocalDateTime now = LocalDateTime.now(); - long minutes = ChronoUnit.MINUTES.between(timestamp, now); - long hours = ChronoUnit.HOURS.between(timestamp, now); - long days = ChronoUnit.DAYS.between(timestamp, now); - - if (minutes < 60) { - return minutes + "min"; - } else if (hours < 24) { - return hours + "h"; - } else if (days < 7) { - return days + "j"; - } else { - long weeks = days / 7; - return weeks + "sem"; - } - } - - public String getActivityIcon() { - if (type == null) { - return "help_outline"; - } - - switch (type.toLowerCase()) { - case "member": - return "person"; - case "event": - return "event"; - case "contribution": - return "payment"; - case "organization": - return "business"; - case "system": - return "settings"; - default: - return "info"; - } - } - - public String getActivityColor() { - if (type == null) { - return "#6B7280"; // grey - } - - switch (type.toLowerCase()) { - case "member": - return "#10B981"; // success - case "event": - return "#3B82F6"; // info - case "contribution": - return "#008B8B"; // teal blue - case "organization": - return "#4169E1"; // royal blue - case "system": - return "#6B7280"; // grey - default: - return "#6B7280"; // grey - } - } - - public Boolean getIsRecent() { - if (timestamp == null) { - return false; - } - - LocalDateTime now = LocalDateTime.now(); - long hours = ChronoUnit.HOURS.between(timestamp, now); - return hours < 24; - } - - public Boolean getIsToday() { - if (timestamp == null) { - return false; - } - - LocalDateTime now = LocalDateTime.now(); - return timestamp.toLocalDate().equals(now.toLocalDate()); - } -} +package dev.lions.unionflow.server.api.dto.dashboard; + +import com.fasterxml.jackson.annotation.JsonFormat; +import com.fasterxml.jackson.annotation.JsonProperty; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.time.LocalDateTime; +import java.time.temporal.ChronoUnit; + +/** + * DTO pour les activités récentes du dashboard + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class RecentActivityResponse { + + @JsonProperty("id") + private String id; + + @JsonProperty("type") + private String type; + + @JsonProperty("title") + private String title; + + @JsonProperty("description") + private String description; + + @JsonProperty("userName") + private String userName; + + @JsonProperty("timestamp") + @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") + private LocalDateTime timestamp; + + @JsonProperty("userAvatar") + private String userAvatar; + + @JsonProperty("actionUrl") + private String actionUrl; + + // Méthodes utilitaires + public String getTimeAgo() { + if (timestamp == null) { + return ""; + } + + LocalDateTime now = LocalDateTime.now(); + long minutes = ChronoUnit.MINUTES.between(timestamp, now); + long hours = ChronoUnit.HOURS.between(timestamp, now); + long days = ChronoUnit.DAYS.between(timestamp, now); + + if (minutes < 60) { + return minutes + "min"; + } else if (hours < 24) { + return hours + "h"; + } else if (days < 7) { + return days + "j"; + } else { + long weeks = days / 7; + return weeks + "sem"; + } + } + + public String getActivityIcon() { + if (type == null) { + return "help_outline"; + } + + switch (type.toLowerCase()) { + case "member": + return "person"; + case "event": + return "event"; + case "contribution": + return "payment"; + case "organization": + return "business"; + case "system": + return "settings"; + default: + return "info"; + } + } + + public String getActivityColor() { + if (type == null) { + return "#6B7280"; // grey + } + + switch (type.toLowerCase()) { + case "member": + return "#10B981"; // success + case "event": + return "#3B82F6"; // info + case "contribution": + return "#008B8B"; // teal blue + case "organization": + return "#4169E1"; // royal blue + case "system": + return "#6B7280"; // grey + default: + return "#6B7280"; // grey + } + } + + public Boolean getIsRecent() { + if (timestamp == null) { + return false; + } + + LocalDateTime now = LocalDateTime.now(); + long hours = ChronoUnit.HOURS.between(timestamp, now); + return hours < 24; + } + + public Boolean getIsToday() { + if (timestamp == null) { + return false; + } + + LocalDateTime now = LocalDateTime.now(); + return timestamp.toLocalDate().equals(now.toLocalDate()); + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/UpcomingEventResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/UpcomingEventResponse.java index e446e97..77eb664 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/UpcomingEventResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/dashboard/UpcomingEventResponse.java @@ -1,183 +1,183 @@ -package dev.lions.unionflow.server.api.dto.dashboard; - -import com.fasterxml.jackson.annotation.JsonFormat; -import com.fasterxml.jackson.annotation.JsonProperty; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.time.LocalDateTime; -import java.time.temporal.ChronoUnit; -import java.util.List; - -/** - * DTO pour les événements à venir du dashboard - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class UpcomingEventResponse { - - @JsonProperty("id") - private String id; - - @JsonProperty("title") - private String title; - - @JsonProperty("description") - private String description; - - @JsonProperty("startDate") - @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") - private LocalDateTime startDate; - - @JsonProperty("endDate") - @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") - private LocalDateTime endDate; - - @JsonProperty("location") - private String location; - - @JsonProperty("maxParticipants") - private Integer maxParticipants; - - @JsonProperty("currentParticipants") - private Integer currentParticipants; - - @JsonProperty("status") - private String status; - - @JsonProperty("imageUrl") - private String imageUrl; - - @JsonProperty("tags") - private List tags; - - // Méthodes utilitaires - public String getDaysUntilEvent() { - return getDaysUntilEvent(LocalDateTime.now()); - } - - /** - * Version testable avec une date de référence fixe (même package). - */ - String getDaysUntilEvent(LocalDateTime now) { - if (startDate == null) { - return ""; - } - long days = ChronoUnit.DAYS.between(now.toLocalDate(), startDate.toLocalDate()); - long hours = ChronoUnit.HOURS.between(now, startDate); - - if (days < 0) { - return "En cours"; - } - if (days == 0) { - // Vérifier si l'événement est déjà passé (même si moins d'1h) - if (startDate.isBefore(now)) { - return "En cours"; - } else if (hours < 2) { - return "Bientôt"; - } else { - return "Aujourd'hui"; - } - } else if (days == 1) { - return "Demain"; - } else if (days < 7) { - return "Dans " + days + " jours"; - } else { - long weeks = days / 7; - return "Dans " + weeks + " semaine" + (weeks > 1 ? "s" : ""); - } - } - - public Double getFillPercentage() { - if (maxParticipants == null || currentParticipants == null || maxParticipants == 0) { - return 0.0; - } - return (double) currentParticipants / maxParticipants * 100; - } - - public Boolean getIsFull() { - if (maxParticipants == null || currentParticipants == null) { - return false; - } - return currentParticipants >= maxParticipants; - } - - public Boolean getIsAlmostFull() { - Double fillPercentage = getFillPercentage(); - return fillPercentage >= 80.0 && fillPercentage < 100.0; - } - - public Boolean getIsToday() { - if (startDate == null) { - return false; - } - - LocalDateTime now = LocalDateTime.now(); - return startDate.toLocalDate().equals(now.toLocalDate()); - } - - public Boolean getIsTomorrow() { - if (startDate == null) { - return false; - } - - LocalDateTime now = LocalDateTime.now(); - return startDate.toLocalDate().equals(now.toLocalDate().plusDays(1)); - } - - public String getStatusColor() { - if (status == null) { - return "#6B7280"; // grey - } - - switch (status.toLowerCase()) { - case "confirmed": - return "#10B981"; // success - case "open": - return "#3B82F6"; // info - case "cancelled": - return "#EF4444"; // error - case "postponed": - return "#F59E0B"; // warning - default: - return "#6B7280"; // grey - } - } - - public String getStatusLabel() { - if (status == null) { - return "Inconnu"; - } - - switch (status.toLowerCase()) { - case "confirmed": - return "Confirmé"; - case "open": - return "Ouvert"; - case "cancelled": - return "Annulé"; - case "postponed": - return "Reporté"; - default: - return status; - } - } - - public Integer getAvailableSpots() { - if (maxParticipants == null || currentParticipants == null) { - return 0; - } - return Math.max(0, maxParticipants - currentParticipants); - } - - public String getParticipationSummary() { - if (maxParticipants == null || currentParticipants == null) { - return "0/0 participants"; - } - return currentParticipants + "/" + maxParticipants + " participants"; - } -} +package dev.lions.unionflow.server.api.dto.dashboard; + +import com.fasterxml.jackson.annotation.JsonFormat; +import com.fasterxml.jackson.annotation.JsonProperty; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.time.LocalDateTime; +import java.time.temporal.ChronoUnit; +import java.util.List; + +/** + * DTO pour les événements à venir du dashboard + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class UpcomingEventResponse { + + @JsonProperty("id") + private String id; + + @JsonProperty("title") + private String title; + + @JsonProperty("description") + private String description; + + @JsonProperty("startDate") + @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") + private LocalDateTime startDate; + + @JsonProperty("endDate") + @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") + private LocalDateTime endDate; + + @JsonProperty("location") + private String location; + + @JsonProperty("maxParticipants") + private Integer maxParticipants; + + @JsonProperty("currentParticipants") + private Integer currentParticipants; + + @JsonProperty("status") + private String status; + + @JsonProperty("imageUrl") + private String imageUrl; + + @JsonProperty("tags") + private List tags; + + // Méthodes utilitaires + public String getDaysUntilEvent() { + return getDaysUntilEvent(LocalDateTime.now()); + } + + /** + * Version testable avec une date de référence fixe (même package). + */ + String getDaysUntilEvent(LocalDateTime now) { + if (startDate == null) { + return ""; + } + long days = ChronoUnit.DAYS.between(now.toLocalDate(), startDate.toLocalDate()); + long hours = ChronoUnit.HOURS.between(now, startDate); + + if (days < 0) { + return "En cours"; + } + if (days == 0) { + // Vérifier si l'événement est déjà passé (même si moins d'1h) + if (startDate.isBefore(now)) { + return "En cours"; + } else if (hours < 2) { + return "Bientôt"; + } else { + return "Aujourd'hui"; + } + } else if (days == 1) { + return "Demain"; + } else if (days < 7) { + return "Dans " + days + " jours"; + } else { + long weeks = days / 7; + return "Dans " + weeks + " semaine" + (weeks > 1 ? "s" : ""); + } + } + + public Double getFillPercentage() { + if (maxParticipants == null || currentParticipants == null || maxParticipants == 0) { + return 0.0; + } + return (double) currentParticipants / maxParticipants * 100; + } + + public Boolean getIsFull() { + if (maxParticipants == null || currentParticipants == null) { + return false; + } + return currentParticipants >= maxParticipants; + } + + public Boolean getIsAlmostFull() { + Double fillPercentage = getFillPercentage(); + return fillPercentage >= 80.0 && fillPercentage < 100.0; + } + + public Boolean getIsToday() { + if (startDate == null) { + return false; + } + + LocalDateTime now = LocalDateTime.now(); + return startDate.toLocalDate().equals(now.toLocalDate()); + } + + public Boolean getIsTomorrow() { + if (startDate == null) { + return false; + } + + LocalDateTime now = LocalDateTime.now(); + return startDate.toLocalDate().equals(now.toLocalDate().plusDays(1)); + } + + public String getStatusColor() { + if (status == null) { + return "#6B7280"; // grey + } + + switch (status.toLowerCase()) { + case "confirmed": + return "#10B981"; // success + case "open": + return "#3B82F6"; // info + case "cancelled": + return "#EF4444"; // error + case "postponed": + return "#F59E0B"; // warning + default: + return "#6B7280"; // grey + } + } + + public String getStatusLabel() { + if (status == null) { + return "Inconnu"; + } + + switch (status.toLowerCase()) { + case "confirmed": + return "Confirmé"; + case "open": + return "Ouvert"; + case "cancelled": + return "Annulé"; + case "postponed": + return "Reporté"; + default: + return status; + } + } + + public Integer getAvailableSpots() { + if (maxParticipants == null || currentParticipants == null) { + return 0; + } + return Math.max(0, maxParticipants - currentParticipants); + } + + public String getParticipationSummary() { + if (maxParticipants == null || currentParticipants == null) { + return "0/0 participants"; + } + return currentParticipants + "/" + maxParticipants + " participants"; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/document/request/CreateDocumentRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/document/request/CreateDocumentRequest.java index 07667d6..a215d04 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/document/request/CreateDocumentRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/document/request/CreateDocumentRequest.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.dto.document.request; - -import dev.lions.unionflow.server.api.enums.document.TypeDocument; -import jakarta.validation.constraints.Min; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import lombok.Builder; - -/** - * Requête de création d'un document. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreateDocumentRequest( - @NotBlank(message = "Le nom du fichier est obligatoire") String nomFichier, - String nomOriginal, - @NotBlank(message = "Le chemin de stockage est obligatoire") String cheminStockage, - String typeMime, - @NotNull(message = "La taille est obligatoire") @Min(value = 0, message = "La taille doit être positive") Long tailleOctets, - TypeDocument typeDocument, - String hashMd5, - String hashSha256, - String description) { -} +package dev.lions.unionflow.server.api.dto.document.request; + +import dev.lions.unionflow.server.api.enums.document.TypeDocument; +import jakarta.validation.constraints.Min; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import lombok.Builder; + +/** + * Requête de création d'un document. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreateDocumentRequest( + @NotBlank(message = "Le nom du fichier est obligatoire") String nomFichier, + String nomOriginal, + @NotBlank(message = "Le chemin de stockage est obligatoire") String cheminStockage, + String typeMime, + @NotNull(message = "La taille est obligatoire") @Min(value = 0, message = "La taille doit être positive") Long tailleOctets, + TypeDocument typeDocument, + String hashMd5, + String hashSha256, + String description) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/document/request/CreatePieceJointeRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/document/request/CreatePieceJointeRequest.java index 30f5770..3d2fbd3 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/document/request/CreatePieceJointeRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/document/request/CreatePieceJointeRequest.java @@ -1,22 +1,22 @@ -package dev.lions.unionflow.server.api.dto.document.request; - -import jakarta.validation.constraints.Min; -import jakarta.validation.constraints.NotNull; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'une pièce jointe. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreatePieceJointeRequest( - @NotNull(message = "L'ordre est obligatoire") @Min(value = 1, message = "L'ordre doit être positif") Integer ordre, - String libelle, - String commentaire, - @NotNull(message = "Le document est obligatoire") UUID documentId, - @NotNull(message = "Le type entité est obligatoire") String typeEntiteRattachee, - @NotNull(message = "L'ID entité est obligatoire") UUID entiteRattacheeId) { -} +package dev.lions.unionflow.server.api.dto.document.request; + +import jakarta.validation.constraints.Min; +import jakarta.validation.constraints.NotNull; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'une pièce jointe. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreatePieceJointeRequest( + @NotNull(message = "L'ordre est obligatoire") @Min(value = 1, message = "L'ordre doit être positif") Integer ordre, + String libelle, + String commentaire, + @NotNull(message = "Le document est obligatoire") UUID documentId, + @NotNull(message = "Le type entité est obligatoire") String typeEntiteRattachee, + @NotNull(message = "L'ID entité est obligatoire") UUID entiteRattacheeId) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/document/request/UpdateDocumentRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/document/request/UpdateDocumentRequest.java index e449926..955ec65 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/document/request/UpdateDocumentRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/document/request/UpdateDocumentRequest.java @@ -1,18 +1,18 @@ -package dev.lions.unionflow.server.api.dto.document.request; - -import dev.lions.unionflow.server.api.enums.document.TypeDocument; -import lombok.Builder; - -/** - * Requête de mise à jour d'un document. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record UpdateDocumentRequest( - String nomFichier, - String nomOriginal, - TypeDocument typeDocument, - String description) { -} +package dev.lions.unionflow.server.api.dto.document.request; + +import dev.lions.unionflow.server.api.enums.document.TypeDocument; +import lombok.Builder; + +/** + * Requête de mise à jour d'un document. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record UpdateDocumentRequest( + String nomFichier, + String nomOriginal, + TypeDocument typeDocument, + String description) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/document/request/UpdatePieceJointeRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/document/request/UpdatePieceJointeRequest.java index 294a3de..7c510e0 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/document/request/UpdatePieceJointeRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/document/request/UpdatePieceJointeRequest.java @@ -1,17 +1,17 @@ -package dev.lions.unionflow.server.api.dto.document.request; - -import jakarta.validation.constraints.Min; -import lombok.Builder; - -/** - * Requête de mise à jour d'une pièce jointe. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record UpdatePieceJointeRequest( - @Min(value = 1, message = "L'ordre doit être positif") Integer ordre, - String libelle, - String commentaire) { -} +package dev.lions.unionflow.server.api.dto.document.request; + +import jakarta.validation.constraints.Min; +import lombok.Builder; + +/** + * Requête de mise à jour d'une pièce jointe. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record UpdatePieceJointeRequest( + @Min(value = 1, message = "L'ordre doit être positif") Integer ordre, + String libelle, + String commentaire) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/document/response/DocumentResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/document/response/DocumentResponse.java index 014081b..b56562d 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/document/response/DocumentResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/document/response/DocumentResponse.java @@ -1,36 +1,36 @@ -package dev.lions.unionflow.server.api.dto.document.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import dev.lions.unionflow.server.api.enums.document.TypeDocument; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée d'un document. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class DocumentResponse extends BaseResponse { - - private String nomFichier; - private String nomOriginal; - private String cheminStockage; - private String typeMime; - private Long tailleOctets; - private TypeDocument typeDocument; - private String hashMd5; - private String hashSha256; - private String description; - private Integer nombreTelechargements; - private String tailleFormatee; -} +package dev.lions.unionflow.server.api.dto.document.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import dev.lions.unionflow.server.api.enums.document.TypeDocument; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée d'un document. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class DocumentResponse extends BaseResponse { + + private String nomFichier; + private String nomOriginal; + private String cheminStockage; + private String typeMime; + private Long tailleOctets; + private TypeDocument typeDocument; + private String hashMd5; + private String hashSha256; + private String description; + private Integer nombreTelechargements; + private String tailleFormatee; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/document/response/PieceJointeResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/document/response/PieceJointeResponse.java index 7c48af2..347ef96 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/document/response/PieceJointeResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/document/response/PieceJointeResponse.java @@ -1,31 +1,31 @@ -package dev.lions.unionflow.server.api.dto.document.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse contenant les données d'une pièce jointe. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class PieceJointeResponse extends BaseResponse { - - private Integer ordre; - private String libelle; - private String commentaire; - private UUID documentId; - private String typeEntiteRattachee; - private UUID entiteRattacheeId; -} +package dev.lions.unionflow.server.api.dto.document.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse contenant les données d'une pièce jointe. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class PieceJointeResponse extends BaseResponse { + + private Integer ordre; + private String libelle; + private String commentaire; + private UUID documentId; + private String typeEntiteRattachee; + private UUID entiteRattacheeId; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/evenement/request/CreateEvenementRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/evenement/request/CreateEvenementRequest.java index 0855135..bb5d36e 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/evenement/request/CreateEvenementRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/evenement/request/CreateEvenementRequest.java @@ -1,70 +1,70 @@ -package dev.lions.unionflow.server.api.dto.evenement.request; - -import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; -import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; -import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; -import dev.lions.unionflow.server.api.validation.ValidationConstants; -import jakarta.validation.constraints.DecimalMax; - -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.Email; -import jakarta.validation.constraints.FutureOrPresent; -import jakarta.validation.constraints.Max; -import jakarta.validation.constraints.Min; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Pattern; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalTime; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'un événement. - */ -@Builder -public record CreateEvenementRequest( - @NotBlank(message = "Le titre" - + ValidationConstants.OBLIGATOIRE_MESSAGE) @Size(min = ValidationConstants.TITRE_MIN_LENGTH, max = ValidationConstants.TITRE_MAX_LENGTH, message = ValidationConstants.TITRE_SIZE_MESSAGE) String titre, - - @Size(max = ValidationConstants.DESCRIPTION_COURTE_MAX_LENGTH, message = ValidationConstants.DESCRIPTION_COURTE_SIZE_MESSAGE) String description, - - @NotNull(message = "Le type d'événement est obligatoire") TypeEvenementMetier typeEvenement, - - @NotNull(message = "Le statut est obligatoire") StatutEvenement statut, - - PrioriteEvenement priorite, - @NotNull(message = "La date de début est obligatoire") @FutureOrPresent(message = "La date de début ne peut pas être dans le passé") LocalDate dateDebut, - LocalDate dateFin, - LocalTime heureDebut, - LocalTime heureFin, - @NotBlank(message = "Le lieu est obligatoire") @Size(max = 100) String lieu, - @Size(max = 200) String adresse, - @Size(max = 50) String ville, - @Size(max = 50) String region, - @DecimalMin(value = "-90.0") @DecimalMax(value = "90.0") BigDecimal latitude, - @DecimalMin(value = "-180.0") @DecimalMax(value = "180.0") BigDecimal longitude, - @NotNull(message = "L'association organisatrice est obligatoire") UUID associationId, - @Size(max = 100) String organisateur, - @Email(message = "Format d'email invalide") @Size(max = 100) String emailOrganisateur, - @Pattern(regexp = "^\\+?[0-9\\s\\-\\(\\)]{8,20}$") String telephoneOrganisateur, - @Min(value = 1) @Max(value = 10000) Integer capaciteMax, - @DecimalMin(value = ValidationConstants.MONTANT_MIN_VALUE, message = ValidationConstants.MONTANT_POSITIF_MESSAGE) @Digits(integer = ValidationConstants.MONTANT_INTEGER_DIGITS, fraction = ValidationConstants.MONTANT_FRACTION_DIGITS, message = ValidationConstants.MONTANT_DIGITS_MESSAGE) BigDecimal budget, - - @DecimalMin(value = ValidationConstants.MONTANT_MIN_VALUE, message = ValidationConstants.MONTANT_POSITIF_MESSAGE) @Digits(integer = ValidationConstants.MONTANT_INTEGER_DIGITS, fraction = ValidationConstants.MONTANT_FRACTION_DIGITS, message = ValidationConstants.MONTANT_DIGITS_MESSAGE) BigDecimal coutReel, - - @Pattern(regexp = ValidationConstants.DEVISE_PATTERN, message = ValidationConstants.DEVISE_MESSAGE) String codeDevise, - Boolean inscriptionObligatoire, - LocalDate dateLimiteInscription, - Boolean evenementPublic, - Boolean recurrent, - String frequenceRecurrence, - @Size(max = 500) String instructions, - @Size(max = 500) String materielNecessaire, - @Size(max = 100) String conditionsMeteo, - @Size(max = 255) String imageUrl, - @Pattern(regexp = "^#[0-9A-Fa-f]{6}$") String couleurTheme) { -} +package dev.lions.unionflow.server.api.dto.evenement.request; + +import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; +import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; +import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; +import dev.lions.unionflow.server.api.validation.ValidationConstants; +import jakarta.validation.constraints.DecimalMax; + +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.Email; +import jakarta.validation.constraints.FutureOrPresent; +import jakarta.validation.constraints.Max; +import jakarta.validation.constraints.Min; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Pattern; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalTime; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'un événement. + */ +@Builder +public record CreateEvenementRequest( + @NotBlank(message = "Le titre" + + ValidationConstants.OBLIGATOIRE_MESSAGE) @Size(min = ValidationConstants.TITRE_MIN_LENGTH, max = ValidationConstants.TITRE_MAX_LENGTH, message = ValidationConstants.TITRE_SIZE_MESSAGE) String titre, + + @Size(max = ValidationConstants.DESCRIPTION_COURTE_MAX_LENGTH, message = ValidationConstants.DESCRIPTION_COURTE_SIZE_MESSAGE) String description, + + @NotNull(message = "Le type d'événement est obligatoire") TypeEvenementMetier typeEvenement, + + @NotNull(message = "Le statut est obligatoire") StatutEvenement statut, + + PrioriteEvenement priorite, + @NotNull(message = "La date de début est obligatoire") @FutureOrPresent(message = "La date de début ne peut pas être dans le passé") LocalDate dateDebut, + LocalDate dateFin, + LocalTime heureDebut, + LocalTime heureFin, + @NotBlank(message = "Le lieu est obligatoire") @Size(max = 100) String lieu, + @Size(max = 200) String adresse, + @Size(max = 50) String ville, + @Size(max = 50) String region, + @DecimalMin(value = "-90.0") @DecimalMax(value = "90.0") BigDecimal latitude, + @DecimalMin(value = "-180.0") @DecimalMax(value = "180.0") BigDecimal longitude, + @NotNull(message = "L'association organisatrice est obligatoire") UUID associationId, + @Size(max = 100) String organisateur, + @Email(message = "Format d'email invalide") @Size(max = 100) String emailOrganisateur, + @Pattern(regexp = "^\\+?[0-9\\s\\-\\(\\)]{8,20}$") String telephoneOrganisateur, + @Min(value = 1) @Max(value = 10000) Integer capaciteMax, + @DecimalMin(value = ValidationConstants.MONTANT_MIN_VALUE, message = ValidationConstants.MONTANT_POSITIF_MESSAGE) @Digits(integer = ValidationConstants.MONTANT_INTEGER_DIGITS, fraction = ValidationConstants.MONTANT_FRACTION_DIGITS, message = ValidationConstants.MONTANT_DIGITS_MESSAGE) BigDecimal budget, + + @DecimalMin(value = ValidationConstants.MONTANT_MIN_VALUE, message = ValidationConstants.MONTANT_POSITIF_MESSAGE) @Digits(integer = ValidationConstants.MONTANT_INTEGER_DIGITS, fraction = ValidationConstants.MONTANT_FRACTION_DIGITS, message = ValidationConstants.MONTANT_DIGITS_MESSAGE) BigDecimal coutReel, + + @Pattern(regexp = ValidationConstants.DEVISE_PATTERN, message = ValidationConstants.DEVISE_MESSAGE) String codeDevise, + Boolean inscriptionObligatoire, + LocalDate dateLimiteInscription, + Boolean evenementPublic, + Boolean recurrent, + String frequenceRecurrence, + @Size(max = 500) String instructions, + @Size(max = 500) String materielNecessaire, + @Size(max = 100) String conditionsMeteo, + @Size(max = 255) String imageUrl, + @Pattern(regexp = "^#[0-9A-Fa-f]{6}$") String couleurTheme) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/evenement/request/UpdateEvenementRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/evenement/request/UpdateEvenementRequest.java index 58a6c21..d8b2053 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/evenement/request/UpdateEvenementRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/evenement/request/UpdateEvenementRequest.java @@ -1,65 +1,65 @@ -package dev.lions.unionflow.server.api.dto.evenement.request; - -import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; -import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; -import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; -import dev.lions.unionflow.server.api.validation.ValidationConstants; -import jakarta.validation.constraints.DecimalMax; - -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.Email; -import jakarta.validation.constraints.Max; -import jakarta.validation.constraints.Min; -import jakarta.validation.constraints.NotBlank; - -import jakarta.validation.constraints.Pattern; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalTime; -import lombok.Builder; - -/** - * Requête de mise à jour d'un événement. - */ -@Builder -public record UpdateEvenementRequest( - @Size(min = ValidationConstants.TITRE_MIN_LENGTH, max = ValidationConstants.TITRE_MAX_LENGTH, message = ValidationConstants.TITRE_SIZE_MESSAGE) String titre, - - @Size(max = ValidationConstants.DESCRIPTION_COURTE_MAX_LENGTH, message = ValidationConstants.DESCRIPTION_COURTE_SIZE_MESSAGE) String description, - - TypeEvenementMetier typeEvenement, - StatutEvenement statut, - PrioriteEvenement priorite, - - LocalDate dateDebut, - LocalDate dateFin, - LocalTime heureDebut, - LocalTime heureFin, - @NotBlank(message = "Le lieu est obligatoire") @Size(max = 100) String lieu, - @Size(max = 200) String adresse, - @Size(max = 50) String ville, - @Size(max = 50) String region, - @DecimalMin(value = "-90.0") @DecimalMax(value = "90.0") BigDecimal latitude, - @DecimalMin(value = "-180.0") @DecimalMax(value = "180.0") BigDecimal longitude, - @Size(max = 100) String organisateur, - @Email(message = "Format d'email invalide") @Size(max = 100) String emailOrganisateur, - @Pattern(regexp = "^\\+?[0-9\\s\\-\\(\\)]{8,20}$") String telephoneOrganisateur, - @Min(value = 1) @Max(value = 10000) Integer capaciteMax, - @DecimalMin(value = ValidationConstants.MONTANT_MIN_VALUE, message = ValidationConstants.MONTANT_POSITIF_MESSAGE) @Digits(integer = ValidationConstants.MONTANT_INTEGER_DIGITS, fraction = ValidationConstants.MONTANT_FRACTION_DIGITS, message = ValidationConstants.MONTANT_DIGITS_MESSAGE) BigDecimal budget, - - @DecimalMin(value = ValidationConstants.MONTANT_MIN_VALUE, message = ValidationConstants.MONTANT_POSITIF_MESSAGE) @Digits(integer = ValidationConstants.MONTANT_INTEGER_DIGITS, fraction = ValidationConstants.MONTANT_FRACTION_DIGITS, message = ValidationConstants.MONTANT_DIGITS_MESSAGE) BigDecimal coutReel, - - @Pattern(regexp = ValidationConstants.DEVISE_PATTERN, message = ValidationConstants.DEVISE_MESSAGE) String codeDevise, - Boolean inscriptionObligatoire, - LocalDate dateLimiteInscription, - Boolean evenementPublic, - Boolean recurrent, - String frequenceRecurrence, - @Size(max = 500) String instructions, - @Size(max = 500) String materielNecessaire, - @Size(max = 100) String conditionsMeteo, - @Size(max = 255) String imageUrl, - @Pattern(regexp = "^#[0-9A-Fa-f]{6}$") String couleurTheme) { -} +package dev.lions.unionflow.server.api.dto.evenement.request; + +import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; +import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; +import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; +import dev.lions.unionflow.server.api.validation.ValidationConstants; +import jakarta.validation.constraints.DecimalMax; + +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.Email; +import jakarta.validation.constraints.Max; +import jakarta.validation.constraints.Min; +import jakarta.validation.constraints.NotBlank; + +import jakarta.validation.constraints.Pattern; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalTime; +import lombok.Builder; + +/** + * Requête de mise à jour d'un événement. + */ +@Builder +public record UpdateEvenementRequest( + @Size(min = ValidationConstants.TITRE_MIN_LENGTH, max = ValidationConstants.TITRE_MAX_LENGTH, message = ValidationConstants.TITRE_SIZE_MESSAGE) String titre, + + @Size(max = ValidationConstants.DESCRIPTION_COURTE_MAX_LENGTH, message = ValidationConstants.DESCRIPTION_COURTE_SIZE_MESSAGE) String description, + + TypeEvenementMetier typeEvenement, + StatutEvenement statut, + PrioriteEvenement priorite, + + LocalDate dateDebut, + LocalDate dateFin, + LocalTime heureDebut, + LocalTime heureFin, + @NotBlank(message = "Le lieu est obligatoire") @Size(max = 100) String lieu, + @Size(max = 200) String adresse, + @Size(max = 50) String ville, + @Size(max = 50) String region, + @DecimalMin(value = "-90.0") @DecimalMax(value = "90.0") BigDecimal latitude, + @DecimalMin(value = "-180.0") @DecimalMax(value = "180.0") BigDecimal longitude, + @Size(max = 100) String organisateur, + @Email(message = "Format d'email invalide") @Size(max = 100) String emailOrganisateur, + @Pattern(regexp = "^\\+?[0-9\\s\\-\\(\\)]{8,20}$") String telephoneOrganisateur, + @Min(value = 1) @Max(value = 10000) Integer capaciteMax, + @DecimalMin(value = ValidationConstants.MONTANT_MIN_VALUE, message = ValidationConstants.MONTANT_POSITIF_MESSAGE) @Digits(integer = ValidationConstants.MONTANT_INTEGER_DIGITS, fraction = ValidationConstants.MONTANT_FRACTION_DIGITS, message = ValidationConstants.MONTANT_DIGITS_MESSAGE) BigDecimal budget, + + @DecimalMin(value = ValidationConstants.MONTANT_MIN_VALUE, message = ValidationConstants.MONTANT_POSITIF_MESSAGE) @Digits(integer = ValidationConstants.MONTANT_INTEGER_DIGITS, fraction = ValidationConstants.MONTANT_FRACTION_DIGITS, message = ValidationConstants.MONTANT_DIGITS_MESSAGE) BigDecimal coutReel, + + @Pattern(regexp = ValidationConstants.DEVISE_PATTERN, message = ValidationConstants.DEVISE_MESSAGE) String codeDevise, + Boolean inscriptionObligatoire, + LocalDate dateLimiteInscription, + Boolean evenementPublic, + Boolean recurrent, + String frequenceRecurrence, + @Size(max = 500) String instructions, + @Size(max = 500) String materielNecessaire, + @Size(max = 100) String conditionsMeteo, + @Size(max = 255) String imageUrl, + @Pattern(regexp = "^#[0-9A-Fa-f]{6}$") String couleurTheme) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/evenement/response/EvenementResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/evenement/response/EvenementResponse.java index c2cddb8..ee9567d 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/evenement/response/EvenementResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/evenement/response/EvenementResponse.java @@ -1,277 +1,277 @@ -package dev.lions.unionflow.server.api.dto.evenement.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalDateTime; -import java.time.LocalTime; -import java.time.format.DateTimeFormatter; -import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; -import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; -import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; - -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée pour un événement. - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class EvenementResponse extends BaseResponse { - - private String titre; - private String description; - private TypeEvenementMetier typeEvenement; - private StatutEvenement statut; - private PrioriteEvenement priorite; - - // Décommenter si l'on a besoin du @JsonFormat, sinon on garde le standard - // @JsonFormat(pattern = "yyyy-MM-dd") - private LocalDate dateDebut; - - // @JsonFormat(pattern = "yyyy-MM-dd") - private LocalDate dateFin; - - // @JsonFormat(pattern = "HH:mm") - private LocalTime heureDebut; - - // @JsonFormat(pattern = "HH:mm") - private LocalTime heureFin; - private String lieu; - private String adresse; - private String ville; - private String region; - private BigDecimal latitude; - private BigDecimal longitude; - private UUID associationId; - private String nomAssociation; - private String organisateur; - private String emailOrganisateur; - private String telephoneOrganisateur; - private Integer capaciteMax; - private Integer participantsInscrits; - private Integer participantsPresents; - private BigDecimal budget; - private BigDecimal coutReel; - private String codeDevise; - private Boolean inscriptionObligatoire; - - // @JsonFormat(pattern = "yyyy-MM-dd") - private LocalDate dateLimiteInscription; - - private Boolean evenementPublic; - private Boolean recurrent; - private String frequenceRecurrence; - private String instructions; - private String materielNecessaire; - private String conditionsMeteo; - private String imageUrl; - private String couleurTheme; - - // @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateAnnulation; - private String raisonAnnulation; - private String nomAnnulateur; - private Long annulePar; - - // === METHODES UTILITAIRES === - - public boolean estEnCours() { - return StatutEvenement.EN_COURS.equals(statut); - } - - public boolean estTermine() { - return StatutEvenement.TERMINE.equals(statut); - } - - public boolean estAnnule() { - return StatutEvenement.ANNULE.equals(statut); - } - - public boolean estComplet() { - return capaciteMax != null - && participantsInscrits != null - && participantsInscrits >= capaciteMax; - } - - public int getPlacesDisponibles() { - if (capaciteMax == null || participantsInscrits == null) { - return 0; - } - return Math.max(0, capaciteMax - participantsInscrits); - } - - public int getTauxRemplissage() { - if (capaciteMax == null || capaciteMax == 0 || participantsInscrits == null) { - return 0; - } - return (participantsInscrits * 100) / capaciteMax; - } - - public int getTauxPresence() { - if (participantsInscrits == null || participantsInscrits == 0 || participantsPresents == null) { - return 0; - } - return (participantsPresents * 100) / participantsInscrits; - } - - public boolean sontInscriptionsOuvertes() { - if (estAnnule() || estTermine()) { - return false; - } - - if (dateLimiteInscription != null && LocalDate.now().isAfter(dateLimiteInscription)) { - return false; - } - - return !estComplet(); - } - - public long getDureeEnHeures() { - if (heureDebut == null || heureFin == null) { - return 0; - } - - return heureDebut.until(heureFin, java.time.temporal.ChronoUnit.HOURS); - } - - public boolean estEvenementMultiJours() { - return dateFin != null && !dateDebut.equals(dateFin); - } - - public String getTypeEvenementLibelle() { - return typeEvenement != null ? typeEvenement.getLibelle() : "Non défini"; - } - - public String getTypeEvenementIcon() { - if (typeEvenement == null) return "pi pi-calendar"; - return switch (typeEvenement) { - case ASSEMBLEE_GENERALE -> "pi pi-building"; - case FORMATION -> "pi pi-book"; - case REUNION_BUREAU -> "pi pi-users"; - case CONFERENCE -> "pi pi-microphone"; - case ATELIER -> "pi pi-wrench"; - case CEREMONIE -> "pi pi-flag"; - case ACTIVITE_SOCIALE, ACTION_CARITATIVE, AUTRE -> "pi pi-calendar"; - }; - } - - public String getTypeEvenementSeverity() { - if (typeEvenement == null) return "secondary"; - return switch (typeEvenement) { - case ASSEMBLEE_GENERALE -> "warning"; - case FORMATION -> "info"; - case ACTIVITE_SOCIALE, ACTION_CARITATIVE, REUNION_BUREAU, CONFERENCE, ATELIER, CEREMONIE, AUTRE -> "secondary"; - }; - } - - public String getStatutLibelle() { - return statut != null ? statut.getLibelle() : "Non défini"; - } - - public String getStatutSeverity() { - if (statut == null) return "secondary"; - return switch (statut) { - case PLANIFIE -> "info"; - case EN_COURS -> "success"; - case TERMINE, CONFIRME -> "secondary"; - case ANNULE -> "danger"; - case REPORTE -> "warning"; - }; - } - - public String getDateDebutFormatee() { - return dateDebut != null ? dateDebut.format(DateTimeFormatter.ofPattern("dd/MM/yyyy")) : "—"; - } - - public String getHeureDebutFormatee() { - return heureDebut != null ? heureDebut.format(DateTimeFormatter.ofPattern("HH:mm")) : "—"; - } - - public String getHeureFinFormatee() { - return heureFin != null ? heureFin.format(DateTimeFormatter.ofPattern("HH:mm")) : "—"; - } - - public String getStatutIcon() { - if (statut == null) return "pi pi-question"; - return switch (statut) { - case PLANIFIE -> "pi pi-clock"; - case CONFIRME -> "pi pi-check-circle"; - case EN_COURS -> "pi pi-play"; - case TERMINE -> "pi pi-check"; - case ANNULE -> "pi pi-times"; - case REPORTE -> "pi pi-refresh"; - }; - } - - public String getPrioriteSeverity() { - if (priorite == null) return "secondary"; - return switch (priorite) { - case CRITIQUE -> "danger"; - case HAUTE -> "warning"; - case NORMALE -> "info"; - case BASSE -> "secondary"; - }; - } - - public String getBudgetFormate() { - if (budget == null) return "—"; - return String.format(java.util.Locale.US, "%,.0f %s", budget, codeDevise != null ? codeDevise : "FCFA"); - } - - public String getPrioriteLibelle() { - return priorite != null ? priorite.getLibelle() : "Normale"; - } - - public String getAdresseComplete() { - StringBuilder adresseComplete = new StringBuilder(); - - if (lieu != null && !lieu.trim().isEmpty()) { - adresseComplete.append(lieu); - } - - if (adresse != null && !adresse.trim().isEmpty()) { - if (adresseComplete.length() > 0) - adresseComplete.append(", "); - adresseComplete.append(adresse); - } - - if (ville != null && !ville.trim().isEmpty()) { - if (adresseComplete.length() > 0) - adresseComplete.append(", "); - adresseComplete.append(ville); - } - - if (region != null && !region.trim().isEmpty()) { - if (adresseComplete.length() > 0) - adresseComplete.append(", "); - adresseComplete.append(region); - } - - return adresseComplete.toString(); - } - - public boolean hasCoordonnees() { - return latitude != null && longitude != null; - } - - public BigDecimal getEcartBudgetaire() { - if (budget == null || coutReel == null) { - return BigDecimal.ZERO; - } - return budget.subtract(coutReel); - } - - public boolean estBudgetDepasse() { - return getEcartBudgetaire().compareTo(BigDecimal.ZERO) < 0; - } -} +package dev.lions.unionflow.server.api.dto.evenement.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.time.LocalTime; +import java.time.format.DateTimeFormatter; +import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; +import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; +import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; + +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée pour un événement. + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class EvenementResponse extends BaseResponse { + + private String titre; + private String description; + private TypeEvenementMetier typeEvenement; + private StatutEvenement statut; + private PrioriteEvenement priorite; + + // Décommenter si l'on a besoin du @JsonFormat, sinon on garde le standard + // @JsonFormat(pattern = "yyyy-MM-dd") + private LocalDate dateDebut; + + // @JsonFormat(pattern = "yyyy-MM-dd") + private LocalDate dateFin; + + // @JsonFormat(pattern = "HH:mm") + private LocalTime heureDebut; + + // @JsonFormat(pattern = "HH:mm") + private LocalTime heureFin; + private String lieu; + private String adresse; + private String ville; + private String region; + private BigDecimal latitude; + private BigDecimal longitude; + private UUID associationId; + private String nomAssociation; + private String organisateur; + private String emailOrganisateur; + private String telephoneOrganisateur; + private Integer capaciteMax; + private Integer participantsInscrits; + private Integer participantsPresents; + private BigDecimal budget; + private BigDecimal coutReel; + private String codeDevise; + private Boolean inscriptionObligatoire; + + // @JsonFormat(pattern = "yyyy-MM-dd") + private LocalDate dateLimiteInscription; + + private Boolean evenementPublic; + private Boolean recurrent; + private String frequenceRecurrence; + private String instructions; + private String materielNecessaire; + private String conditionsMeteo; + private String imageUrl; + private String couleurTheme; + + // @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateAnnulation; + private String raisonAnnulation; + private String nomAnnulateur; + private Long annulePar; + + // === METHODES UTILITAIRES === + + public boolean estEnCours() { + return StatutEvenement.EN_COURS.equals(statut); + } + + public boolean estTermine() { + return StatutEvenement.TERMINE.equals(statut); + } + + public boolean estAnnule() { + return StatutEvenement.ANNULE.equals(statut); + } + + public boolean estComplet() { + return capaciteMax != null + && participantsInscrits != null + && participantsInscrits >= capaciteMax; + } + + public int getPlacesDisponibles() { + if (capaciteMax == null || participantsInscrits == null) { + return 0; + } + return Math.max(0, capaciteMax - participantsInscrits); + } + + public int getTauxRemplissage() { + if (capaciteMax == null || capaciteMax == 0 || participantsInscrits == null) { + return 0; + } + return (participantsInscrits * 100) / capaciteMax; + } + + public int getTauxPresence() { + if (participantsInscrits == null || participantsInscrits == 0 || participantsPresents == null) { + return 0; + } + return (participantsPresents * 100) / participantsInscrits; + } + + public boolean sontInscriptionsOuvertes() { + if (estAnnule() || estTermine()) { + return false; + } + + if (dateLimiteInscription != null && LocalDate.now().isAfter(dateLimiteInscription)) { + return false; + } + + return !estComplet(); + } + + public long getDureeEnHeures() { + if (heureDebut == null || heureFin == null) { + return 0; + } + + return heureDebut.until(heureFin, java.time.temporal.ChronoUnit.HOURS); + } + + public boolean estEvenementMultiJours() { + return dateFin != null && !dateDebut.equals(dateFin); + } + + public String getTypeEvenementLibelle() { + return typeEvenement != null ? typeEvenement.getLibelle() : "Non défini"; + } + + public String getTypeEvenementIcon() { + if (typeEvenement == null) return "pi pi-calendar"; + return switch (typeEvenement) { + case ASSEMBLEE_GENERALE -> "pi pi-building"; + case FORMATION -> "pi pi-book"; + case REUNION_BUREAU -> "pi pi-users"; + case CONFERENCE -> "pi pi-microphone"; + case ATELIER -> "pi pi-wrench"; + case CEREMONIE -> "pi pi-flag"; + case ACTIVITE_SOCIALE, ACTION_CARITATIVE, AUTRE -> "pi pi-calendar"; + }; + } + + public String getTypeEvenementSeverity() { + if (typeEvenement == null) return "secondary"; + return switch (typeEvenement) { + case ASSEMBLEE_GENERALE -> "warning"; + case FORMATION -> "info"; + case ACTIVITE_SOCIALE, ACTION_CARITATIVE, REUNION_BUREAU, CONFERENCE, ATELIER, CEREMONIE, AUTRE -> "secondary"; + }; + } + + public String getStatutLibelle() { + return statut != null ? statut.getLibelle() : "Non défini"; + } + + public String getStatutSeverity() { + if (statut == null) return "secondary"; + return switch (statut) { + case PLANIFIE -> "info"; + case EN_COURS -> "success"; + case TERMINE, CONFIRME -> "secondary"; + case ANNULE -> "danger"; + case REPORTE -> "warning"; + }; + } + + public String getDateDebutFormatee() { + return dateDebut != null ? dateDebut.format(DateTimeFormatter.ofPattern("dd/MM/yyyy")) : "—"; + } + + public String getHeureDebutFormatee() { + return heureDebut != null ? heureDebut.format(DateTimeFormatter.ofPattern("HH:mm")) : "—"; + } + + public String getHeureFinFormatee() { + return heureFin != null ? heureFin.format(DateTimeFormatter.ofPattern("HH:mm")) : "—"; + } + + public String getStatutIcon() { + if (statut == null) return "pi pi-question"; + return switch (statut) { + case PLANIFIE -> "pi pi-clock"; + case CONFIRME -> "pi pi-check-circle"; + case EN_COURS -> "pi pi-play"; + case TERMINE -> "pi pi-check"; + case ANNULE -> "pi pi-times"; + case REPORTE -> "pi pi-refresh"; + }; + } + + public String getPrioriteSeverity() { + if (priorite == null) return "secondary"; + return switch (priorite) { + case CRITIQUE -> "danger"; + case HAUTE -> "warning"; + case NORMALE -> "info"; + case BASSE -> "secondary"; + }; + } + + public String getBudgetFormate() { + if (budget == null) return "—"; + return String.format(java.util.Locale.US, "%,.0f %s", budget, codeDevise != null ? codeDevise : "FCFA"); + } + + public String getPrioriteLibelle() { + return priorite != null ? priorite.getLibelle() : "Normale"; + } + + public String getAdresseComplete() { + StringBuilder adresseComplete = new StringBuilder(); + + if (lieu != null && !lieu.trim().isEmpty()) { + adresseComplete.append(lieu); + } + + if (adresse != null && !adresse.trim().isEmpty()) { + if (adresseComplete.length() > 0) + adresseComplete.append(", "); + adresseComplete.append(adresse); + } + + if (ville != null && !ville.trim().isEmpty()) { + if (adresseComplete.length() > 0) + adresseComplete.append(", "); + adresseComplete.append(ville); + } + + if (region != null && !region.trim().isEmpty()) { + if (adresseComplete.length() > 0) + adresseComplete.append(", "); + adresseComplete.append(region); + } + + return adresseComplete.toString(); + } + + public boolean hasCoordonnees() { + return latitude != null && longitude != null; + } + + public BigDecimal getEcartBudgetaire() { + if (budget == null || coutReel == null) { + return BigDecimal.ZERO; + } + return budget.subtract(coutReel); + } + + public boolean estBudgetDepasse() { + return getEcartBudgetaire().compareTo(BigDecimal.ZERO) < 0; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/favoris/request/CreateFavoriRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/favoris/request/CreateFavoriRequest.java index 450df8c..de177d2 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/favoris/request/CreateFavoriRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/favoris/request/CreateFavoriRequest.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.dto.favoris.request; - -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'un favori. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreateFavoriRequest( - UUID utilisateurId, - String typeFavori, - String titre, - String description, - String url, - String icon, - String couleur, - String categorie, - Integer ordre, - Integer nbVisites, - String derniereVisite, - Boolean estPlusUtilise) { -} +package dev.lions.unionflow.server.api.dto.favoris.request; + +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'un favori. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreateFavoriRequest( + UUID utilisateurId, + String typeFavori, + String titre, + String description, + String url, + String icon, + String couleur, + String categorie, + Integer ordre, + Integer nbVisites, + String derniereVisite, + Boolean estPlusUtilise) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/favoris/response/FavoriResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/favoris/response/FavoriResponse.java index c409747..bd1f5c2 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/favoris/response/FavoriResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/favoris/response/FavoriResponse.java @@ -1,37 +1,37 @@ -package dev.lions.unionflow.server.api.dto.favoris.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.util.UUID; -import lombok.Getter; -import lombok.Setter; -import lombok.Builder; -import lombok.NoArgsConstructor; -import lombok.AllArgsConstructor; -import lombok.EqualsAndHashCode; - -/** - * Réponse pour un favori utilisateur. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class FavoriResponse extends BaseResponse { - - private UUID utilisateurId; - private String typeFavori; - private String titre; - private String description; - private String url; - private String icon; - private String couleur; - private String categorie; - private Integer ordre; - private Integer nbVisites; - private String derniereVisite; - private Boolean estPlusUtilise; -} +package dev.lions.unionflow.server.api.dto.favoris.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.util.UUID; +import lombok.Getter; +import lombok.Setter; +import lombok.Builder; +import lombok.NoArgsConstructor; +import lombok.AllArgsConstructor; +import lombok.EqualsAndHashCode; + +/** + * Réponse pour un favori utilisateur. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class FavoriResponse extends BaseResponse { + + private UUID utilisateurId; + private String typeFavori; + private String titre; + private String description; + private String url; + private String icon; + private String couleur; + private String categorie; + private Integer ordre; + private Integer nbVisites; + private String derniereVisite; + private Boolean estPlusUtilise; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/finance/request/CreateAdhesionRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/finance/request/CreateAdhesionRequest.java index 6bbcd72..90dc835 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/finance/request/CreateAdhesionRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/finance/request/CreateAdhesionRequest.java @@ -1,33 +1,33 @@ -package dev.lions.unionflow.server.api.dto.finance.request; - -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Pattern; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'une adhésion. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreateAdhesionRequest( - @NotBlank(message = "Le numéro de référence est obligatoire") @Size(max = 50, message = "Le numéro de référence ne peut pas dépasser 50 caractères") String numeroReference, - - @NotNull(message = "L'identifiant du membre est obligatoire") UUID membreId, - @NotNull(message = "L'identifiant de l'organisation est obligatoire") UUID organisationId, - @NotNull(message = "La date de demande est obligatoire") LocalDate dateDemande, - - @NotNull(message = "Les frais d'adhésion sont obligatoires") @DecimalMin(value = "0.0", inclusive = false, message = "Les frais d'adhésion doivent être positifs") @Digits(integer = 10, fraction = 2, message = "Format de montant invalide") BigDecimal fraisAdhesion, - - @NotBlank(message = "Le code devise est obligatoire") @Pattern(regexp = "^[A-Z]{3}$", message = "Le code devise doit être un code ISO à 3 lettres") String codeDevise, - - @Size(max = 1000, message = "Les observations ne peuvent pas dépasser 1000 caractères") String observations) { -} +package dev.lions.unionflow.server.api.dto.finance.request; + +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Pattern; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'une adhésion. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreateAdhesionRequest( + @NotBlank(message = "Le numéro de référence est obligatoire") @Size(max = 50, message = "Le numéro de référence ne peut pas dépasser 50 caractères") String numeroReference, + + @NotNull(message = "L'identifiant du membre est obligatoire") UUID membreId, + @NotNull(message = "L'identifiant de l'organisation est obligatoire") UUID organisationId, + @NotNull(message = "La date de demande est obligatoire") LocalDate dateDemande, + + @NotNull(message = "Les frais d'adhésion sont obligatoires") @DecimalMin(value = "0.0", inclusive = false, message = "Les frais d'adhésion doivent être positifs") @Digits(integer = 10, fraction = 2, message = "Format de montant invalide") BigDecimal fraisAdhesion, + + @NotBlank(message = "Le code devise est obligatoire") @Pattern(regexp = "^[A-Z]{3}$", message = "Le code devise doit être un code ISO à 3 lettres") String codeDevise, + + @Size(max = 1000, message = "Les observations ne peuvent pas dépasser 1000 caractères") String observations) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/finance/request/UpdateAdhesionRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/finance/request/UpdateAdhesionRequest.java index a277eb0..aa02a89 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/finance/request/UpdateAdhesionRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/finance/request/UpdateAdhesionRequest.java @@ -1,38 +1,38 @@ -package dev.lions.unionflow.server.api.dto.finance.request; - -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.Pattern; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalDateTime; -import lombok.Builder; - -/** - * Requête de mise à jour d'une adhésion. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record UpdateAdhesionRequest( - @DecimalMin(value = "0.0", message = "Le montant payé ne peut pas être négatif") @Digits(integer = 10, fraction = 2, message = "Format de montant invalide") BigDecimal montantPaye, - - @Pattern(regexp = "^(EN_ATTENTE|APPROUVEE|REJETEE|ANNULEE|EN_PAIEMENT|PAYEE)$", message = "Statut invalide") String statut, - - LocalDate dateApprobation, - LocalDateTime datePaiement, - - @Pattern(regexp = "^(ESPECES|VIREMENT|CHEQUE|WAVE_MONEY|ORANGE_MONEY|FREE_MONEY|CARTE_BANCAIRE)$", message = "Méthode de paiement invalide") String methodePaiement, - - @Size(max = 100, message = "La référence de paiement ne peut pas dépasser 100 caractères") String referencePaiement, - - @Size(max = 1000, message = "Le motif de rejet ne peut pas dépasser 1000 caractères") String motifRejet, - - @Size(max = 1000, message = "Les observations ne peuvent pas dépasser 1000 caractères") String observations, - - @Size(max = 255, message = "Le nom de l'approbateur ne peut pas dépasser 255 caractères") String approuvePar, - - LocalDate dateValidation) { -} +package dev.lions.unionflow.server.api.dto.finance.request; + +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.Pattern; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalDateTime; +import lombok.Builder; + +/** + * Requête de mise à jour d'une adhésion. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record UpdateAdhesionRequest( + @DecimalMin(value = "0.0", message = "Le montant payé ne peut pas être négatif") @Digits(integer = 10, fraction = 2, message = "Format de montant invalide") BigDecimal montantPaye, + + @Pattern(regexp = "^(EN_ATTENTE|APPROUVEE|REJETEE|ANNULEE|EN_PAIEMENT|PAYEE)$", message = "Statut invalide") String statut, + + LocalDate dateApprobation, + LocalDateTime datePaiement, + + @Pattern(regexp = "^(ESPECES|VIREMENT|CHEQUE|WAVE_MONEY|ORANGE_MONEY|FREE_MONEY|CARTE_BANCAIRE)$", message = "Méthode de paiement invalide") String methodePaiement, + + @Size(max = 100, message = "La référence de paiement ne peut pas dépasser 100 caractères") String referencePaiement, + + @Size(max = 1000, message = "Le motif de rejet ne peut pas dépasser 1000 caractères") String motifRejet, + + @Size(max = 1000, message = "Les observations ne peuvent pas dépasser 1000 caractères") String observations, + + @Size(max = 255, message = "Le nom de l'approbateur ne peut pas dépasser 255 caractères") String approuvePar, + + LocalDate dateValidation) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/finance/response/AdhesionResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/finance/response/AdhesionResponse.java index bfe3d04..090cd79 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/finance/response/AdhesionResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/finance/response/AdhesionResponse.java @@ -1,171 +1,171 @@ -package dev.lions.unionflow.server.api.dto.finance.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalDateTime; -import java.time.format.DateTimeFormatter; -import java.time.temporal.ChronoUnit; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse contenant les données d'une adhésion. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class AdhesionResponse extends BaseResponse { - - private String numeroReference; - private UUID membreId; - private String numeroMembre; - private String nomMembre; - private String emailMembre; - private UUID organisationId; - private String nomOrganisation; - private LocalDate dateDemande; - private BigDecimal fraisAdhesion; - private BigDecimal montantPaye; - private String codeDevise; - private String statut; - private LocalDate dateApprobation; - private LocalDateTime datePaiement; - private String methodePaiement; - private String referencePaiement; - private String motifRejet; - private String observations; - private String approuvePar; - private LocalDate dateValidation; - - // Méthodes utilitaires héritées de l'ancien DTO - public boolean isPayeeIntegralement() { - return montantPaye != null && fraisAdhesion != null && montantPaye.compareTo(fraisAdhesion) >= 0; - } - - public boolean isEnAttentePaiement() { - return "APPROUVEE".equals(statut) && !isPayeeIntegralement(); - } - - public BigDecimal getMontantRestant() { - if (fraisAdhesion == null) - return BigDecimal.ZERO; - if (montantPaye == null) - return fraisAdhesion; - BigDecimal restant = fraisAdhesion.subtract(montantPaye); - return restant.compareTo(BigDecimal.ZERO) > 0 ? restant : BigDecimal.ZERO; - } - - public int getPourcentagePaiement() { - if (fraisAdhesion == null || fraisAdhesion.compareTo(BigDecimal.ZERO) == 0) - return 0; - if (montantPaye == null) - return 0; - return montantPaye.multiply(BigDecimal.valueOf(100)).divide(fraisAdhesion, 0, java.math.RoundingMode.HALF_UP) - .intValue(); - } - - public long getJoursDepuisDemande() { - if (dateDemande == null) - return 0; - return ChronoUnit.DAYS.between(dateDemande, LocalDate.now()); - } - - public String getStatutLibelle() { - if (statut == null) - return "Non défini"; - return switch (statut) { - case "EN_ATTENTE" -> "En attente"; - case "APPROUVEE" -> "Approuvée"; - case "REJETEE" -> "Rejetée"; - case "ANNULEE" -> "Annulée"; - case "EN_PAIEMENT" -> "En paiement"; - case "PAYEE" -> "Payée"; - default -> statut; - }; - } - - public String getStatutSeverity() { - if (statut == null) - return "secondary"; - return switch (statut) { - case "APPROUVEE", "PAYEE" -> "success"; - case "EN_ATTENTE", "EN_PAIEMENT" -> "warning"; - case "REJETEE" -> "danger"; - case "ANNULEE" -> "secondary"; - default -> "secondary"; - }; - } - - public String getStatutIcon() { - if (statut == null) - return "pi-circle"; - return switch (statut) { - case "APPROUVEE", "PAYEE" -> "pi-check"; - case "EN_ATTENTE" -> "pi-clock"; - case "EN_PAIEMENT" -> "pi-credit-card"; - case "REJETEE" -> "pi-times"; - case "ANNULEE" -> "pi-ban"; - default -> "pi-circle"; - }; - } - - public String getMethodePaiementLibelle() { - if (methodePaiement == null) - return "Non défini"; - return switch (methodePaiement) { - case "ESPECES" -> "Espèces"; - case "VIREMENT" -> "Virement bancaire"; - case "CHEQUE" -> "Chèque"; - case "WAVE_MONEY" -> "Wave Money"; - case "ORANGE_MONEY" -> "Orange Money"; - case "FREE_MONEY" -> "Free Money"; - case "CARTE_BANCAIRE" -> "Carte bancaire"; - default -> methodePaiement; - }; - } - - public String getDateDemandeFormatee() { - if (dateDemande == null) - return ""; - return dateDemande.format(DateTimeFormatter.ofPattern("dd/MM/yyyy")); - } - - public String getDateApprobationFormatee() { - if (dateApprobation == null) - return ""; - return dateApprobation.format(DateTimeFormatter.ofPattern("dd/MM/yyyy")); - } - - public String getDatePaiementFormatee() { - if (datePaiement == null) - return ""; - return datePaiement.format(DateTimeFormatter.ofPattern("dd/MM/yyyy HH:mm")); - } - - public String getFraisAdhesionFormatte() { - if (fraisAdhesion == null) - return "0 FCFA"; - return String.format("%,.0f FCFA", fraisAdhesion.doubleValue()); - } - - public String getMontantPayeFormatte() { - if (montantPaye == null) - return "0 FCFA"; - return String.format("%,.0f FCFA", montantPaye.doubleValue()); - } - - public String getMontantRestantFormatte() { - return String.format("%,.0f FCFA", getMontantRestant().doubleValue()); - } -} +package dev.lions.unionflow.server.api.dto.finance.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.time.format.DateTimeFormatter; +import java.time.temporal.ChronoUnit; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse contenant les données d'une adhésion. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class AdhesionResponse extends BaseResponse { + + private String numeroReference; + private UUID membreId; + private String numeroMembre; + private String nomMembre; + private String emailMembre; + private UUID organisationId; + private String nomOrganisation; + private LocalDate dateDemande; + private BigDecimal fraisAdhesion; + private BigDecimal montantPaye; + private String codeDevise; + private String statut; + private LocalDate dateApprobation; + private LocalDateTime datePaiement; + private String methodePaiement; + private String referencePaiement; + private String motifRejet; + private String observations; + private String approuvePar; + private LocalDate dateValidation; + + // Méthodes utilitaires héritées de l'ancien DTO + public boolean isPayeeIntegralement() { + return montantPaye != null && fraisAdhesion != null && montantPaye.compareTo(fraisAdhesion) >= 0; + } + + public boolean isEnAttentePaiement() { + return "APPROUVEE".equals(statut) && !isPayeeIntegralement(); + } + + public BigDecimal getMontantRestant() { + if (fraisAdhesion == null) + return BigDecimal.ZERO; + if (montantPaye == null) + return fraisAdhesion; + BigDecimal restant = fraisAdhesion.subtract(montantPaye); + return restant.compareTo(BigDecimal.ZERO) > 0 ? restant : BigDecimal.ZERO; + } + + public int getPourcentagePaiement() { + if (fraisAdhesion == null || fraisAdhesion.compareTo(BigDecimal.ZERO) == 0) + return 0; + if (montantPaye == null) + return 0; + return montantPaye.multiply(BigDecimal.valueOf(100)).divide(fraisAdhesion, 0, java.math.RoundingMode.HALF_UP) + .intValue(); + } + + public long getJoursDepuisDemande() { + if (dateDemande == null) + return 0; + return ChronoUnit.DAYS.between(dateDemande, LocalDate.now()); + } + + public String getStatutLibelle() { + if (statut == null) + return "Non défini"; + return switch (statut) { + case "EN_ATTENTE" -> "En attente"; + case "APPROUVEE" -> "Approuvée"; + case "REJETEE" -> "Rejetée"; + case "ANNULEE" -> "Annulée"; + case "EN_PAIEMENT" -> "En paiement"; + case "PAYEE" -> "Payée"; + default -> statut; + }; + } + + public String getStatutSeverity() { + if (statut == null) + return "secondary"; + return switch (statut) { + case "APPROUVEE", "PAYEE" -> "success"; + case "EN_ATTENTE", "EN_PAIEMENT" -> "warning"; + case "REJETEE" -> "danger"; + case "ANNULEE" -> "secondary"; + default -> "secondary"; + }; + } + + public String getStatutIcon() { + if (statut == null) + return "pi-circle"; + return switch (statut) { + case "APPROUVEE", "PAYEE" -> "pi-check"; + case "EN_ATTENTE" -> "pi-clock"; + case "EN_PAIEMENT" -> "pi-credit-card"; + case "REJETEE" -> "pi-times"; + case "ANNULEE" -> "pi-ban"; + default -> "pi-circle"; + }; + } + + public String getMethodePaiementLibelle() { + if (methodePaiement == null) + return "Non défini"; + return switch (methodePaiement) { + case "ESPECES" -> "Espèces"; + case "VIREMENT" -> "Virement bancaire"; + case "CHEQUE" -> "Chèque"; + case "WAVE_MONEY" -> "Wave Money"; + case "ORANGE_MONEY" -> "Orange Money"; + case "FREE_MONEY" -> "Free Money"; + case "CARTE_BANCAIRE" -> "Carte bancaire"; + default -> methodePaiement; + }; + } + + public String getDateDemandeFormatee() { + if (dateDemande == null) + return ""; + return dateDemande.format(DateTimeFormatter.ofPattern("dd/MM/yyyy")); + } + + public String getDateApprobationFormatee() { + if (dateApprobation == null) + return ""; + return dateApprobation.format(DateTimeFormatter.ofPattern("dd/MM/yyyy")); + } + + public String getDatePaiementFormatee() { + if (datePaiement == null) + return ""; + return datePaiement.format(DateTimeFormatter.ofPattern("dd/MM/yyyy HH:mm")); + } + + public String getFraisAdhesionFormatte() { + if (fraisAdhesion == null) + return "0 FCFA"; + return String.format("%,.0f FCFA", fraisAdhesion.doubleValue()); + } + + public String getMontantPayeFormatte() { + if (montantPaye == null) + return "0 FCFA"; + return String.format("%,.0f FCFA", montantPaye.doubleValue()); + } + + public String getMontantRestantFormatte() { + return String.format("%,.0f FCFA", getMontantRestant().doubleValue()); + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/ApproveTransactionRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/ApproveTransactionRequest.java index 0d53ad8..4ec19fc 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/ApproveTransactionRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/ApproveTransactionRequest.java @@ -1,24 +1,24 @@ -package dev.lions.unionflow.server.api.dto.finance_workflow.request; - -import jakarta.validation.constraints.Size; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO de requête pour approuver une transaction - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class ApproveTransactionRequest { - - @Size(max = 1000, message = "Le commentaire ne peut pas dépasser 1000 caractères") - private String comment; -} +package dev.lions.unionflow.server.api.dto.finance_workflow.request; + +import jakarta.validation.constraints.Size; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO de requête pour approuver une transaction + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class ApproveTransactionRequest { + + @Size(max = 1000, message = "Le commentaire ne peut pas dépasser 1000 caractères") + private String comment; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/CreateBudgetLineRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/CreateBudgetLineRequest.java index a8c310b..2364fee 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/CreateBudgetLineRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/CreateBudgetLineRequest.java @@ -1,42 +1,42 @@ -package dev.lions.unionflow.server.api.dto.finance_workflow.request; - -import jakarta.validation.constraints.*; -import java.math.BigDecimal; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO de requête pour créer une ligne budgétaire - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class CreateBudgetLineRequest { - - @NotBlank(message = "La catégorie est requise") - @Pattern(regexp = "^(CONTRIBUTIONS|SAVINGS|SOLIDARITY|EVENTS|OPERATIONAL|INVESTMENTS|OTHER)$", - message = "Catégorie invalide") - private String category; - - @NotBlank(message = "Le nom est requis") - @Size(max = 200, message = "Le nom ne peut pas dépasser 200 caractères") - private String name; - - @Size(max = 500, message = "La description ne peut pas dépasser 500 caractères") - private String description; - - @NotNull(message = "Le montant prévu est requis") - @DecimalMin(value = "0.0", message = "Le montant prévu doit être positif") - @Digits(integer = 14, fraction = 2, message = "Format du montant invalide") - private BigDecimal amountPlanned; - - @Size(max = 1000, message = "Les notes ne peuvent pas dépasser 1000 caractères") - private String notes; -} +package dev.lions.unionflow.server.api.dto.finance_workflow.request; + +import jakarta.validation.constraints.*; +import java.math.BigDecimal; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO de requête pour créer une ligne budgétaire + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class CreateBudgetLineRequest { + + @NotBlank(message = "La catégorie est requise") + @Pattern(regexp = "^(CONTRIBUTIONS|SAVINGS|SOLIDARITY|EVENTS|OPERATIONAL|INVESTMENTS|OTHER)$", + message = "Catégorie invalide") + private String category; + + @NotBlank(message = "Le nom est requis") + @Size(max = 200, message = "Le nom ne peut pas dépasser 200 caractères") + private String name; + + @Size(max = 500, message = "La description ne peut pas dépasser 500 caractères") + private String description; + + @NotNull(message = "Le montant prévu est requis") + @DecimalMin(value = "0.0", message = "Le montant prévu doit être positif") + @Digits(integer = 14, fraction = 2, message = "Format du montant invalide") + private BigDecimal amountPlanned; + + @Size(max = 1000, message = "Les notes ne peuvent pas dépasser 1000 caractères") + private String notes; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/CreateBudgetRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/CreateBudgetRequest.java index a634781..ed7afa4 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/CreateBudgetRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/CreateBudgetRequest.java @@ -1,58 +1,58 @@ -package dev.lions.unionflow.server.api.dto.finance_workflow.request; - -import jakarta.validation.Valid; -import jakarta.validation.constraints.*; -import java.util.ArrayList; -import java.util.List; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO de requête pour créer un budget - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class CreateBudgetRequest { - - @NotBlank(message = "Le nom est requis") - @Size(max = 200, message = "Le nom ne peut pas dépasser 200 caractères") - private String name; - - @Size(max = 1000, message = "La description ne peut pas dépasser 1000 caractères") - private String description; - - @NotNull(message = "L'ID de l'organisation est requis") - private UUID organizationId; - - @NotBlank(message = "La période est requise") - @Pattern(regexp = "^(MONTHLY|QUARTERLY|SEMIANNUAL|ANNUAL)$", - message = "Période invalide") - private String period; - - @NotNull(message = "L'année est requise") - @Min(value = 2020, message = "L'année doit être >= 2020") - @Max(value = 2100, message = "L'année doit être <= 2100") - private Integer year; - - @Min(value = 1, message = "Le mois doit être entre 1 et 12") - @Max(value = 12, message = "Le mois doit être entre 1 et 12") - private Integer month; - - @NotNull(message = "Au moins une ligne budgétaire est requise") - @Size(min = 1, message = "Au moins une ligne budgétaire est requise") - @Valid - @Builder.Default - private List lines = new ArrayList<>(); - - @Pattern(regexp = "^[A-Z]{3}$", message = "Code devise invalide (doit être ISO 3 lettres)") - private String currency; // Optionnel, défaut XOF -} +package dev.lions.unionflow.server.api.dto.finance_workflow.request; + +import jakarta.validation.Valid; +import jakarta.validation.constraints.*; +import java.util.ArrayList; +import java.util.List; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO de requête pour créer un budget + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class CreateBudgetRequest { + + @NotBlank(message = "Le nom est requis") + @Size(max = 200, message = "Le nom ne peut pas dépasser 200 caractères") + private String name; + + @Size(max = 1000, message = "La description ne peut pas dépasser 1000 caractères") + private String description; + + @NotNull(message = "L'ID de l'organisation est requis") + private UUID organizationId; + + @NotBlank(message = "La période est requise") + @Pattern(regexp = "^(MONTHLY|QUARTERLY|SEMIANNUAL|ANNUAL)$", + message = "Période invalide") + private String period; + + @NotNull(message = "L'année est requise") + @Min(value = 2020, message = "L'année doit être >= 2020") + @Max(value = 2100, message = "L'année doit être <= 2100") + private Integer year; + + @Min(value = 1, message = "Le mois doit être entre 1 et 12") + @Max(value = 12, message = "Le mois doit être entre 1 et 12") + private Integer month; + + @NotNull(message = "Au moins une ligne budgétaire est requise") + @Size(min = 1, message = "Au moins une ligne budgétaire est requise") + @Valid + @Builder.Default + private List lines = new ArrayList<>(); + + @Pattern(regexp = "^[A-Z]{3}$", message = "Code devise invalide (doit être ISO 3 lettres)") + private String currency; // Optionnel, défaut XOF +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/RejectTransactionRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/RejectTransactionRequest.java index 3d52701..6eff748 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/RejectTransactionRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/request/RejectTransactionRequest.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.dto.finance_workflow.request; - -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.Size; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO de requête pour rejeter une transaction - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class RejectTransactionRequest { - - @NotBlank(message = "La raison du rejet est requise") - @Size(min = 10, max = 1000, message = "La raison doit contenir entre 10 et 1000 caractères") - private String reason; -} +package dev.lions.unionflow.server.api.dto.finance_workflow.request; + +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.Size; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO de requête pour rejeter une transaction + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class RejectTransactionRequest { + + @NotBlank(message = "La raison du rejet est requise") + @Size(min = 10, max = 1000, message = "La raison doit contenir entre 10 et 1000 caractères") + private String reason; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/ApproverActionResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/ApproverActionResponse.java index d75f69e..4cf7f31 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/ApproverActionResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/ApproverActionResponse.java @@ -1,44 +1,44 @@ -package dev.lions.unionflow.server.api.dto.finance_workflow.response; - -import com.fasterxml.jackson.annotation.JsonFormat; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import java.time.LocalDateTime; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO de réponse pour une action d'approbateur - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class ApproverActionResponse { - - private UUID id; - - @NotNull - private UUID approverId; - - @NotBlank - private String approverName; - - @NotBlank - private String approverRole; - - @NotBlank - private String decision; // PENDING, APPROVED, REJECTED - - private String comment; - - @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") - private LocalDateTime decidedAt; -} +package dev.lions.unionflow.server.api.dto.finance_workflow.response; + +import com.fasterxml.jackson.annotation.JsonFormat; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import java.time.LocalDateTime; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO de réponse pour une action d'approbateur + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class ApproverActionResponse { + + private UUID id; + + @NotNull + private UUID approverId; + + @NotBlank + private String approverName; + + @NotBlank + private String approverRole; + + @NotBlank + private String decision; // PENDING, APPROVED, REJECTED + + private String comment; + + @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") + private LocalDateTime decidedAt; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/BudgetLineResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/BudgetLineResponse.java index bddbbee..b06c97a 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/BudgetLineResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/BudgetLineResponse.java @@ -1,47 +1,47 @@ -package dev.lions.unionflow.server.api.dto.finance_workflow.response; - -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import java.math.BigDecimal; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO de réponse pour une ligne budgétaire - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class BudgetLineResponse { - - private UUID id; - - @NotBlank - private String category; // CONTRIBUTIONS, SAVINGS, SOLIDARITY, etc. - - @NotBlank - private String name; - - private String description; - - @NotNull - private BigDecimal amountPlanned; - - @NotNull - private BigDecimal amountRealized; - - private String notes; - - // Champs calculés - private Double realizationRate; - private BigDecimal variance; - private Boolean isOverBudget; -} +package dev.lions.unionflow.server.api.dto.finance_workflow.response; + +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import java.math.BigDecimal; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO de réponse pour une ligne budgétaire + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class BudgetLineResponse { + + private UUID id; + + @NotBlank + private String category; // CONTRIBUTIONS, SAVINGS, SOLIDARITY, etc. + + @NotBlank + private String name; + + private String description; + + @NotNull + private BigDecimal amountPlanned; + + @NotNull + private BigDecimal amountRealized; + + private String notes; + + // Champs calculés + private Double realizationRate; + private BigDecimal variance; + private Boolean isOverBudget; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/BudgetResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/BudgetResponse.java index 31d8f80..3628132 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/BudgetResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/BudgetResponse.java @@ -1,92 +1,92 @@ -package dev.lions.unionflow.server.api.dto.finance_workflow.response; - -import com.fasterxml.jackson.annotation.JsonFormat; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalDateTime; -import java.util.ArrayList; -import java.util.List; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO de réponse pour un budget - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class BudgetResponse { - - private UUID id; - - @NotBlank - private String name; - - private String description; - - @NotNull - private UUID organizationId; - - @NotBlank - private String period; // MONTHLY, QUARTERLY, SEMIANNUAL, ANNUAL - - @NotNull - private Integer year; - - private Integer month; - - @NotBlank - private String status; // DRAFT, ACTIVE, CLOSED, CANCELLED - - @Builder.Default - private List lines = new ArrayList<>(); - - @NotNull - private BigDecimal totalPlanned; - - @NotNull - private BigDecimal totalRealized; - - @NotBlank - private String currency; - - @NotNull - private UUID createdById; - - @NotNull - @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") - private LocalDateTime createdAt; - - @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") - private LocalDateTime approvedAt; - - private UUID approvedById; - - @NotNull - @JsonFormat(pattern = "yyyy-MM-dd") - private LocalDate startDate; - - @NotNull - @JsonFormat(pattern = "yyyy-MM-dd") - private LocalDate endDate; - - private String metadata; - - // Champs calculés - private Double realizationRate; - private BigDecimal variance; - private Double varianceRate; - private Boolean isOverBudget; - private Boolean isActive; - private Boolean isCurrentPeriod; -} +package dev.lions.unionflow.server.api.dto.finance_workflow.response; + +import com.fasterxml.jackson.annotation.JsonFormat; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.util.ArrayList; +import java.util.List; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO de réponse pour un budget + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class BudgetResponse { + + private UUID id; + + @NotBlank + private String name; + + private String description; + + @NotNull + private UUID organizationId; + + @NotBlank + private String period; // MONTHLY, QUARTERLY, SEMIANNUAL, ANNUAL + + @NotNull + private Integer year; + + private Integer month; + + @NotBlank + private String status; // DRAFT, ACTIVE, CLOSED, CANCELLED + + @Builder.Default + private List lines = new ArrayList<>(); + + @NotNull + private BigDecimal totalPlanned; + + @NotNull + private BigDecimal totalRealized; + + @NotBlank + private String currency; + + @NotNull + private UUID createdById; + + @NotNull + @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") + private LocalDateTime createdAt; + + @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") + private LocalDateTime approvedAt; + + private UUID approvedById; + + @NotNull + @JsonFormat(pattern = "yyyy-MM-dd") + private LocalDate startDate; + + @NotNull + @JsonFormat(pattern = "yyyy-MM-dd") + private LocalDate endDate; + + private String metadata; + + // Champs calculés + private Double realizationRate; + private BigDecimal variance; + private Double varianceRate; + private Boolean isOverBudget; + private Boolean isActive; + private Boolean isCurrentPeriod; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/TransactionApprovalResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/TransactionApprovalResponse.java index a5a9802..6a2a63a 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/TransactionApprovalResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/finance_workflow/response/TransactionApprovalResponse.java @@ -1,81 +1,81 @@ -package dev.lions.unionflow.server.api.dto.finance_workflow.response; - -import com.fasterxml.jackson.annotation.JsonFormat; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import java.math.BigDecimal; -import java.time.LocalDateTime; -import java.util.ArrayList; -import java.util.List; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO de réponse pour une approbation de transaction - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class TransactionApprovalResponse { - - private UUID id; - - @NotNull - private UUID transactionId; - - @NotBlank - private String transactionType; // CONTRIBUTION, DEPOSIT, WITHDRAWAL, etc. - - @NotNull - private BigDecimal amount; - - @NotBlank - private String currency; - - @NotNull - private UUID requesterId; - - @NotBlank - private String requesterName; - - private UUID organizationId; - - @NotBlank - private String requiredLevel; // NONE, LEVEL1, LEVEL2, LEVEL3 - - @NotBlank - private String status; // PENDING, APPROVED, VALIDATED, REJECTED, EXPIRED, CANCELLED - - @Builder.Default - private List approvers = new ArrayList<>(); - - private String rejectionReason; - - @NotNull - @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") - private LocalDateTime createdAt; - - @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") - private LocalDateTime expiresAt; - - @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") - private LocalDateTime completedAt; - - private String metadata; - - // Champs calculés - private Integer approvalCount; - private Integer requiredApprovals; - private Boolean hasAllApprovals; - private Boolean isExpired; - private Boolean isPending; - private Boolean isCompleted; -} +package dev.lions.unionflow.server.api.dto.finance_workflow.response; + +import com.fasterxml.jackson.annotation.JsonFormat; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import java.math.BigDecimal; +import java.time.LocalDateTime; +import java.util.ArrayList; +import java.util.List; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO de réponse pour une approbation de transaction + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class TransactionApprovalResponse { + + private UUID id; + + @NotNull + private UUID transactionId; + + @NotBlank + private String transactionType; // CONTRIBUTION, DEPOSIT, WITHDRAWAL, etc. + + @NotNull + private BigDecimal amount; + + @NotBlank + private String currency; + + @NotNull + private UUID requesterId; + + @NotBlank + private String requesterName; + + private UUID organizationId; + + @NotBlank + private String requiredLevel; // NONE, LEVEL1, LEVEL2, LEVEL3 + + @NotBlank + private String status; // PENDING, APPROVED, VALIDATED, REJECTED, EXPIRED, CANCELLED + + @Builder.Default + private List approvers = new ArrayList<>(); + + private String rejectionReason; + + @NotNull + @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") + private LocalDateTime createdAt; + + @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") + private LocalDateTime expiresAt; + + @JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss") + private LocalDateTime completedAt; + + private String metadata; + + // Champs calculés + private Integer approvalCount; + private Integer requiredApprovals; + private Boolean hasAllApprovals; + private Boolean isExpired; + private Boolean isPending; + private Boolean isCompleted; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/CreateFormuleAbonnementRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/CreateFormuleAbonnementRequest.java index a42cfa3..e38ab04 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/CreateFormuleAbonnementRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/CreateFormuleAbonnementRequest.java @@ -1,51 +1,51 @@ -package dev.lions.unionflow.server.api.dto.formuleabonnement.request; - -import dev.lions.unionflow.server.api.enums.formuleabonnement.StatutFormule; -import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Pattern; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; -import lombok.Builder; - -/** - * Requête de création d'une formule d'abonnement. - */ -@Builder -public record CreateFormuleAbonnementRequest( - @NotBlank(message = "Le nom de la formule est obligatoire") @Size(min = 2, max = 100, message = "Le nom de la formule doit contenir entre 2 et 100 caractères") String nom, - @NotBlank(message = "Le code de la formule est obligatoire") @Pattern(regexp = "^[A-Z_]{2,20}$", message = "Le code doit contenir uniquement des lettres majuscules et underscores") String code, - @Size(max = 1000, message = "La description ne peut pas dépasser 1000 caractères") String description, - @NotNull(message = "Le type de formule est obligatoire") TypeFormule type, - @NotNull(message = "Le statut est obligatoire") StatutFormule statut, - @NotNull(message = "Le prix mensuel est obligatoire") @DecimalMin(value = "0.0", inclusive = false) @Digits(integer = 10, fraction = 2) BigDecimal prixMensuel, - @DecimalMin(value = "0.0", inclusive = false) @Digits(integer = 10, fraction = 2) BigDecimal prixAnnuel, - @NotBlank(message = "La devise est obligatoire") @Pattern(regexp = "^[A-Z]{3}$") String devise, - @NotNull(message = "Le nombre maximum de membres est obligatoire") Integer maxMembres, - @NotNull(message = "Le nombre maximum d'administrateurs est obligatoire") Integer maxAdministrateurs, - @NotNull(message = "L'espace de stockage est obligatoire") @DecimalMin(value = "0.1", message = "L'espace de stockage doit être d'au moins 0.1 GB") BigDecimal espaceStockageGB, - @NotNull(message = "Le support technique doit être spécifié") Boolean supportTechnique, - @Pattern(regexp = "^(EMAIL|CHAT|TELEPHONE|PREMIUM)$", message = "Le niveau de support doit être EMAIL, CHAT, TELEPHONE ou PREMIUM") String niveauSupport, - Boolean fonctionnalitesAvancees, - Boolean apiAccess, - Boolean rapportsPersonnalises, - Boolean integrationsTierces, - Boolean sauvegardeAutomatique, - Boolean multiLangues, - Boolean personnalisationInterface, - Boolean formationIncluse, - Integer heuresFormation, - Boolean populaire, - Boolean recommandee, - Integer periodeEssaiJours, - LocalDate dateDebutValidite, - LocalDate dateFinValidite, - Integer ordreAffichage, - @Pattern(regexp = "^#[0-9A-Fa-f]{6}$", message = "La couleur doit être un code hexadécimal valide") String couleur, - @Size(max = 50, message = "Le nom de l'icône ne peut pas dépasser 50 caractères") String icone, - @Size(max = 500, message = "Les notes ne peuvent pas dépasser 500 caractères") String notes) { -} +package dev.lions.unionflow.server.api.dto.formuleabonnement.request; + +import dev.lions.unionflow.server.api.enums.formuleabonnement.StatutFormule; +import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Pattern; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; +import lombok.Builder; + +/** + * Requête de création d'une formule d'abonnement. + */ +@Builder +public record CreateFormuleAbonnementRequest( + @NotBlank(message = "Le nom de la formule est obligatoire") @Size(min = 2, max = 100, message = "Le nom de la formule doit contenir entre 2 et 100 caractères") String nom, + @NotBlank(message = "Le code de la formule est obligatoire") @Pattern(regexp = "^[A-Z_]{2,20}$", message = "Le code doit contenir uniquement des lettres majuscules et underscores") String code, + @Size(max = 1000, message = "La description ne peut pas dépasser 1000 caractères") String description, + @NotNull(message = "Le type de formule est obligatoire") TypeFormule type, + @NotNull(message = "Le statut est obligatoire") StatutFormule statut, + @NotNull(message = "Le prix mensuel est obligatoire") @DecimalMin(value = "0.0", inclusive = false) @Digits(integer = 10, fraction = 2) BigDecimal prixMensuel, + @DecimalMin(value = "0.0", inclusive = false) @Digits(integer = 10, fraction = 2) BigDecimal prixAnnuel, + @NotBlank(message = "La devise est obligatoire") @Pattern(regexp = "^[A-Z]{3}$") String devise, + @NotNull(message = "Le nombre maximum de membres est obligatoire") Integer maxMembres, + @NotNull(message = "Le nombre maximum d'administrateurs est obligatoire") Integer maxAdministrateurs, + @NotNull(message = "L'espace de stockage est obligatoire") @DecimalMin(value = "0.1", message = "L'espace de stockage doit être d'au moins 0.1 GB") BigDecimal espaceStockageGB, + @NotNull(message = "Le support technique doit être spécifié") Boolean supportTechnique, + @Pattern(regexp = "^(EMAIL|CHAT|TELEPHONE|PREMIUM)$", message = "Le niveau de support doit être EMAIL, CHAT, TELEPHONE ou PREMIUM") String niveauSupport, + Boolean fonctionnalitesAvancees, + Boolean apiAccess, + Boolean rapportsPersonnalises, + Boolean integrationsTierces, + Boolean sauvegardeAutomatique, + Boolean multiLangues, + Boolean personnalisationInterface, + Boolean formationIncluse, + Integer heuresFormation, + Boolean populaire, + Boolean recommandee, + Integer periodeEssaiJours, + LocalDate dateDebutValidite, + LocalDate dateFinValidite, + Integer ordreAffichage, + @Pattern(regexp = "^#[0-9A-Fa-f]{6}$", message = "La couleur doit être un code hexadécimal valide") String couleur, + @Size(max = 50, message = "Le nom de l'icône ne peut pas dépasser 50 caractères") String icone, + @Size(max = 500, message = "Les notes ne peuvent pas dépasser 500 caractères") String notes) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/UpdateFormuleAbonnementRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/UpdateFormuleAbonnementRequest.java index 2db879b..6d8aa56 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/UpdateFormuleAbonnementRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/UpdateFormuleAbonnementRequest.java @@ -1,49 +1,49 @@ -package dev.lions.unionflow.server.api.dto.formuleabonnement.request; - -import dev.lions.unionflow.server.api.enums.formuleabonnement.StatutFormule; -import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.Pattern; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; -import lombok.Builder; - -/** - * Requête de mise à jour d'une formule d'abonnement. - */ -@Builder -public record UpdateFormuleAbonnementRequest( - @Size(min = 2, max = 100, message = "Le nom de la formule doit contenir entre 2 et 100 caractères") String nom, - @Pattern(regexp = "^[A-Z_]{2,20}$", message = "Le code doit contenir uniquement des lettres majuscules et underscores") String code, - @Size(max = 1000, message = "La description ne peut pas dépasser 1000 caractères") String description, - TypeFormule type, - StatutFormule statut, - @DecimalMin(value = "0.0", inclusive = false, message = "Le prix mensuel doit être positif") @Digits(integer = 10, fraction = 2) BigDecimal prixMensuel, - @DecimalMin(value = "0.0", inclusive = false, message = "Le prix annuel doit être positif") @Digits(integer = 10, fraction = 2) BigDecimal prixAnnuel, - @Pattern(regexp = "^[A-Z]{3}$") String devise, - Integer maxMembres, - Integer maxAdministrateurs, - @DecimalMin(value = "0.1", message = "L'espace de stockage doit être d'au moins 0.1 GB") BigDecimal espaceStockageGB, - Boolean supportTechnique, - @Pattern(regexp = "^(EMAIL|CHAT|TELEPHONE|PREMIUM)$", message = "Le niveau de support doit être EMAIL, CHAT, TELEPHONE ou PREMIUM") String niveauSupport, - Boolean fonctionnalitesAvancees, - Boolean apiAccess, - Boolean rapportsPersonnalises, - Boolean integrationsTierces, - Boolean sauvegardeAutomatique, - Boolean multiLangues, - Boolean personnalisationInterface, - Boolean formationIncluse, - Integer heuresFormation, - Boolean populaire, - Boolean recommandee, - Integer periodeEssaiJours, - LocalDate dateDebutValidite, - LocalDate dateFinValidite, - Integer ordreAffichage, - @Pattern(regexp = "^#[0-9A-Fa-f]{6}$", message = "La couleur doit être un code hexadécimal valide") String couleur, - @Size(max = 50, message = "Le nom de l'icône ne peut pas dépasser 50 caractères") String icone, - @Size(max = 500, message = "Les notes ne peuvent pas dépasser 500 caractères") String notes) { -} +package dev.lions.unionflow.server.api.dto.formuleabonnement.request; + +import dev.lions.unionflow.server.api.enums.formuleabonnement.StatutFormule; +import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.Pattern; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; +import lombok.Builder; + +/** + * Requête de mise à jour d'une formule d'abonnement. + */ +@Builder +public record UpdateFormuleAbonnementRequest( + @Size(min = 2, max = 100, message = "Le nom de la formule doit contenir entre 2 et 100 caractères") String nom, + @Pattern(regexp = "^[A-Z_]{2,20}$", message = "Le code doit contenir uniquement des lettres majuscules et underscores") String code, + @Size(max = 1000, message = "La description ne peut pas dépasser 1000 caractères") String description, + TypeFormule type, + StatutFormule statut, + @DecimalMin(value = "0.0", inclusive = false, message = "Le prix mensuel doit être positif") @Digits(integer = 10, fraction = 2) BigDecimal prixMensuel, + @DecimalMin(value = "0.0", inclusive = false, message = "Le prix annuel doit être positif") @Digits(integer = 10, fraction = 2) BigDecimal prixAnnuel, + @Pattern(regexp = "^[A-Z]{3}$") String devise, + Integer maxMembres, + Integer maxAdministrateurs, + @DecimalMin(value = "0.1", message = "L'espace de stockage doit être d'au moins 0.1 GB") BigDecimal espaceStockageGB, + Boolean supportTechnique, + @Pattern(regexp = "^(EMAIL|CHAT|TELEPHONE|PREMIUM)$", message = "Le niveau de support doit être EMAIL, CHAT, TELEPHONE ou PREMIUM") String niveauSupport, + Boolean fonctionnalitesAvancees, + Boolean apiAccess, + Boolean rapportsPersonnalises, + Boolean integrationsTierces, + Boolean sauvegardeAutomatique, + Boolean multiLangues, + Boolean personnalisationInterface, + Boolean formationIncluse, + Integer heuresFormation, + Boolean populaire, + Boolean recommandee, + Integer periodeEssaiJours, + LocalDate dateDebutValidite, + LocalDate dateFinValidite, + Integer ordreAffichage, + @Pattern(regexp = "^#[0-9A-Fa-f]{6}$", message = "La couleur doit être un code hexadécimal valide") String couleur, + @Size(max = 50, message = "Le nom de l'icône ne peut pas dépasser 50 caractères") String icone, + @Size(max = 500, message = "Les notes ne peuvent pas dépasser 500 caractères") String notes) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/formuleabonnement/response/FormuleAbonnementResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/formuleabonnement/response/FormuleAbonnementResponse.java index 8fc05a9..bb8ce7d 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/formuleabonnement/response/FormuleAbonnementResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/formuleabonnement/response/FormuleAbonnementResponse.java @@ -1,161 +1,161 @@ -package dev.lions.unionflow.server.api.dto.formuleabonnement.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import dev.lions.unionflow.server.api.enums.formuleabonnement.StatutFormule; -import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; -import java.math.BigDecimal; -import java.time.LocalDate; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée pour une formule d'abonnement. - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class FormuleAbonnementResponse extends BaseResponse { - - private String nom; - private String code; - private String description; - private TypeFormule type; - private StatutFormule statut; - private BigDecimal prixMensuel; - private BigDecimal prixAnnuel; - @Builder.Default - private String devise = "XOF"; - private Integer maxMembres; - private Integer maxAdministrateurs; - private BigDecimal espaceStockageGB; - private Boolean supportTechnique; - private String niveauSupport; - private Boolean fonctionnalitesAvancees; - private Boolean apiAccess; - private Boolean rapportsPersonnalises; - private Boolean integrationsTierces; - private Boolean sauvegardeAutomatique; - private Boolean multiLangues; - private Boolean personnalisationInterface; - private Boolean formationIncluse; - private Integer heuresFormation; - private Boolean populaire; - private Boolean recommandee; - private Integer periodeEssaiJours; - private LocalDate dateDebutValidite; - private LocalDate dateFinValidite; - private Integer ordreAffichage; - private String couleur; - private String icone; - private String notes; - - public boolean isActive() { - return StatutFormule.ACTIVE.equals(statut); - } - - public boolean isInactive() { - return StatutFormule.INACTIVE.equals(statut); - } - - public boolean isArchivee() { - return StatutFormule.ARCHIVEE.equals(statut); - } - - public boolean isValide() { - if (!isActive()) - return false; - - LocalDate aujourd = LocalDate.now(); - if (dateDebutValidite != null && aujourd.isBefore(dateDebutValidite)) - return false; - if (dateFinValidite != null && aujourd.isAfter(dateFinValidite)) - return false; - return true; - } - - public BigDecimal getEconomieAnnuelle() { - if (prixMensuel == null || prixAnnuel == null) - return BigDecimal.ZERO; - BigDecimal coutMensuelAnnuel = prixMensuel.multiply(BigDecimal.valueOf(12)); - return coutMensuelAnnuel.subtract(prixAnnuel); - } - - public int getPourcentageEconomieAnnuelle() { - if (prixMensuel == null || prixAnnuel == null) - return 0; - BigDecimal coutMensuelAnnuel = prixMensuel.multiply(BigDecimal.valueOf(12)); - if (coutMensuelAnnuel.compareTo(BigDecimal.ZERO) > 0) { - return getEconomieAnnuelle() - .multiply(BigDecimal.valueOf(100)) - .divide(coutMensuelAnnuel, 0, java.math.RoundingMode.HALF_UP) - .intValue(); - } - return 0; - } - - public boolean hasPeriodeEssai() { - return periodeEssaiJours != null && periodeEssaiJours > 0; - } - - public boolean hasFormation() { - return Boolean.TRUE.equals(formationIncluse) && heuresFormation != null && heuresFormation > 0; - } - - public boolean isMiseEnAvant() { - return Boolean.TRUE.equals(populaire) || Boolean.TRUE.equals(recommandee); - } - - public String getBadge() { - if (Boolean.TRUE.equals(populaire)) - return "POPULAIRE"; - if (Boolean.TRUE.equals(recommandee)) - return "RECOMMANDÉE"; - if (hasPeriodeEssai()) - return "ESSAI GRATUIT"; - return null; - } - - public int getScoreFonctionnalites() { - if (supportTechnique == null && sauvegardeAutomatique == null && fonctionnalitesAvancees == null - && apiAccess == null && rapportsPersonnalises == null && integrationsTierces == null - && multiLangues == null && personnalisationInterface == null) { - return 0; - } - int score = 0; - int total = 0; - if (Boolean.TRUE.equals(supportTechnique)) score += 10; - total += 10; - if (Boolean.TRUE.equals(sauvegardeAutomatique)) score += 10; - total += 10; - if (Boolean.TRUE.equals(fonctionnalitesAvancees)) score += 15; - total += 15; - if (Boolean.TRUE.equals(apiAccess)) score += 15; - total += 15; - if (Boolean.TRUE.equals(rapportsPersonnalises)) score += 15; - total += 15; - if (Boolean.TRUE.equals(integrationsTierces)) score += 15; - total += 15; - if (Boolean.TRUE.equals(multiLangues)) score += 10; - total += 10; - if (Boolean.TRUE.equals(personnalisationInterface)) score += 10; - total += 10; - return (score * 100) / total; - } - - public String getCssClass() { - if (type == null) - return "formule-default"; - return switch (type) { - case BASIC -> "formule-basic"; - case STANDARD -> "formule-standard"; - case PREMIUM -> "formule-premium"; - case ENTERPRISE -> "formule-enterprise"; - }; - } -} +package dev.lions.unionflow.server.api.dto.formuleabonnement.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import dev.lions.unionflow.server.api.enums.formuleabonnement.StatutFormule; +import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; +import java.math.BigDecimal; +import java.time.LocalDate; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée pour une formule d'abonnement. + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class FormuleAbonnementResponse extends BaseResponse { + + private String nom; + private String code; + private String description; + private TypeFormule type; + private StatutFormule statut; + private BigDecimal prixMensuel; + private BigDecimal prixAnnuel; + @Builder.Default + private String devise = "XOF"; + private Integer maxMembres; + private Integer maxAdministrateurs; + private BigDecimal espaceStockageGB; + private Boolean supportTechnique; + private String niveauSupport; + private Boolean fonctionnalitesAvancees; + private Boolean apiAccess; + private Boolean rapportsPersonnalises; + private Boolean integrationsTierces; + private Boolean sauvegardeAutomatique; + private Boolean multiLangues; + private Boolean personnalisationInterface; + private Boolean formationIncluse; + private Integer heuresFormation; + private Boolean populaire; + private Boolean recommandee; + private Integer periodeEssaiJours; + private LocalDate dateDebutValidite; + private LocalDate dateFinValidite; + private Integer ordreAffichage; + private String couleur; + private String icone; + private String notes; + + public boolean isActive() { + return StatutFormule.ACTIVE.equals(statut); + } + + public boolean isInactive() { + return StatutFormule.INACTIVE.equals(statut); + } + + public boolean isArchivee() { + return StatutFormule.ARCHIVEE.equals(statut); + } + + public boolean isValide() { + if (!isActive()) + return false; + + LocalDate aujourd = LocalDate.now(); + if (dateDebutValidite != null && aujourd.isBefore(dateDebutValidite)) + return false; + if (dateFinValidite != null && aujourd.isAfter(dateFinValidite)) + return false; + return true; + } + + public BigDecimal getEconomieAnnuelle() { + if (prixMensuel == null || prixAnnuel == null) + return BigDecimal.ZERO; + BigDecimal coutMensuelAnnuel = prixMensuel.multiply(BigDecimal.valueOf(12)); + return coutMensuelAnnuel.subtract(prixAnnuel); + } + + public int getPourcentageEconomieAnnuelle() { + if (prixMensuel == null || prixAnnuel == null) + return 0; + BigDecimal coutMensuelAnnuel = prixMensuel.multiply(BigDecimal.valueOf(12)); + if (coutMensuelAnnuel.compareTo(BigDecimal.ZERO) > 0) { + return getEconomieAnnuelle() + .multiply(BigDecimal.valueOf(100)) + .divide(coutMensuelAnnuel, 0, java.math.RoundingMode.HALF_UP) + .intValue(); + } + return 0; + } + + public boolean hasPeriodeEssai() { + return periodeEssaiJours != null && periodeEssaiJours > 0; + } + + public boolean hasFormation() { + return Boolean.TRUE.equals(formationIncluse) && heuresFormation != null && heuresFormation > 0; + } + + public boolean isMiseEnAvant() { + return Boolean.TRUE.equals(populaire) || Boolean.TRUE.equals(recommandee); + } + + public String getBadge() { + if (Boolean.TRUE.equals(populaire)) + return "POPULAIRE"; + if (Boolean.TRUE.equals(recommandee)) + return "RECOMMANDÉE"; + if (hasPeriodeEssai()) + return "ESSAI GRATUIT"; + return null; + } + + public int getScoreFonctionnalites() { + if (supportTechnique == null && sauvegardeAutomatique == null && fonctionnalitesAvancees == null + && apiAccess == null && rapportsPersonnalises == null && integrationsTierces == null + && multiLangues == null && personnalisationInterface == null) { + return 0; + } + int score = 0; + int total = 0; + if (Boolean.TRUE.equals(supportTechnique)) score += 10; + total += 10; + if (Boolean.TRUE.equals(sauvegardeAutomatique)) score += 10; + total += 10; + if (Boolean.TRUE.equals(fonctionnalitesAvancees)) score += 15; + total += 15; + if (Boolean.TRUE.equals(apiAccess)) score += 15; + total += 15; + if (Boolean.TRUE.equals(rapportsPersonnalises)) score += 15; + total += 15; + if (Boolean.TRUE.equals(integrationsTierces)) score += 15; + total += 15; + if (Boolean.TRUE.equals(multiLangues)) score += 10; + total += 10; + if (Boolean.TRUE.equals(personnalisationInterface)) score += 10; + total += 10; + return (score * 100) / total; + } + + public String getCssClass() { + if (type == null) + return "formule-default"; + return switch (type) { + case BASIC -> "formule-basic"; + case STANDARD -> "formule-standard"; + case PREMIUM -> "formule-premium"; + case ENTERPRISE -> "formule-enterprise"; + }; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/gouvernance/EchelonOrganigrammeDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/gouvernance/EchelonOrganigrammeDTO.java index f33a349..14c0ce1 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/gouvernance/EchelonOrganigrammeDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/gouvernance/EchelonOrganigrammeDTO.java @@ -1,29 +1,29 @@ -package dev.lions.unionflow.server.api.dto.gouvernance; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.gouvernance.NiveauEchelon; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class EchelonOrganigrammeDTO extends BaseDTO { - - // L'Id physique de l'organisation dans le système (une organisation == un - // échelon) - private String organisationId; - - // L'organisation mère / chapeau de cet échelon - private String echelonParentId; - - private NiveauEchelon niveau; - - private String designation; - private String zoneGeographiqueOuDelegation; -} +package dev.lions.unionflow.server.api.dto.gouvernance; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.gouvernance.NiveauEchelon; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class EchelonOrganigrammeDTO extends BaseDTO { + + // L'Id physique de l'organisation dans le système (une organisation == un + // échelon) + private String organisationId; + + // L'organisation mère / chapeau de cet échelon + private String echelonParentId; + + private NiveauEchelon niveau; + + private String designation; + private String zoneGeographiqueOuDelegation; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/lcbft/AlerteLcbFtResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/lcbft/AlerteLcbFtResponse.java index bea07e0..9147320 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/lcbft/AlerteLcbFtResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/lcbft/AlerteLcbFtResponse.java @@ -1,42 +1,42 @@ -package dev.lions.unionflow.server.api.dto.lcbft; - -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.math.BigDecimal; -import java.time.LocalDateTime; - -/** - * DTO de réponse pour une alerte LCB-FT. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-15 - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class AlerteLcbFtResponse { - - private String id; - private String organisationId; - private String organisationNom; - private String membreId; - private String membreNomComplet; - private String typeAlerte; - private LocalDateTime dateAlerte; - private String description; - private String details; - private BigDecimal montant; - private BigDecimal seuil; - private String typeOperation; - private String transactionRef; - private String severite; - private Boolean traitee; - private LocalDateTime dateTraitement; - private String traitePar; - private String commentaireTraitement; -} +package dev.lions.unionflow.server.api.dto.lcbft; + +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.math.BigDecimal; +import java.time.LocalDateTime; + +/** + * DTO de réponse pour une alerte LCB-FT. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-15 + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class AlerteLcbFtResponse { + + private String id; + private String organisationId; + private String organisationNom; + private String membreId; + private String membreNomComplet; + private String typeAlerte; + private LocalDateTime dateAlerte; + private String description; + private String details; + private BigDecimal montant; + private BigDecimal seuil; + private String typeOperation; + private String transactionRef; + private String severite; + private Boolean traitee; + private LocalDateTime dateTraitement; + private String traitePar; + private String commentaireTraitement; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchCriteria.java b/src/main/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchCriteria.java index b6dfd4e..5ac4613 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchCriteria.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchCriteria.java @@ -1,226 +1,226 @@ -package dev.lions.unionflow.server.api.dto.membre; - -import com.fasterxml.jackson.annotation.JsonFormat; -import jakarta.validation.constraints.Max; -import jakarta.validation.constraints.Min; -import jakarta.validation.constraints.Pattern; -import jakarta.validation.constraints.Size; -import java.time.LocalDate; -import java.util.List; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -/** - * DTO pour les critères de recherche avancée des membres Permet de filtrer les membres selon de - * multiples critères - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-19 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Critères de recherche avancée pour les membres") -public class MembreSearchCriteria { - - /** Terme de recherche général (nom, prénom, email) */ - @Schema(description = "Terme de recherche général dans nom, prénom ou email", example = "marie") - @Size(max = 100, message = "Le terme de recherche ne peut pas dépasser 100 caractères") - private String query; - - /** Recherche par nom exact ou partiel */ - @Schema(description = "Filtre par nom (recherche partielle)", example = "Dupont") - @Size(max = 50, message = "Le nom ne peut pas dépasser 50 caractères") - private String nom; - - /** Recherche par prénom exact ou partiel */ - @Schema(description = "Filtre par prénom (recherche partielle)", example = "Marie") - @Size(max = 50, message = "Le prénom ne peut pas dépasser 50 caractères") - private String prenom; - - /** Recherche par email exact ou partiel */ - @Schema(description = "Filtre par email (recherche partielle)", example = "@unionflow.com") - @Size(max = 100, message = "L'email ne peut pas dépasser 100 caractères") - private String email; - - /** Filtre par numéro de téléphone */ - @Schema(description = "Filtre par numéro de téléphone", example = "+221") - @Size(max = 20, message = "Le téléphone ne peut pas dépasser 20 caractères") - private String telephone; - - /** Liste des IDs d'organisations */ - @Schema(description = "Liste des IDs d'organisations à inclure") - private List organisationIds; - - /** Liste des rôles à rechercher */ - @Schema(description = "Liste des rôles à rechercher", example = "[\"PRESIDENT\", \"SECRETAIRE\"]") - private List roles; - - /** Filtre par statut d'activité */ - @Schema(description = "Filtre par statut d'activité", example = "ACTIF") - @Pattern(regexp = "^(ACTIF|INACTIF|SUSPENDU|RADIE)$", message = "Statut invalide") - private String statut; - - /** Date d'adhésion minimum */ - @Schema(description = "Date d'adhésion minimum", example = "2020-01-01") - @JsonFormat(pattern = "yyyy-MM-dd") - private LocalDate dateAdhesionMin; - - /** Date d'adhésion maximum */ - @Schema(description = "Date d'adhésion maximum", example = "2025-12-31") - @JsonFormat(pattern = "yyyy-MM-dd") - private LocalDate dateAdhesionMax; - - /** Âge minimum */ - @Schema(description = "Âge minimum", example = "18") - @Min(value = 0, message = "L'âge minimum doit être positif") - @Max(value = 120, message = "L'âge minimum ne peut pas dépasser 120 ans") - private Integer ageMin; - - /** Âge maximum */ - @Schema(description = "Âge maximum", example = "65") - @Min(value = 0, message = "L'âge maximum doit être positif") - @Max(value = 120, message = "L'âge maximum ne peut pas dépasser 120 ans") - private Integer ageMax; - - /** Filtre par région */ - @Schema(description = "Filtre par région", example = "Dakar") - @Size(max = 50, message = "La région ne peut pas dépasser 50 caractères") - private String region; - - /** Filtre par ville */ - @Schema(description = "Filtre par ville", example = "Dakar") - @Size(max = 50, message = "La ville ne peut pas dépasser 50 caractères") - private String ville; - - /** Filtre par profession */ - @Schema(description = "Filtre par profession", example = "Ingénieur") - @Size(max = 100, message = "La profession ne peut pas dépasser 100 caractères") - private String profession; - - /** Filtre par nationalité */ - @Schema(description = "Filtre par nationalité", example = "Sénégalaise") - @Size(max = 50, message = "La nationalité ne peut pas dépasser 50 caractères") - private String nationalite; - - /** Filtre membres du bureau uniquement */ - @Schema(description = "Filtre pour les membres du bureau uniquement") - private Boolean membreBureau; - - /** Filtre responsables uniquement */ - @Schema(description = "Filtre pour les responsables uniquement") - private Boolean responsable; - - /** Inclure les membres inactifs dans la recherche */ - @Schema(description = "Inclure les membres inactifs", defaultValue = "false") - @Builder.Default - private Boolean includeInactifs = false; - - /** - * Vérifie si au moins un critère de recherche est défini - * - * @return true si au moins un critère est défini - */ - public boolean hasAnyCriteria() { - return query != null && !query.trim().isEmpty() - || nom != null && !nom.trim().isEmpty() - || prenom != null && !prenom.trim().isEmpty() - || email != null && !email.trim().isEmpty() - || telephone != null && !telephone.trim().isEmpty() - || organisationIds != null && !organisationIds.isEmpty() - || roles != null && !roles.isEmpty() - || statut != null && !statut.trim().isEmpty() - || dateAdhesionMin != null - || dateAdhesionMax != null - || ageMin != null - || ageMax != null - || region != null && !region.trim().isEmpty() - || ville != null && !ville.trim().isEmpty() - || profession != null && !profession.trim().isEmpty() - || nationalite != null && !nationalite.trim().isEmpty() - || membreBureau != null - || responsable != null; - } - - /** - * Valide la cohérence des critères de recherche - * - * @return true si les critères sont cohérents - */ - public boolean isValid() { - // Validation des dates - if (dateAdhesionMin != null && dateAdhesionMax != null) { - if (dateAdhesionMin.isAfter(dateAdhesionMax)) { - return false; - } - } - - // Validation des âges - if (ageMin != null && ageMax != null) { - if (ageMin > ageMax) { - return false; - } - } - - return true; - } - - /** Nettoie les chaînes de caractères (trim et null si vide) */ - public void sanitize() { - query = sanitizeString(query); - nom = sanitizeString(nom); - prenom = sanitizeString(prenom); - email = sanitizeString(email); - telephone = sanitizeString(telephone); - statut = sanitizeString(statut); - region = sanitizeString(region); - ville = sanitizeString(ville); - profession = sanitizeString(profession); - nationalite = sanitizeString(nationalite); - } - - private String sanitizeString(String str) { - if (str == null) return null; - str = str.trim(); - return str.isEmpty() ? null : str; - } - - /** - * Retourne une description textuelle des critères actifs - * - * @return Description des critères - */ - public String getDescription() { - StringBuilder sb = new StringBuilder(); - - if (query != null) sb.append("Recherche: '").append(query).append("' "); - if (nom != null) sb.append("Nom: '").append(nom).append("' "); - if (prenom != null) sb.append("Prénom: '").append(prenom).append("' "); - if (email != null) sb.append("Email: '").append(email).append("' "); - if (statut != null) sb.append("Statut: ").append(statut).append(" "); - if (organisationIds != null && !organisationIds.isEmpty()) { - sb.append("Organisations: ").append(organisationIds.size()).append(" "); - } - if (roles != null && !roles.isEmpty()) { - sb.append("Rôles: ").append(String.join(", ", roles)).append(" "); - } - if (dateAdhesionMin != null) sb.append("Adhésion >= ").append(dateAdhesionMin).append(" "); - if (dateAdhesionMax != null) sb.append("Adhésion <= ").append(dateAdhesionMax).append(" "); - if (ageMin != null) sb.append("Âge >= ").append(ageMin).append(" "); - if (ageMax != null) sb.append("Âge <= ").append(ageMax).append(" "); - if (region != null) sb.append("Région: '").append(region).append("' "); - if (ville != null) sb.append("Ville: '").append(ville).append("' "); - if (profession != null) sb.append("Profession: '").append(profession).append("' "); - if (nationalite != null) sb.append("Nationalité: '").append(nationalite).append("' "); - if (Boolean.TRUE.equals(membreBureau)) sb.append("Membre bureau "); - if (Boolean.TRUE.equals(responsable)) sb.append("Responsable "); - - return sb.toString().trim(); - } -} +package dev.lions.unionflow.server.api.dto.membre; + +import com.fasterxml.jackson.annotation.JsonFormat; +import jakarta.validation.constraints.Max; +import jakarta.validation.constraints.Min; +import jakarta.validation.constraints.Pattern; +import jakarta.validation.constraints.Size; +import java.time.LocalDate; +import java.util.List; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +/** + * DTO pour les critères de recherche avancée des membres Permet de filtrer les membres selon de + * multiples critères + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-19 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Critères de recherche avancée pour les membres") +public class MembreSearchCriteria { + + /** Terme de recherche général (nom, prénom, email) */ + @Schema(description = "Terme de recherche général dans nom, prénom ou email", example = "marie") + @Size(max = 100, message = "Le terme de recherche ne peut pas dépasser 100 caractères") + private String query; + + /** Recherche par nom exact ou partiel */ + @Schema(description = "Filtre par nom (recherche partielle)", example = "Dupont") + @Size(max = 50, message = "Le nom ne peut pas dépasser 50 caractères") + private String nom; + + /** Recherche par prénom exact ou partiel */ + @Schema(description = "Filtre par prénom (recherche partielle)", example = "Marie") + @Size(max = 50, message = "Le prénom ne peut pas dépasser 50 caractères") + private String prenom; + + /** Recherche par email exact ou partiel */ + @Schema(description = "Filtre par email (recherche partielle)", example = "@unionflow.com") + @Size(max = 100, message = "L'email ne peut pas dépasser 100 caractères") + private String email; + + /** Filtre par numéro de téléphone */ + @Schema(description = "Filtre par numéro de téléphone", example = "+221") + @Size(max = 20, message = "Le téléphone ne peut pas dépasser 20 caractères") + private String telephone; + + /** Liste des IDs d'organisations */ + @Schema(description = "Liste des IDs d'organisations à inclure") + private List organisationIds; + + /** Liste des rôles à rechercher */ + @Schema(description = "Liste des rôles à rechercher", example = "[\"PRESIDENT\", \"SECRETAIRE\"]") + private List roles; + + /** Filtre par statut d'activité */ + @Schema(description = "Filtre par statut d'activité", example = "ACTIF") + @Pattern(regexp = "^(ACTIF|INACTIF|SUSPENDU|RADIE)$", message = "Statut invalide") + private String statut; + + /** Date d'adhésion minimum */ + @Schema(description = "Date d'adhésion minimum", example = "2020-01-01") + @JsonFormat(pattern = "yyyy-MM-dd") + private LocalDate dateAdhesionMin; + + /** Date d'adhésion maximum */ + @Schema(description = "Date d'adhésion maximum", example = "2025-12-31") + @JsonFormat(pattern = "yyyy-MM-dd") + private LocalDate dateAdhesionMax; + + /** Âge minimum */ + @Schema(description = "Âge minimum", example = "18") + @Min(value = 0, message = "L'âge minimum doit être positif") + @Max(value = 120, message = "L'âge minimum ne peut pas dépasser 120 ans") + private Integer ageMin; + + /** Âge maximum */ + @Schema(description = "Âge maximum", example = "65") + @Min(value = 0, message = "L'âge maximum doit être positif") + @Max(value = 120, message = "L'âge maximum ne peut pas dépasser 120 ans") + private Integer ageMax; + + /** Filtre par région */ + @Schema(description = "Filtre par région", example = "Dakar") + @Size(max = 50, message = "La région ne peut pas dépasser 50 caractères") + private String region; + + /** Filtre par ville */ + @Schema(description = "Filtre par ville", example = "Dakar") + @Size(max = 50, message = "La ville ne peut pas dépasser 50 caractères") + private String ville; + + /** Filtre par profession */ + @Schema(description = "Filtre par profession", example = "Ingénieur") + @Size(max = 100, message = "La profession ne peut pas dépasser 100 caractères") + private String profession; + + /** Filtre par nationalité */ + @Schema(description = "Filtre par nationalité", example = "Sénégalaise") + @Size(max = 50, message = "La nationalité ne peut pas dépasser 50 caractères") + private String nationalite; + + /** Filtre membres du bureau uniquement */ + @Schema(description = "Filtre pour les membres du bureau uniquement") + private Boolean membreBureau; + + /** Filtre responsables uniquement */ + @Schema(description = "Filtre pour les responsables uniquement") + private Boolean responsable; + + /** Inclure les membres inactifs dans la recherche */ + @Schema(description = "Inclure les membres inactifs", defaultValue = "false") + @Builder.Default + private Boolean includeInactifs = false; + + /** + * Vérifie si au moins un critère de recherche est défini + * + * @return true si au moins un critère est défini + */ + public boolean hasAnyCriteria() { + return query != null && !query.trim().isEmpty() + || nom != null && !nom.trim().isEmpty() + || prenom != null && !prenom.trim().isEmpty() + || email != null && !email.trim().isEmpty() + || telephone != null && !telephone.trim().isEmpty() + || organisationIds != null && !organisationIds.isEmpty() + || roles != null && !roles.isEmpty() + || statut != null && !statut.trim().isEmpty() + || dateAdhesionMin != null + || dateAdhesionMax != null + || ageMin != null + || ageMax != null + || region != null && !region.trim().isEmpty() + || ville != null && !ville.trim().isEmpty() + || profession != null && !profession.trim().isEmpty() + || nationalite != null && !nationalite.trim().isEmpty() + || membreBureau != null + || responsable != null; + } + + /** + * Valide la cohérence des critères de recherche + * + * @return true si les critères sont cohérents + */ + public boolean isValid() { + // Validation des dates + if (dateAdhesionMin != null && dateAdhesionMax != null) { + if (dateAdhesionMin.isAfter(dateAdhesionMax)) { + return false; + } + } + + // Validation des âges + if (ageMin != null && ageMax != null) { + if (ageMin > ageMax) { + return false; + } + } + + return true; + } + + /** Nettoie les chaînes de caractères (trim et null si vide) */ + public void sanitize() { + query = sanitizeString(query); + nom = sanitizeString(nom); + prenom = sanitizeString(prenom); + email = sanitizeString(email); + telephone = sanitizeString(telephone); + statut = sanitizeString(statut); + region = sanitizeString(region); + ville = sanitizeString(ville); + profession = sanitizeString(profession); + nationalite = sanitizeString(nationalite); + } + + private String sanitizeString(String str) { + if (str == null) return null; + str = str.trim(); + return str.isEmpty() ? null : str; + } + + /** + * Retourne une description textuelle des critères actifs + * + * @return Description des critères + */ + public String getDescription() { + StringBuilder sb = new StringBuilder(); + + if (query != null) sb.append("Recherche: '").append(query).append("' "); + if (nom != null) sb.append("Nom: '").append(nom).append("' "); + if (prenom != null) sb.append("Prénom: '").append(prenom).append("' "); + if (email != null) sb.append("Email: '").append(email).append("' "); + if (statut != null) sb.append("Statut: ").append(statut).append(" "); + if (organisationIds != null && !organisationIds.isEmpty()) { + sb.append("Organisations: ").append(organisationIds.size()).append(" "); + } + if (roles != null && !roles.isEmpty()) { + sb.append("Rôles: ").append(String.join(", ", roles)).append(" "); + } + if (dateAdhesionMin != null) sb.append("Adhésion >= ").append(dateAdhesionMin).append(" "); + if (dateAdhesionMax != null) sb.append("Adhésion <= ").append(dateAdhesionMax).append(" "); + if (ageMin != null) sb.append("Âge >= ").append(ageMin).append(" "); + if (ageMax != null) sb.append("Âge <= ").append(ageMax).append(" "); + if (region != null) sb.append("Région: '").append(region).append("' "); + if (ville != null) sb.append("Ville: '").append(ville).append("' "); + if (profession != null) sb.append("Profession: '").append(profession).append("' "); + if (nationalite != null) sb.append("Nationalité: '").append(nationalite).append("' "); + if (Boolean.TRUE.equals(membreBureau)) sb.append("Membre bureau "); + if (Boolean.TRUE.equals(responsable)) sb.append("Responsable "); + + return sb.toString().trim(); + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchResultDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchResultDTO.java index 14b9ecf..f5219bf 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchResultDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchResultDTO.java @@ -1,227 +1,227 @@ -package dev.lions.unionflow.server.api.dto.membre; - -import com.fasterxml.jackson.annotation.JsonProperty; -import dev.lions.unionflow.server.api.dto.membre.response.MembreSummaryResponse; -import java.util.List; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -/** - * DTO pour les résultats de recherche avancée des membres Contient les - * résultats paginés et les - * métadonnées de recherche - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-19 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Résultats de recherche avancée des membres avec pagination") -public class MembreSearchResultDTO { - - /** Liste des membres trouvés */ - @Schema(description = "Liste des membres correspondant aux critères") - private List membres; - - /** Nombre total de résultats (toutes pages confondues) */ - @Schema(description = "Nombre total de résultats trouvés", example = "247") - private long totalElements; - - /** Nombre total de pages */ - @Schema(description = "Nombre total de pages", example = "13") - private int totalPages; - - /** Numéro de la page actuelle (0-based) */ - @Schema(description = "Numéro de la page actuelle", example = "0") - private int currentPage; - - /** Taille de la page */ - @Schema(description = "Nombre d'éléments par page", example = "20") - private int pageSize; - - /** Nombre d'éléments sur la page actuelle */ - @Schema(description = "Nombre d'éléments sur cette page", example = "20") - private int numberOfElements; - - /** Indique s'il y a une page suivante */ - @Schema(description = "Indique s'il y a une page suivante") - private boolean hasNext; - - /** Indique s'il y a une page précédente */ - @Schema(description = "Indique s'il y a une page précédente") - private boolean hasPrevious; - - /** Indique si c'est la première page */ - @Schema(description = "Indique si c'est la première page") - @JsonProperty("isFirst") - private boolean isFirst; - - /** Indique si c'est la dernière page */ - @Schema(description = "Indique si c'est la dernière page") - @JsonProperty("isLast") - private boolean isLast; - - /** Critères de recherche utilisés */ - @Schema(description = "Critères de recherche qui ont été appliqués") - private MembreSearchCriteria criteria; - - /** Temps d'exécution de la recherche en millisecondes */ - @Schema(description = "Temps d'exécution de la recherche en ms", example = "45") - private long executionTimeMs; - - /** Statistiques de recherche */ - @Schema(description = "Statistiques sur les résultats de recherche") - private SearchStatistics statistics; - - /** Statistiques sur les résultats de recherche */ - @Data - @NoArgsConstructor - @AllArgsConstructor - @Builder - @Schema(description = "Statistiques sur les résultats de recherche") - public static class SearchStatistics { - - /** Répartition par statut */ - @Schema(description = "Nombre de membres actifs dans les résultats") - private long membresActifs; - - @Schema(description = "Nombre de membres inactifs dans les résultats") - private long membresInactifs; - - /** Répartition par âge */ - @Schema(description = "Âge moyen des membres trouvés") - private double ageMoyen; - - @Schema(description = "Âge minimum des membres trouvés") - private int ageMin; - - @Schema(description = "Âge maximum des membres trouvés") - private int ageMax; - - /** Répartition par organisation */ - @Schema(description = "Nombre d'organisations représentées") - private long nombreOrganisations; - - /** Répartition par région */ - @Schema(description = "Nombre de régions représentées") - private long nombreRegions; - - /** Ancienneté moyenne */ - @Schema(description = "Ancienneté moyenne en années") - private double ancienneteMoyenne; - } - - /** Calcule et met à jour les indicateurs de pagination */ - public void calculatePaginationFlags() { - this.isFirst = currentPage == 0; - this.isLast = currentPage >= totalPages - 1; - this.hasPrevious = currentPage > 0; - this.hasNext = currentPage < totalPages - 1; - this.numberOfElements = membres != null ? membres.size() : 0; - } - - /** - * Vérifie si les résultats sont vides - * - * @return true si aucun résultat - */ - public boolean isEmpty() { - return membres == null || membres.isEmpty(); - } - - /** - * Retourne le numéro de la page suivante (1-based pour affichage) - * - * @return Numéro de page suivante ou -1 si pas de page suivante - */ - public int getNextPageNumber() { - return hasNext ? currentPage + 2 : -1; - } - - /** - * Retourne le numéro de la page précédente (1-based pour affichage) - * - * @return Numéro de page précédente ou -1 si pas de page précédente - */ - public int getPreviousPageNumber() { - return hasPrevious ? currentPage : -1; - } - - /** - * Retourne une description textuelle des résultats - * - * @return Description des résultats - */ - public String getResultDescription() { - if (isEmpty()) { - return "Aucun membre trouvé"; - } - - if (totalElements == 1) { - return "1 membre trouvé"; - } - - if (totalPages == 1) { - return String.format("%d membres trouvés", totalElements); - } - - int startElement = currentPage * pageSize + 1; - int endElement = Math.min(startElement + numberOfElements - 1, (int) totalElements); - - return String.format( - "Membres %d-%d sur %d (page %d/%d)", - startElement, endElement, totalElements, currentPage + 1, totalPages); - } - - /** - * Factory method pour créer un résultat vide - * - * @param criteria Critères de recherche - * @return Résultat vide - */ - public static MembreSearchResultDTO empty(MembreSearchCriteria criteria) { - return empty(criteria, 20, 0); - } - - /** - * Factory method pour créer un résultat vide avec pageSize spécifique - * - * @param criteria Critères de recherche - * @param pageSize Taille de la page - * @param currentPage Page actuelle - * @return Résultat vide - */ - public static MembreSearchResultDTO empty(MembreSearchCriteria criteria, int pageSize, int currentPage) { - MembreSearchResultDTO result = new MembreSearchResultDTO(); - result.setMembres(List.of()); - result.setTotalElements(0L); - result.setTotalPages(0); - result.setCurrentPage(currentPage); - result.setPageSize(pageSize); - result.setNumberOfElements(0); - result.setHasNext(false); - result.setHasPrevious(false); - result.isFirst = true; // Assignation directe pour éviter les problèmes avec les setters Lombok - result.isLast = true; // Assignation directe pour éviter les problèmes avec les setters Lombok - result.setCriteria(criteria); - result.setExecutionTimeMs(0L); - // Initialiser statistics avec des valeurs vides - result.setStatistics(SearchStatistics.builder() - .membresActifs(0) - .membresInactifs(0) - .ageMoyen(0.0) - .ageMin(0) - .ageMax(0) - .nombreOrganisations(0) - .nombreRegions(0) - .ancienneteMoyenne(0.0) - .build()); - return result; - } -} +package dev.lions.unionflow.server.api.dto.membre; + +import com.fasterxml.jackson.annotation.JsonProperty; +import dev.lions.unionflow.server.api.dto.membre.response.MembreSummaryResponse; +import java.util.List; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +/** + * DTO pour les résultats de recherche avancée des membres Contient les + * résultats paginés et les + * métadonnées de recherche + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-19 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Résultats de recherche avancée des membres avec pagination") +public class MembreSearchResultDTO { + + /** Liste des membres trouvés */ + @Schema(description = "Liste des membres correspondant aux critères") + private List membres; + + /** Nombre total de résultats (toutes pages confondues) */ + @Schema(description = "Nombre total de résultats trouvés", example = "247") + private long totalElements; + + /** Nombre total de pages */ + @Schema(description = "Nombre total de pages", example = "13") + private int totalPages; + + /** Numéro de la page actuelle (0-based) */ + @Schema(description = "Numéro de la page actuelle", example = "0") + private int currentPage; + + /** Taille de la page */ + @Schema(description = "Nombre d'éléments par page", example = "20") + private int pageSize; + + /** Nombre d'éléments sur la page actuelle */ + @Schema(description = "Nombre d'éléments sur cette page", example = "20") + private int numberOfElements; + + /** Indique s'il y a une page suivante */ + @Schema(description = "Indique s'il y a une page suivante") + private boolean hasNext; + + /** Indique s'il y a une page précédente */ + @Schema(description = "Indique s'il y a une page précédente") + private boolean hasPrevious; + + /** Indique si c'est la première page */ + @Schema(description = "Indique si c'est la première page") + @JsonProperty("isFirst") + private boolean isFirst; + + /** Indique si c'est la dernière page */ + @Schema(description = "Indique si c'est la dernière page") + @JsonProperty("isLast") + private boolean isLast; + + /** Critères de recherche utilisés */ + @Schema(description = "Critères de recherche qui ont été appliqués") + private MembreSearchCriteria criteria; + + /** Temps d'exécution de la recherche en millisecondes */ + @Schema(description = "Temps d'exécution de la recherche en ms", example = "45") + private long executionTimeMs; + + /** Statistiques de recherche */ + @Schema(description = "Statistiques sur les résultats de recherche") + private SearchStatistics statistics; + + /** Statistiques sur les résultats de recherche */ + @Data + @NoArgsConstructor + @AllArgsConstructor + @Builder + @Schema(description = "Statistiques sur les résultats de recherche") + public static class SearchStatistics { + + /** Répartition par statut */ + @Schema(description = "Nombre de membres actifs dans les résultats") + private long membresActifs; + + @Schema(description = "Nombre de membres inactifs dans les résultats") + private long membresInactifs; + + /** Répartition par âge */ + @Schema(description = "Âge moyen des membres trouvés") + private double ageMoyen; + + @Schema(description = "Âge minimum des membres trouvés") + private int ageMin; + + @Schema(description = "Âge maximum des membres trouvés") + private int ageMax; + + /** Répartition par organisation */ + @Schema(description = "Nombre d'organisations représentées") + private long nombreOrganisations; + + /** Répartition par région */ + @Schema(description = "Nombre de régions représentées") + private long nombreRegions; + + /** Ancienneté moyenne */ + @Schema(description = "Ancienneté moyenne en années") + private double ancienneteMoyenne; + } + + /** Calcule et met à jour les indicateurs de pagination */ + public void calculatePaginationFlags() { + this.isFirst = currentPage == 0; + this.isLast = currentPage >= totalPages - 1; + this.hasPrevious = currentPage > 0; + this.hasNext = currentPage < totalPages - 1; + this.numberOfElements = membres != null ? membres.size() : 0; + } + + /** + * Vérifie si les résultats sont vides + * + * @return true si aucun résultat + */ + public boolean isEmpty() { + return membres == null || membres.isEmpty(); + } + + /** + * Retourne le numéro de la page suivante (1-based pour affichage) + * + * @return Numéro de page suivante ou -1 si pas de page suivante + */ + public int getNextPageNumber() { + return hasNext ? currentPage + 2 : -1; + } + + /** + * Retourne le numéro de la page précédente (1-based pour affichage) + * + * @return Numéro de page précédente ou -1 si pas de page précédente + */ + public int getPreviousPageNumber() { + return hasPrevious ? currentPage : -1; + } + + /** + * Retourne une description textuelle des résultats + * + * @return Description des résultats + */ + public String getResultDescription() { + if (isEmpty()) { + return "Aucun membre trouvé"; + } + + if (totalElements == 1) { + return "1 membre trouvé"; + } + + if (totalPages == 1) { + return String.format("%d membres trouvés", totalElements); + } + + int startElement = currentPage * pageSize + 1; + int endElement = Math.min(startElement + numberOfElements - 1, (int) totalElements); + + return String.format( + "Membres %d-%d sur %d (page %d/%d)", + startElement, endElement, totalElements, currentPage + 1, totalPages); + } + + /** + * Factory method pour créer un résultat vide + * + * @param criteria Critères de recherche + * @return Résultat vide + */ + public static MembreSearchResultDTO empty(MembreSearchCriteria criteria) { + return empty(criteria, 20, 0); + } + + /** + * Factory method pour créer un résultat vide avec pageSize spécifique + * + * @param criteria Critères de recherche + * @param pageSize Taille de la page + * @param currentPage Page actuelle + * @return Résultat vide + */ + public static MembreSearchResultDTO empty(MembreSearchCriteria criteria, int pageSize, int currentPage) { + MembreSearchResultDTO result = new MembreSearchResultDTO(); + result.setMembres(List.of()); + result.setTotalElements(0L); + result.setTotalPages(0); + result.setCurrentPage(currentPage); + result.setPageSize(pageSize); + result.setNumberOfElements(0); + result.setHasNext(false); + result.setHasPrevious(false); + result.isFirst = true; // Assignation directe pour éviter les problèmes avec les setters Lombok + result.isLast = true; // Assignation directe pour éviter les problèmes avec les setters Lombok + result.setCriteria(criteria); + result.setExecutionTimeMs(0L); + // Initialiser statistics avec des valeurs vides + result.setStatistics(SearchStatistics.builder() + .membresActifs(0) + .membresInactifs(0) + .ageMoyen(0.0) + .ageMin(0) + .ageMax(0) + .nombreOrganisations(0) + .nombreRegions(0) + .ancienneteMoyenne(0.0) + .build()); + return result; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/membre/request/CreateMembreRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/membre/request/CreateMembreRequest.java index 1a57671..b182062 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/membre/request/CreateMembreRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/membre/request/CreateMembreRequest.java @@ -1,52 +1,52 @@ -package dev.lions.unionflow.server.api.dto.membre.request; - -import jakarta.validation.constraints.Email; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import java.time.LocalDate; -import java.util.UUID; - -import lombok.Builder; - -/** - * Requête de création d'un membre. - * - *

- * Immutable via {@code record}. Exclut l'ID, - * les champs d'audit, et le numéroMembre - * (généré côté serveur). - * - * @author UnionFlow Team - * @version 3.0 - * @since 2026-02-21 - * @param prenom prénom - * @param nom nom de famille - * @param email email - * @param telephone téléphone - * @param telephoneWave numéro Wave - * @param dateNaissance date de naissance - * @param profession profession - * @param photoUrl URL de la photo - * @param statutMatrimonial statut matrimonial - * @param nationalite nationalité - * @param typeIdentite type pièce d'identité - * @param numeroIdentite numéro d'identité - * @param organisationId ID de l'organisation (obligatoire pour ADMIN_ORGANISATION) - */ -@Builder -public record CreateMembreRequest( - @NotBlank @Size(max = 100) String prenom, - @NotBlank @Size(max = 100) String nom, - @NotBlank @Email @Size(max = 255) String email, - @Size(max = 20) String telephone, - @Size(max = 20) String telephoneWave, - @NotNull LocalDate dateNaissance, - @Size(max = 100) String profession, - @Size(max = 500) String photoUrl, - @Size(max = 50) String statutMatrimonial, - @Size(max = 100) String nationalite, - @Size(max = 50) String typeIdentite, - @Size(max = 100) String numeroIdentite, - UUID organisationId) { -} +package dev.lions.unionflow.server.api.dto.membre.request; + +import jakarta.validation.constraints.Email; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import java.time.LocalDate; +import java.util.UUID; + +import lombok.Builder; + +/** + * Requête de création d'un membre. + * + *

+ * Immutable via {@code record}. Exclut l'ID, + * les champs d'audit, et le numéroMembre + * (généré côté serveur). + * + * @author UnionFlow Team + * @version 3.0 + * @since 2026-02-21 + * @param prenom prénom + * @param nom nom de famille + * @param email email + * @param telephone téléphone + * @param telephoneWave numéro Wave + * @param dateNaissance date de naissance + * @param profession profession + * @param photoUrl URL de la photo + * @param statutMatrimonial statut matrimonial + * @param nationalite nationalité + * @param typeIdentite type pièce d'identité + * @param numeroIdentite numéro d'identité + * @param organisationId ID de l'organisation (obligatoire pour ADMIN_ORGANISATION) + */ +@Builder +public record CreateMembreRequest( + @NotBlank @Size(max = 100) String prenom, + @NotBlank @Size(max = 100) String nom, + @NotBlank @Email @Size(max = 255) String email, + @Size(max = 20) String telephone, + @Size(max = 20) String telephoneWave, + @NotNull LocalDate dateNaissance, + @Size(max = 100) String profession, + @Size(max = 500) String photoUrl, + @Size(max = 50) String statutMatrimonial, + @Size(max = 100) String nationalite, + @Size(max = 50) String typeIdentite, + @Size(max = 100) String numeroIdentite, + UUID organisationId) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/membre/request/UpdateMembreRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/membre/request/UpdateMembreRequest.java index 59f2c70..9e39633 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/membre/request/UpdateMembreRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/membre/request/UpdateMembreRequest.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.dto.membre.request; - -import jakarta.validation.constraints.*; -import java.time.LocalDate; - -import lombok.Builder; - -/** - * Requête pour mettre à jour un membre existant. - */ -@Builder -public record UpdateMembreRequest( - @NotBlank @Size(max = 100) String prenom, - @NotBlank @Size(max = 100) String nom, - @NotBlank @Email @Size(max = 255) String email, - @Size(max = 20) String telephone, - @Size(max = 20) String telephoneWave, - @NotNull LocalDate dateNaissance, - @Size(max = 100) String profession, - @Size(max = 500) String photoUrl, - @Size(max = 50) String statutMatrimonial, - @Size(max = 100) String nationalite, - @Size(max = 50) String typeIdentite, - @Size(max = 100) String numeroIdentite, - Boolean actif) { -} +package dev.lions.unionflow.server.api.dto.membre.request; + +import jakarta.validation.constraints.*; +import java.time.LocalDate; + +import lombok.Builder; + +/** + * Requête pour mettre à jour un membre existant. + */ +@Builder +public record UpdateMembreRequest( + @NotBlank @Size(max = 100) String prenom, + @NotBlank @Size(max = 100) String nom, + @NotBlank @Email @Size(max = 255) String email, + @Size(max = 20) String telephone, + @Size(max = 20) String telephoneWave, + @NotNull LocalDate dateNaissance, + @Size(max = 100) String profession, + @Size(max = 500) String photoUrl, + @Size(max = 50) String statutMatrimonial, + @Size(max = 100) String nationalite, + @Size(max = 50) String typeIdentite, + @Size(max = 100) String numeroIdentite, + Boolean actif) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/membre/response/MembreResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/membre/response/MembreResponse.java index ae38058..e57904f 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/membre/response/MembreResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/membre/response/MembreResponse.java @@ -1,136 +1,136 @@ -package dev.lions.unionflow.server.api.dto.membre.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.time.LocalDate; -import java.time.format.DateTimeFormatter; -import java.util.UUID; -import java.util.List; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse contenant les données d'un membre. - * - *

- * Classe Lombok (getters/setters) pour la - * compatibilité avec les frameworks d'affichage - * (PrimeFaces, etc.). - * - * @author UnionFlow Team - * @version 3.0 - * @since 2026-02-21 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class MembreResponse extends BaseResponse { - - // ── Identité ─────────────────────────────── - private String numeroMembre; - private UUID keycloakId; - private String prenom; - private String nom; - private String nomComplet; - private String email; - private String telephone; - private String telephoneWave; - private LocalDate dateNaissance; - private int age; - - // ── Personnel ────────────────────────────── - private String profession; - private String photoUrl; - private String statutMatrimonial; - private String statutMatrimonialLibelle; - private String nationalite; - private String typeIdentite; - private String typeIdentiteLibelle; - private String numeroIdentite; - - // ── KYC / LCB-FT ─────────────────────────── - private String niveauVigilanceKyc; - private String statutKyc; - private LocalDate dateVerificationIdentite; - - // ── Statut ───────────────────────────────── - private String statutCompte; - private String statutCompteLibelle; - private String statutCompteSeverity; - private List roles; - - // ── Adhésion (contexte organisation) ─────── - private UUID organisationId; - private String organisationNom; - private LocalDate dateAdhesion; - - // ── Adresse principale ───────────────────── - private String adresse; - private String ville; - private String codePostal; - - // ── Notes / biographie ───────────────────── - private String notes; - - // ── Statistiques ─────────────────────────── - private int nombreEvenementsParticipes; - - // ── Provisionnement (retourné une seule fois à la création) ──── - /** Mot de passe temporaire généré lors du provisionnement Keycloak. - * Null pour toutes les autres opérations. L'utilisateur devra le changer à la première connexion. */ - private String motDePasseTemporaire; - - // ── Méthodes calculées pour la compatibilité JSF EL ──────────── - - /** Initiales (première lettre prénom + première lettre nom) pour les avatars JSF. */ - public String getInitiales() { - String p = (prenom != null && !prenom.isEmpty()) ? prenom.substring(0, 1).toUpperCase() : ""; - String n = (nom != null && !nom.isEmpty()) ? nom.substring(0, 1).toUpperCase() : ""; - return p + n; - } - - /** Date d'adhésion formatée "dd/MM/yyyy" pour #{membre.dateAdhesionFormatee}. */ - public String getDateAdhesionFormatee() { - if (dateAdhesion == null) return null; - return dateAdhesion.format(DateTimeFormatter.ofPattern("dd/MM/yyyy")); - } - - /** Alias de statutCompte pour #{membre.statut}. */ - public String getStatut() { - return statutCompte; - } - - /** Alias de statutCompteSeverity pour #{membre.statutSeverity}. */ - public String getStatutSeverity() { - return statutCompteSeverity; - } - - /** Libellé du rôle principal calculé depuis les rôles. */ - public String getTypeMembre() { - if (roles == null || roles.isEmpty()) return "Membre"; - if (roles.contains("PRESIDENT")) return "Président"; - if (roles.contains("VICE_PRESIDENT")) return "Vice-Président"; - if (roles.contains("SECRETAIRE")) return "Secrétaire"; - if (roles.contains("TRESORIER")) return "Trésorier"; - if (roles.contains("ADMIN_ORGANISATION")) return "Administrateur"; - if (roles.contains("MODERATEUR")) return "Modérateur"; - return "Membre"; - } - - /** Severity PrimeUI calculée depuis les rôles. */ - public String getTypeSeverity() { - if (roles == null || roles.isEmpty()) return "secondary"; - if (roles.contains("PRESIDENT")) return "primary"; - if (roles.contains("VICE_PRESIDENT")) return "primary"; - if (roles.contains("SECRETAIRE")) return "info"; - if (roles.contains("TRESORIER")) return "warning"; - if (roles.contains("ADMIN_ORGANISATION")) return "danger"; - if (roles.contains("MODERATEUR")) return "warning"; - return "secondary"; - } -} +package dev.lions.unionflow.server.api.dto.membre.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.time.LocalDate; +import java.time.format.DateTimeFormatter; +import java.util.UUID; +import java.util.List; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse contenant les données d'un membre. + * + *

+ * Classe Lombok (getters/setters) pour la + * compatibilité avec les frameworks d'affichage + * (PrimeFaces, etc.). + * + * @author UnionFlow Team + * @version 3.0 + * @since 2026-02-21 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class MembreResponse extends BaseResponse { + + // ── Identité ─────────────────────────────── + private String numeroMembre; + private UUID keycloakId; + private String prenom; + private String nom; + private String nomComplet; + private String email; + private String telephone; + private String telephoneWave; + private LocalDate dateNaissance; + private int age; + + // ── Personnel ────────────────────────────── + private String profession; + private String photoUrl; + private String statutMatrimonial; + private String statutMatrimonialLibelle; + private String nationalite; + private String typeIdentite; + private String typeIdentiteLibelle; + private String numeroIdentite; + + // ── KYC / LCB-FT ─────────────────────────── + private String niveauVigilanceKyc; + private String statutKyc; + private LocalDate dateVerificationIdentite; + + // ── Statut ───────────────────────────────── + private String statutCompte; + private String statutCompteLibelle; + private String statutCompteSeverity; + private List roles; + + // ── Adhésion (contexte organisation) ─────── + private UUID organisationId; + private String organisationNom; + private LocalDate dateAdhesion; + + // ── Adresse principale ───────────────────── + private String adresse; + private String ville; + private String codePostal; + + // ── Notes / biographie ───────────────────── + private String notes; + + // ── Statistiques ─────────────────────────── + private int nombreEvenementsParticipes; + + // ── Provisionnement (retourné une seule fois à la création) ──── + /** Mot de passe temporaire généré lors du provisionnement Keycloak. + * Null pour toutes les autres opérations. L'utilisateur devra le changer à la première connexion. */ + private String motDePasseTemporaire; + + // ── Méthodes calculées pour la compatibilité JSF EL ──────────── + + /** Initiales (première lettre prénom + première lettre nom) pour les avatars JSF. */ + public String getInitiales() { + String p = (prenom != null && !prenom.isEmpty()) ? prenom.substring(0, 1).toUpperCase() : ""; + String n = (nom != null && !nom.isEmpty()) ? nom.substring(0, 1).toUpperCase() : ""; + return p + n; + } + + /** Date d'adhésion formatée "dd/MM/yyyy" pour #{membre.dateAdhesionFormatee}. */ + public String getDateAdhesionFormatee() { + if (dateAdhesion == null) return null; + return dateAdhesion.format(DateTimeFormatter.ofPattern("dd/MM/yyyy")); + } + + /** Alias de statutCompte pour #{membre.statut}. */ + public String getStatut() { + return statutCompte; + } + + /** Alias de statutCompteSeverity pour #{membre.statutSeverity}. */ + public String getStatutSeverity() { + return statutCompteSeverity; + } + + /** Libellé du rôle principal calculé depuis les rôles. */ + public String getTypeMembre() { + if (roles == null || roles.isEmpty()) return "Membre"; + if (roles.contains("PRESIDENT")) return "Président"; + if (roles.contains("VICE_PRESIDENT")) return "Vice-Président"; + if (roles.contains("SECRETAIRE")) return "Secrétaire"; + if (roles.contains("TRESORIER")) return "Trésorier"; + if (roles.contains("ADMIN_ORGANISATION")) return "Administrateur"; + if (roles.contains("MODERATEUR")) return "Modérateur"; + return "Membre"; + } + + /** Severity PrimeUI calculée depuis les rôles. */ + public String getTypeSeverity() { + if (roles == null || roles.isEmpty()) return "secondary"; + if (roles.contains("PRESIDENT")) return "primary"; + if (roles.contains("VICE_PRESIDENT")) return "primary"; + if (roles.contains("SECRETAIRE")) return "info"; + if (roles.contains("TRESORIER")) return "warning"; + if (roles.contains("ADMIN_ORGANISATION")) return "danger"; + if (roles.contains("MODERATEUR")) return "warning"; + return "secondary"; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/DemandeCreditRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/DemandeCreditRequest.java index 9574795..50ddfe8 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/DemandeCreditRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/DemandeCreditRequest.java @@ -1,49 +1,49 @@ -package dev.lions.unionflow.server.api.dto.mutuelle.credit; - -import dev.lions.unionflow.server.api.enums.mutuelle.credit.TypeCredit; -import dev.lions.unionflow.server.api.enums.mutuelle.credit.TypeGarantie; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Min; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -import java.math.BigDecimal; -import java.util.List; - -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Requête initiale pour une demande de financement (Crédit)") -public class DemandeCreditRequest { - - @NotBlank(message = "L'ID du demandeur est obligatoire") - private String membreId; - - @NotNull(message = "Le type de crédit est obligatoire") - private TypeCredit typeCredit; - - @NotNull(message = "Le montant demandé est obligatoire") - @DecimalMin(value = "1.0", message = "Le montant demandé doit être positif") - private BigDecimal montantDemande; - - @Min(value = 1, message = "La durée (en mois) doit être au moins de 1 mois") - private Integer dureeMois; - - @Schema(description = "Compte épargne adossé (si remboursement automatique ou nantissement)") - private String compteLieId; - - @NotBlank(message = "Le motif détaillé du financement est requis (Plan d'affaires, usage...)") - private String justificationDetaillee; - - @Schema(description = "Liste des IDs de documents justificatifs attachés au dossier") - private List documentIds; - - @Schema(description = "Liste des garanties proposées avec la demande") - private List garantiesProposees; -} +package dev.lions.unionflow.server.api.dto.mutuelle.credit; + +import dev.lions.unionflow.server.api.enums.mutuelle.credit.TypeCredit; +import dev.lions.unionflow.server.api.enums.mutuelle.credit.TypeGarantie; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Min; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +import java.math.BigDecimal; +import java.util.List; + +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Requête initiale pour une demande de financement (Crédit)") +public class DemandeCreditRequest { + + @NotBlank(message = "L'ID du demandeur est obligatoire") + private String membreId; + + @NotNull(message = "Le type de crédit est obligatoire") + private TypeCredit typeCredit; + + @NotNull(message = "Le montant demandé est obligatoire") + @DecimalMin(value = "1.0", message = "Le montant demandé doit être positif") + private BigDecimal montantDemande; + + @Min(value = 1, message = "La durée (en mois) doit être au moins de 1 mois") + private Integer dureeMois; + + @Schema(description = "Compte épargne adossé (si remboursement automatique ou nantissement)") + private String compteLieId; + + @NotBlank(message = "Le motif détaillé du financement est requis (Plan d'affaires, usage...)") + private String justificationDetaillee; + + @Schema(description = "Liste des IDs de documents justificatifs attachés au dossier") + private List documentIds; + + @Schema(description = "Liste des garanties proposées avec la demande") + private List garantiesProposees; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/DemandeCreditResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/DemandeCreditResponse.java index b306201..6cd32f4 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/DemandeCreditResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/DemandeCreditResponse.java @@ -1,48 +1,48 @@ -package dev.lions.unionflow.server.api.dto.mutuelle.credit; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.mutuelle.credit.StatutDemandeCredit; -import dev.lions.unionflow.server.api.enums.mutuelle.credit.TypeCredit; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.List; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Réponse avec le tableau de bord résumé d'un dossier de crédit") -public class DemandeCreditResponse extends BaseDTO { - - private String numeroDossier; - private String membreId; - private TypeCredit typeCredit; - private String compteLieId; - - private BigDecimal montantDemande; - private Integer dureeMoisDemande; - - // Conditions actées par le comité de crédit (peuvent différer de la demande) - private BigDecimal montantApprouve; - private Integer dureeMoisApprouvee; - private BigDecimal tauxInteretAnnuel; // Pourcentage - private BigDecimal coutTotalCredit; // Total Intérêts - - private StatutDemandeCredit statut; - private String notesComite; - - private LocalDate dateSoumission; - private LocalDate dateValidation; - private LocalDate datePremierEcheance; - - @Schema(description = "Aperçu des échéances générées pour le tableau d'amortissement") - private List echeancier; -} +package dev.lions.unionflow.server.api.dto.mutuelle.credit; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.mutuelle.credit.StatutDemandeCredit; +import dev.lions.unionflow.server.api.enums.mutuelle.credit.TypeCredit; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.List; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Réponse avec le tableau de bord résumé d'un dossier de crédit") +public class DemandeCreditResponse extends BaseDTO { + + private String numeroDossier; + private String membreId; + private TypeCredit typeCredit; + private String compteLieId; + + private BigDecimal montantDemande; + private Integer dureeMoisDemande; + + // Conditions actées par le comité de crédit (peuvent différer de la demande) + private BigDecimal montantApprouve; + private Integer dureeMoisApprouvee; + private BigDecimal tauxInteretAnnuel; // Pourcentage + private BigDecimal coutTotalCredit; // Total Intérêts + + private StatutDemandeCredit statut; + private String notesComite; + + private LocalDate dateSoumission; + private LocalDate dateValidation; + private LocalDate datePremierEcheance; + + @Schema(description = "Aperçu des échéances générées pour le tableau d'amortissement") + private List echeancier; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/EcheanceCreditDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/EcheanceCreditDTO.java index 3461bba..b54d223 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/EcheanceCreditDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/EcheanceCreditDTO.java @@ -1,44 +1,44 @@ -package dev.lions.unionflow.server.api.dto.mutuelle.credit; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.mutuelle.credit.StatutEcheanceCredit; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -import java.math.BigDecimal; -import java.time.LocalDate; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Représente une ligne unique du tableau d'amortissement d'un crédit") -public class EcheanceCreditDTO extends BaseDTO { - - private String demandeCreditId; - - @Schema(description = "Indice de l'échéance (ex: mois 1, 2, 3...)") - private Integer ordre; - - private LocalDate dateEcheancePrevue; - private LocalDate datePaiementEffectif; - - private BigDecimal capitalAmorti; - private BigDecimal interetsDeLaPeriode; - private BigDecimal montantTotalExigible; - - private BigDecimal capitalRestantDu; - - // Pénalités éventuelles additionnelles liées au retard - private BigDecimal penalitesRetard; - - // Somme physiquement encaissée pour cette traite à l'instant T - private BigDecimal montantRegle; - - private StatutEcheanceCredit statut; -} +package dev.lions.unionflow.server.api.dto.mutuelle.credit; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.mutuelle.credit.StatutEcheanceCredit; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +import java.math.BigDecimal; +import java.time.LocalDate; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Représente une ligne unique du tableau d'amortissement d'un crédit") +public class EcheanceCreditDTO extends BaseDTO { + + private String demandeCreditId; + + @Schema(description = "Indice de l'échéance (ex: mois 1, 2, 3...)") + private Integer ordre; + + private LocalDate dateEcheancePrevue; + private LocalDate datePaiementEffectif; + + private BigDecimal capitalAmorti; + private BigDecimal interetsDeLaPeriode; + private BigDecimal montantTotalExigible; + + private BigDecimal capitalRestantDu; + + // Pénalités éventuelles additionnelles liées au retard + private BigDecimal penalitesRetard; + + // Somme physiquement encaissée pour cette traite à l'instant T + private BigDecimal montantRegle; + + private StatutEcheanceCredit statut; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/GarantieDemandeDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/GarantieDemandeDTO.java index 108fa61..87cb2b5 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/GarantieDemandeDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/credit/GarantieDemandeDTO.java @@ -1,28 +1,28 @@ -package dev.lions.unionflow.server.api.dto.mutuelle.credit; - -import dev.lions.unionflow.server.api.enums.mutuelle.credit.TypeGarantie; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.math.BigDecimal; - -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class GarantieDemandeDTO { - - @NotNull(message = "Le type de garantie est requis") - private TypeGarantie typeGarantie; - - private BigDecimal valeurEstimee; - - @NotBlank(message = "Description ou référence requise (Id Membre Caution, SN du Véhicule, Titre Foncier...)") - private String referenceOuDescription; - - private String documentPreuveId; -} +package dev.lions.unionflow.server.api.dto.mutuelle.credit; + +import dev.lions.unionflow.server.api.enums.mutuelle.credit.TypeGarantie; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.math.BigDecimal; + +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class GarantieDemandeDTO { + + @NotNull(message = "Le type de garantie est requis") + private TypeGarantie typeGarantie; + + private BigDecimal valeurEstimee; + + @NotBlank(message = "Description ou référence requise (Id Membre Caution, SN du Véhicule, Titre Foncier...)") + private String referenceOuDescription; + + private String documentPreuveId; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/CompteEpargneRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/CompteEpargneRequest.java index 76284da..c53ef2c 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/CompteEpargneRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/CompteEpargneRequest.java @@ -1,33 +1,33 @@ -package dev.lions.unionflow.server.api.dto.mutuelle.epargne; - -import dev.lions.unionflow.server.api.enums.mutuelle.epargne.TypeCompteEpargne; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Requête d'ouverture d'un compte d'épargne") -public class CompteEpargneRequest { - - @NotBlank(message = "L'ID du membre propriétaire est obligatoire") - @Schema(description = "ID UUID du Membre détenteur") - private String membreId; - - @NotBlank(message = "L'ID de l'organisation est obligatoire") - @Schema(description = "ID UUID de l'Organisation / Mutuelle") - private String organisationId; - - @NotNull(message = "Le type de compte est obligatoire") - @Schema(description = "Le type du compte d'épargne demandé") - private TypeCompteEpargne typeCompte; - - @Schema(description = "Notes ou détails éventuels lors de l'ouverture") - private String notesOuverture; -} +package dev.lions.unionflow.server.api.dto.mutuelle.epargne; + +import dev.lions.unionflow.server.api.enums.mutuelle.epargne.TypeCompteEpargne; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Requête d'ouverture d'un compte d'épargne") +public class CompteEpargneRequest { + + @NotBlank(message = "L'ID du membre propriétaire est obligatoire") + @Schema(description = "ID UUID du Membre détenteur") + private String membreId; + + @NotBlank(message = "L'ID de l'organisation est obligatoire") + @Schema(description = "ID UUID de l'Organisation / Mutuelle") + private String organisationId; + + @NotNull(message = "Le type de compte est obligatoire") + @Schema(description = "Le type du compte d'épargne demandé") + private TypeCompteEpargne typeCompte; + + @Schema(description = "Notes ou détails éventuels lors de l'ouverture") + private String notesOuverture; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/CompteEpargneResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/CompteEpargneResponse.java index f04d8de..d57ffab 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/CompteEpargneResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/CompteEpargneResponse.java @@ -1,42 +1,42 @@ -package dev.lions.unionflow.server.api.dto.mutuelle.epargne; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.mutuelle.epargne.StatutCompteEpargne; -import dev.lions.unionflow.server.api.enums.mutuelle.epargne.TypeCompteEpargne; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -import java.math.BigDecimal; -import java.time.LocalDate; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Réponse des informations d'un compte épargne") -public class CompteEpargneResponse extends BaseDTO { - - private String membreId; - private String organisationId; - - @Schema(description = "Numéro de compte généré de manière unique (ex: MEC-00123)") - private String numeroCompte; - - private TypeCompteEpargne typeCompte; - - @Schema(description = "Solde principal disponible") - private BigDecimal soldeActuel; - - @Schema(description = "Fonds gelés pour garantie de crédits") - private BigDecimal soldeBloque; - - private StatutCompteEpargne statut; - private LocalDate dateOuverture; - private LocalDate dateDerniereTransaction; - private String description; -} +package dev.lions.unionflow.server.api.dto.mutuelle.epargne; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.mutuelle.epargne.StatutCompteEpargne; +import dev.lions.unionflow.server.api.enums.mutuelle.epargne.TypeCompteEpargne; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +import java.math.BigDecimal; +import java.time.LocalDate; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Réponse des informations d'un compte épargne") +public class CompteEpargneResponse extends BaseDTO { + + private String membreId; + private String organisationId; + + @Schema(description = "Numéro de compte généré de manière unique (ex: MEC-00123)") + private String numeroCompte; + + private TypeCompteEpargne typeCompte; + + @Schema(description = "Solde principal disponible") + private BigDecimal soldeActuel; + + @Schema(description = "Fonds gelés pour garantie de crédits") + private BigDecimal soldeBloque; + + private StatutCompteEpargne statut; + private LocalDate dateOuverture; + private LocalDate dateDerniereTransaction; + private String description; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/TransactionEpargneRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/TransactionEpargneRequest.java index 9942adc..ec0badd 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/TransactionEpargneRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/TransactionEpargneRequest.java @@ -1,43 +1,43 @@ -package dev.lions.unionflow.server.api.dto.mutuelle.epargne; - -import dev.lions.unionflow.server.api.enums.mutuelle.epargne.TypeTransactionEpargne; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -import java.math.BigDecimal; - -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Requête d'initialisation d'une transaction sur un compte d'épargne") -public class TransactionEpargneRequest { - - @NotBlank(message = "L'ID du compte épargne cible est obligatoire") - private String compteId; - - @NotNull(message = "Le type de transaction est requis") - private TypeTransactionEpargne typeTransaction; - - @NotNull(message = "Le montant est obligatoire") - @DecimalMin(value = "0.01", message = "Le montant doit être supérieur à 0") - private BigDecimal montant; - - @Schema(description = "ID d'un compte de destination en cas de transfert interne") - private String compteDestinationId; - - @Schema(description = "Motif, libellé ou preuve de dépôt") - private String motif; - - @Schema(description = "Origine des fonds (LCB-FT) — obligatoire au-dessus du seuil configuré (ex. Salaire, Vente, Héritage)") - private String origineFonds; - - @Schema(description = "ID de la pièce justificative (document) — requis au-dessus du seuil LCB-FT") - private String pieceJustificativeId; -} +package dev.lions.unionflow.server.api.dto.mutuelle.epargne; + +import dev.lions.unionflow.server.api.enums.mutuelle.epargne.TypeTransactionEpargne; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +import java.math.BigDecimal; + +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Requête d'initialisation d'une transaction sur un compte d'épargne") +public class TransactionEpargneRequest { + + @NotBlank(message = "L'ID du compte épargne cible est obligatoire") + private String compteId; + + @NotNull(message = "Le type de transaction est requis") + private TypeTransactionEpargne typeTransaction; + + @NotNull(message = "Le montant est obligatoire") + @DecimalMin(value = "0.01", message = "Le montant doit être supérieur à 0") + private BigDecimal montant; + + @Schema(description = "ID d'un compte de destination en cas de transfert interne") + private String compteDestinationId; + + @Schema(description = "Motif, libellé ou preuve de dépôt") + private String motif; + + @Schema(description = "Origine des fonds (LCB-FT) — obligatoire au-dessus du seuil configuré (ex. Salaire, Vente, Héritage)") + private String origineFonds; + + @Schema(description = "ID de la pièce justificative (document) — requis au-dessus du seuil LCB-FT") + private String pieceJustificativeId; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/TransactionEpargneResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/TransactionEpargneResponse.java index bbd45b9..5ae0a56 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/TransactionEpargneResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/mutuelle/epargne/TransactionEpargneResponse.java @@ -1,44 +1,44 @@ -package dev.lions.unionflow.server.api.dto.mutuelle.epargne; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.mutuelle.epargne.TypeTransactionEpargne; -import dev.lions.unionflow.server.api.enums.wave.StatutTransactionWave; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; - -import java.math.BigDecimal; -import java.time.LocalDateTime; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class TransactionEpargneResponse extends BaseDTO { - - private String compteId; - private TypeTransactionEpargne type; - private BigDecimal montant; - - // Pour assurer un audit et les principes de comptabilité double entrée - private BigDecimal soldeAvant; - private BigDecimal soldeApres; - - private String motif; - private LocalDateTime dateTransaction; - private String operateurId; - - private String referenceExterne; - - // Status général d'une transaction (Validée, Rejetée, En traitement Wave) - private StatutTransactionWave statutExecution; - - /** Origine des fonds déclarée (LCB-FT) */ - private String origineFonds; - - /** Référence pièce justificative (LCB-FT) */ - private String pieceJustificativeId; -} +package dev.lions.unionflow.server.api.dto.mutuelle.epargne; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.mutuelle.epargne.TypeTransactionEpargne; +import dev.lions.unionflow.server.api.enums.wave.StatutTransactionWave; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; + +import java.math.BigDecimal; +import java.time.LocalDateTime; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class TransactionEpargneResponse extends BaseDTO { + + private String compteId; + private TypeTransactionEpargne type; + private BigDecimal montant; + + // Pour assurer un audit et les principes de comptabilité double entrée + private BigDecimal soldeAvant; + private BigDecimal soldeApres; + + private String motif; + private LocalDateTime dateTransaction; + private String operateurId; + + private String referenceExterne; + + // Status général d'une transaction (Validée, Rejetée, En traitement Wave) + private StatutTransactionWave statutExecution; + + /** Origine des fonds déclarée (LCB-FT) */ + private String origineFonds; + + /** Référence pièce justificative (LCB-FT) */ + private String pieceJustificativeId; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/notification/ActionNotificationDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/notification/ActionNotificationDTO.java index e246178..776da9e 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/notification/ActionNotificationDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/notification/ActionNotificationDTO.java @@ -1,477 +1,477 @@ -package dev.lions.unionflow.server.api.dto.notification; - -import com.fasterxml.jackson.annotation.JsonInclude; -import jakarta.validation.constraints.*; -import java.util.Map; - -/** - * DTO pour les actions rapides des notifications UnionFlow - * - *

Ce DTO représente une action que l'utilisateur peut exécuter directement depuis la - * notification sans ouvrir l'application. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@JsonInclude(JsonInclude.Include.NON_NULL) -public class ActionNotificationDTO { - - /** Identifiant unique de l'action */ - @NotBlank(message = "L'identifiant de l'action est obligatoire") - private String id; - - /** Libellé affiché sur le bouton d'action */ - @NotBlank(message = "Le libellé de l'action est obligatoire") - @Size(max = 30, message = "Le libellé ne peut pas dépasser 30 caractères") - private String libelle; - - /** Description de l'action (tooltip) */ - @Size(max = 100, message = "La description ne peut pas dépasser 100 caractères") - private String description; - - /** Type d'action à exécuter */ - @NotBlank(message = "Le type d'action est obligatoire") - private String typeAction; - - /** Icône de l'action (Material Design) */ - private String icone; - - /** Couleur de l'action (hexadécimal) */ - private String couleur; - - /** URL à ouvrir (pour les actions de type "url") */ - private String url; - - /** Route de l'application à ouvrir (pour les actions de type "route") */ - private String route; - - /** Paramètres de l'action */ - private Map parametres; - - /** Indique si l'action ferme la notification */ - private Boolean fermeNotification; - - /** Indique si l'action nécessite une confirmation */ - private Boolean necessiteConfirmation; - - /** Message de confirmation à afficher */ - private String messageConfirmation; - - /** Indique si l'action est destructive (suppression, etc.) */ - private Boolean estDestructive; - - /** Ordre d'affichage de l'action */ - private Integer ordre; - - /** Indique si l'action est activée */ - private Boolean estActivee; - - /** Condition d'affichage de l'action (expression) */ - private String conditionAffichage; - - /** Rôles autorisés à exécuter cette action */ - private String[] rolesAutorises; - - /** Permissions requises pour exécuter cette action */ - private String[] permissionsRequises; - - /** Délai d'expiration de l'action en minutes */ - private Integer delaiExpirationMinutes; - - /** Nombre maximum d'exécutions autorisées */ - private Integer maxExecutions; - - /** Nombre d'exécutions actuelles */ - private Integer nombreExecutions; - - /** Indique si l'action peut être exécutée plusieurs fois */ - private Boolean peutEtreRepetee; - - /** Style du bouton (primary, secondary, outline, text) */ - private String styleBouton; - - /** Taille du bouton (small, medium, large) */ - private String tailleBouton; - - /** Position du bouton (left, center, right) */ - private String positionBouton; - - /** Données personnalisées de l'action */ - private Map donneesPersonnalisees; - - // === CONSTRUCTEURS === - - /** Constructeur par défaut */ - public ActionNotificationDTO() { - this.fermeNotification = true; - this.necessiteConfirmation = false; - this.estDestructive = false; - this.ordre = 0; - this.estActivee = true; - this.maxExecutions = 1; - this.nombreExecutions = 0; - this.peutEtreRepetee = false; - this.styleBouton = "primary"; - this.tailleBouton = "medium"; - this.positionBouton = "right"; - } - - /** Constructeur avec paramètres essentiels */ - public ActionNotificationDTO(String id, String libelle, String typeAction) { - this(); - this.id = id; - this.libelle = libelle; - this.typeAction = typeAction; - } - - /** Constructeur pour action URL */ - public ActionNotificationDTO(String id, String libelle, String url, String icone) { - this(id, libelle, "url"); - this.url = url; - this.icone = icone; - } - - /** Constructeur pour action de route */ - public ActionNotificationDTO( - String id, String libelle, String route, String icone, Map parametres) { - this(id, libelle, "route"); - this.route = route; - this.icone = icone; - this.parametres = parametres; - } - - // === GETTERS ET SETTERS === - - public String getId() { - return id; - } - - public void setId(String id) { - this.id = id; - } - - public String getLibelle() { - return libelle; - } - - public void setLibelle(String libelle) { - this.libelle = libelle; - } - - public String getDescription() { - return description; - } - - public void setDescription(String description) { - this.description = description; - } - - public String getTypeAction() { - return typeAction; - } - - public void setTypeAction(String typeAction) { - this.typeAction = typeAction; - } - - public String getIcone() { - return icone; - } - - public void setIcone(String icone) { - this.icone = icone; - } - - public String getCouleur() { - return couleur; - } - - public void setCouleur(String couleur) { - this.couleur = couleur; - } - - public String getUrl() { - return url; - } - - public void setUrl(String url) { - this.url = url; - } - - public String getRoute() { - return route; - } - - public void setRoute(String route) { - this.route = route; - } - - public Map getParametres() { - return parametres; - } - - public void setParametres(Map parametres) { - this.parametres = parametres; - } - - public Boolean getFermeNotification() { - return fermeNotification; - } - - public void setFermeNotification(Boolean fermeNotification) { - this.fermeNotification = fermeNotification; - } - - public Boolean getNecessiteConfirmation() { - return necessiteConfirmation; - } - - public void setNecessiteConfirmation(Boolean necessiteConfirmation) { - this.necessiteConfirmation = necessiteConfirmation; - } - - public String getMessageConfirmation() { - return messageConfirmation; - } - - public void setMessageConfirmation(String messageConfirmation) { - this.messageConfirmation = messageConfirmation; - } - - public Boolean getEstDestructive() { - return estDestructive; - } - - public void setEstDestructive(Boolean estDestructive) { - this.estDestructive = estDestructive; - } - - public Integer getOrdre() { - return ordre; - } - - public void setOrdre(Integer ordre) { - this.ordre = ordre; - } - - public Boolean getEstActivee() { - return estActivee; - } - - public void setEstActivee(Boolean estActivee) { - this.estActivee = estActivee; - } - - public String getConditionAffichage() { - return conditionAffichage; - } - - public void setConditionAffichage(String conditionAffichage) { - this.conditionAffichage = conditionAffichage; - } - - public String[] getRolesAutorises() { - return rolesAutorises; - } - - public void setRolesAutorises(String[] rolesAutorises) { - this.rolesAutorises = rolesAutorises; - } - - public String[] getPermissionsRequises() { - return permissionsRequises; - } - - public void setPermissionsRequises(String[] permissionsRequises) { - this.permissionsRequises = permissionsRequises; - } - - public Integer getDelaiExpirationMinutes() { - return delaiExpirationMinutes; - } - - public void setDelaiExpirationMinutes(Integer delaiExpirationMinutes) { - this.delaiExpirationMinutes = delaiExpirationMinutes; - } - - public Integer getMaxExecutions() { - return maxExecutions; - } - - public void setMaxExecutions(Integer maxExecutions) { - this.maxExecutions = maxExecutions; - } - - public Integer getNombreExecutions() { - return nombreExecutions; - } - - public void setNombreExecutions(Integer nombreExecutions) { - this.nombreExecutions = nombreExecutions; - } - - public Boolean getPeutEtreRepetee() { - return peutEtreRepetee; - } - - public void setPeutEtreRepetee(Boolean peutEtreRepetee) { - this.peutEtreRepetee = peutEtreRepetee; - } - - public String getStyleBouton() { - return styleBouton; - } - - public void setStyleBouton(String styleBouton) { - this.styleBouton = styleBouton; - } - - public String getTailleBouton() { - return tailleBouton; - } - - public void setTailleBouton(String tailleBouton) { - this.tailleBouton = tailleBouton; - } - - public String getPositionBouton() { - return positionBouton; - } - - public void setPositionBouton(String positionBouton) { - this.positionBouton = positionBouton; - } - - public Map getDonneesPersonnalisees() { - return donneesPersonnalisees; - } - - public void setDonneesPersonnalisees(Map donneesPersonnalisees) { - this.donneesPersonnalisees = donneesPersonnalisees; - } - - // === MÉTHODES UTILITAIRES === - - /** Vérifie si l'action peut être exécutée */ - public boolean peutEtreExecutee() { - return estActivee && (nombreExecutions < maxExecutions || peutEtreRepetee); - } - - /** Vérifie si l'action est expirée */ - public boolean isExpiree() { - // Implémentation basée sur delaiExpirationMinutes et date de création de la notification - return false; // À implémenter selon la logique métier - } - - /** Incrémente le nombre d'exécutions */ - public void incrementerExecutions() { - if (nombreExecutions == null) { - nombreExecutions = 0; - } - nombreExecutions++; - } - - /** Vérifie si l'utilisateur a les permissions requises */ - public boolean utilisateurAutorise(String[] rolesUtilisateur, String[] permissionsUtilisateur) { - // Vérification des rôles - if (rolesAutorises != null && rolesAutorises.length > 0) { - boolean roleAutorise = false; - for (String roleRequis : rolesAutorises) { - for (String roleUtilisateur : rolesUtilisateur) { - if (roleRequis.equals(roleUtilisateur)) { - roleAutorise = true; - break; - } - } - if (roleAutorise) break; - } - if (!roleAutorise) return false; - } - - // Vérification des permissions - if (permissionsRequises != null && permissionsRequises.length > 0) { - boolean permissionAutorisee = false; - for (String permissionRequise : permissionsRequises) { - for (String permissionUtilisateur : permissionsUtilisateur) { - if (permissionRequise.equals(permissionUtilisateur)) { - permissionAutorisee = true; - break; - } - } - if (permissionAutorisee) break; - } - if (!permissionAutorisee) return false; - } - - return true; - } - - /** Retourne la couleur par défaut selon le type d'action */ - public String getCouleurParDefaut() { - if (couleur != null) return couleur; - - return switch (typeAction) { - case "confirm" -> "#4CAF50"; // Vert pour confirmation - case "cancel" -> "#F44336"; // Rouge pour annulation - case "info" -> "#2196F3"; // Bleu pour information - case "warning" -> "#FF9800"; // Orange pour avertissement - case "url", "route" -> "#2196F3"; // Bleu pour navigation - default -> "#9E9E9E"; // Gris par défaut - }; - } - - /** Retourne l'icône par défaut selon le type d'action */ - public String getIconeParDefaut() { - if (icone != null) return icone; - - return switch (typeAction) { - case "confirm" -> "check"; - case "cancel" -> "close"; - case "info" -> "info"; - case "warning" -> "warning"; - case "url" -> "open_in_new"; - case "route" -> "arrow_forward"; - case "call" -> "phone"; - case "message" -> "message"; - case "email" -> "email"; - case "share" -> "share"; - default -> "touch_app"; - }; - } - - /** Crée une action de confirmation */ - public static ActionNotificationDTO creerActionConfirmation(String id, String libelle) { - ActionNotificationDTO action = new ActionNotificationDTO(id, libelle, "confirm"); - action.setCouleur("#4CAF50"); - action.setIcone("check"); - action.setStyleBouton("primary"); - return action; - } - - /** Crée une action d'annulation */ - public static ActionNotificationDTO creerActionAnnulation(String id, String libelle) { - ActionNotificationDTO action = new ActionNotificationDTO(id, libelle, "cancel"); - action.setCouleur("#F44336"); - action.setIcone("close"); - action.setStyleBouton("outline"); - action.setEstDestructive(true); - return action; - } - - /** Crée une action de navigation */ - public static ActionNotificationDTO creerActionNavigation( - String id, String libelle, String route) { - ActionNotificationDTO action = new ActionNotificationDTO(id, libelle, "route"); - action.setRoute(route); - action.setCouleur("#2196F3"); - action.setIcone("arrow_forward"); - return action; - } - - @Override - public String toString() { - return String.format( - "ActionNotificationDTO{id='%s', libelle='%s', type='%s'}", id, libelle, typeAction); - } -} +package dev.lions.unionflow.server.api.dto.notification; + +import com.fasterxml.jackson.annotation.JsonInclude; +import jakarta.validation.constraints.*; +import java.util.Map; + +/** + * DTO pour les actions rapides des notifications UnionFlow + * + *

Ce DTO représente une action que l'utilisateur peut exécuter directement depuis la + * notification sans ouvrir l'application. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@JsonInclude(JsonInclude.Include.NON_NULL) +public class ActionNotificationDTO { + + /** Identifiant unique de l'action */ + @NotBlank(message = "L'identifiant de l'action est obligatoire") + private String id; + + /** Libellé affiché sur le bouton d'action */ + @NotBlank(message = "Le libellé de l'action est obligatoire") + @Size(max = 30, message = "Le libellé ne peut pas dépasser 30 caractères") + private String libelle; + + /** Description de l'action (tooltip) */ + @Size(max = 100, message = "La description ne peut pas dépasser 100 caractères") + private String description; + + /** Type d'action à exécuter */ + @NotBlank(message = "Le type d'action est obligatoire") + private String typeAction; + + /** Icône de l'action (Material Design) */ + private String icone; + + /** Couleur de l'action (hexadécimal) */ + private String couleur; + + /** URL à ouvrir (pour les actions de type "url") */ + private String url; + + /** Route de l'application à ouvrir (pour les actions de type "route") */ + private String route; + + /** Paramètres de l'action */ + private Map parametres; + + /** Indique si l'action ferme la notification */ + private Boolean fermeNotification; + + /** Indique si l'action nécessite une confirmation */ + private Boolean necessiteConfirmation; + + /** Message de confirmation à afficher */ + private String messageConfirmation; + + /** Indique si l'action est destructive (suppression, etc.) */ + private Boolean estDestructive; + + /** Ordre d'affichage de l'action */ + private Integer ordre; + + /** Indique si l'action est activée */ + private Boolean estActivee; + + /** Condition d'affichage de l'action (expression) */ + private String conditionAffichage; + + /** Rôles autorisés à exécuter cette action */ + private String[] rolesAutorises; + + /** Permissions requises pour exécuter cette action */ + private String[] permissionsRequises; + + /** Délai d'expiration de l'action en minutes */ + private Integer delaiExpirationMinutes; + + /** Nombre maximum d'exécutions autorisées */ + private Integer maxExecutions; + + /** Nombre d'exécutions actuelles */ + private Integer nombreExecutions; + + /** Indique si l'action peut être exécutée plusieurs fois */ + private Boolean peutEtreRepetee; + + /** Style du bouton (primary, secondary, outline, text) */ + private String styleBouton; + + /** Taille du bouton (small, medium, large) */ + private String tailleBouton; + + /** Position du bouton (left, center, right) */ + private String positionBouton; + + /** Données personnalisées de l'action */ + private Map donneesPersonnalisees; + + // === CONSTRUCTEURS === + + /** Constructeur par défaut */ + public ActionNotificationDTO() { + this.fermeNotification = true; + this.necessiteConfirmation = false; + this.estDestructive = false; + this.ordre = 0; + this.estActivee = true; + this.maxExecutions = 1; + this.nombreExecutions = 0; + this.peutEtreRepetee = false; + this.styleBouton = "primary"; + this.tailleBouton = "medium"; + this.positionBouton = "right"; + } + + /** Constructeur avec paramètres essentiels */ + public ActionNotificationDTO(String id, String libelle, String typeAction) { + this(); + this.id = id; + this.libelle = libelle; + this.typeAction = typeAction; + } + + /** Constructeur pour action URL */ + public ActionNotificationDTO(String id, String libelle, String url, String icone) { + this(id, libelle, "url"); + this.url = url; + this.icone = icone; + } + + /** Constructeur pour action de route */ + public ActionNotificationDTO( + String id, String libelle, String route, String icone, Map parametres) { + this(id, libelle, "route"); + this.route = route; + this.icone = icone; + this.parametres = parametres; + } + + // === GETTERS ET SETTERS === + + public String getId() { + return id; + } + + public void setId(String id) { + this.id = id; + } + + public String getLibelle() { + return libelle; + } + + public void setLibelle(String libelle) { + this.libelle = libelle; + } + + public String getDescription() { + return description; + } + + public void setDescription(String description) { + this.description = description; + } + + public String getTypeAction() { + return typeAction; + } + + public void setTypeAction(String typeAction) { + this.typeAction = typeAction; + } + + public String getIcone() { + return icone; + } + + public void setIcone(String icone) { + this.icone = icone; + } + + public String getCouleur() { + return couleur; + } + + public void setCouleur(String couleur) { + this.couleur = couleur; + } + + public String getUrl() { + return url; + } + + public void setUrl(String url) { + this.url = url; + } + + public String getRoute() { + return route; + } + + public void setRoute(String route) { + this.route = route; + } + + public Map getParametres() { + return parametres; + } + + public void setParametres(Map parametres) { + this.parametres = parametres; + } + + public Boolean getFermeNotification() { + return fermeNotification; + } + + public void setFermeNotification(Boolean fermeNotification) { + this.fermeNotification = fermeNotification; + } + + public Boolean getNecessiteConfirmation() { + return necessiteConfirmation; + } + + public void setNecessiteConfirmation(Boolean necessiteConfirmation) { + this.necessiteConfirmation = necessiteConfirmation; + } + + public String getMessageConfirmation() { + return messageConfirmation; + } + + public void setMessageConfirmation(String messageConfirmation) { + this.messageConfirmation = messageConfirmation; + } + + public Boolean getEstDestructive() { + return estDestructive; + } + + public void setEstDestructive(Boolean estDestructive) { + this.estDestructive = estDestructive; + } + + public Integer getOrdre() { + return ordre; + } + + public void setOrdre(Integer ordre) { + this.ordre = ordre; + } + + public Boolean getEstActivee() { + return estActivee; + } + + public void setEstActivee(Boolean estActivee) { + this.estActivee = estActivee; + } + + public String getConditionAffichage() { + return conditionAffichage; + } + + public void setConditionAffichage(String conditionAffichage) { + this.conditionAffichage = conditionAffichage; + } + + public String[] getRolesAutorises() { + return rolesAutorises; + } + + public void setRolesAutorises(String[] rolesAutorises) { + this.rolesAutorises = rolesAutorises; + } + + public String[] getPermissionsRequises() { + return permissionsRequises; + } + + public void setPermissionsRequises(String[] permissionsRequises) { + this.permissionsRequises = permissionsRequises; + } + + public Integer getDelaiExpirationMinutes() { + return delaiExpirationMinutes; + } + + public void setDelaiExpirationMinutes(Integer delaiExpirationMinutes) { + this.delaiExpirationMinutes = delaiExpirationMinutes; + } + + public Integer getMaxExecutions() { + return maxExecutions; + } + + public void setMaxExecutions(Integer maxExecutions) { + this.maxExecutions = maxExecutions; + } + + public Integer getNombreExecutions() { + return nombreExecutions; + } + + public void setNombreExecutions(Integer nombreExecutions) { + this.nombreExecutions = nombreExecutions; + } + + public Boolean getPeutEtreRepetee() { + return peutEtreRepetee; + } + + public void setPeutEtreRepetee(Boolean peutEtreRepetee) { + this.peutEtreRepetee = peutEtreRepetee; + } + + public String getStyleBouton() { + return styleBouton; + } + + public void setStyleBouton(String styleBouton) { + this.styleBouton = styleBouton; + } + + public String getTailleBouton() { + return tailleBouton; + } + + public void setTailleBouton(String tailleBouton) { + this.tailleBouton = tailleBouton; + } + + public String getPositionBouton() { + return positionBouton; + } + + public void setPositionBouton(String positionBouton) { + this.positionBouton = positionBouton; + } + + public Map getDonneesPersonnalisees() { + return donneesPersonnalisees; + } + + public void setDonneesPersonnalisees(Map donneesPersonnalisees) { + this.donneesPersonnalisees = donneesPersonnalisees; + } + + // === MÉTHODES UTILITAIRES === + + /** Vérifie si l'action peut être exécutée */ + public boolean peutEtreExecutee() { + return estActivee && (nombreExecutions < maxExecutions || peutEtreRepetee); + } + + /** Vérifie si l'action est expirée */ + public boolean isExpiree() { + // Implémentation basée sur delaiExpirationMinutes et date de création de la notification + return false; // À implémenter selon la logique métier + } + + /** Incrémente le nombre d'exécutions */ + public void incrementerExecutions() { + if (nombreExecutions == null) { + nombreExecutions = 0; + } + nombreExecutions++; + } + + /** Vérifie si l'utilisateur a les permissions requises */ + public boolean utilisateurAutorise(String[] rolesUtilisateur, String[] permissionsUtilisateur) { + // Vérification des rôles + if (rolesAutorises != null && rolesAutorises.length > 0) { + boolean roleAutorise = false; + for (String roleRequis : rolesAutorises) { + for (String roleUtilisateur : rolesUtilisateur) { + if (roleRequis.equals(roleUtilisateur)) { + roleAutorise = true; + break; + } + } + if (roleAutorise) break; + } + if (!roleAutorise) return false; + } + + // Vérification des permissions + if (permissionsRequises != null && permissionsRequises.length > 0) { + boolean permissionAutorisee = false; + for (String permissionRequise : permissionsRequises) { + for (String permissionUtilisateur : permissionsUtilisateur) { + if (permissionRequise.equals(permissionUtilisateur)) { + permissionAutorisee = true; + break; + } + } + if (permissionAutorisee) break; + } + if (!permissionAutorisee) return false; + } + + return true; + } + + /** Retourne la couleur par défaut selon le type d'action */ + public String getCouleurParDefaut() { + if (couleur != null) return couleur; + + return switch (typeAction) { + case "confirm" -> "#4CAF50"; // Vert pour confirmation + case "cancel" -> "#F44336"; // Rouge pour annulation + case "info" -> "#2196F3"; // Bleu pour information + case "warning" -> "#FF9800"; // Orange pour avertissement + case "url", "route" -> "#2196F3"; // Bleu pour navigation + default -> "#9E9E9E"; // Gris par défaut + }; + } + + /** Retourne l'icône par défaut selon le type d'action */ + public String getIconeParDefaut() { + if (icone != null) return icone; + + return switch (typeAction) { + case "confirm" -> "check"; + case "cancel" -> "close"; + case "info" -> "info"; + case "warning" -> "warning"; + case "url" -> "open_in_new"; + case "route" -> "arrow_forward"; + case "call" -> "phone"; + case "message" -> "message"; + case "email" -> "email"; + case "share" -> "share"; + default -> "touch_app"; + }; + } + + /** Crée une action de confirmation */ + public static ActionNotificationDTO creerActionConfirmation(String id, String libelle) { + ActionNotificationDTO action = new ActionNotificationDTO(id, libelle, "confirm"); + action.setCouleur("#4CAF50"); + action.setIcone("check"); + action.setStyleBouton("primary"); + return action; + } + + /** Crée une action d'annulation */ + public static ActionNotificationDTO creerActionAnnulation(String id, String libelle) { + ActionNotificationDTO action = new ActionNotificationDTO(id, libelle, "cancel"); + action.setCouleur("#F44336"); + action.setIcone("close"); + action.setStyleBouton("outline"); + action.setEstDestructive(true); + return action; + } + + /** Crée une action de navigation */ + public static ActionNotificationDTO creerActionNavigation( + String id, String libelle, String route) { + ActionNotificationDTO action = new ActionNotificationDTO(id, libelle, "route"); + action.setRoute(route); + action.setCouleur("#2196F3"); + action.setIcone("arrow_forward"); + return action; + } + + @Override + public String toString() { + return String.format( + "ActionNotificationDTO{id='%s', libelle='%s', type='%s'}", id, libelle, typeAction); + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/notification/PreferenceCanalNotificationDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/notification/PreferenceCanalNotificationDTO.java index 0c77dba..738f0c5 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/notification/PreferenceCanalNotificationDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/notification/PreferenceCanalNotificationDTO.java @@ -1,119 +1,119 @@ -package dev.lions.unionflow.server.api.dto.notification; - -import com.fasterxml.jackson.annotation.JsonInclude; -import jakarta.validation.constraints.*; - -/** - * DTO pour les préférences spécifiques à un canal de notification - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@JsonInclude(JsonInclude.Include.NON_NULL) -public class PreferenceCanalNotificationDTO { - - /** Indique si ce canal est activé */ - private Boolean active; - - /** Niveau d'importance personnalisé (1-5) */ - @Min(value = 1, message = "L'importance doit être comprise entre 1 et 5") - @Max(value = 5, message = "L'importance doit être comprise entre 1 et 5") - private Integer importance; - - /** Son personnalisé pour ce canal */ - private String sonPersonnalise; - - /** Pattern de vibration personnalisé */ - private long[] patternVibration; - - /** Couleur LED personnalisée */ - private String couleurLED; - - /** Indique si le son est activé pour ce canal */ - private Boolean sonActive; - - /** Indique si la vibration est activée pour ce canal */ - private Boolean vibrationActive; - - /** Indique si la LED est activée pour ce canal */ - private Boolean ledActive; - - /** Indique si ce canal peut être désactivé par l'utilisateur */ - private Boolean peutEtreDesactive; - - // Constructeurs, getters et setters - public PreferenceCanalNotificationDTO() {} - - public Boolean getActive() { - return active; - } - - public void setActive(Boolean active) { - this.active = active; - } - - public Integer getImportance() { - return importance; - } - - public void setImportance(Integer importance) { - this.importance = importance; - } - - public String getSonPersonnalise() { - return sonPersonnalise; - } - - public void setSonPersonnalise(String sonPersonnalise) { - this.sonPersonnalise = sonPersonnalise; - } - - public long[] getPatternVibration() { - return patternVibration; - } - - public void setPatternVibration(long[] patternVibration) { - this.patternVibration = patternVibration; - } - - public String getCouleurLED() { - return couleurLED; - } - - public void setCouleurLED(String couleurLED) { - this.couleurLED = couleurLED; - } - - public Boolean getSonActive() { - return sonActive; - } - - public void setSonActive(Boolean sonActive) { - this.sonActive = sonActive; - } - - public Boolean getVibrationActive() { - return vibrationActive; - } - - public void setVibrationActive(Boolean vibrationActive) { - this.vibrationActive = vibrationActive; - } - - public Boolean getLedActive() { - return ledActive; - } - - public void setLedActive(Boolean ledActive) { - this.ledActive = ledActive; - } - - public Boolean getPeutEtreDesactive() { - return peutEtreDesactive; - } - - public void setPeutEtreDesactive(Boolean peutEtreDesactive) { - this.peutEtreDesactive = peutEtreDesactive; - } -} +package dev.lions.unionflow.server.api.dto.notification; + +import com.fasterxml.jackson.annotation.JsonInclude; +import jakarta.validation.constraints.*; + +/** + * DTO pour les préférences spécifiques à un canal de notification + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@JsonInclude(JsonInclude.Include.NON_NULL) +public class PreferenceCanalNotificationDTO { + + /** Indique si ce canal est activé */ + private Boolean active; + + /** Niveau d'importance personnalisé (1-5) */ + @Min(value = 1, message = "L'importance doit être comprise entre 1 et 5") + @Max(value = 5, message = "L'importance doit être comprise entre 1 et 5") + private Integer importance; + + /** Son personnalisé pour ce canal */ + private String sonPersonnalise; + + /** Pattern de vibration personnalisé */ + private long[] patternVibration; + + /** Couleur LED personnalisée */ + private String couleurLED; + + /** Indique si le son est activé pour ce canal */ + private Boolean sonActive; + + /** Indique si la vibration est activée pour ce canal */ + private Boolean vibrationActive; + + /** Indique si la LED est activée pour ce canal */ + private Boolean ledActive; + + /** Indique si ce canal peut être désactivé par l'utilisateur */ + private Boolean peutEtreDesactive; + + // Constructeurs, getters et setters + public PreferenceCanalNotificationDTO() {} + + public Boolean getActive() { + return active; + } + + public void setActive(Boolean active) { + this.active = active; + } + + public Integer getImportance() { + return importance; + } + + public void setImportance(Integer importance) { + this.importance = importance; + } + + public String getSonPersonnalise() { + return sonPersonnalise; + } + + public void setSonPersonnalise(String sonPersonnalise) { + this.sonPersonnalise = sonPersonnalise; + } + + public long[] getPatternVibration() { + return patternVibration; + } + + public void setPatternVibration(long[] patternVibration) { + this.patternVibration = patternVibration; + } + + public String getCouleurLED() { + return couleurLED; + } + + public void setCouleurLED(String couleurLED) { + this.couleurLED = couleurLED; + } + + public Boolean getSonActive() { + return sonActive; + } + + public void setSonActive(Boolean sonActive) { + this.sonActive = sonActive; + } + + public Boolean getVibrationActive() { + return vibrationActive; + } + + public void setVibrationActive(Boolean vibrationActive) { + this.vibrationActive = vibrationActive; + } + + public Boolean getLedActive() { + return ledActive; + } + + public void setLedActive(Boolean ledActive) { + this.ledActive = ledActive; + } + + public Boolean getPeutEtreDesactive() { + return peutEtreDesactive; + } + + public void setPeutEtreDesactive(Boolean peutEtreDesactive) { + this.peutEtreDesactive = peutEtreDesactive; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/notification/PreferenceTypeNotificationDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/notification/PreferenceTypeNotificationDTO.java index c251838..9c13ab1 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/notification/PreferenceTypeNotificationDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/notification/PreferenceTypeNotificationDTO.java @@ -1,132 +1,132 @@ -package dev.lions.unionflow.server.api.dto.notification; - -import com.fasterxml.jackson.annotation.JsonInclude; -import jakarta.validation.constraints.*; - -/** - * DTO pour les préférences spécifiques à un type de notification - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@JsonInclude(JsonInclude.Include.NON_NULL) -public class PreferenceTypeNotificationDTO { - - /** Indique si ce type de notification est activé */ - private Boolean active; - - /** Priorité personnalisée (1-5) */ - @Min(value = 1, message = "La priorité doit être comprise entre 1 et 5") - @Max(value = 5, message = "La priorité doit être comprise entre 1 et 5") - private Integer priorite; - - /** Son personnalisé pour ce type */ - private String sonPersonnalise; - - /** Pattern de vibration personnalisé */ - private long[] patternVibration; - - /** Couleur LED personnalisée */ - private String couleurLED; - - /** Durée d'affichage personnalisée (secondes) */ - @Min(value = 1, message = "La durée d'affichage doit être au moins 1 seconde") - @Max(value = 300, message = "La durée d'affichage ne peut pas dépasser 5 minutes") - private Integer dureeAffichageSecondes; - - /** Indique si les notifications de ce type doivent vibrer */ - private Boolean doitVibrer; - - /** Indique si les notifications de ce type doivent émettre un son */ - private Boolean doitEmettreSon; - - /** Indique si les notifications de ce type doivent allumer la LED */ - private Boolean doitAllumerLED; - - /** Indique si ce type ignore le mode silencieux */ - private Boolean ignoreModesilencieux; - - // Constructeurs, getters et setters - public PreferenceTypeNotificationDTO() {} - - public Boolean getActive() { - return active; - } - - public void setActive(Boolean active) { - this.active = active; - } - - public Integer getPriorite() { - return priorite; - } - - public void setPriorite(Integer priorite) { - this.priorite = priorite; - } - - public String getSonPersonnalise() { - return sonPersonnalise; - } - - public void setSonPersonnalise(String sonPersonnalise) { - this.sonPersonnalise = sonPersonnalise; - } - - public long[] getPatternVibration() { - return patternVibration; - } - - public void setPatternVibration(long[] patternVibration) { - this.patternVibration = patternVibration; - } - - public String getCouleurLED() { - return couleurLED; - } - - public void setCouleurLED(String couleurLED) { - this.couleurLED = couleurLED; - } - - public Integer getDureeAffichageSecondes() { - return dureeAffichageSecondes; - } - - public void setDureeAffichageSecondes(Integer dureeAffichageSecondes) { - this.dureeAffichageSecondes = dureeAffichageSecondes; - } - - public Boolean getDoitVibrer() { - return doitVibrer; - } - - public void setDoitVibrer(Boolean doitVibrer) { - this.doitVibrer = doitVibrer; - } - - public Boolean getDoitEmettreSon() { - return doitEmettreSon; - } - - public void setDoitEmettreSon(Boolean doitEmettreSon) { - this.doitEmettreSon = doitEmettreSon; - } - - public Boolean getDoitAllumerLED() { - return doitAllumerLED; - } - - public void setDoitAllumerLED(Boolean doitAllumerLED) { - this.doitAllumerLED = doitAllumerLED; - } - - public Boolean getIgnoreModeSilencieux() { - return ignoreModesilencieux; - } - - public void setIgnoreModeSilencieux(Boolean ignoreModesilencieux) { - this.ignoreModesilencieux = ignoreModesilencieux; - } -} +package dev.lions.unionflow.server.api.dto.notification; + +import com.fasterxml.jackson.annotation.JsonInclude; +import jakarta.validation.constraints.*; + +/** + * DTO pour les préférences spécifiques à un type de notification + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@JsonInclude(JsonInclude.Include.NON_NULL) +public class PreferenceTypeNotificationDTO { + + /** Indique si ce type de notification est activé */ + private Boolean active; + + /** Priorité personnalisée (1-5) */ + @Min(value = 1, message = "La priorité doit être comprise entre 1 et 5") + @Max(value = 5, message = "La priorité doit être comprise entre 1 et 5") + private Integer priorite; + + /** Son personnalisé pour ce type */ + private String sonPersonnalise; + + /** Pattern de vibration personnalisé */ + private long[] patternVibration; + + /** Couleur LED personnalisée */ + private String couleurLED; + + /** Durée d'affichage personnalisée (secondes) */ + @Min(value = 1, message = "La durée d'affichage doit être au moins 1 seconde") + @Max(value = 300, message = "La durée d'affichage ne peut pas dépasser 5 minutes") + private Integer dureeAffichageSecondes; + + /** Indique si les notifications de ce type doivent vibrer */ + private Boolean doitVibrer; + + /** Indique si les notifications de ce type doivent émettre un son */ + private Boolean doitEmettreSon; + + /** Indique si les notifications de ce type doivent allumer la LED */ + private Boolean doitAllumerLED; + + /** Indique si ce type ignore le mode silencieux */ + private Boolean ignoreModesilencieux; + + // Constructeurs, getters et setters + public PreferenceTypeNotificationDTO() {} + + public Boolean getActive() { + return active; + } + + public void setActive(Boolean active) { + this.active = active; + } + + public Integer getPriorite() { + return priorite; + } + + public void setPriorite(Integer priorite) { + this.priorite = priorite; + } + + public String getSonPersonnalise() { + return sonPersonnalise; + } + + public void setSonPersonnalise(String sonPersonnalise) { + this.sonPersonnalise = sonPersonnalise; + } + + public long[] getPatternVibration() { + return patternVibration; + } + + public void setPatternVibration(long[] patternVibration) { + this.patternVibration = patternVibration; + } + + public String getCouleurLED() { + return couleurLED; + } + + public void setCouleurLED(String couleurLED) { + this.couleurLED = couleurLED; + } + + public Integer getDureeAffichageSecondes() { + return dureeAffichageSecondes; + } + + public void setDureeAffichageSecondes(Integer dureeAffichageSecondes) { + this.dureeAffichageSecondes = dureeAffichageSecondes; + } + + public Boolean getDoitVibrer() { + return doitVibrer; + } + + public void setDoitVibrer(Boolean doitVibrer) { + this.doitVibrer = doitVibrer; + } + + public Boolean getDoitEmettreSon() { + return doitEmettreSon; + } + + public void setDoitEmettreSon(Boolean doitEmettreSon) { + this.doitEmettreSon = doitEmettreSon; + } + + public Boolean getDoitAllumerLED() { + return doitAllumerLED; + } + + public void setDoitAllumerLED(Boolean doitAllumerLED) { + this.doitAllumerLED = doitAllumerLED; + } + + public Boolean getIgnoreModeSilencieux() { + return ignoreModesilencieux; + } + + public void setIgnoreModeSilencieux(Boolean ignoreModesilencieux) { + this.ignoreModesilencieux = ignoreModesilencieux; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/notification/PreferencesNotificationDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/notification/PreferencesNotificationDTO.java index a15ffc4..7770304 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/notification/PreferencesNotificationDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/notification/PreferencesNotificationDTO.java @@ -1,636 +1,636 @@ -package dev.lions.unionflow.server.api.dto.notification; - -import com.fasterxml.jackson.annotation.JsonFormat; -import com.fasterxml.jackson.annotation.JsonInclude; -import dev.lions.unionflow.server.api.enums.notification.CanalNotification; -import dev.lions.unionflow.server.api.enums.notification.TypeNotification; -import jakarta.validation.constraints.*; -import java.time.LocalTime; -import java.util.Map; -import java.util.Set; - -/** - * DTO pour les préférences de notification d'un utilisateur - * - *

Ce DTO représente les préférences personnalisées d'un utilisateur concernant la réception et - * l'affichage des notifications. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@JsonInclude(JsonInclude.Include.NON_NULL) -public class PreferencesNotificationDTO { - - /** Identifiant unique des préférences */ - private String id; - - /** Identifiant de l'utilisateur */ - @NotBlank(message = "L'identifiant utilisateur est obligatoire") - private String utilisateurId; - - /** Identifiant de l'organisation */ - private String organisationId; - - /** Indique si les notifications sont activées globalement */ - @NotNull(message = "L'activation globale des notifications est obligatoire") - private Boolean notificationsActivees; - - /** Indique si les notifications push sont activées */ - private Boolean pushActivees; - - /** Indique si les notifications par email sont activées */ - private Boolean emailActivees; - - /** Indique si les notifications SMS sont activées */ - private Boolean smsActivees; - - /** Indique si les notifications in-app sont activées */ - private Boolean inAppActivees; - - /** Types de notifications activés */ - private Set typesActives; - - /** Types de notifications désactivés */ - private Set typesDesactivees; - - /** Canaux de notification activés */ - private Set canauxActifs; - - /** Canaux de notification désactivés */ - private Set canauxDesactives; - - /** Mode Ne Pas Déranger activé */ - private Boolean modeSilencieux; - - /** Heure de début du mode silencieux */ - @JsonFormat(pattern = "HH:mm") - private LocalTime heureDebutSilencieux; - - /** Heure de fin du mode silencieux */ - @JsonFormat(pattern = "HH:mm") - private LocalTime heureFinSilencieux; - - /** Jours de la semaine pour le mode silencieux (1=Lundi, 7=Dimanche) */ - private Set joursSilencieux; - - /** Indique si les notifications urgentes passent outre le mode silencieux */ - private Boolean urgentesIgnorentSilencieux; - - /** Fréquence de regroupement des notifications (minutes) */ - @Min(value = 0, message = "La fréquence de regroupement doit être positive") - @Max(value = 1440, message = "La fréquence de regroupement ne peut pas dépasser 24h") - private Integer frequenceRegroupementMinutes; - - /** Nombre maximum de notifications affichées simultanément */ - @Min(value = 1, message = "Le nombre maximum de notifications doit être au moins 1") - @Max(value = 50, message = "Le nombre maximum de notifications ne peut pas dépasser 50") - private Integer maxNotificationsSimultanees; - - /** Durée d'affichage par défaut des notifications (secondes) */ - @Min(value = 1, message = "La durée d'affichage doit être au moins 1 seconde") - @Max(value = 300, message = "La durée d'affichage ne peut pas dépasser 5 minutes") - private Integer dureeAffichageSecondes; - - /** Indique si les notifications doivent vibrer */ - private Boolean vibrationActivee; - - /** Indique si les notifications doivent émettre un son */ - private Boolean sonActive; - - /** Indique si la LED doit s'allumer */ - private Boolean ledActivee; - - /** Son personnalisé pour les notifications */ - private String sonPersonnalise; - - /** Pattern de vibration personnalisé */ - private long[] patternVibrationPersonnalise; - - /** Couleur de LED personnalisée */ - private String couleurLEDPersonnalisee; - - /** Indique si les aperçus de contenu sont affichés sur l'écran de verrouillage */ - private Boolean apercuEcranVerrouillage; - - /** Indique si les notifications sont affichées dans l'historique */ - private Boolean affichageHistorique; - - /** Durée de conservation dans l'historique (jours) */ - @Min(value = 1, message = "La durée de conservation doit être au moins 1 jour") - @Max(value = 365, message = "La durée de conservation ne peut pas dépasser 1 an") - private Integer dureeConservationJours; - - /** Indique si les notifications sont automatiquement marquées comme lues */ - private Boolean marquageLectureAutomatique; - - /** Délai avant marquage automatique comme lu (secondes) */ - private Integer delaiMarquageLectureSecondes; - - /** Indique si les notifications sont automatiquement archivées */ - private Boolean archivageAutomatique; - - /** Délai avant archivage automatique (heures) */ - private Integer delaiArchivageHeures; - - /** Préférences par type de notification */ - private Map preferencesParType; - - /** Préférences par canal de notification */ - private Map preferencesParCanal; - - /** Mots-clés pour filtrage automatique */ - private Set motsClesFiltre; - - /** Expéditeurs bloqués */ - private Set expediteursBloqués; - - /** Expéditeurs prioritaires */ - private Set expediteursPrioritaires; - - /** Indique si les notifications de test sont activées */ - private Boolean notificationsTestActivees; - - /** Niveau de log pour les notifications (DEBUG, INFO, WARN, ERROR) */ - private String niveauLog; - - /** Token FCM pour les notifications push */ - private String tokenFCM; - - /** Plateforme de l'appareil (android, ios, web) */ - private String plateforme; - - /** Version de l'application */ - private String versionApp; - - /** Langue préférée pour les notifications */ - private String langue; - - /** Fuseau horaire de l'utilisateur */ - private String fuseauHoraire; - - /** Métadonnées personnalisées */ - private Map metadonnees; - - // === CONSTRUCTEURS === - - /** Constructeur par défaut avec valeurs par défaut */ - public PreferencesNotificationDTO() { - this.notificationsActivees = true; - this.pushActivees = true; - this.emailActivees = true; - this.smsActivees = false; - this.inAppActivees = true; - this.modeSilencieux = false; - this.urgentesIgnorentSilencieux = true; - this.frequenceRegroupementMinutes = 5; - this.maxNotificationsSimultanees = 10; - this.dureeAffichageSecondes = 10; - this.vibrationActivee = true; - this.sonActive = true; - this.ledActivee = true; - this.apercuEcranVerrouillage = true; - this.affichageHistorique = true; - this.dureeConservationJours = 30; - this.marquageLectureAutomatique = false; - this.archivageAutomatique = true; - this.delaiArchivageHeures = 168; // 1 semaine - this.notificationsTestActivees = false; - this.niveauLog = "INFO"; - this.langue = "fr"; - } - - /** Constructeur avec utilisateur */ - public PreferencesNotificationDTO(String utilisateurId) { - this(); - this.utilisateurId = utilisateurId; - } - - // === GETTERS ET SETTERS === - - public String getId() { - return id; - } - - public void setId(String id) { - this.id = id; - } - - public String getUtilisateurId() { - return utilisateurId; - } - - public void setUtilisateurId(String utilisateurId) { - this.utilisateurId = utilisateurId; - } - - public String getOrganisationId() { - return organisationId; - } - - public void setOrganisationId(String organisationId) { - this.organisationId = organisationId; - } - - public Boolean getNotificationsActivees() { - return notificationsActivees; - } - - public void setNotificationsActivees(Boolean notificationsActivees) { - this.notificationsActivees = notificationsActivees; - } - - public Boolean getPushActivees() { - return pushActivees; - } - - public void setPushActivees(Boolean pushActivees) { - this.pushActivees = pushActivees; - } - - public Boolean getEmailActivees() { - return emailActivees; - } - - public void setEmailActivees(Boolean emailActivees) { - this.emailActivees = emailActivees; - } - - public Boolean getSmsActivees() { - return smsActivees; - } - - public void setSmsActivees(Boolean smsActivees) { - this.smsActivees = smsActivees; - } - - public Boolean getInAppActivees() { - return inAppActivees; - } - - public void setInAppActivees(Boolean inAppActivees) { - this.inAppActivees = inAppActivees; - } - - public Set getTypesActives() { - return typesActives; - } - - public void setTypesActives(Set typesActives) { - this.typesActives = typesActives; - } - - public Set getTypesDesactivees() { - return typesDesactivees; - } - - public void setTypesDesactivees(Set typesDesactivees) { - this.typesDesactivees = typesDesactivees; - } - - public Set getCanauxActifs() { - return canauxActifs; - } - - public void setCanauxActifs(Set canauxActifs) { - this.canauxActifs = canauxActifs; - } - - public Set getCanauxDesactives() { - return canauxDesactives; - } - - public void setCanauxDesactives(Set canauxDesactives) { - this.canauxDesactives = canauxDesactives; - } - - public Boolean getModeSilencieux() { - return modeSilencieux; - } - - public void setModeSilencieux(Boolean modeSilencieux) { - this.modeSilencieux = modeSilencieux; - } - - public LocalTime getHeureDebutSilencieux() { - return heureDebutSilencieux; - } - - public void setHeureDebutSilencieux(LocalTime heureDebutSilencieux) { - this.heureDebutSilencieux = heureDebutSilencieux; - } - - public LocalTime getHeureFinSilencieux() { - return heureFinSilencieux; - } - - public void setHeureFinSilencieux(LocalTime heureFinSilencieux) { - this.heureFinSilencieux = heureFinSilencieux; - } - - public Set getJoursSilencieux() { - return joursSilencieux; - } - - public void setJoursSilencieux(Set joursSilencieux) { - this.joursSilencieux = joursSilencieux; - } - - public Boolean getUrgentesIgnorentSilencieux() { - return urgentesIgnorentSilencieux; - } - - public void setUrgentesIgnorentSilencieux(Boolean urgentesIgnorentSilencieux) { - this.urgentesIgnorentSilencieux = urgentesIgnorentSilencieux; - } - - public Integer getFrequenceRegroupementMinutes() { - return frequenceRegroupementMinutes; - } - - public void setFrequenceRegroupementMinutes(Integer frequenceRegroupementMinutes) { - this.frequenceRegroupementMinutes = frequenceRegroupementMinutes; - } - - public Integer getMaxNotificationsSimultanees() { - return maxNotificationsSimultanees; - } - - public void setMaxNotificationsSimultanees(Integer maxNotificationsSimultanees) { - this.maxNotificationsSimultanees = maxNotificationsSimultanees; - } - - public Integer getDureeAffichageSecondes() { - return dureeAffichageSecondes; - } - - public void setDureeAffichageSecondes(Integer dureeAffichageSecondes) { - this.dureeAffichageSecondes = dureeAffichageSecondes; - } - - public Boolean getVibrationActivee() { - return vibrationActivee; - } - - public void setVibrationActivee(Boolean vibrationActivee) { - this.vibrationActivee = vibrationActivee; - } - - public Boolean getSonActive() { - return sonActive; - } - - public void setSonActive(Boolean sonActive) { - this.sonActive = sonActive; - } - - public Boolean getLedActivee() { - return ledActivee; - } - - public void setLedActivee(Boolean ledActivee) { - this.ledActivee = ledActivee; - } - - public String getSonPersonnalise() { - return sonPersonnalise; - } - - public void setSonPersonnalise(String sonPersonnalise) { - this.sonPersonnalise = sonPersonnalise; - } - - public long[] getPatternVibrationPersonnalise() { - return patternVibrationPersonnalise; - } - - public void setPatternVibrationPersonnalise(long[] patternVibrationPersonnalise) { - this.patternVibrationPersonnalise = patternVibrationPersonnalise; - } - - public String getCouleurLEDPersonnalisee() { - return couleurLEDPersonnalisee; - } - - public void setCouleurLEDPersonnalisee(String couleurLEDPersonnalisee) { - this.couleurLEDPersonnalisee = couleurLEDPersonnalisee; - } - - public Boolean getApercuEcranVerrouillage() { - return apercuEcranVerrouillage; - } - - public void setApercuEcranVerrouillage(Boolean apercuEcranVerrouillage) { - this.apercuEcranVerrouillage = apercuEcranVerrouillage; - } - - public Boolean getAffichageHistorique() { - return affichageHistorique; - } - - public void setAffichageHistorique(Boolean affichageHistorique) { - this.affichageHistorique = affichageHistorique; - } - - public Integer getDureeConservationJours() { - return dureeConservationJours; - } - - public void setDureeConservationJours(Integer dureeConservationJours) { - this.dureeConservationJours = dureeConservationJours; - } - - public Boolean getMarquageLectureAutomatique() { - return marquageLectureAutomatique; - } - - public void setMarquageLectureAutomatique(Boolean marquageLectureAutomatique) { - this.marquageLectureAutomatique = marquageLectureAutomatique; - } - - public Integer getDelaiMarquageLectureSecondes() { - return delaiMarquageLectureSecondes; - } - - public void setDelaiMarquageLectureSecondes(Integer delaiMarquageLectureSecondes) { - this.delaiMarquageLectureSecondes = delaiMarquageLectureSecondes; - } - - public Boolean getArchivageAutomatique() { - return archivageAutomatique; - } - - public void setArchivageAutomatique(Boolean archivageAutomatique) { - this.archivageAutomatique = archivageAutomatique; - } - - public Integer getDelaiArchivageHeures() { - return delaiArchivageHeures; - } - - public void setDelaiArchivageHeures(Integer delaiArchivageHeures) { - this.delaiArchivageHeures = delaiArchivageHeures; - } - - public Map getPreferencesParType() { - return preferencesParType; - } - - public void setPreferencesParType( - Map preferencesParType) { - this.preferencesParType = preferencesParType; - } - - public Map getPreferencesParCanal() { - return preferencesParCanal; - } - - public void setPreferencesParCanal( - Map preferencesParCanal) { - this.preferencesParCanal = preferencesParCanal; - } - - public Set getMotsClesFiltre() { - return motsClesFiltre; - } - - public void setMotsClesFiltre(Set motsClesFiltre) { - this.motsClesFiltre = motsClesFiltre; - } - - public Set getExpediteursBloques() { - return expediteursBloqués; - } - - public void setExpediteursBloques(Set expediteursBloqués) { - this.expediteursBloqués = expediteursBloqués; - } - - public Set getExpediteursPrioritaires() { - return expediteursPrioritaires; - } - - public void setExpediteursPrioritaires(Set expediteursPrioritaires) { - this.expediteursPrioritaires = expediteursPrioritaires; - } - - public Boolean getNotificationsTestActivees() { - return notificationsTestActivees; - } - - public void setNotificationsTestActivees(Boolean notificationsTestActivees) { - this.notificationsTestActivees = notificationsTestActivees; - } - - public String getNiveauLog() { - return niveauLog; - } - - public void setNiveauLog(String niveauLog) { - this.niveauLog = niveauLog; - } - - public String getTokenFCM() { - return tokenFCM; - } - - public void setTokenFCM(String tokenFCM) { - this.tokenFCM = tokenFCM; - } - - public String getPlateforme() { - return plateforme; - } - - public void setPlateforme(String plateforme) { - this.plateforme = plateforme; - } - - public String getVersionApp() { - return versionApp; - } - - public void setVersionApp(String versionApp) { - this.versionApp = versionApp; - } - - public String getLangue() { - return langue; - } - - public void setLangue(String langue) { - this.langue = langue; - } - - public String getFuseauHoraire() { - return fuseauHoraire; - } - - public void setFuseauHoraire(String fuseauHoraire) { - this.fuseauHoraire = fuseauHoraire; - } - - public Map getMetadonnees() { - return metadonnees; - } - - public void setMetadonnees(Map metadonnees) { - this.metadonnees = metadonnees; - } - - // === MÉTHODES UTILITAIRES === - - /** Vérifie si un type de notification est activé */ - public boolean isTypeActive(TypeNotification type) { - if (!notificationsActivees) return false; - if (typesDesactivees != null && typesDesactivees.contains(type)) return false; - if (typesActives != null) return typesActives.contains(type); - return type.isActiveeParDefaut(); - } - - /** Vérifie si un canal de notification est activé */ - public boolean isCanalActif(CanalNotification canal) { - if (!notificationsActivees) return false; - if (canauxDesactives != null && canauxDesactives.contains(canal)) return false; - if (canauxActifs != null) return canauxActifs.contains(canal); - return true; - } - - /** - * Version de test de isEnModeSilencieux avec une heure fixe - * Permet de tester toutes les branches sans dépendre de l'heure actuelle - */ - boolean isEnModeSilencieux(LocalTime heureActuelle) { - if (!modeSilencieux) return false; - if (heureDebutSilencieux == null || heureFinSilencieux == null) return false; - - // Gestion du cas où la période traverse minuit - if (heureDebutSilencieux.isAfter(heureFinSilencieux)) { - return heureActuelle.isAfter(heureDebutSilencieux) || heureActuelle.isBefore(heureFinSilencieux); - } else { - return heureActuelle.isAfter(heureDebutSilencieux) && heureActuelle.isBefore(heureFinSilencieux); - } - } - - /** Vérifie si on est en mode silencieux actuellement */ - public boolean isEnModeSilencieux() { - return isEnModeSilencieux(LocalTime.now()); - } - - /** Vérifie si un expéditeur est bloqué */ - public boolean isExpediteurBloque(String expediteurId) { - return expediteursBloqués != null && expediteursBloqués.contains(expediteurId); - } - - /** Vérifie si un expéditeur est prioritaire */ - public boolean isExpediteurPrioritaire(String expediteurId) { - return expediteursPrioritaires != null && expediteursPrioritaires.contains(expediteurId); - } - - @Override - public String toString() { - return String.format( - "PreferencesNotificationDTO{utilisateurId='%s', notificationsActivees=%s}", - utilisateurId, notificationsActivees); - } -} +package dev.lions.unionflow.server.api.dto.notification; + +import com.fasterxml.jackson.annotation.JsonFormat; +import com.fasterxml.jackson.annotation.JsonInclude; +import dev.lions.unionflow.server.api.enums.notification.CanalNotification; +import dev.lions.unionflow.server.api.enums.notification.TypeNotification; +import jakarta.validation.constraints.*; +import java.time.LocalTime; +import java.util.Map; +import java.util.Set; + +/** + * DTO pour les préférences de notification d'un utilisateur + * + *

Ce DTO représente les préférences personnalisées d'un utilisateur concernant la réception et + * l'affichage des notifications. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@JsonInclude(JsonInclude.Include.NON_NULL) +public class PreferencesNotificationDTO { + + /** Identifiant unique des préférences */ + private String id; + + /** Identifiant de l'utilisateur */ + @NotBlank(message = "L'identifiant utilisateur est obligatoire") + private String utilisateurId; + + /** Identifiant de l'organisation */ + private String organisationId; + + /** Indique si les notifications sont activées globalement */ + @NotNull(message = "L'activation globale des notifications est obligatoire") + private Boolean notificationsActivees; + + /** Indique si les notifications push sont activées */ + private Boolean pushActivees; + + /** Indique si les notifications par email sont activées */ + private Boolean emailActivees; + + /** Indique si les notifications SMS sont activées */ + private Boolean smsActivees; + + /** Indique si les notifications in-app sont activées */ + private Boolean inAppActivees; + + /** Types de notifications activés */ + private Set typesActives; + + /** Types de notifications désactivés */ + private Set typesDesactivees; + + /** Canaux de notification activés */ + private Set canauxActifs; + + /** Canaux de notification désactivés */ + private Set canauxDesactives; + + /** Mode Ne Pas Déranger activé */ + private Boolean modeSilencieux; + + /** Heure de début du mode silencieux */ + @JsonFormat(pattern = "HH:mm") + private LocalTime heureDebutSilencieux; + + /** Heure de fin du mode silencieux */ + @JsonFormat(pattern = "HH:mm") + private LocalTime heureFinSilencieux; + + /** Jours de la semaine pour le mode silencieux (1=Lundi, 7=Dimanche) */ + private Set joursSilencieux; + + /** Indique si les notifications urgentes passent outre le mode silencieux */ + private Boolean urgentesIgnorentSilencieux; + + /** Fréquence de regroupement des notifications (minutes) */ + @Min(value = 0, message = "La fréquence de regroupement doit être positive") + @Max(value = 1440, message = "La fréquence de regroupement ne peut pas dépasser 24h") + private Integer frequenceRegroupementMinutes; + + /** Nombre maximum de notifications affichées simultanément */ + @Min(value = 1, message = "Le nombre maximum de notifications doit être au moins 1") + @Max(value = 50, message = "Le nombre maximum de notifications ne peut pas dépasser 50") + private Integer maxNotificationsSimultanees; + + /** Durée d'affichage par défaut des notifications (secondes) */ + @Min(value = 1, message = "La durée d'affichage doit être au moins 1 seconde") + @Max(value = 300, message = "La durée d'affichage ne peut pas dépasser 5 minutes") + private Integer dureeAffichageSecondes; + + /** Indique si les notifications doivent vibrer */ + private Boolean vibrationActivee; + + /** Indique si les notifications doivent émettre un son */ + private Boolean sonActive; + + /** Indique si la LED doit s'allumer */ + private Boolean ledActivee; + + /** Son personnalisé pour les notifications */ + private String sonPersonnalise; + + /** Pattern de vibration personnalisé */ + private long[] patternVibrationPersonnalise; + + /** Couleur de LED personnalisée */ + private String couleurLEDPersonnalisee; + + /** Indique si les aperçus de contenu sont affichés sur l'écran de verrouillage */ + private Boolean apercuEcranVerrouillage; + + /** Indique si les notifications sont affichées dans l'historique */ + private Boolean affichageHistorique; + + /** Durée de conservation dans l'historique (jours) */ + @Min(value = 1, message = "La durée de conservation doit être au moins 1 jour") + @Max(value = 365, message = "La durée de conservation ne peut pas dépasser 1 an") + private Integer dureeConservationJours; + + /** Indique si les notifications sont automatiquement marquées comme lues */ + private Boolean marquageLectureAutomatique; + + /** Délai avant marquage automatique comme lu (secondes) */ + private Integer delaiMarquageLectureSecondes; + + /** Indique si les notifications sont automatiquement archivées */ + private Boolean archivageAutomatique; + + /** Délai avant archivage automatique (heures) */ + private Integer delaiArchivageHeures; + + /** Préférences par type de notification */ + private Map preferencesParType; + + /** Préférences par canal de notification */ + private Map preferencesParCanal; + + /** Mots-clés pour filtrage automatique */ + private Set motsClesFiltre; + + /** Expéditeurs bloqués */ + private Set expediteursBloqués; + + /** Expéditeurs prioritaires */ + private Set expediteursPrioritaires; + + /** Indique si les notifications de test sont activées */ + private Boolean notificationsTestActivees; + + /** Niveau de log pour les notifications (DEBUG, INFO, WARN, ERROR) */ + private String niveauLog; + + /** Token FCM pour les notifications push */ + private String tokenFCM; + + /** Plateforme de l'appareil (android, ios, web) */ + private String plateforme; + + /** Version de l'application */ + private String versionApp; + + /** Langue préférée pour les notifications */ + private String langue; + + /** Fuseau horaire de l'utilisateur */ + private String fuseauHoraire; + + /** Métadonnées personnalisées */ + private Map metadonnees; + + // === CONSTRUCTEURS === + + /** Constructeur par défaut avec valeurs par défaut */ + public PreferencesNotificationDTO() { + this.notificationsActivees = true; + this.pushActivees = true; + this.emailActivees = true; + this.smsActivees = false; + this.inAppActivees = true; + this.modeSilencieux = false; + this.urgentesIgnorentSilencieux = true; + this.frequenceRegroupementMinutes = 5; + this.maxNotificationsSimultanees = 10; + this.dureeAffichageSecondes = 10; + this.vibrationActivee = true; + this.sonActive = true; + this.ledActivee = true; + this.apercuEcranVerrouillage = true; + this.affichageHistorique = true; + this.dureeConservationJours = 30; + this.marquageLectureAutomatique = false; + this.archivageAutomatique = true; + this.delaiArchivageHeures = 168; // 1 semaine + this.notificationsTestActivees = false; + this.niveauLog = "INFO"; + this.langue = "fr"; + } + + /** Constructeur avec utilisateur */ + public PreferencesNotificationDTO(String utilisateurId) { + this(); + this.utilisateurId = utilisateurId; + } + + // === GETTERS ET SETTERS === + + public String getId() { + return id; + } + + public void setId(String id) { + this.id = id; + } + + public String getUtilisateurId() { + return utilisateurId; + } + + public void setUtilisateurId(String utilisateurId) { + this.utilisateurId = utilisateurId; + } + + public String getOrganisationId() { + return organisationId; + } + + public void setOrganisationId(String organisationId) { + this.organisationId = organisationId; + } + + public Boolean getNotificationsActivees() { + return notificationsActivees; + } + + public void setNotificationsActivees(Boolean notificationsActivees) { + this.notificationsActivees = notificationsActivees; + } + + public Boolean getPushActivees() { + return pushActivees; + } + + public void setPushActivees(Boolean pushActivees) { + this.pushActivees = pushActivees; + } + + public Boolean getEmailActivees() { + return emailActivees; + } + + public void setEmailActivees(Boolean emailActivees) { + this.emailActivees = emailActivees; + } + + public Boolean getSmsActivees() { + return smsActivees; + } + + public void setSmsActivees(Boolean smsActivees) { + this.smsActivees = smsActivees; + } + + public Boolean getInAppActivees() { + return inAppActivees; + } + + public void setInAppActivees(Boolean inAppActivees) { + this.inAppActivees = inAppActivees; + } + + public Set getTypesActives() { + return typesActives; + } + + public void setTypesActives(Set typesActives) { + this.typesActives = typesActives; + } + + public Set getTypesDesactivees() { + return typesDesactivees; + } + + public void setTypesDesactivees(Set typesDesactivees) { + this.typesDesactivees = typesDesactivees; + } + + public Set getCanauxActifs() { + return canauxActifs; + } + + public void setCanauxActifs(Set canauxActifs) { + this.canauxActifs = canauxActifs; + } + + public Set getCanauxDesactives() { + return canauxDesactives; + } + + public void setCanauxDesactives(Set canauxDesactives) { + this.canauxDesactives = canauxDesactives; + } + + public Boolean getModeSilencieux() { + return modeSilencieux; + } + + public void setModeSilencieux(Boolean modeSilencieux) { + this.modeSilencieux = modeSilencieux; + } + + public LocalTime getHeureDebutSilencieux() { + return heureDebutSilencieux; + } + + public void setHeureDebutSilencieux(LocalTime heureDebutSilencieux) { + this.heureDebutSilencieux = heureDebutSilencieux; + } + + public LocalTime getHeureFinSilencieux() { + return heureFinSilencieux; + } + + public void setHeureFinSilencieux(LocalTime heureFinSilencieux) { + this.heureFinSilencieux = heureFinSilencieux; + } + + public Set getJoursSilencieux() { + return joursSilencieux; + } + + public void setJoursSilencieux(Set joursSilencieux) { + this.joursSilencieux = joursSilencieux; + } + + public Boolean getUrgentesIgnorentSilencieux() { + return urgentesIgnorentSilencieux; + } + + public void setUrgentesIgnorentSilencieux(Boolean urgentesIgnorentSilencieux) { + this.urgentesIgnorentSilencieux = urgentesIgnorentSilencieux; + } + + public Integer getFrequenceRegroupementMinutes() { + return frequenceRegroupementMinutes; + } + + public void setFrequenceRegroupementMinutes(Integer frequenceRegroupementMinutes) { + this.frequenceRegroupementMinutes = frequenceRegroupementMinutes; + } + + public Integer getMaxNotificationsSimultanees() { + return maxNotificationsSimultanees; + } + + public void setMaxNotificationsSimultanees(Integer maxNotificationsSimultanees) { + this.maxNotificationsSimultanees = maxNotificationsSimultanees; + } + + public Integer getDureeAffichageSecondes() { + return dureeAffichageSecondes; + } + + public void setDureeAffichageSecondes(Integer dureeAffichageSecondes) { + this.dureeAffichageSecondes = dureeAffichageSecondes; + } + + public Boolean getVibrationActivee() { + return vibrationActivee; + } + + public void setVibrationActivee(Boolean vibrationActivee) { + this.vibrationActivee = vibrationActivee; + } + + public Boolean getSonActive() { + return sonActive; + } + + public void setSonActive(Boolean sonActive) { + this.sonActive = sonActive; + } + + public Boolean getLedActivee() { + return ledActivee; + } + + public void setLedActivee(Boolean ledActivee) { + this.ledActivee = ledActivee; + } + + public String getSonPersonnalise() { + return sonPersonnalise; + } + + public void setSonPersonnalise(String sonPersonnalise) { + this.sonPersonnalise = sonPersonnalise; + } + + public long[] getPatternVibrationPersonnalise() { + return patternVibrationPersonnalise; + } + + public void setPatternVibrationPersonnalise(long[] patternVibrationPersonnalise) { + this.patternVibrationPersonnalise = patternVibrationPersonnalise; + } + + public String getCouleurLEDPersonnalisee() { + return couleurLEDPersonnalisee; + } + + public void setCouleurLEDPersonnalisee(String couleurLEDPersonnalisee) { + this.couleurLEDPersonnalisee = couleurLEDPersonnalisee; + } + + public Boolean getApercuEcranVerrouillage() { + return apercuEcranVerrouillage; + } + + public void setApercuEcranVerrouillage(Boolean apercuEcranVerrouillage) { + this.apercuEcranVerrouillage = apercuEcranVerrouillage; + } + + public Boolean getAffichageHistorique() { + return affichageHistorique; + } + + public void setAffichageHistorique(Boolean affichageHistorique) { + this.affichageHistorique = affichageHistorique; + } + + public Integer getDureeConservationJours() { + return dureeConservationJours; + } + + public void setDureeConservationJours(Integer dureeConservationJours) { + this.dureeConservationJours = dureeConservationJours; + } + + public Boolean getMarquageLectureAutomatique() { + return marquageLectureAutomatique; + } + + public void setMarquageLectureAutomatique(Boolean marquageLectureAutomatique) { + this.marquageLectureAutomatique = marquageLectureAutomatique; + } + + public Integer getDelaiMarquageLectureSecondes() { + return delaiMarquageLectureSecondes; + } + + public void setDelaiMarquageLectureSecondes(Integer delaiMarquageLectureSecondes) { + this.delaiMarquageLectureSecondes = delaiMarquageLectureSecondes; + } + + public Boolean getArchivageAutomatique() { + return archivageAutomatique; + } + + public void setArchivageAutomatique(Boolean archivageAutomatique) { + this.archivageAutomatique = archivageAutomatique; + } + + public Integer getDelaiArchivageHeures() { + return delaiArchivageHeures; + } + + public void setDelaiArchivageHeures(Integer delaiArchivageHeures) { + this.delaiArchivageHeures = delaiArchivageHeures; + } + + public Map getPreferencesParType() { + return preferencesParType; + } + + public void setPreferencesParType( + Map preferencesParType) { + this.preferencesParType = preferencesParType; + } + + public Map getPreferencesParCanal() { + return preferencesParCanal; + } + + public void setPreferencesParCanal( + Map preferencesParCanal) { + this.preferencesParCanal = preferencesParCanal; + } + + public Set getMotsClesFiltre() { + return motsClesFiltre; + } + + public void setMotsClesFiltre(Set motsClesFiltre) { + this.motsClesFiltre = motsClesFiltre; + } + + public Set getExpediteursBloques() { + return expediteursBloqués; + } + + public void setExpediteursBloques(Set expediteursBloqués) { + this.expediteursBloqués = expediteursBloqués; + } + + public Set getExpediteursPrioritaires() { + return expediteursPrioritaires; + } + + public void setExpediteursPrioritaires(Set expediteursPrioritaires) { + this.expediteursPrioritaires = expediteursPrioritaires; + } + + public Boolean getNotificationsTestActivees() { + return notificationsTestActivees; + } + + public void setNotificationsTestActivees(Boolean notificationsTestActivees) { + this.notificationsTestActivees = notificationsTestActivees; + } + + public String getNiveauLog() { + return niveauLog; + } + + public void setNiveauLog(String niveauLog) { + this.niveauLog = niveauLog; + } + + public String getTokenFCM() { + return tokenFCM; + } + + public void setTokenFCM(String tokenFCM) { + this.tokenFCM = tokenFCM; + } + + public String getPlateforme() { + return plateforme; + } + + public void setPlateforme(String plateforme) { + this.plateforme = plateforme; + } + + public String getVersionApp() { + return versionApp; + } + + public void setVersionApp(String versionApp) { + this.versionApp = versionApp; + } + + public String getLangue() { + return langue; + } + + public void setLangue(String langue) { + this.langue = langue; + } + + public String getFuseauHoraire() { + return fuseauHoraire; + } + + public void setFuseauHoraire(String fuseauHoraire) { + this.fuseauHoraire = fuseauHoraire; + } + + public Map getMetadonnees() { + return metadonnees; + } + + public void setMetadonnees(Map metadonnees) { + this.metadonnees = metadonnees; + } + + // === MÉTHODES UTILITAIRES === + + /** Vérifie si un type de notification est activé */ + public boolean isTypeActive(TypeNotification type) { + if (!notificationsActivees) return false; + if (typesDesactivees != null && typesDesactivees.contains(type)) return false; + if (typesActives != null) return typesActives.contains(type); + return type.isActiveeParDefaut(); + } + + /** Vérifie si un canal de notification est activé */ + public boolean isCanalActif(CanalNotification canal) { + if (!notificationsActivees) return false; + if (canauxDesactives != null && canauxDesactives.contains(canal)) return false; + if (canauxActifs != null) return canauxActifs.contains(canal); + return true; + } + + /** + * Version de test de isEnModeSilencieux avec une heure fixe + * Permet de tester toutes les branches sans dépendre de l'heure actuelle + */ + boolean isEnModeSilencieux(LocalTime heureActuelle) { + if (!modeSilencieux) return false; + if (heureDebutSilencieux == null || heureFinSilencieux == null) return false; + + // Gestion du cas où la période traverse minuit + if (heureDebutSilencieux.isAfter(heureFinSilencieux)) { + return heureActuelle.isAfter(heureDebutSilencieux) || heureActuelle.isBefore(heureFinSilencieux); + } else { + return heureActuelle.isAfter(heureDebutSilencieux) && heureActuelle.isBefore(heureFinSilencieux); + } + } + + /** Vérifie si on est en mode silencieux actuellement */ + public boolean isEnModeSilencieux() { + return isEnModeSilencieux(LocalTime.now()); + } + + /** Vérifie si un expéditeur est bloqué */ + public boolean isExpediteurBloque(String expediteurId) { + return expediteursBloqués != null && expediteursBloqués.contains(expediteurId); + } + + /** Vérifie si un expéditeur est prioritaire */ + public boolean isExpediteurPrioritaire(String expediteurId) { + return expediteursPrioritaires != null && expediteursPrioritaires.contains(expediteurId); + } + + @Override + public String toString() { + return String.format( + "PreferencesNotificationDTO{utilisateurId='%s', notificationsActivees=%s}", + utilisateurId, notificationsActivees); + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/CreateNotificationRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/CreateNotificationRequest.java index 5f55866..03834a1 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/CreateNotificationRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/CreateNotificationRequest.java @@ -1,25 +1,25 @@ -package dev.lions.unionflow.server.api.dto.notification.request; - -import jakarta.validation.constraints.NotNull; -import java.time.LocalDateTime; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'une notification. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreateNotificationRequest( - @NotNull(message = "Le type de notification est obligatoire") String typeNotification, - String priorite, - String sujet, - String corps, - LocalDateTime dateEnvoiPrevue, - String donneesAdditionnelles, - UUID membreId, - UUID organisationId, - UUID templateId) { -} +package dev.lions.unionflow.server.api.dto.notification.request; + +import jakarta.validation.constraints.NotNull; +import java.time.LocalDateTime; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'une notification. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreateNotificationRequest( + @NotNull(message = "Le type de notification est obligatoire") String typeNotification, + String priorite, + String sujet, + String corps, + LocalDateTime dateEnvoiPrevue, + String donneesAdditionnelles, + UUID membreId, + UUID organisationId, + UUID templateId) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/CreateTemplateNotificationRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/CreateTemplateNotificationRequest.java index 55d0ff2..6c3a848 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/CreateTemplateNotificationRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/CreateTemplateNotificationRequest.java @@ -1,22 +1,22 @@ -package dev.lions.unionflow.server.api.dto.notification.request; - -import jakarta.validation.constraints.NotBlank; -import lombok.Builder; - -/** - * Requête de création d'un template de notification. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreateTemplateNotificationRequest( - @NotBlank(message = "Le code est obligatoire") String code, - String sujet, - String corpsTexte, - String corpsHtml, - String variablesDisponibles, - String canauxSupportes, - String langue, - String description) { -} +package dev.lions.unionflow.server.api.dto.notification.request; + +import jakarta.validation.constraints.NotBlank; +import lombok.Builder; + +/** + * Requête de création d'un template de notification. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreateTemplateNotificationRequest( + @NotBlank(message = "Le code est obligatoire") String code, + String sujet, + String corpsTexte, + String corpsHtml, + String variablesDisponibles, + String canauxSupportes, + String langue, + String description) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateNotificationRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateNotificationRequest.java index 2ef77e3..280f961 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateNotificationRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateNotificationRequest.java @@ -1,18 +1,18 @@ -package dev.lions.unionflow.server.api.dto.notification.request; - -import java.time.LocalDateTime; -import lombok.Builder; - -/** - * Requête de mise à jour d'une notification. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record UpdateNotificationRequest( - String statut, - LocalDateTime dateLecture, - Integer nombreTentatives, - String messageErreur) { -} +package dev.lions.unionflow.server.api.dto.notification.request; + +import java.time.LocalDateTime; +import lombok.Builder; + +/** + * Requête de mise à jour d'une notification. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record UpdateNotificationRequest( + String statut, + LocalDateTime dateLecture, + Integer nombreTentatives, + String messageErreur) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateTemplateNotificationRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateTemplateNotificationRequest.java index 53939d8..27d404e 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateTemplateNotificationRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateTemplateNotificationRequest.java @@ -1,22 +1,22 @@ -package dev.lions.unionflow.server.api.dto.notification.request; - -import jakarta.validation.constraints.NotBlank; -import lombok.Builder; - -/** - * Requête de mise à jour d'un template de notification. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record UpdateTemplateNotificationRequest( - @NotBlank(message = "Le code est obligatoire") String code, - String sujet, - String corpsTexte, - String corpsHtml, - String variablesDisponibles, - String canauxSupportes, - String langue, - String description) { -} +package dev.lions.unionflow.server.api.dto.notification.request; + +import jakarta.validation.constraints.NotBlank; +import lombok.Builder; + +/** + * Requête de mise à jour d'un template de notification. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record UpdateTemplateNotificationRequest( + @NotBlank(message = "Le code est obligatoire") String code, + String sujet, + String corpsTexte, + String corpsHtml, + String variablesDisponibles, + String canauxSupportes, + String langue, + String description) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/notification/response/NotificationResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/notification/response/NotificationResponse.java index 74ce59a..7d2f75b 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/notification/response/NotificationResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/notification/response/NotificationResponse.java @@ -1,40 +1,40 @@ -package dev.lions.unionflow.server.api.dto.notification.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.time.LocalDateTime; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse contenant les données d'une notification. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class NotificationResponse extends BaseResponse { - - private String typeNotification; - private String priorite; - private String statut; - private String sujet; - private String corps; - private LocalDateTime dateEnvoiPrevue; - private LocalDateTime dateEnvoi; - private LocalDateTime dateLecture; - private Integer nombreTentatives; - private String messageErreur; - private String donneesAdditionnelles; - private UUID membreId; - private UUID organisationId; - private UUID templateId; -} +package dev.lions.unionflow.server.api.dto.notification.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.time.LocalDateTime; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse contenant les données d'une notification. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class NotificationResponse extends BaseResponse { + + private String typeNotification; + private String priorite; + private String statut; + private String sujet; + private String corps; + private LocalDateTime dateEnvoiPrevue; + private LocalDateTime dateEnvoi; + private LocalDateTime dateLecture; + private Integer nombreTentatives; + private String messageErreur; + private String donneesAdditionnelles; + private UUID membreId; + private UUID organisationId; + private UUID templateId; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/notification/response/TemplateNotificationResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/notification/response/TemplateNotificationResponse.java index 1c3b726..012f069 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/notification/response/TemplateNotificationResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/notification/response/TemplateNotificationResponse.java @@ -1,32 +1,32 @@ -package dev.lions.unionflow.server.api.dto.notification.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse contenant les données d'un template de notification. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class TemplateNotificationResponse extends BaseResponse { - - private String code; - private String sujet; - private String corpsTexte; - private String corpsHtml; - private String variablesDisponibles; - private String canauxSupportes; - private String langue; - private String description; -} +package dev.lions.unionflow.server.api.dto.notification.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse contenant les données d'un template de notification. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class TemplateNotificationResponse extends BaseResponse { + + private String code; + private String sujet; + private String corpsTexte; + private String corpsHtml; + private String variablesDisponibles; + private String canauxSupportes; + private String langue; + private String description; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/ong/ProjetOngDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/ong/ProjetOngDTO.java index 4c4c876..e471797 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/ong/ProjetOngDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/ong/ProjetOngDTO.java @@ -1,35 +1,35 @@ -package dev.lions.unionflow.server.api.dto.ong; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.ong.StatutProjetOng; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; - -import java.math.BigDecimal; -import java.time.LocalDate; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class ProjetOngDTO extends BaseDTO { - - private String organisationId; - - private String nomProjet; - private String descriptionMandat; - - private String zoneGeographiqueIntervention; - - private BigDecimal budgetPrevisionnel; - private BigDecimal depensesReelles; - - private LocalDate dateLancement; - private LocalDate dateFinEstimee; - - private StatutProjetOng statut; -} +package dev.lions.unionflow.server.api.dto.ong; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.ong.StatutProjetOng; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; + +import java.math.BigDecimal; +import java.time.LocalDate; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class ProjetOngDTO extends BaseDTO { + + private String organisationId; + + private String nomProjet; + private String descriptionMandat; + + private String zoneGeographiqueIntervention; + + private BigDecimal budgetPrevisionnel; + private BigDecimal depensesReelles; + + private LocalDate dateLancement; + private LocalDate dateFinEstimee; + + private StatutProjetOng statut; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/organisation/request/CreateOrganisationRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/organisation/request/CreateOrganisationRequest.java index a15745e..c24fafe 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/organisation/request/CreateOrganisationRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/organisation/request/CreateOrganisationRequest.java @@ -1,81 +1,81 @@ -package dev.lions.unionflow.server.api.dto.organisation.request; - -import jakarta.validation.constraints.Email; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; - -import lombok.Builder; - -/** - * Requête de création d'une organisation. - * - *

- * Immutable via {@code record}. Exclut les - * champs d'audit et l'ID (générés côté serveur). - * - * @author UnionFlow Team - * @version 3.0 - * @since 2026-02-21 - * @param nom nom officiel - * @param nomCourt sigle - * @param description description - * @param email email principal - * @param telephone téléphone - * @param telephoneSecondaire téléphone 2 - * @param emailSecondaire email 2 - * @param siteWeb site web - * @param logo URL du logo - * @param reseauxSociaux réseaux sociaux - * @param typeOrganisation type (types_reference) - * @param statut statut initial - * @param dateFondation date de fondation - * @param numeroEnregistrement numéro légal - * @param devise code devise - * @param budgetAnnuel budget annuel - * @param cotisationObligatoire cotisation requise - * @param montantCotisationAnnuelle montant annuel - * @param objectifs objectifs - * @param activitesPrincipales activités - * @param certifications certifications - * @param partenaires partenaires - * @param notes notes internes - * @param latitude latitude GPS - * @param longitude longitude GPS - */ -@Builder -public record CreateOrganisationRequest( - @NotBlank @Size(max = 255) String nom, - @Size(max = 50) String nomCourt, - @Size(max = 2000) String description, - @NotBlank @Email @Size(max = 255) String email, - @Size(max = 20) String telephone, - @Size(max = 20) String telephoneSecondaire, - @Email @Size(max = 255) String emailSecondaire, - @Size(max = 500) String siteWeb, - @Size(max = 500) String logo, - @Size(max = 1000) String reseauxSociaux, - @Size(max = 50) String typeOrganisation, - @Size(max = 30) String statut, - LocalDate dateFondation, - @Size(max = 100) String numeroEnregistrement, - @Size(max = 3) String devise, - BigDecimal budgetAnnuel, - Boolean cotisationObligatoire, - BigDecimal montantCotisationAnnuelle, - @Size(max = 2000) String objectifs, - @Size(max = 2000) String activitesPrincipales, - @Size(max = 500) String certifications, - @Size(max = 1000) String partenaires, - @Size(max = 1000) String notes, - BigDecimal latitude, - BigDecimal longitude, - @Size(max = 500) String adresse, - @Size(max = 100) String ville, - @Size(max = 100) String region, - @Size(max = 100) String pays, - @Size(max = 20) String codePostal, - Boolean organisationPublique, - Boolean accepteNouveauxMembres) { -} +package dev.lions.unionflow.server.api.dto.organisation.request; + +import jakarta.validation.constraints.Email; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; + +import lombok.Builder; + +/** + * Requête de création d'une organisation. + * + *

+ * Immutable via {@code record}. Exclut les + * champs d'audit et l'ID (générés côté serveur). + * + * @author UnionFlow Team + * @version 3.0 + * @since 2026-02-21 + * @param nom nom officiel + * @param nomCourt sigle + * @param description description + * @param email email principal + * @param telephone téléphone + * @param telephoneSecondaire téléphone 2 + * @param emailSecondaire email 2 + * @param siteWeb site web + * @param logo URL du logo + * @param reseauxSociaux réseaux sociaux + * @param typeOrganisation type (types_reference) + * @param statut statut initial + * @param dateFondation date de fondation + * @param numeroEnregistrement numéro légal + * @param devise code devise + * @param budgetAnnuel budget annuel + * @param cotisationObligatoire cotisation requise + * @param montantCotisationAnnuelle montant annuel + * @param objectifs objectifs + * @param activitesPrincipales activités + * @param certifications certifications + * @param partenaires partenaires + * @param notes notes internes + * @param latitude latitude GPS + * @param longitude longitude GPS + */ +@Builder +public record CreateOrganisationRequest( + @NotBlank @Size(max = 255) String nom, + @Size(max = 50) String nomCourt, + @Size(max = 2000) String description, + @NotBlank @Email @Size(max = 255) String email, + @Size(max = 20) String telephone, + @Size(max = 20) String telephoneSecondaire, + @Email @Size(max = 255) String emailSecondaire, + @Size(max = 500) String siteWeb, + @Size(max = 500) String logo, + @Size(max = 1000) String reseauxSociaux, + @Size(max = 50) String typeOrganisation, + @Size(max = 30) String statut, + LocalDate dateFondation, + @Size(max = 100) String numeroEnregistrement, + @Size(max = 3) String devise, + BigDecimal budgetAnnuel, + Boolean cotisationObligatoire, + BigDecimal montantCotisationAnnuelle, + @Size(max = 2000) String objectifs, + @Size(max = 2000) String activitesPrincipales, + @Size(max = 500) String certifications, + @Size(max = 1000) String partenaires, + @Size(max = 1000) String notes, + BigDecimal latitude, + BigDecimal longitude, + @Size(max = 500) String adresse, + @Size(max = 100) String ville, + @Size(max = 100) String region, + @Size(max = 100) String pays, + @Size(max = 20) String codePostal, + Boolean organisationPublique, + Boolean accepteNouveauxMembres) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/organisation/request/UpdateOrganisationRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/organisation/request/UpdateOrganisationRequest.java index feda188..0701594 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/organisation/request/UpdateOrganisationRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/organisation/request/UpdateOrganisationRequest.java @@ -1,55 +1,55 @@ -package dev.lions.unionflow.server.api.dto.organisation.request; - -import jakarta.validation.constraints.Email; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; - -import lombok.Builder; - -/** - * Requête de mise à jour d'une organisation. - * - *

- * ID passé dans le path de l'URL. - * - * @author UnionFlow Team - * @version 3.0 - * @since 2026-02-22 - */ -@Builder -public record UpdateOrganisationRequest( - @NotBlank @Size(max = 255) String nom, - @Size(max = 50) String nomCourt, - @Size(max = 2000) String description, - @NotBlank @Email @Size(max = 255) String email, - @Size(max = 20) String telephone, - @Size(max = 20) String telephoneSecondaire, - @Email @Size(max = 255) String emailSecondaire, - @Size(max = 500) String siteWeb, - @Size(max = 500) String logo, - @Size(max = 1000) String reseauxSociaux, - @Size(max = 50) String typeOrganisation, - @Size(max = 30) String statut, - LocalDate dateFondation, - @Size(max = 100) String numeroEnregistrement, - @Size(max = 3) String devise, - BigDecimal budgetAnnuel, - Boolean cotisationObligatoire, - BigDecimal montantCotisationAnnuelle, - @Size(max = 2000) String objectifs, - @Size(max = 2000) String activitesPrincipales, - @Size(max = 500) String certifications, - @Size(max = 1000) String partenaires, - @Size(max = 1000) String notes, - BigDecimal latitude, - BigDecimal longitude, - @Size(max = 500) String adresse, - @Size(max = 100) String ville, - @Size(max = 100) String region, - @Size(max = 100) String pays, - @Size(max = 20) String codePostal, - Boolean organisationPublique, - Boolean accepteNouveauxMembres) { -} +package dev.lions.unionflow.server.api.dto.organisation.request; + +import jakarta.validation.constraints.Email; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; + +import lombok.Builder; + +/** + * Requête de mise à jour d'une organisation. + * + *

+ * ID passé dans le path de l'URL. + * + * @author UnionFlow Team + * @version 3.0 + * @since 2026-02-22 + */ +@Builder +public record UpdateOrganisationRequest( + @NotBlank @Size(max = 255) String nom, + @Size(max = 50) String nomCourt, + @Size(max = 2000) String description, + @NotBlank @Email @Size(max = 255) String email, + @Size(max = 20) String telephone, + @Size(max = 20) String telephoneSecondaire, + @Email @Size(max = 255) String emailSecondaire, + @Size(max = 500) String siteWeb, + @Size(max = 500) String logo, + @Size(max = 1000) String reseauxSociaux, + @Size(max = 50) String typeOrganisation, + @Size(max = 30) String statut, + LocalDate dateFondation, + @Size(max = 100) String numeroEnregistrement, + @Size(max = 3) String devise, + BigDecimal budgetAnnuel, + Boolean cotisationObligatoire, + BigDecimal montantCotisationAnnuelle, + @Size(max = 2000) String objectifs, + @Size(max = 2000) String activitesPrincipales, + @Size(max = 500) String certifications, + @Size(max = 1000) String partenaires, + @Size(max = 1000) String notes, + BigDecimal latitude, + BigDecimal longitude, + @Size(max = 500) String adresse, + @Size(max = 100) String ville, + @Size(max = 100) String region, + @Size(max = 100) String pays, + @Size(max = 20) String codePostal, + Boolean organisationPublique, + Boolean accepteNouveauxMembres) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/organisation/response/OrganisationResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/organisation/response/OrganisationResponse.java index eb7cf19..9d95704 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/organisation/response/OrganisationResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/organisation/response/OrganisationResponse.java @@ -1,94 +1,94 @@ -package dev.lions.unionflow.server.api.dto.organisation.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse contenant les données d'une organisation. - * - *

- * Classe Lombok (getters/setters) pour la - * compatibilité avec les frameworks d'affichage - * (PrimeFaces, etc.). - * - * @author UnionFlow Team - * @version 3.0 - * @since 2026-02-21 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class OrganisationResponse extends BaseResponse { - - // ── Identité ─────────────────────────────── - private String nom; - private String nomCourt; - private String description; - private String email; - private String telephone; - private String telephoneSecondaire; - private String emailSecondaire; - - // ── Web ──────────────────────────────────── - private String siteWeb; - private String logo; - private String reseauxSociaux; - - // ── Classification ───────────────────────── - private String typeOrganisation; - private String typeOrganisationLibelle; - private String statut; - private String statutLibelle; - private String statutSeverity; - private LocalDate dateFondation; - private String numeroEnregistrement; - - // ── Géographie ───────────────────────────── - private String adresse; - private String quartier; - private String ville; - private String region; - private String pays; - private String codePostal; - private BigDecimal latitude; - private BigDecimal longitude; - - // ── Hiérarchie ───────────────────────────── - private UUID organisationParenteId; - private String organisationParenteNom; - private Integer niveauHierarchique; - private Boolean estOrganisationRacine; - - // ── Finances ─────────────────────────────── - private String devise; - private BigDecimal budgetAnnuel; - private Boolean cotisationObligatoire; - private BigDecimal montantCotisationAnnuelle; - - // ── Statistiques ─────────────────────────── - private Integer nombreMembres; - private Integer nombreAdministrateurs; - /** Nombre d'événements (actifs) de l'organisation. */ - private Integer nombreEvenements; - - // ── Contenu ──────────────────────────────── - private String objectifs; - private String activitesPrincipales; - private String certifications; - private String partenaires; - private String notes; - - // ── Paramètres ───────────────────────────── - private Boolean organisationPublique; - private Boolean accepteNouveauxMembres; -} +package dev.lions.unionflow.server.api.dto.organisation.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse contenant les données d'une organisation. + * + *

+ * Classe Lombok (getters/setters) pour la + * compatibilité avec les frameworks d'affichage + * (PrimeFaces, etc.). + * + * @author UnionFlow Team + * @version 3.0 + * @since 2026-02-21 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class OrganisationResponse extends BaseResponse { + + // ── Identité ─────────────────────────────── + private String nom; + private String nomCourt; + private String description; + private String email; + private String telephone; + private String telephoneSecondaire; + private String emailSecondaire; + + // ── Web ──────────────────────────────────── + private String siteWeb; + private String logo; + private String reseauxSociaux; + + // ── Classification ───────────────────────── + private String typeOrganisation; + private String typeOrganisationLibelle; + private String statut; + private String statutLibelle; + private String statutSeverity; + private LocalDate dateFondation; + private String numeroEnregistrement; + + // ── Géographie ───────────────────────────── + private String adresse; + private String quartier; + private String ville; + private String region; + private String pays; + private String codePostal; + private BigDecimal latitude; + private BigDecimal longitude; + + // ── Hiérarchie ───────────────────────────── + private UUID organisationParenteId; + private String organisationParenteNom; + private Integer niveauHierarchique; + private Boolean estOrganisationRacine; + + // ── Finances ─────────────────────────────── + private String devise; + private BigDecimal budgetAnnuel; + private Boolean cotisationObligatoire; + private BigDecimal montantCotisationAnnuelle; + + // ── Statistiques ─────────────────────────── + private Integer nombreMembres; + private Integer nombreAdministrateurs; + /** Nombre d'événements (actifs) de l'organisation. */ + private Integer nombreEvenements; + + // ── Contenu ──────────────────────────────── + private String objectifs; + private String activitesPrincipales; + private String certifications; + private String partenaires; + private String notes; + + // ── Paramètres ───────────────────────────── + private Boolean organisationPublique; + private Boolean accepteNouveauxMembres; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/organisation/response/OrganisationSummaryResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/organisation/response/OrganisationSummaryResponse.java index b9122c4..05f33e8 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/organisation/response/OrganisationSummaryResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/organisation/response/OrganisationSummaryResponse.java @@ -1,33 +1,33 @@ -package dev.lions.unionflow.server.api.dto.organisation.response; - -import lombok.AllArgsConstructor; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.util.UUID; - -/** - * Résumé d'une organisation pour les listes. - * Classe JavaBean (pas un record) pour compatibilité JSF/EL (getNom() requis). - * - * @author UnionFlow Team - * @version 3.1 - * @since 2026-02-22 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -public class OrganisationSummaryResponse { - private UUID id; - private String nom; - private String nomCourt; - private String typeOrganisation; - private String typeOrganisationLibelle; - private String statut; - private String statutLibelle; - private String statutSeverity; - private Integer nombreMembres; - private Boolean actif; - private String ville; - private String pays; -} +package dev.lions.unionflow.server.api.dto.organisation.response; + +import lombok.AllArgsConstructor; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.util.UUID; + +/** + * Résumé d'une organisation pour les listes. + * Classe JavaBean (pas un record) pour compatibilité JSF/EL (getNom() requis). + * + * @author UnionFlow Team + * @version 3.1 + * @since 2026-02-22 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +public class OrganisationSummaryResponse { + private UUID id; + private String nom; + private String nomCourt; + private String typeOrganisation; + private String typeOrganisationLibelle; + private String statut; + private String statutLibelle; + private String statutSeverity; + private Integer nombreMembres; + private Boolean actif; + private String ville; + private String pays; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/paiement/WaveBalanceDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/paiement/WaveBalanceDTO.java index 4054b73..bc518d3 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/paiement/WaveBalanceDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/paiement/WaveBalanceDTO.java @@ -1,363 +1,363 @@ -package dev.lions.unionflow.server.api.dto.paiement; - -import com.fasterxml.jackson.annotation.JsonFormat; -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Pattern; -import java.math.BigDecimal; -import java.time.LocalDateTime; -import lombok.Getter; -import lombok.Setter; - -/** - * DTO pour la consultation du solde Wave Money (Balance API) Représente le solde d'un wallet Wave - * Business - * - *

Basé sur l'API officielle Wave : https://docs.wave.com/business#balance-api - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -@Getter -@Setter -public class WaveBalanceDTO extends BaseDTO { - - private static final long serialVersionUID = 1L; - - /** Solde disponible */ - @NotNull(message = "Le solde disponible est obligatoire") - @DecimalMin(value = "0.0", message = "Le solde doit être positif ou nul") - @Digits( - integer = 12, - fraction = 2, - message = "Le solde ne peut avoir plus de 12 chiffres entiers et 2 décimales") - private BigDecimal soldeDisponible; - - /** Solde en attente (transactions en cours) */ - @DecimalMin(value = "0.0", message = "Le solde en attente doit être positif ou nul") - @Digits( - integer = 12, - fraction = 2, - message = "Le solde ne peut avoir plus de 12 chiffres entiers et 2 décimales") - private BigDecimal soldeEnAttente; - - /** Solde total (disponible + en attente) */ - @DecimalMin(value = "0.0", message = "Le solde total doit être positif ou nul") - @Digits( - integer = 12, - fraction = 2, - message = "Le solde ne peut avoir plus de 12 chiffres entiers et 2 décimales") - private BigDecimal soldeTotal; - - /** Devise du wallet */ - @NotBlank(message = "La devise est obligatoire") - @Pattern(regexp = "^[A-Z]{3}$", message = "La devise doit être un code ISO à 3 lettres") - private String devise = "XOF"; - - /** Numéro du wallet Wave */ - @NotBlank(message = "Le numéro de wallet est obligatoire") - private String numeroWallet; - - /** Nom du business associé au wallet */ - private String nomBusiness; - - /** Date de dernière mise à jour du solde */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateDerniereMiseAJour; - - /** Date de dernière synchronisation avec Wave */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateDerniereSynchronisation; - - /** Statut du wallet */ - @Pattern( - regexp = "^(ACTIVE|INACTIVE|SUSPENDED|BLOCKED)$", - message = "Le statut doit être ACTIVE, INACTIVE, SUSPENDED ou BLOCKED") - private String statutWallet; - - /** Limite de transaction quotidienne */ - @DecimalMin(value = "0.0", message = "La limite doit être positive ou nulle") - @Digits( - integer = 12, - fraction = 2, - message = "La limite ne peut avoir plus de 12 chiffres entiers et 2 décimales") - private BigDecimal limiteQuotidienne; - - /** Montant déjà utilisé aujourd'hui */ - @DecimalMin(value = "0.0", message = "Le montant utilisé doit être positif ou nul") - @Digits( - integer = 12, - fraction = 2, - message = "Le montant ne peut avoir plus de 12 chiffres entiers et 2 décimales") - private BigDecimal montantUtiliseAujourdhui; - - /** Limite mensuelle */ - @DecimalMin(value = "0.0", message = "La limite doit être positive ou nulle") - @Digits( - integer = 12, - fraction = 2, - message = "La limite ne peut avoir plus de 12 chiffres entiers et 2 décimales") - private BigDecimal limiteMensuelle; - - /** Montant utilisé ce mois */ - @DecimalMin(value = "0.0", message = "Le montant utilisé doit être positif ou nul") - @Digits( - integer = 12, - fraction = 2, - message = "Le montant ne peut avoir plus de 12 chiffres entiers et 2 décimales") - private BigDecimal montantUtiliseCeMois; - - /** Nombre de transactions aujourd'hui */ - private Integer nombreTransactionsAujourdhui; - - /** Nombre de transactions ce mois */ - private Integer nombreTransactionsCeMois; - - /** Dernière erreur de synchronisation */ - private String derniereErreur; - - /** Code de la dernière erreur */ - private String codeDerniereErreur; - - // Constructeurs - public WaveBalanceDTO() { - super(); - this.devise = "XOF"; - this.statutWallet = "ACTIVE"; - this.soldeEnAttente = BigDecimal.ZERO; - this.montantUtiliseAujourdhui = BigDecimal.ZERO; - this.montantUtiliseCeMois = BigDecimal.ZERO; - this.nombreTransactionsAujourdhui = 0; - this.nombreTransactionsCeMois = 0; - } - - public WaveBalanceDTO(String numeroWallet, BigDecimal soldeDisponible) { - this(); - this.numeroWallet = numeroWallet; - this.soldeDisponible = soldeDisponible; - this.soldeTotal = soldeDisponible; - } - - // Getters et Setters - public BigDecimal getSoldeDisponible() { - return soldeDisponible; - } - - public void setSoldeDisponible(BigDecimal soldeDisponible) { - this.soldeDisponible = soldeDisponible; - calculerSoldeTotal(); - } - - public BigDecimal getSoldeEnAttente() { - return soldeEnAttente; - } - - public void setSoldeEnAttente(BigDecimal soldeEnAttente) { - this.soldeEnAttente = soldeEnAttente; - calculerSoldeTotal(); - } - - public BigDecimal getSoldeTotal() { - return soldeTotal; - } - - public void setSoldeTotal(BigDecimal soldeTotal) { - this.soldeTotal = soldeTotal; - } - - public String getDevise() { - return devise; - } - - public void setDevise(String devise) { - this.devise = devise; - } - - public String getNumeroWallet() { - return numeroWallet; - } - - public void setNumeroWallet(String numeroWallet) { - this.numeroWallet = numeroWallet; - } - - public String getNomBusiness() { - return nomBusiness; - } - - public void setNomBusiness(String nomBusiness) { - this.nomBusiness = nomBusiness; - } - - public LocalDateTime getDateDerniereMiseAJour() { - return dateDerniereMiseAJour; - } - - public void setDateDerniereMiseAJour(LocalDateTime dateDerniereMiseAJour) { - this.dateDerniereMiseAJour = dateDerniereMiseAJour; - } - - public LocalDateTime getDateDerniereSynchronisation() { - return dateDerniereSynchronisation; - } - - public void setDateDerniereSynchronisation(LocalDateTime dateDerniereSynchronisation) { - this.dateDerniereSynchronisation = dateDerniereSynchronisation; - } - - public String getStatutWallet() { - return statutWallet; - } - - public void setStatutWallet(String statutWallet) { - this.statutWallet = statutWallet; - } - - public BigDecimal getLimiteQuotidienne() { - return limiteQuotidienne; - } - - public void setLimiteQuotidienne(BigDecimal limiteQuotidienne) { - this.limiteQuotidienne = limiteQuotidienne; - } - - public BigDecimal getMontantUtiliseAujourdhui() { - return montantUtiliseAujourdhui; - } - - public void setMontantUtiliseAujourdhui(BigDecimal montantUtiliseAujourdhui) { - this.montantUtiliseAujourdhui = montantUtiliseAujourdhui; - } - - public BigDecimal getLimiteMensuelle() { - return limiteMensuelle; - } - - public void setLimiteMensuelle(BigDecimal limiteMensuelle) { - this.limiteMensuelle = limiteMensuelle; - } - - public BigDecimal getMontantUtiliseCeMois() { - return montantUtiliseCeMois; - } - - public void setMontantUtiliseCeMois(BigDecimal montantUtiliseCeMois) { - this.montantUtiliseCeMois = montantUtiliseCeMois; - } - - public Integer getNombreTransactionsAujourdhui() { - return nombreTransactionsAujourdhui; - } - - public void setNombreTransactionsAujourdhui(Integer nombreTransactionsAujourdhui) { - this.nombreTransactionsAujourdhui = nombreTransactionsAujourdhui; - } - - public Integer getNombreTransactionsCeMois() { - return nombreTransactionsCeMois; - } - - public void setNombreTransactionsCeMois(Integer nombreTransactionsCeMois) { - this.nombreTransactionsCeMois = nombreTransactionsCeMois; - } - - public String getDerniereErreur() { - return derniereErreur; - } - - public void setDerniereErreur(String derniereErreur) { - this.derniereErreur = derniereErreur; - } - - public String getCodeDerniereErreur() { - return codeDerniereErreur; - } - - public void setCodeDerniereErreur(String codeDerniereErreur) { - this.codeDerniereErreur = codeDerniereErreur; - } - - // Méthodes utilitaires - - /** Calcule le solde total */ - private void calculerSoldeTotal() { - if (soldeDisponible != null && soldeEnAttente != null) { - this.soldeTotal = soldeDisponible.add(soldeEnAttente); - } - } - - /** - * Vérifie si le wallet est actif - * - * @return true si le wallet est actif - */ - public boolean isWalletActif() { - return "ACTIVE".equals(statutWallet); - } - - /** - * Vérifie si le solde est suffisant pour un montant donné - * - * @param montant Le montant à vérifier - * @return true si le solde est suffisant - */ - public boolean isSoldeSuffisant(BigDecimal montant) { - return soldeDisponible != null && soldeDisponible.compareTo(montant) >= 0; - } - - /** - * Calcule le solde disponible restant pour aujourd'hui - * - * @return Le montant encore disponible aujourd'hui - */ - public BigDecimal getSoldeDisponibleAujourdhui() { - if (soldeDisponible == null || limiteQuotidienne == null || montantUtiliseAujourdhui == null) { - return soldeDisponible; - } - - BigDecimal limiteRestante = limiteQuotidienne.subtract(montantUtiliseAujourdhui); - return soldeDisponible.min(limiteRestante); - } - - /** - * Met à jour les statistiques après une transaction - * - * @param montant Le montant de la transaction - */ - public void mettreAJourApresTransaction(BigDecimal montant) { - if (montantUtiliseAujourdhui == null) montantUtiliseAujourdhui = BigDecimal.ZERO; - if (montantUtiliseCeMois == null) montantUtiliseCeMois = BigDecimal.ZERO; - if (nombreTransactionsAujourdhui == null) nombreTransactionsAujourdhui = 0; - if (nombreTransactionsCeMois == null) nombreTransactionsCeMois = 0; - - this.montantUtiliseAujourdhui = montantUtiliseAujourdhui.add(montant); - this.montantUtiliseCeMois = montantUtiliseCeMois.add(montant); - this.nombreTransactionsAujourdhui++; - this.nombreTransactionsCeMois++; - this.dateDerniereMiseAJour = LocalDateTime.now(); - } - - @Override - public String toString() { - return "WaveBalanceDTO{" - + "numeroWallet='" - + numeroWallet - + '\'' - + ", soldeDisponible=" - + soldeDisponible - + ", soldeTotal=" - + soldeTotal - + ", devise='" - + devise - + '\'' - + ", statutWallet='" - + statutWallet - + '\'' - + "} " - + super.toString(); - } -} +package dev.lions.unionflow.server.api.dto.paiement; + +import com.fasterxml.jackson.annotation.JsonFormat; +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Pattern; +import java.math.BigDecimal; +import java.time.LocalDateTime; +import lombok.Getter; +import lombok.Setter; + +/** + * DTO pour la consultation du solde Wave Money (Balance API) Représente le solde d'un wallet Wave + * Business + * + *

Basé sur l'API officielle Wave : https://docs.wave.com/business#balance-api + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +@Getter +@Setter +public class WaveBalanceDTO extends BaseDTO { + + private static final long serialVersionUID = 1L; + + /** Solde disponible */ + @NotNull(message = "Le solde disponible est obligatoire") + @DecimalMin(value = "0.0", message = "Le solde doit être positif ou nul") + @Digits( + integer = 12, + fraction = 2, + message = "Le solde ne peut avoir plus de 12 chiffres entiers et 2 décimales") + private BigDecimal soldeDisponible; + + /** Solde en attente (transactions en cours) */ + @DecimalMin(value = "0.0", message = "Le solde en attente doit être positif ou nul") + @Digits( + integer = 12, + fraction = 2, + message = "Le solde ne peut avoir plus de 12 chiffres entiers et 2 décimales") + private BigDecimal soldeEnAttente; + + /** Solde total (disponible + en attente) */ + @DecimalMin(value = "0.0", message = "Le solde total doit être positif ou nul") + @Digits( + integer = 12, + fraction = 2, + message = "Le solde ne peut avoir plus de 12 chiffres entiers et 2 décimales") + private BigDecimal soldeTotal; + + /** Devise du wallet */ + @NotBlank(message = "La devise est obligatoire") + @Pattern(regexp = "^[A-Z]{3}$", message = "La devise doit être un code ISO à 3 lettres") + private String devise = "XOF"; + + /** Numéro du wallet Wave */ + @NotBlank(message = "Le numéro de wallet est obligatoire") + private String numeroWallet; + + /** Nom du business associé au wallet */ + private String nomBusiness; + + /** Date de dernière mise à jour du solde */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateDerniereMiseAJour; + + /** Date de dernière synchronisation avec Wave */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateDerniereSynchronisation; + + /** Statut du wallet */ + @Pattern( + regexp = "^(ACTIVE|INACTIVE|SUSPENDED|BLOCKED)$", + message = "Le statut doit être ACTIVE, INACTIVE, SUSPENDED ou BLOCKED") + private String statutWallet; + + /** Limite de transaction quotidienne */ + @DecimalMin(value = "0.0", message = "La limite doit être positive ou nulle") + @Digits( + integer = 12, + fraction = 2, + message = "La limite ne peut avoir plus de 12 chiffres entiers et 2 décimales") + private BigDecimal limiteQuotidienne; + + /** Montant déjà utilisé aujourd'hui */ + @DecimalMin(value = "0.0", message = "Le montant utilisé doit être positif ou nul") + @Digits( + integer = 12, + fraction = 2, + message = "Le montant ne peut avoir plus de 12 chiffres entiers et 2 décimales") + private BigDecimal montantUtiliseAujourdhui; + + /** Limite mensuelle */ + @DecimalMin(value = "0.0", message = "La limite doit être positive ou nulle") + @Digits( + integer = 12, + fraction = 2, + message = "La limite ne peut avoir plus de 12 chiffres entiers et 2 décimales") + private BigDecimal limiteMensuelle; + + /** Montant utilisé ce mois */ + @DecimalMin(value = "0.0", message = "Le montant utilisé doit être positif ou nul") + @Digits( + integer = 12, + fraction = 2, + message = "Le montant ne peut avoir plus de 12 chiffres entiers et 2 décimales") + private BigDecimal montantUtiliseCeMois; + + /** Nombre de transactions aujourd'hui */ + private Integer nombreTransactionsAujourdhui; + + /** Nombre de transactions ce mois */ + private Integer nombreTransactionsCeMois; + + /** Dernière erreur de synchronisation */ + private String derniereErreur; + + /** Code de la dernière erreur */ + private String codeDerniereErreur; + + // Constructeurs + public WaveBalanceDTO() { + super(); + this.devise = "XOF"; + this.statutWallet = "ACTIVE"; + this.soldeEnAttente = BigDecimal.ZERO; + this.montantUtiliseAujourdhui = BigDecimal.ZERO; + this.montantUtiliseCeMois = BigDecimal.ZERO; + this.nombreTransactionsAujourdhui = 0; + this.nombreTransactionsCeMois = 0; + } + + public WaveBalanceDTO(String numeroWallet, BigDecimal soldeDisponible) { + this(); + this.numeroWallet = numeroWallet; + this.soldeDisponible = soldeDisponible; + this.soldeTotal = soldeDisponible; + } + + // Getters et Setters + public BigDecimal getSoldeDisponible() { + return soldeDisponible; + } + + public void setSoldeDisponible(BigDecimal soldeDisponible) { + this.soldeDisponible = soldeDisponible; + calculerSoldeTotal(); + } + + public BigDecimal getSoldeEnAttente() { + return soldeEnAttente; + } + + public void setSoldeEnAttente(BigDecimal soldeEnAttente) { + this.soldeEnAttente = soldeEnAttente; + calculerSoldeTotal(); + } + + public BigDecimal getSoldeTotal() { + return soldeTotal; + } + + public void setSoldeTotal(BigDecimal soldeTotal) { + this.soldeTotal = soldeTotal; + } + + public String getDevise() { + return devise; + } + + public void setDevise(String devise) { + this.devise = devise; + } + + public String getNumeroWallet() { + return numeroWallet; + } + + public void setNumeroWallet(String numeroWallet) { + this.numeroWallet = numeroWallet; + } + + public String getNomBusiness() { + return nomBusiness; + } + + public void setNomBusiness(String nomBusiness) { + this.nomBusiness = nomBusiness; + } + + public LocalDateTime getDateDerniereMiseAJour() { + return dateDerniereMiseAJour; + } + + public void setDateDerniereMiseAJour(LocalDateTime dateDerniereMiseAJour) { + this.dateDerniereMiseAJour = dateDerniereMiseAJour; + } + + public LocalDateTime getDateDerniereSynchronisation() { + return dateDerniereSynchronisation; + } + + public void setDateDerniereSynchronisation(LocalDateTime dateDerniereSynchronisation) { + this.dateDerniereSynchronisation = dateDerniereSynchronisation; + } + + public String getStatutWallet() { + return statutWallet; + } + + public void setStatutWallet(String statutWallet) { + this.statutWallet = statutWallet; + } + + public BigDecimal getLimiteQuotidienne() { + return limiteQuotidienne; + } + + public void setLimiteQuotidienne(BigDecimal limiteQuotidienne) { + this.limiteQuotidienne = limiteQuotidienne; + } + + public BigDecimal getMontantUtiliseAujourdhui() { + return montantUtiliseAujourdhui; + } + + public void setMontantUtiliseAujourdhui(BigDecimal montantUtiliseAujourdhui) { + this.montantUtiliseAujourdhui = montantUtiliseAujourdhui; + } + + public BigDecimal getLimiteMensuelle() { + return limiteMensuelle; + } + + public void setLimiteMensuelle(BigDecimal limiteMensuelle) { + this.limiteMensuelle = limiteMensuelle; + } + + public BigDecimal getMontantUtiliseCeMois() { + return montantUtiliseCeMois; + } + + public void setMontantUtiliseCeMois(BigDecimal montantUtiliseCeMois) { + this.montantUtiliseCeMois = montantUtiliseCeMois; + } + + public Integer getNombreTransactionsAujourdhui() { + return nombreTransactionsAujourdhui; + } + + public void setNombreTransactionsAujourdhui(Integer nombreTransactionsAujourdhui) { + this.nombreTransactionsAujourdhui = nombreTransactionsAujourdhui; + } + + public Integer getNombreTransactionsCeMois() { + return nombreTransactionsCeMois; + } + + public void setNombreTransactionsCeMois(Integer nombreTransactionsCeMois) { + this.nombreTransactionsCeMois = nombreTransactionsCeMois; + } + + public String getDerniereErreur() { + return derniereErreur; + } + + public void setDerniereErreur(String derniereErreur) { + this.derniereErreur = derniereErreur; + } + + public String getCodeDerniereErreur() { + return codeDerniereErreur; + } + + public void setCodeDerniereErreur(String codeDerniereErreur) { + this.codeDerniereErreur = codeDerniereErreur; + } + + // Méthodes utilitaires + + /** Calcule le solde total */ + private void calculerSoldeTotal() { + if (soldeDisponible != null && soldeEnAttente != null) { + this.soldeTotal = soldeDisponible.add(soldeEnAttente); + } + } + + /** + * Vérifie si le wallet est actif + * + * @return true si le wallet est actif + */ + public boolean isWalletActif() { + return "ACTIVE".equals(statutWallet); + } + + /** + * Vérifie si le solde est suffisant pour un montant donné + * + * @param montant Le montant à vérifier + * @return true si le solde est suffisant + */ + public boolean isSoldeSuffisant(BigDecimal montant) { + return soldeDisponible != null && soldeDisponible.compareTo(montant) >= 0; + } + + /** + * Calcule le solde disponible restant pour aujourd'hui + * + * @return Le montant encore disponible aujourd'hui + */ + public BigDecimal getSoldeDisponibleAujourdhui() { + if (soldeDisponible == null || limiteQuotidienne == null || montantUtiliseAujourdhui == null) { + return soldeDisponible; + } + + BigDecimal limiteRestante = limiteQuotidienne.subtract(montantUtiliseAujourdhui); + return soldeDisponible.min(limiteRestante); + } + + /** + * Met à jour les statistiques après une transaction + * + * @param montant Le montant de la transaction + */ + public void mettreAJourApresTransaction(BigDecimal montant) { + if (montantUtiliseAujourdhui == null) montantUtiliseAujourdhui = BigDecimal.ZERO; + if (montantUtiliseCeMois == null) montantUtiliseCeMois = BigDecimal.ZERO; + if (nombreTransactionsAujourdhui == null) nombreTransactionsAujourdhui = 0; + if (nombreTransactionsCeMois == null) nombreTransactionsCeMois = 0; + + this.montantUtiliseAujourdhui = montantUtiliseAujourdhui.add(montant); + this.montantUtiliseCeMois = montantUtiliseCeMois.add(montant); + this.nombreTransactionsAujourdhui++; + this.nombreTransactionsCeMois++; + this.dateDerniereMiseAJour = LocalDateTime.now(); + } + + @Override + public String toString() { + return "WaveBalanceDTO{" + + "numeroWallet='" + + numeroWallet + + '\'' + + ", soldeDisponible=" + + soldeDisponible + + ", soldeTotal=" + + soldeTotal + + ", devise='" + + devise + + '\'' + + ", statutWallet='" + + statutWallet + + '\'' + + "} " + + super.toString(); + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/paiement/WaveCheckoutSessionDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/paiement/WaveCheckoutSessionDTO.java index 0969c33..4493763 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/paiement/WaveCheckoutSessionDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/paiement/WaveCheckoutSessionDTO.java @@ -1,168 +1,168 @@ -package dev.lions.unionflow.server.api.dto.paiement; - -import com.fasterxml.jackson.annotation.JsonFormat; -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.paiement.StatutSession; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Pattern; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDateTime; -import java.util.UUID; -import lombok.Getter; -import lombok.Setter; - -/** - * DTO pour les sessions de paiement Wave Money (Checkout API) Représente une session de paiement - * créée via l'API Wave Checkout - * - *

Basé sur l'API officielle Wave : https://docs.wave.com/business#checkout-api - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -@Getter -@Setter -public class WaveCheckoutSessionDTO extends BaseDTO { - - private static final long serialVersionUID = 1L; - - /** ID de la session Wave (retourné par l'API) */ - @NotBlank(message = "L'ID de session Wave est obligatoire") - private String waveSessionId; - - /** URL de la session de paiement Wave (générée par l'API Wave) */ - @Size(max = 500, message = "L'URL ne peut pas dépasser 500 caractères") - private String waveUrl; - - /** Montant du paiement */ - @NotNull(message = "Le montant est obligatoire") - @DecimalMin(value = "0.01", message = "Le montant doit être positif") - @Digits( - integer = 10, - fraction = 2, - message = "Le montant ne peut avoir plus de 10 chiffres entiers et 2 décimales") - private BigDecimal montant; - - /** Devise (XOF pour le Sénégal) */ - @NotBlank(message = "La devise est obligatoire") - @Pattern(regexp = "^[A-Z]{3}$", message = "La devise doit être un code ISO à 3 lettres") - private String devise = "XOF"; - - /** URL de succès (redirection après paiement réussi) */ - @NotBlank(message = "L'URL de succès est obligatoire") - @Size(max = 500, message = "L'URL de succès ne peut pas dépasser 500 caractères") - private String successUrl; - - /** URL d'erreur (redirection après échec) */ - @NotBlank(message = "L'URL d'erreur est obligatoire") - @Size(max = 500, message = "L'URL d'erreur ne peut pas dépasser 500 caractères") - private String errorUrl; - - /** Statut de la session */ - @NotNull(message = "Le statut est obligatoire") - private StatutSession statut; - - /** ID de l'organisation qui effectue le paiement */ - private UUID organisationId; - - /** Nom de l'organisation */ - private String nomOrganisation; - - /** ID du membre qui effectue le paiement */ - private UUID membreId; - - /** Nom du membre */ - private String nomMembre; - - /** Type de paiement (COTISATION, ABONNEMENT, DON, AUTRE) */ - @Pattern( - regexp = "^(COTISATION|ABONNEMENT|DON|EVENEMENT|FORMATION|AUTRE)$", - message = "Type de paiement invalide") - private String typePaiement; - - /** Référence du paiement dans UnionFlow */ - @Size(max = 100, message = "La référence ne peut pas dépasser 100 caractères") - private String referenceUnionFlow; - - /** Description du paiement */ - @Size(max = 500, message = "La description ne peut pas dépasser 500 caractères") - private String description; - - /** Nom du business affiché (override_business_name) */ - @Size(max = 100, message = "Le nom du business ne peut pas dépasser 100 caractères") - private String nomBusinessAffiche; - - /** ID du marchand agrégé (si applicable) */ - private String aggregatedMerchantId; - - /** Date d'expiration de la session */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateExpiration; - - /** Date de completion du paiement */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateCompletion; - - /** Numéro de téléphone du payeur (si fourni) */ - @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Format de numéro de téléphone invalide") - private String telephonePayeur; - - /** Email du payeur (si fourni) */ - @Pattern(regexp = "^[A-Za-z0-9+_.-]+@(.+)$", message = "Format d'email invalide") - private String emailPayeur; - - /** Adresse IP du client */ - private String adresseIpClient; - - /** User Agent du navigateur */ - @Size(max = 500, message = "Le User Agent ne peut pas dépasser 500 caractères") - private String userAgent; - - /** Données de callback reçues de Wave */ - @Size(max = 2000, message = "Les données callback ne peuvent pas dépasser 2000 caractères") - private String callbackData; - - /** Code d'erreur Wave (si échec) */ - private String codeErreurWave; - - /** Message d'erreur Wave (si échec) */ - @Size(max = 500, message = "Le message d'erreur ne peut pas dépasser 500 caractères") - private String messageErreurWave; - - /** Nombre de tentatives de paiement */ - private Integer nombreTentatives; - - /** Session liée à un webhook */ - private Boolean webhookRecu; - - /** Date de réception du webhook */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateWebhook; - - /** Données du webhook reçu */ - @Size(max = 2000, message = "Les données webhook ne peuvent pas dépasser 2000 caractères") - private String donneesWebhook; - - // Constructeurs - public WaveCheckoutSessionDTO() { - super(); - this.devise = "XOF"; - this.statut = StatutSession.PENDING; - this.nombreTentatives = 0; - this.webhookRecu = false; - } - - public WaveCheckoutSessionDTO(BigDecimal montant, String successUrl, String errorUrl) { - this(); - this.montant = montant; - this.successUrl = successUrl; - this.errorUrl = errorUrl; - } - - // Getters et Setters générés automatiquement par Lombok @Getter/@Setter -} +package dev.lions.unionflow.server.api.dto.paiement; + +import com.fasterxml.jackson.annotation.JsonFormat; +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.paiement.StatutSession; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Pattern; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDateTime; +import java.util.UUID; +import lombok.Getter; +import lombok.Setter; + +/** + * DTO pour les sessions de paiement Wave Money (Checkout API) Représente une session de paiement + * créée via l'API Wave Checkout + * + *

Basé sur l'API officielle Wave : https://docs.wave.com/business#checkout-api + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +@Getter +@Setter +public class WaveCheckoutSessionDTO extends BaseDTO { + + private static final long serialVersionUID = 1L; + + /** ID de la session Wave (retourné par l'API) */ + @NotBlank(message = "L'ID de session Wave est obligatoire") + private String waveSessionId; + + /** URL de la session de paiement Wave (générée par l'API Wave) */ + @Size(max = 500, message = "L'URL ne peut pas dépasser 500 caractères") + private String waveUrl; + + /** Montant du paiement */ + @NotNull(message = "Le montant est obligatoire") + @DecimalMin(value = "0.01", message = "Le montant doit être positif") + @Digits( + integer = 10, + fraction = 2, + message = "Le montant ne peut avoir plus de 10 chiffres entiers et 2 décimales") + private BigDecimal montant; + + /** Devise (XOF pour le Sénégal) */ + @NotBlank(message = "La devise est obligatoire") + @Pattern(regexp = "^[A-Z]{3}$", message = "La devise doit être un code ISO à 3 lettres") + private String devise = "XOF"; + + /** URL de succès (redirection après paiement réussi) */ + @NotBlank(message = "L'URL de succès est obligatoire") + @Size(max = 500, message = "L'URL de succès ne peut pas dépasser 500 caractères") + private String successUrl; + + /** URL d'erreur (redirection après échec) */ + @NotBlank(message = "L'URL d'erreur est obligatoire") + @Size(max = 500, message = "L'URL d'erreur ne peut pas dépasser 500 caractères") + private String errorUrl; + + /** Statut de la session */ + @NotNull(message = "Le statut est obligatoire") + private StatutSession statut; + + /** ID de l'organisation qui effectue le paiement */ + private UUID organisationId; + + /** Nom de l'organisation */ + private String nomOrganisation; + + /** ID du membre qui effectue le paiement */ + private UUID membreId; + + /** Nom du membre */ + private String nomMembre; + + /** Type de paiement (COTISATION, ABONNEMENT, DON, AUTRE) */ + @Pattern( + regexp = "^(COTISATION|ABONNEMENT|DON|EVENEMENT|FORMATION|AUTRE)$", + message = "Type de paiement invalide") + private String typePaiement; + + /** Référence du paiement dans UnionFlow */ + @Size(max = 100, message = "La référence ne peut pas dépasser 100 caractères") + private String referenceUnionFlow; + + /** Description du paiement */ + @Size(max = 500, message = "La description ne peut pas dépasser 500 caractères") + private String description; + + /** Nom du business affiché (override_business_name) */ + @Size(max = 100, message = "Le nom du business ne peut pas dépasser 100 caractères") + private String nomBusinessAffiche; + + /** ID du marchand agrégé (si applicable) */ + private String aggregatedMerchantId; + + /** Date d'expiration de la session */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateExpiration; + + /** Date de completion du paiement */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateCompletion; + + /** Numéro de téléphone du payeur (si fourni) */ + @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Format de numéro de téléphone invalide") + private String telephonePayeur; + + /** Email du payeur (si fourni) */ + @Pattern(regexp = "^[A-Za-z0-9+_.-]+@(.+)$", message = "Format d'email invalide") + private String emailPayeur; + + /** Adresse IP du client */ + private String adresseIpClient; + + /** User Agent du navigateur */ + @Size(max = 500, message = "Le User Agent ne peut pas dépasser 500 caractères") + private String userAgent; + + /** Données de callback reçues de Wave */ + @Size(max = 2000, message = "Les données callback ne peuvent pas dépasser 2000 caractères") + private String callbackData; + + /** Code d'erreur Wave (si échec) */ + private String codeErreurWave; + + /** Message d'erreur Wave (si échec) */ + @Size(max = 500, message = "Le message d'erreur ne peut pas dépasser 500 caractères") + private String messageErreurWave; + + /** Nombre de tentatives de paiement */ + private Integer nombreTentatives; + + /** Session liée à un webhook */ + private Boolean webhookRecu; + + /** Date de réception du webhook */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateWebhook; + + /** Données du webhook reçu */ + @Size(max = 2000, message = "Les données webhook ne peuvent pas dépasser 2000 caractères") + private String donneesWebhook; + + // Constructeurs + public WaveCheckoutSessionDTO() { + super(); + this.devise = "XOF"; + this.statut = StatutSession.PENDING; + this.nombreTentatives = 0; + this.webhookRecu = false; + } + + public WaveCheckoutSessionDTO(BigDecimal montant, String successUrl, String errorUrl) { + this(); + this.montant = montant; + this.successUrl = successUrl; + this.errorUrl = errorUrl; + } + + // Getters et Setters générés automatiquement par Lombok @Getter/@Setter +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/paiement/WaveWebhookDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/paiement/WaveWebhookDTO.java index 73cb9e0..69fcc6a 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/paiement/WaveWebhookDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/paiement/WaveWebhookDTO.java @@ -1,464 +1,464 @@ -package dev.lions.unionflow.server.api.dto.paiement; - -import com.fasterxml.jackson.annotation.JsonFormat; -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.paiement.StatutTraitement; -import dev.lions.unionflow.server.api.enums.paiement.TypeEvenement; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Pattern; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDateTime; -import java.util.UUID; -import lombok.Getter; -import lombok.Setter; - -/** - * DTO pour les webhooks Wave Money Représente les notifications reçues de Wave lors d'événements - * - *

Basé sur l'API officielle Wave : https://docs.wave.com/business#webhooks - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -@Getter -@Setter -public class WaveWebhookDTO extends BaseDTO { - - private static final long serialVersionUID = 1L; - - /** ID unique du webhook Wave */ - @NotBlank(message = "L'ID du webhook est obligatoire") - private String webhookId; - - /** Type d'événement */ - @NotNull(message = "Le type d'événement est obligatoire") - private TypeEvenement typeEvenement; - - /** Code de l'événement tel que reçu de Wave */ - @NotBlank(message = "Le code événement est obligatoire") - private String codeEvenement; - - /** Statut de traitement du webhook */ - @NotNull(message = "Le statut de traitement est obligatoire") - private StatutTraitement statutTraitement; - - /** Payload JSON complet reçu de Wave */ - @NotBlank(message = "Le payload est obligatoire") - @Size(max = 5000, message = "Le payload ne peut pas dépasser 5000 caractères") - private String payloadJson; - - /** Headers HTTP reçus */ - @Size(max = 2000, message = "Les headers ne peuvent pas dépasser 2000 caractères") - private String headersHttp; - - /** Signature Wave pour vérification */ - private String signatureWave; - - /** Date de réception du webhook */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateReception; - - /** Date de traitement du webhook */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateTraitement; - - /** ID de la session checkout concernée (si applicable) */ - private String sessionCheckoutId; - - /** ID de la transaction Wave concernée */ - private String transactionWaveId; - - /** Montant de la transaction (si applicable) */ - private BigDecimal montantTransaction; - - /** Devise de la transaction */ - @Pattern(regexp = "^[A-Z]{3}$", message = "La devise doit être un code ISO à 3 lettres") - private String deviseTransaction; - - /** Statut de la transaction Wave */ - private String statutTransactionWave; - - /** ID de l'organisation UnionFlow concernée */ - private UUID organisationId; - - /** ID du membre UnionFlow concerné */ - private UUID membreId; - - /** Référence UnionFlow liée */ - private String referenceUnionFlow; - - /** Type de paiement UnionFlow */ - @Pattern( - regexp = "^(COTISATION|ABONNEMENT|DON|EVENEMENT|FORMATION|AUTRE)$", - message = "Type de paiement invalide") - private String typePaiementUnionFlow; - - /** Adresse IP source du webhook */ - private String adresseIpSource; - - /** User Agent du webhook */ - @Size(max = 500, message = "Le User Agent ne peut pas dépasser 500 caractères") - private String userAgentSource; - - /** Nombre de tentatives de traitement */ - private Integer nombreTentativesTraitement; - - /** Message d'erreur de traitement (si échec) */ - @Size(max = 1000, message = "Le message d'erreur ne peut pas dépasser 1000 caractères") - private String messageErreurTraitement; - - /** Code d'erreur de traitement (si échec) */ - private String codeErreurTraitement; - - /** Stack trace de l'erreur (si échec) */ - @Size(max = 3000, message = "La stack trace ne peut pas dépasser 3000 caractères") - private String stackTraceErreur; - - /** Webhook traité automatiquement */ - private Boolean traitementAutomatique; - - /** Webhook nécessitant une intervention manuelle */ - private Boolean interventionManuelleRequise; - - /** Notes de traitement manuel */ - @Size(max = 1000, message = "Les notes ne peuvent pas dépasser 1000 caractères") - private String notesTraitementManuel; - - /** Utilisateur ayant traité manuellement */ - private String utilisateurTraitementManuel; - - /** Date du traitement manuel */ - @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") - private LocalDateTime dateTraitementManuel; - - // Constructeurs - public WaveWebhookDTO() { - super(); - this.statutTraitement = StatutTraitement.RECU; - this.dateReception = LocalDateTime.now(); - this.nombreTentativesTraitement = 0; - this.traitementAutomatique = true; - this.interventionManuelleRequise = false; - } - - public WaveWebhookDTO(String webhookId, TypeEvenement typeEvenement, String payloadJson) { - this(); - this.webhookId = webhookId; - this.typeEvenement = typeEvenement; - this.codeEvenement = typeEvenement.getCodeWave(); - this.payloadJson = payloadJson; - } - - // Getters et Setters - public String getWebhookId() { - return webhookId; - } - - public void setWebhookId(String webhookId) { - this.webhookId = webhookId; - } - - public TypeEvenement getTypeEvenement() { - return typeEvenement; - } - - public void setTypeEvenement(TypeEvenement typeEvenement) { - this.typeEvenement = typeEvenement; - if (typeEvenement != null) { - this.codeEvenement = typeEvenement.getCodeWave(); - } - } - - public String getCodeEvenement() { - return codeEvenement; - } - - public void setCodeEvenement(String codeEvenement) { - this.codeEvenement = codeEvenement; - this.typeEvenement = TypeEvenement.fromCode(codeEvenement); - } - - public StatutTraitement getStatutTraitement() { - return statutTraitement; - } - - public void setStatutTraitement(StatutTraitement statutTraitement) { - this.statutTraitement = statutTraitement; - } - - public String getPayloadJson() { - return payloadJson; - } - - public void setPayloadJson(String payloadJson) { - this.payloadJson = payloadJson; - } - - public String getHeadersHttp() { - return headersHttp; - } - - public void setHeadersHttp(String headersHttp) { - this.headersHttp = headersHttp; - } - - public String getSignatureWave() { - return signatureWave; - } - - public void setSignatureWave(String signatureWave) { - this.signatureWave = signatureWave; - } - - public LocalDateTime getDateReception() { - return dateReception; - } - - public void setDateReception(LocalDateTime dateReception) { - this.dateReception = dateReception; - } - - public LocalDateTime getDateTraitement() { - return dateTraitement; - } - - public void setDateTraitement(LocalDateTime dateTraitement) { - this.dateTraitement = dateTraitement; - } - - public String getSessionCheckoutId() { - return sessionCheckoutId; - } - - public void setSessionCheckoutId(String sessionCheckoutId) { - this.sessionCheckoutId = sessionCheckoutId; - } - - public String getTransactionWaveId() { - return transactionWaveId; - } - - public void setTransactionWaveId(String transactionWaveId) { - this.transactionWaveId = transactionWaveId; - } - - public BigDecimal getMontantTransaction() { - return montantTransaction; - } - - public void setMontantTransaction(BigDecimal montantTransaction) { - this.montantTransaction = montantTransaction; - } - - public String getDeviseTransaction() { - return deviseTransaction; - } - - public void setDeviseTransaction(String deviseTransaction) { - this.deviseTransaction = deviseTransaction; - } - - public String getStatutTransactionWave() { - return statutTransactionWave; - } - - public void setStatutTransactionWave(String statutTransactionWave) { - this.statutTransactionWave = statutTransactionWave; - } - - public UUID getOrganisationId() { - return organisationId; - } - - public void setOrganisationId(UUID organisationId) { - this.organisationId = organisationId; - } - - public UUID getMembreId() { - return membreId; - } - - public void setMembreId(UUID membreId) { - this.membreId = membreId; - } - - public String getReferenceUnionFlow() { - return referenceUnionFlow; - } - - public void setReferenceUnionFlow(String referenceUnionFlow) { - this.referenceUnionFlow = referenceUnionFlow; - } - - public String getTypePaiementUnionFlow() { - return typePaiementUnionFlow; - } - - public void setTypePaiementUnionFlow(String typePaiementUnionFlow) { - this.typePaiementUnionFlow = typePaiementUnionFlow; - } - - public String getAdresseIpSource() { - return adresseIpSource; - } - - public void setAdresseIpSource(String adresseIpSource) { - this.adresseIpSource = adresseIpSource; - } - - public String getUserAgentSource() { - return userAgentSource; - } - - public void setUserAgentSource(String userAgentSource) { - this.userAgentSource = userAgentSource; - } - - public Integer getNombreTentativesTraitement() { - return nombreTentativesTraitement; - } - - public void setNombreTentativesTraitement(Integer nombreTentativesTraitement) { - this.nombreTentativesTraitement = nombreTentativesTraitement; - } - - public String getMessageErreurTraitement() { - return messageErreurTraitement; - } - - public void setMessageErreurTraitement(String messageErreurTraitement) { - this.messageErreurTraitement = messageErreurTraitement; - } - - public String getCodeErreurTraitement() { - return codeErreurTraitement; - } - - public void setCodeErreurTraitement(String codeErreurTraitement) { - this.codeErreurTraitement = codeErreurTraitement; - } - - public String getStackTraceErreur() { - return stackTraceErreur; - } - - public void setStackTraceErreur(String stackTraceErreur) { - this.stackTraceErreur = stackTraceErreur; - } - - public Boolean getTraitementAutomatique() { - return traitementAutomatique; - } - - public void setTraitementAutomatique(Boolean traitementAutomatique) { - this.traitementAutomatique = traitementAutomatique; - } - - public Boolean getInterventionManuelleRequise() { - return interventionManuelleRequise; - } - - public void setInterventionManuelleRequise(Boolean interventionManuelleRequise) { - this.interventionManuelleRequise = interventionManuelleRequise; - } - - public String getNotesTraitementManuel() { - return notesTraitementManuel; - } - - public void setNotesTraitementManuel(String notesTraitementManuel) { - this.notesTraitementManuel = notesTraitementManuel; - } - - public String getUtilisateurTraitementManuel() { - return utilisateurTraitementManuel; - } - - public void setUtilisateurTraitementManuel(String utilisateurTraitementManuel) { - this.utilisateurTraitementManuel = utilisateurTraitementManuel; - } - - public LocalDateTime getDateTraitementManuel() { - return dateTraitementManuel; - } - - public void setDateTraitementManuel(LocalDateTime dateTraitementManuel) { - this.dateTraitementManuel = dateTraitementManuel; - } - - // Méthodes utilitaires - - /** - * Vérifie si le webhook concerne un checkout - * - * @return true si c'est un événement de checkout - */ - public boolean isEvenementCheckout() { - return typeEvenement == TypeEvenement.CHECKOUT_COMPLETE - || typeEvenement == TypeEvenement.CHECKOUT_CANCELLED - || typeEvenement == TypeEvenement.CHECKOUT_EXPIRED; - } - - /** - * Vérifie si le webhook concerne un payout - * - * @return true si c'est un événement de payout - */ - public boolean isEvenementPayout() { - return typeEvenement == TypeEvenement.PAYOUT_COMPLETE - || typeEvenement == TypeEvenement.PAYOUT_FAILED; - } - - /** Marque le webhook comme traité avec succès */ - public void marquerCommeTraite() { - this.statutTraitement = StatutTraitement.TRAITE; - this.dateTraitement = LocalDateTime.now(); - marquerCommeModifie("SYSTEM"); - } - - /** - * Marque le webhook comme échoué - * - * @param messageErreur Le message d'erreur - * @param codeErreur Le code d'erreur - */ - public void marquerCommeEchec(String messageErreur, String codeErreur) { - this.statutTraitement = StatutTraitement.ECHEC; - this.messageErreurTraitement = messageErreur; - this.codeErreurTraitement = codeErreur; - this.nombreTentativesTraitement++; - this.dateTraitement = LocalDateTime.now(); - marquerCommeModifie("SYSTEM"); - } - - /** Démarre le traitement du webhook */ - public void demarrerTraitement() { - this.statutTraitement = StatutTraitement.EN_COURS; - this.nombreTentativesTraitement++; - marquerCommeModifie("SYSTEM"); - } - - @Override - public String toString() { - return "WaveWebhookDTO{" - + "webhookId='" - + webhookId - + '\'' - + ", typeEvenement=" - + typeEvenement - + ", statutTraitement=" - + statutTraitement - + ", dateReception=" - + dateReception - + ", sessionCheckoutId='" - + sessionCheckoutId - + '\'' - + ", montantTransaction=" - + montantTransaction - + "} " - + super.toString(); - } -} +package dev.lions.unionflow.server.api.dto.paiement; + +import com.fasterxml.jackson.annotation.JsonFormat; +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.paiement.StatutTraitement; +import dev.lions.unionflow.server.api.enums.paiement.TypeEvenement; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Pattern; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDateTime; +import java.util.UUID; +import lombok.Getter; +import lombok.Setter; + +/** + * DTO pour les webhooks Wave Money Représente les notifications reçues de Wave lors d'événements + * + *

Basé sur l'API officielle Wave : https://docs.wave.com/business#webhooks + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +@Getter +@Setter +public class WaveWebhookDTO extends BaseDTO { + + private static final long serialVersionUID = 1L; + + /** ID unique du webhook Wave */ + @NotBlank(message = "L'ID du webhook est obligatoire") + private String webhookId; + + /** Type d'événement */ + @NotNull(message = "Le type d'événement est obligatoire") + private TypeEvenement typeEvenement; + + /** Code de l'événement tel que reçu de Wave */ + @NotBlank(message = "Le code événement est obligatoire") + private String codeEvenement; + + /** Statut de traitement du webhook */ + @NotNull(message = "Le statut de traitement est obligatoire") + private StatutTraitement statutTraitement; + + /** Payload JSON complet reçu de Wave */ + @NotBlank(message = "Le payload est obligatoire") + @Size(max = 5000, message = "Le payload ne peut pas dépasser 5000 caractères") + private String payloadJson; + + /** Headers HTTP reçus */ + @Size(max = 2000, message = "Les headers ne peuvent pas dépasser 2000 caractères") + private String headersHttp; + + /** Signature Wave pour vérification */ + private String signatureWave; + + /** Date de réception du webhook */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateReception; + + /** Date de traitement du webhook */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateTraitement; + + /** ID de la session checkout concernée (si applicable) */ + private String sessionCheckoutId; + + /** ID de la transaction Wave concernée */ + private String transactionWaveId; + + /** Montant de la transaction (si applicable) */ + private BigDecimal montantTransaction; + + /** Devise de la transaction */ + @Pattern(regexp = "^[A-Z]{3}$", message = "La devise doit être un code ISO à 3 lettres") + private String deviseTransaction; + + /** Statut de la transaction Wave */ + private String statutTransactionWave; + + /** ID de l'organisation UnionFlow concernée */ + private UUID organisationId; + + /** ID du membre UnionFlow concerné */ + private UUID membreId; + + /** Référence UnionFlow liée */ + private String referenceUnionFlow; + + /** Type de paiement UnionFlow */ + @Pattern( + regexp = "^(COTISATION|ABONNEMENT|DON|EVENEMENT|FORMATION|AUTRE)$", + message = "Type de paiement invalide") + private String typePaiementUnionFlow; + + /** Adresse IP source du webhook */ + private String adresseIpSource; + + /** User Agent du webhook */ + @Size(max = 500, message = "Le User Agent ne peut pas dépasser 500 caractères") + private String userAgentSource; + + /** Nombre de tentatives de traitement */ + private Integer nombreTentativesTraitement; + + /** Message d'erreur de traitement (si échec) */ + @Size(max = 1000, message = "Le message d'erreur ne peut pas dépasser 1000 caractères") + private String messageErreurTraitement; + + /** Code d'erreur de traitement (si échec) */ + private String codeErreurTraitement; + + /** Stack trace de l'erreur (si échec) */ + @Size(max = 3000, message = "La stack trace ne peut pas dépasser 3000 caractères") + private String stackTraceErreur; + + /** Webhook traité automatiquement */ + private Boolean traitementAutomatique; + + /** Webhook nécessitant une intervention manuelle */ + private Boolean interventionManuelleRequise; + + /** Notes de traitement manuel */ + @Size(max = 1000, message = "Les notes ne peuvent pas dépasser 1000 caractères") + private String notesTraitementManuel; + + /** Utilisateur ayant traité manuellement */ + private String utilisateurTraitementManuel; + + /** Date du traitement manuel */ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime dateTraitementManuel; + + // Constructeurs + public WaveWebhookDTO() { + super(); + this.statutTraitement = StatutTraitement.RECU; + this.dateReception = LocalDateTime.now(); + this.nombreTentativesTraitement = 0; + this.traitementAutomatique = true; + this.interventionManuelleRequise = false; + } + + public WaveWebhookDTO(String webhookId, TypeEvenement typeEvenement, String payloadJson) { + this(); + this.webhookId = webhookId; + this.typeEvenement = typeEvenement; + this.codeEvenement = typeEvenement.getCodeWave(); + this.payloadJson = payloadJson; + } + + // Getters et Setters + public String getWebhookId() { + return webhookId; + } + + public void setWebhookId(String webhookId) { + this.webhookId = webhookId; + } + + public TypeEvenement getTypeEvenement() { + return typeEvenement; + } + + public void setTypeEvenement(TypeEvenement typeEvenement) { + this.typeEvenement = typeEvenement; + if (typeEvenement != null) { + this.codeEvenement = typeEvenement.getCodeWave(); + } + } + + public String getCodeEvenement() { + return codeEvenement; + } + + public void setCodeEvenement(String codeEvenement) { + this.codeEvenement = codeEvenement; + this.typeEvenement = TypeEvenement.fromCode(codeEvenement); + } + + public StatutTraitement getStatutTraitement() { + return statutTraitement; + } + + public void setStatutTraitement(StatutTraitement statutTraitement) { + this.statutTraitement = statutTraitement; + } + + public String getPayloadJson() { + return payloadJson; + } + + public void setPayloadJson(String payloadJson) { + this.payloadJson = payloadJson; + } + + public String getHeadersHttp() { + return headersHttp; + } + + public void setHeadersHttp(String headersHttp) { + this.headersHttp = headersHttp; + } + + public String getSignatureWave() { + return signatureWave; + } + + public void setSignatureWave(String signatureWave) { + this.signatureWave = signatureWave; + } + + public LocalDateTime getDateReception() { + return dateReception; + } + + public void setDateReception(LocalDateTime dateReception) { + this.dateReception = dateReception; + } + + public LocalDateTime getDateTraitement() { + return dateTraitement; + } + + public void setDateTraitement(LocalDateTime dateTraitement) { + this.dateTraitement = dateTraitement; + } + + public String getSessionCheckoutId() { + return sessionCheckoutId; + } + + public void setSessionCheckoutId(String sessionCheckoutId) { + this.sessionCheckoutId = sessionCheckoutId; + } + + public String getTransactionWaveId() { + return transactionWaveId; + } + + public void setTransactionWaveId(String transactionWaveId) { + this.transactionWaveId = transactionWaveId; + } + + public BigDecimal getMontantTransaction() { + return montantTransaction; + } + + public void setMontantTransaction(BigDecimal montantTransaction) { + this.montantTransaction = montantTransaction; + } + + public String getDeviseTransaction() { + return deviseTransaction; + } + + public void setDeviseTransaction(String deviseTransaction) { + this.deviseTransaction = deviseTransaction; + } + + public String getStatutTransactionWave() { + return statutTransactionWave; + } + + public void setStatutTransactionWave(String statutTransactionWave) { + this.statutTransactionWave = statutTransactionWave; + } + + public UUID getOrganisationId() { + return organisationId; + } + + public void setOrganisationId(UUID organisationId) { + this.organisationId = organisationId; + } + + public UUID getMembreId() { + return membreId; + } + + public void setMembreId(UUID membreId) { + this.membreId = membreId; + } + + public String getReferenceUnionFlow() { + return referenceUnionFlow; + } + + public void setReferenceUnionFlow(String referenceUnionFlow) { + this.referenceUnionFlow = referenceUnionFlow; + } + + public String getTypePaiementUnionFlow() { + return typePaiementUnionFlow; + } + + public void setTypePaiementUnionFlow(String typePaiementUnionFlow) { + this.typePaiementUnionFlow = typePaiementUnionFlow; + } + + public String getAdresseIpSource() { + return adresseIpSource; + } + + public void setAdresseIpSource(String adresseIpSource) { + this.adresseIpSource = adresseIpSource; + } + + public String getUserAgentSource() { + return userAgentSource; + } + + public void setUserAgentSource(String userAgentSource) { + this.userAgentSource = userAgentSource; + } + + public Integer getNombreTentativesTraitement() { + return nombreTentativesTraitement; + } + + public void setNombreTentativesTraitement(Integer nombreTentativesTraitement) { + this.nombreTentativesTraitement = nombreTentativesTraitement; + } + + public String getMessageErreurTraitement() { + return messageErreurTraitement; + } + + public void setMessageErreurTraitement(String messageErreurTraitement) { + this.messageErreurTraitement = messageErreurTraitement; + } + + public String getCodeErreurTraitement() { + return codeErreurTraitement; + } + + public void setCodeErreurTraitement(String codeErreurTraitement) { + this.codeErreurTraitement = codeErreurTraitement; + } + + public String getStackTraceErreur() { + return stackTraceErreur; + } + + public void setStackTraceErreur(String stackTraceErreur) { + this.stackTraceErreur = stackTraceErreur; + } + + public Boolean getTraitementAutomatique() { + return traitementAutomatique; + } + + public void setTraitementAutomatique(Boolean traitementAutomatique) { + this.traitementAutomatique = traitementAutomatique; + } + + public Boolean getInterventionManuelleRequise() { + return interventionManuelleRequise; + } + + public void setInterventionManuelleRequise(Boolean interventionManuelleRequise) { + this.interventionManuelleRequise = interventionManuelleRequise; + } + + public String getNotesTraitementManuel() { + return notesTraitementManuel; + } + + public void setNotesTraitementManuel(String notesTraitementManuel) { + this.notesTraitementManuel = notesTraitementManuel; + } + + public String getUtilisateurTraitementManuel() { + return utilisateurTraitementManuel; + } + + public void setUtilisateurTraitementManuel(String utilisateurTraitementManuel) { + this.utilisateurTraitementManuel = utilisateurTraitementManuel; + } + + public LocalDateTime getDateTraitementManuel() { + return dateTraitementManuel; + } + + public void setDateTraitementManuel(LocalDateTime dateTraitementManuel) { + this.dateTraitementManuel = dateTraitementManuel; + } + + // Méthodes utilitaires + + /** + * Vérifie si le webhook concerne un checkout + * + * @return true si c'est un événement de checkout + */ + public boolean isEvenementCheckout() { + return typeEvenement == TypeEvenement.CHECKOUT_COMPLETE + || typeEvenement == TypeEvenement.CHECKOUT_CANCELLED + || typeEvenement == TypeEvenement.CHECKOUT_EXPIRED; + } + + /** + * Vérifie si le webhook concerne un payout + * + * @return true si c'est un événement de payout + */ + public boolean isEvenementPayout() { + return typeEvenement == TypeEvenement.PAYOUT_COMPLETE + || typeEvenement == TypeEvenement.PAYOUT_FAILED; + } + + /** Marque le webhook comme traité avec succès */ + public void marquerCommeTraite() { + this.statutTraitement = StatutTraitement.TRAITE; + this.dateTraitement = LocalDateTime.now(); + marquerCommeModifie("SYSTEM"); + } + + /** + * Marque le webhook comme échoué + * + * @param messageErreur Le message d'erreur + * @param codeErreur Le code d'erreur + */ + public void marquerCommeEchec(String messageErreur, String codeErreur) { + this.statutTraitement = StatutTraitement.ECHEC; + this.messageErreurTraitement = messageErreur; + this.codeErreurTraitement = codeErreur; + this.nombreTentativesTraitement++; + this.dateTraitement = LocalDateTime.now(); + marquerCommeModifie("SYSTEM"); + } + + /** Démarre le traitement du webhook */ + public void demarrerTraitement() { + this.statutTraitement = StatutTraitement.EN_COURS; + this.nombreTentativesTraitement++; + marquerCommeModifie("SYSTEM"); + } + + @Override + public String toString() { + return "WaveWebhookDTO{" + + "webhookId='" + + webhookId + + '\'' + + ", typeEvenement=" + + typeEvenement + + ", statutTraitement=" + + statutTraitement + + ", dateReception=" + + dateReception + + ", sessionCheckoutId='" + + sessionCheckoutId + + '\'' + + ", montantTransaction=" + + montantTransaction + + "} " + + super.toString(); + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/paiement/request/InitierDepotEpargneRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/paiement/request/InitierDepotEpargneRequest.java index 4b1a82a..e686936 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/paiement/request/InitierDepotEpargneRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/paiement/request/InitierDepotEpargneRequest.java @@ -1,38 +1,38 @@ -package dev.lions.unionflow.server.api.dto.paiement.request; - -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Pattern; -import java.math.BigDecimal; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête pour initier un dépôt sur compte épargne via Wave (mobile money). - * Réutilise le même flux que les cotisations : Wave Checkout → redirection → deep link. - * - * @param compteId ID du compte épargne à créditer - * @param montant Montant du dépôt (XOF) - * @param numeroTelephone Numéro Wave du membre (9 chiffres) - * @param origineFonds Origine des fonds (LCB-FT) — obligatoire au-dessus du seuil configuré - * @param justificationLcbFt Justification complémentaire LCB-FT si nécessaire - */ -@Builder -public record InitierDepotEpargneRequest( - @NotNull(message = "L'ID du compte épargne est obligatoire") - UUID compteId, - - @NotNull(message = "Le montant est obligatoire") - @DecimalMin(value = "1", message = "Le montant doit être strictement positif") - BigDecimal montant, - - @NotBlank(message = "Le numéro de téléphone Wave est obligatoire") - @Pattern(regexp = "^\\d{9,15}$", message = "Numéro de téléphone invalide (9-15 chiffres)") - String numeroTelephone, - - String origineFonds, - - String justificationLcbFt -) { -} +package dev.lions.unionflow.server.api.dto.paiement.request; + +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Pattern; +import java.math.BigDecimal; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête pour initier un dépôt sur compte épargne via Wave (mobile money). + * Réutilise le même flux que les cotisations : Wave Checkout → redirection → deep link. + * + * @param compteId ID du compte épargne à créditer + * @param montant Montant du dépôt (XOF) + * @param numeroTelephone Numéro Wave du membre (9 chiffres) + * @param origineFonds Origine des fonds (LCB-FT) — obligatoire au-dessus du seuil configuré + * @param justificationLcbFt Justification complémentaire LCB-FT si nécessaire + */ +@Builder +public record InitierDepotEpargneRequest( + @NotNull(message = "L'ID du compte épargne est obligatoire") + UUID compteId, + + @NotNull(message = "Le montant est obligatoire") + @DecimalMin(value = "1", message = "Le montant doit être strictement positif") + BigDecimal montant, + + @NotBlank(message = "Le numéro de téléphone Wave est obligatoire") + @Pattern(regexp = "^\\d{9,15}$", message = "Numéro de téléphone invalide (9-15 chiffres)") + String numeroTelephone, + + String origineFonds, + + String justificationLcbFt +) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/reference/request/CreateTypeReferenceRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/reference/request/CreateTypeReferenceRequest.java index b8ad671..8b099b3 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/reference/request/CreateTypeReferenceRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/reference/request/CreateTypeReferenceRequest.java @@ -1,68 +1,68 @@ -package dev.lions.unionflow.server.api.dto.reference.request; - -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.Size; -import java.util.UUID; - -import lombok.Builder; - -/** - * Requête de création d'une donnée de référence. - * - *

- * Utilisé pour ajouter une nouvelle valeur dans - * un domaine existant de la table - * {@code types_reference}. - * - * @author UnionFlow Team - * @version 3.0 - * @since 2026-02-21 - */ -@Builder -public record CreateTypeReferenceRequest( - - /** Domaine fonctionnel (ex: STATUT_ORGANISATION). */ - @NotBlank @Size(max = 50) String domaine, - - /** Code technique unique dans le domaine. */ - @NotBlank @Size(max = 50) String code, - - /** Libellé affiché dans l'interface. */ - @NotBlank @Size(max = 200) String libelle, - - /** Description longue optionnelle. */ - @Size(max = 1000) String description, - - /** Classe d'icône PrimeFaces (ex: pi-check). */ - @Size(max = 100) String icone, - - /** Code couleur hexadécimal (ex: #22C55E). */ - @Size(max = 50) String couleur, - - /** Sévérité PrimeFaces (success, warning...). */ - @Size(max = 20) String severity, - - /** Ordre d'affichage dans les listes. */ - Integer ordreAffichage, - - /** Valeur par défaut pour ce domaine. */ - Boolean estDefaut, - - /** Protégée contre la suppression admin. */ - Boolean estSysteme, - - /** UUID de l'organisation (null = global). */ - UUID organisationId, - - /** - * Catégorie fonctionnelle (ex: FINANCIER_SOLIDAIRE). - * Obligatoire pour domaine=TYPE_ORGANISATION. - */ - @Size(max = 50) String categorie, - - /** - * Modules métier CSV (ex: "MEMBRES,COTISATIONS,TONTINE,FINANCE"). - * Obligatoire pour domaine=TYPE_ORGANISATION. - */ - String modulesRequis) { -} +package dev.lions.unionflow.server.api.dto.reference.request; + +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.Size; +import java.util.UUID; + +import lombok.Builder; + +/** + * Requête de création d'une donnée de référence. + * + *

+ * Utilisé pour ajouter une nouvelle valeur dans + * un domaine existant de la table + * {@code types_reference}. + * + * @author UnionFlow Team + * @version 3.0 + * @since 2026-02-21 + */ +@Builder +public record CreateTypeReferenceRequest( + + /** Domaine fonctionnel (ex: STATUT_ORGANISATION). */ + @NotBlank @Size(max = 50) String domaine, + + /** Code technique unique dans le domaine. */ + @NotBlank @Size(max = 50) String code, + + /** Libellé affiché dans l'interface. */ + @NotBlank @Size(max = 200) String libelle, + + /** Description longue optionnelle. */ + @Size(max = 1000) String description, + + /** Classe d'icône PrimeFaces (ex: pi-check). */ + @Size(max = 100) String icone, + + /** Code couleur hexadécimal (ex: #22C55E). */ + @Size(max = 50) String couleur, + + /** Sévérité PrimeFaces (success, warning...). */ + @Size(max = 20) String severity, + + /** Ordre d'affichage dans les listes. */ + Integer ordreAffichage, + + /** Valeur par défaut pour ce domaine. */ + Boolean estDefaut, + + /** Protégée contre la suppression admin. */ + Boolean estSysteme, + + /** UUID de l'organisation (null = global). */ + UUID organisationId, + + /** + * Catégorie fonctionnelle (ex: FINANCIER_SOLIDAIRE). + * Obligatoire pour domaine=TYPE_ORGANISATION. + */ + @Size(max = 50) String categorie, + + /** + * Modules métier CSV (ex: "MEMBRES,COTISATIONS,TONTINE,FINANCE"). + * Obligatoire pour domaine=TYPE_ORGANISATION. + */ + String modulesRequis) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/reference/request/UpdateTypeReferenceRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/reference/request/UpdateTypeReferenceRequest.java index d06dd37..d52a131 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/reference/request/UpdateTypeReferenceRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/reference/request/UpdateTypeReferenceRequest.java @@ -1,51 +1,51 @@ -package dev.lions.unionflow.server.api.dto.reference.request; - -import jakarta.validation.constraints.Size; - -/** - * Requête de mise à jour d'une donnée de référence. - * - *

- * Tous les champs sont optionnels : seuls les - * champs renseignés seront mis à jour (patch - * partiel). - * - * @author UnionFlow Team - * @version 3.0 - * @since 2026-02-21 - */ -public record UpdateTypeReferenceRequest( - - /** Nouveau code (optionnel). */ - @Size(max = 50) String code, - - /** Nouveau libellé (optionnel). */ - @Size(max = 200) String libelle, - - /** Nouvelle description (optionnel). */ - @Size(max = 1000) String description, - - /** Nouvelle icône (optionnel). */ - @Size(max = 100) String icone, - - /** Nouvelle couleur (optionnel). */ - @Size(max = 50) String couleur, - - /** Nouvelle sévérité (optionnel). */ - @Size(max = 20) String severity, - - /** Nouvel ordre d'affichage (optionnel). */ - Integer ordreAffichage, - - /** Nouveau flag par défaut (optionnel). */ - Boolean estDefaut, - - /** Nouvel état actif/inactif (optionnel). */ - Boolean actif, - - /** Nouvelle catégorie fonctionnelle (optionnel). */ - @Size(max = 50) String categorie, - - /** Nouveaux modules requis CSV (optionnel). */ - String modulesRequis) { -} +package dev.lions.unionflow.server.api.dto.reference.request; + +import jakarta.validation.constraints.Size; + +/** + * Requête de mise à jour d'une donnée de référence. + * + *

+ * Tous les champs sont optionnels : seuls les + * champs renseignés seront mis à jour (patch + * partiel). + * + * @author UnionFlow Team + * @version 3.0 + * @since 2026-02-21 + */ +public record UpdateTypeReferenceRequest( + + /** Nouveau code (optionnel). */ + @Size(max = 50) String code, + + /** Nouveau libellé (optionnel). */ + @Size(max = 200) String libelle, + + /** Nouvelle description (optionnel). */ + @Size(max = 1000) String description, + + /** Nouvelle icône (optionnel). */ + @Size(max = 100) String icone, + + /** Nouvelle couleur (optionnel). */ + @Size(max = 50) String couleur, + + /** Nouvelle sévérité (optionnel). */ + @Size(max = 20) String severity, + + /** Nouvel ordre d'affichage (optionnel). */ + Integer ordreAffichage, + + /** Nouveau flag par défaut (optionnel). */ + Boolean estDefaut, + + /** Nouvel état actif/inactif (optionnel). */ + Boolean actif, + + /** Nouvelle catégorie fonctionnelle (optionnel). */ + @Size(max = 50) String categorie, + + /** Nouveaux modules requis CSV (optionnel). */ + String modulesRequis) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/reference/response/TypeReferenceResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/reference/response/TypeReferenceResponse.java index 607b00a..4ea4cb7 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/reference/response/TypeReferenceResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/reference/response/TypeReferenceResponse.java @@ -1,78 +1,78 @@ -package dev.lions.unionflow.server.api.dto.reference.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse complète d'une donnée de référence. - * - *

- * Inclut les champs d'audit (id, dates, version) - * et toutes les métadonnées UI (icône, couleur, - * sévérité). - * - * @author UnionFlow Team - * @version 3.0 - * @since 2026-02-21 - */ -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class TypeReferenceResponse extends BaseResponse { - - /** Domaine fonctionnel. */ - private String domaine; - - /** Code technique. */ - private String code; - - /** Libellé affiché. */ - private String libelle; - - /** Description longue. */ - private String description; - - /** Classe d'icône PrimeFaces. */ - private String icone; - - /** Code couleur hexadécimal. */ - private String couleur; - - /** Sévérité PrimeFaces. */ - private String severity; - - /** Ordre d'affichage. */ - private Integer ordreAffichage; - - /** Valeur par défaut du domaine. */ - private Boolean estDefaut; - - /** Protégée contre la suppression. */ - private Boolean estSysteme; - - /** UUID de l'organisation (null = global). */ - private UUID organisationId; - - /** - * Catégorie fonctionnelle du type d'organisation. - * Valeurs: ASSOCIATIF, FINANCIER_SOLIDAIRE, RELIGIEUX, PROFESSIONNEL, RESEAU_FEDERATION. - * Uniquement pertinent pour domaine=TYPE_ORGANISATION. - */ - private String categorie; - - /** - * Modules métier activés pour ce type d'organisation (CSV). - * Exemple: "MEMBRES,COTISATIONS,TONTINE,FINANCE" - * Utilisé pour initialiser Organisation.modulesActifs à la création. - * Uniquement pertinent pour domaine=TYPE_ORGANISATION. - */ - private String modulesRequis; -} +package dev.lions.unionflow.server.api.dto.reference.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse complète d'une donnée de référence. + * + *

+ * Inclut les champs d'audit (id, dates, version) + * et toutes les métadonnées UI (icône, couleur, + * sévérité). + * + * @author UnionFlow Team + * @version 3.0 + * @since 2026-02-21 + */ +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class TypeReferenceResponse extends BaseResponse { + + /** Domaine fonctionnel. */ + private String domaine; + + /** Code technique. */ + private String code; + + /** Libellé affiché. */ + private String libelle; + + /** Description longue. */ + private String description; + + /** Classe d'icône PrimeFaces. */ + private String icone; + + /** Code couleur hexadécimal. */ + private String couleur; + + /** Sévérité PrimeFaces. */ + private String severity; + + /** Ordre d'affichage. */ + private Integer ordreAffichage; + + /** Valeur par défaut du domaine. */ + private Boolean estDefaut; + + /** Protégée contre la suppression. */ + private Boolean estSysteme; + + /** UUID de l'organisation (null = global). */ + private UUID organisationId; + + /** + * Catégorie fonctionnelle du type d'organisation. + * Valeurs: ASSOCIATIF, FINANCIER_SOLIDAIRE, RELIGIEUX, PROFESSIONNEL, RESEAU_FEDERATION. + * Uniquement pertinent pour domaine=TYPE_ORGANISATION. + */ + private String categorie; + + /** + * Modules métier activés pour ce type d'organisation (CSV). + * Exemple: "MEMBRES,COTISATIONS,TONTINE,FINANCE" + * Utilisé pour initialiser Organisation.modulesActifs à la création. + * Uniquement pertinent pour domaine=TYPE_ORGANISATION. + */ + private String modulesRequis; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/registre/AgrementProfessionnelDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/registre/AgrementProfessionnelDTO.java index 90e227a..60a0af0 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/registre/AgrementProfessionnelDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/registre/AgrementProfessionnelDTO.java @@ -1,33 +1,33 @@ -package dev.lions.unionflow.server.api.dto.registre; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.registre.StatutAgrement; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; - -import java.time.LocalDate; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class AgrementProfessionnelDTO extends BaseDTO { - - private String membreId; - private String organisationId; - - // Métier, Ordre (Médecins, Avocats, Artisans...) - private String secteurOuOrdre; - - private String numeroLicenceOuRegistre; - private String categorieClassement; - - private LocalDate dateDelivrance; - private LocalDate dateExpiration; - - private StatutAgrement statut; -} +package dev.lions.unionflow.server.api.dto.registre; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.registre.StatutAgrement; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; + +import java.time.LocalDate; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class AgrementProfessionnelDTO extends BaseDTO { + + private String membreId; + private String organisationId; + + // Métier, Ordre (Médecins, Avocats, Artisans...) + private String secteurOuOrdre; + + private String numeroLicenceOuRegistre; + private String categorieClassement; + + private LocalDate dateDelivrance; + private LocalDate dateExpiration; + + private StatutAgrement statut; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/role/request/CreateRoleRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/role/request/CreateRoleRequest.java index a826217..f58ec31 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/role/request/CreateRoleRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/role/request/CreateRoleRequest.java @@ -1,20 +1,20 @@ -package dev.lions.unionflow.server.api.dto.role.request; - -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'un rôle. - */ -@Builder -public record CreateRoleRequest( - @NotBlank(message = "Le code est obligatoire") @Size(max = 50) String code, - @NotBlank(message = "Le libellé est obligatoire") @Size(max = 100) String libelle, - @Size(max = 500) String description, - @NotBlank(message = "Le type de rôle est obligatoire") String typeRole, - @NotNull(message = "Le niveau hiérarchique est obligatoire") Integer niveauHierarchique, - UUID organisationId) { -} +package dev.lions.unionflow.server.api.dto.role.request; + +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'un rôle. + */ +@Builder +public record CreateRoleRequest( + @NotBlank(message = "Le code est obligatoire") @Size(max = 50) String code, + @NotBlank(message = "Le libellé est obligatoire") @Size(max = 100) String libelle, + @Size(max = 500) String description, + @NotBlank(message = "Le type de rôle est obligatoire") String typeRole, + @NotNull(message = "Le niveau hiérarchique est obligatoire") Integer niveauHierarchique, + UUID organisationId) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/role/request/UpdateRoleRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/role/request/UpdateRoleRequest.java index e076fbb..9b6761f 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/role/request/UpdateRoleRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/role/request/UpdateRoleRequest.java @@ -1,17 +1,17 @@ -package dev.lions.unionflow.server.api.dto.role.request; - -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import lombok.Builder; - -/** - * Requête de mise à jour d'un rôle. - */ -@Builder -public record UpdateRoleRequest( - @NotBlank(message = "Le libellé est obligatoire") @Size(max = 100) String libelle, - @Size(max = 500) String description, - @NotNull(message = "Le niveau hiérarchique est obligatoire") Integer niveauHierarchique, - Boolean actif) { -} +package dev.lions.unionflow.server.api.dto.role.request; + +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import lombok.Builder; + +/** + * Requête de mise à jour d'un rôle. + */ +@Builder +public record UpdateRoleRequest( + @NotBlank(message = "Le libellé est obligatoire") @Size(max = 100) String libelle, + @Size(max = 500) String description, + @NotNull(message = "Le niveau hiérarchique est obligatoire") Integer niveauHierarchique, + Boolean actif) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/role/response/PermissionResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/role/response/PermissionResponse.java index 6ead6e5..a271fcf 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/role/response/PermissionResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/role/response/PermissionResponse.java @@ -1,28 +1,28 @@ -package dev.lions.unionflow.server.api.dto.role.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; - -/** - * Réponse contenant les données d'une permission. - * - * @author UnionFlow Team - * @version 3.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class PermissionResponse extends BaseResponse { - private String code; - private String module; - private String ressource; - private String action; - private String libelle; - private String description; -} +package dev.lions.unionflow.server.api.dto.role.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; + +/** + * Réponse contenant les données d'une permission. + * + * @author UnionFlow Team + * @version 3.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class PermissionResponse extends BaseResponse { + private String code; + private String module; + private String ressource; + private String action; + private String libelle; + private String description; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/role/response/RoleResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/role/response/RoleResponse.java index c504e73..3d10346 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/role/response/RoleResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/role/response/RoleResponse.java @@ -1,29 +1,29 @@ -package dev.lions.unionflow.server.api.dto.role.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée pour un rôle. - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class RoleResponse extends BaseResponse { - - private String code; - private String libelle; - private String description; - private String typeRole; - private Integer niveauHierarchique; - private UUID organisationId; - private String nomOrganisation; -} +package dev.lions.unionflow.server.api.dto.role.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée pour un rôle. + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class RoleResponse extends BaseResponse { + + private String code; + private String libelle; + private String description; + private String typeRole; + private Integer niveauHierarchique; + private UUID organisationId; + private String nomOrganisation; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/BeneficiaireAideDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/BeneficiaireAideDTO.java index 0d9cab5..3c37d23 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/BeneficiaireAideDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/BeneficiaireAideDTO.java @@ -1,71 +1,71 @@ -package dev.lions.unionflow.server.api.dto.solidarite; - -import jakarta.validation.constraints.*; -import java.time.LocalDate; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO pour les bénéficiaires d'une aide - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class BeneficiaireAideDTO { - - /** Identifiant unique du bénéficiaire */ - private String id; - - /** Nom complet du bénéficiaire */ - @NotBlank(message = "Le nom du bénéficiaire est obligatoire") - @Size(max = 100, message = "Le nom ne peut pas dépasser 100 caractères") - private String nomComplet; - - /** Relation avec le demandeur */ - @NotBlank(message = "La relation avec le demandeur est obligatoire") - private String relationDemandeur; - - /** Date de naissance */ - private LocalDate dateNaissance; - - /** Âge calculé */ - private Integer age; - - /** Genre */ - private String genre; - - /** Numéro de téléphone */ - @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Le numéro de téléphone n'est pas valide") - private String telephone; - - /** Adresse email */ - @Email(message = "L'adresse email n'est pas valide") - private String email; - - /** Adresse physique */ - @Size(max = 200, message = "L'adresse ne peut pas dépasser 200 caractères") - private String adresse; - - /** Situation particulière (handicap, maladie, etc.) */ - @Size(max = 500, message = "La situation particulière ne peut pas dépasser 500 caractères") - private String situationParticuliere; - - /** Indique si le bénéficiaire est le demandeur principal */ - @Builder.Default private Boolean estDemandeurPrincipal = false; - - /** Pourcentage de l'aide destiné à ce bénéficiaire */ - @DecimalMin(value = "0.0", message = "Le pourcentage doit être positif") - @DecimalMax(value = "100.0", message = "Le pourcentage ne peut pas dépasser 100%") - private Double pourcentageAide; - - /** Montant spécifique pour ce bénéficiaire */ - @DecimalMin(value = "0.0", message = "Le montant doit être positif") - private Double montantSpecifique; -} +package dev.lions.unionflow.server.api.dto.solidarite; + +import jakarta.validation.constraints.*; +import java.time.LocalDate; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO pour les bénéficiaires d'une aide + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class BeneficiaireAideDTO { + + /** Identifiant unique du bénéficiaire */ + private String id; + + /** Nom complet du bénéficiaire */ + @NotBlank(message = "Le nom du bénéficiaire est obligatoire") + @Size(max = 100, message = "Le nom ne peut pas dépasser 100 caractères") + private String nomComplet; + + /** Relation avec le demandeur */ + @NotBlank(message = "La relation avec le demandeur est obligatoire") + private String relationDemandeur; + + /** Date de naissance */ + private LocalDate dateNaissance; + + /** Âge calculé */ + private Integer age; + + /** Genre */ + private String genre; + + /** Numéro de téléphone */ + @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Le numéro de téléphone n'est pas valide") + private String telephone; + + /** Adresse email */ + @Email(message = "L'adresse email n'est pas valide") + private String email; + + /** Adresse physique */ + @Size(max = 200, message = "L'adresse ne peut pas dépasser 200 caractères") + private String adresse; + + /** Situation particulière (handicap, maladie, etc.) */ + @Size(max = 500, message = "La situation particulière ne peut pas dépasser 500 caractères") + private String situationParticuliere; + + /** Indique si le bénéficiaire est le demandeur principal */ + @Builder.Default private Boolean estDemandeurPrincipal = false; + + /** Pourcentage de l'aide destiné à ce bénéficiaire */ + @DecimalMin(value = "0.0", message = "Le pourcentage doit être positif") + @DecimalMax(value = "100.0", message = "Le pourcentage ne peut pas dépasser 100%") + private Double pourcentageAide; + + /** Montant spécifique pour ce bénéficiaire */ + @DecimalMin(value = "0.0", message = "Le montant doit être positif") + private Double montantSpecifique; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/ContactProposantDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/ContactProposantDTO.java index 3918e43..25aab99 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/ContactProposantDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/ContactProposantDTO.java @@ -1,77 +1,77 @@ -package dev.lions.unionflow.server.api.dto.solidarite; - -import jakarta.validation.constraints.*; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO pour les informations de contact du proposant d'aide - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class ContactProposantDTO { - - /** Numéro de téléphone principal */ - @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Le numéro de téléphone n'est pas valide") - private String telephonePrincipal; - - /** Numéro de téléphone secondaire */ - @Pattern( - regexp = "^\\+?[0-9]{8,15}$", - message = "Le numéro de téléphone secondaire n'est pas valide") - private String telephoneSecondaire; - - /** Adresse email */ - @Email(message = "L'adresse email n'est pas valide") - private String email; - - /** Adresse email secondaire */ - @Email(message = "L'adresse email secondaire n'est pas valide") - private String emailSecondaire; - - /** Identifiant WhatsApp */ - @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Le numéro WhatsApp n'est pas valide") - private String whatsapp; - - /** Identifiant Telegram */ - @Size(max = 50, message = "L'identifiant Telegram ne peut pas dépasser 50 caractères") - private String telegram; - - /** Autres moyens de contact (réseaux sociaux, etc.) */ - private java.util.Map autresContacts; - - /** Adresse physique pour rencontres */ - @Size(max = 200, message = "L'adresse ne peut pas dépasser 200 caractères") - private String adressePhysique; - - /** Indique si les rencontres physiques sont possibles */ - @Builder.Default private Boolean rencontresPhysiquesPossibles = false; - - /** Indique si les appels téléphoniques sont acceptés */ - @Builder.Default private Boolean appelsAcceptes = true; - - /** Indique si les SMS sont acceptés */ - @Builder.Default private Boolean smsAcceptes = true; - - /** Indique si les emails sont acceptés */ - @Builder.Default private Boolean emailsAcceptes = true; - - /** Horaires de disponibilité pour contact */ - @Size(max = 200, message = "Les horaires ne peuvent pas dépasser 200 caractères") - private String horairesDisponibilite; - - /** Langue(s) de communication préférée(s) */ - private java.util.List languesPreferees; - - /** Instructions spéciales pour le contact */ - @Size(max = 300, message = "Les instructions ne peuvent pas dépasser 300 caractères") - private String instructionsSpeciales; -} +package dev.lions.unionflow.server.api.dto.solidarite; + +import jakarta.validation.constraints.*; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO pour les informations de contact du proposant d'aide + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class ContactProposantDTO { + + /** Numéro de téléphone principal */ + @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Le numéro de téléphone n'est pas valide") + private String telephonePrincipal; + + /** Numéro de téléphone secondaire */ + @Pattern( + regexp = "^\\+?[0-9]{8,15}$", + message = "Le numéro de téléphone secondaire n'est pas valide") + private String telephoneSecondaire; + + /** Adresse email */ + @Email(message = "L'adresse email n'est pas valide") + private String email; + + /** Adresse email secondaire */ + @Email(message = "L'adresse email secondaire n'est pas valide") + private String emailSecondaire; + + /** Identifiant WhatsApp */ + @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Le numéro WhatsApp n'est pas valide") + private String whatsapp; + + /** Identifiant Telegram */ + @Size(max = 50, message = "L'identifiant Telegram ne peut pas dépasser 50 caractères") + private String telegram; + + /** Autres moyens de contact (réseaux sociaux, etc.) */ + private java.util.Map autresContacts; + + /** Adresse physique pour rencontres */ + @Size(max = 200, message = "L'adresse ne peut pas dépasser 200 caractères") + private String adressePhysique; + + /** Indique si les rencontres physiques sont possibles */ + @Builder.Default private Boolean rencontresPhysiquesPossibles = false; + + /** Indique si les appels téléphoniques sont acceptés */ + @Builder.Default private Boolean appelsAcceptes = true; + + /** Indique si les SMS sont acceptés */ + @Builder.Default private Boolean smsAcceptes = true; + + /** Indique si les emails sont acceptés */ + @Builder.Default private Boolean emailsAcceptes = true; + + /** Horaires de disponibilité pour contact */ + @Size(max = 200, message = "Les horaires ne peuvent pas dépasser 200 caractères") + private String horairesDisponibilite; + + /** Langue(s) de communication préférée(s) */ + private java.util.List languesPreferees; + + /** Instructions spéciales pour le contact */ + @Size(max = 300, message = "Les instructions ne peuvent pas dépasser 300 caractères") + private String instructionsSpeciales; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/ContactUrgenceDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/ContactUrgenceDTO.java index 6d8e088..99bc383 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/ContactUrgenceDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/ContactUrgenceDTO.java @@ -1,64 +1,64 @@ -package dev.lions.unionflow.server.api.dto.solidarite; - -import jakarta.validation.constraints.*; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO pour les informations de contact d'urgence - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class ContactUrgenceDTO { - - /** Nom complet du contact d'urgence */ - @NotBlank(message = "Le nom du contact d'urgence est obligatoire") - @Size(max = 100, message = "Le nom ne peut pas dépasser 100 caractères") - private String nomComplet; - - /** Relation avec le demandeur */ - @NotBlank(message = "La relation avec le demandeur est obligatoire") - @Size(max = 50, message = "La relation ne peut pas dépasser 50 caractères") - private String relation; - - /** Numéro de téléphone principal */ - @NotBlank(message = "Le numéro de téléphone est obligatoire") - @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Le numéro de téléphone n'est pas valide") - private String telephonePrincipal; - - /** Numéro de téléphone secondaire */ - @Pattern( - regexp = "^\\+?[0-9]{8,15}$", - message = "Le numéro de téléphone secondaire n'est pas valide") - private String telephoneSecondaire; - - /** Adresse email */ - @Email(message = "L'adresse email n'est pas valide") - private String email; - - /** Adresse physique */ - @Size(max = 200, message = "L'adresse ne peut pas dépasser 200 caractères") - private String adresse; - - /** Disponibilité (horaires) */ - @Size(max = 100, message = "La disponibilité ne peut pas dépasser 100 caractères") - private String disponibilite; - - /** Indique si ce contact peut prendre des décisions pour le demandeur */ - @Builder.Default private Boolean peutPrendreDecisions = false; - - /** Indique si ce contact doit être notifié automatiquement */ - @Builder.Default private Boolean notificationAutomatique = true; - - /** Commentaires additionnels */ - @Size(max = 300, message = "Les commentaires ne peuvent pas dépasser 300 caractères") - private String commentaires; -} +package dev.lions.unionflow.server.api.dto.solidarite; + +import jakarta.validation.constraints.*; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO pour les informations de contact d'urgence + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class ContactUrgenceDTO { + + /** Nom complet du contact d'urgence */ + @NotBlank(message = "Le nom du contact d'urgence est obligatoire") + @Size(max = 100, message = "Le nom ne peut pas dépasser 100 caractères") + private String nomComplet; + + /** Relation avec le demandeur */ + @NotBlank(message = "La relation avec le demandeur est obligatoire") + @Size(max = 50, message = "La relation ne peut pas dépasser 50 caractères") + private String relation; + + /** Numéro de téléphone principal */ + @NotBlank(message = "Le numéro de téléphone est obligatoire") + @Pattern(regexp = "^\\+?[0-9]{8,15}$", message = "Le numéro de téléphone n'est pas valide") + private String telephonePrincipal; + + /** Numéro de téléphone secondaire */ + @Pattern( + regexp = "^\\+?[0-9]{8,15}$", + message = "Le numéro de téléphone secondaire n'est pas valide") + private String telephoneSecondaire; + + /** Adresse email */ + @Email(message = "L'adresse email n'est pas valide") + private String email; + + /** Adresse physique */ + @Size(max = 200, message = "L'adresse ne peut pas dépasser 200 caractères") + private String adresse; + + /** Disponibilité (horaires) */ + @Size(max = 100, message = "La disponibilité ne peut pas dépasser 100 caractères") + private String disponibilite; + + /** Indique si ce contact peut prendre des décisions pour le demandeur */ + @Builder.Default private Boolean peutPrendreDecisions = false; + + /** Indique si ce contact doit être notifié automatiquement */ + @Builder.Default private Boolean notificationAutomatique = true; + + /** Commentaires additionnels */ + @Size(max = 300, message = "Les commentaires ne peuvent pas dépasser 300 caractères") + private String commentaires; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/CreneauDisponibiliteDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/CreneauDisponibiliteDTO.java index f84ba30..467b836 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/CreneauDisponibiliteDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/CreneauDisponibiliteDTO.java @@ -1,139 +1,139 @@ -package dev.lions.unionflow.server.api.dto.solidarite; - -import jakarta.validation.constraints.*; -import java.time.DayOfWeek; -import java.time.LocalDate; -import java.time.LocalTime; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO pour les créneaux de disponibilité du proposant - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class CreneauDisponibiliteDTO { - - /** Identifiant unique du créneau */ - private String id; - - /** Jour de la semaine (pour créneaux récurrents) */ - private DayOfWeek jourSemaine; - - /** Date spécifique (pour créneaux ponctuels) */ - private LocalDate dateSpecifique; - - /** Heure de début */ - @NotNull(message = "L'heure de début est obligatoire") - private LocalTime heureDebut; - - /** Heure de fin */ - @NotNull(message = "L'heure de fin est obligatoire") - private LocalTime heureFin; - - /** Type de créneau */ - @NotNull(message = "Le type de créneau est obligatoire") - @Builder.Default - private TypeCreneau type = TypeCreneau.RECURRENT; - - /** Indique si le créneau est actif */ - @Builder.Default private Boolean estActif = true; - - /** Fuseau horaire */ - @Builder.Default private String fuseauHoraire = "Africa/Abidjan"; - - /** Commentaires sur le créneau */ - @Size(max = 200, message = "Les commentaires ne peuvent pas dépasser 200 caractères") - private String commentaires; - - /** Priorité du créneau (1 = haute, 5 = basse) */ - @Min(value = 1, message = "La priorité doit être au moins 1") - @Max(value = 5, message = "La priorité ne peut pas dépasser 5") - @Builder.Default - private Integer priorite = 3; - - /** Durée maximale d'intervention en minutes */ - @Min(value = 15, message = "La durée doit être au moins 15 minutes") - @Max(value = 480, message = "La durée ne peut pas dépasser 8 heures") - private Integer dureeMaxMinutes; - - /** Indique si des pauses sont nécessaires */ - @Builder.Default private Boolean pausesNecessaires = false; - - /** Durée des pauses en minutes */ - @Min(value = 5, message = "La durée de pause doit être au moins 5 minutes") - private Integer dureePauseMinutes; - - /** Énumération des types de créneaux */ - public enum TypeCreneau { - RECURRENT("Récurrent"), - PONCTUEL("Ponctuel"), - URGENCE("Urgence"), - FLEXIBLE("Flexible"); - - private final String libelle; - - TypeCreneau(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } - } - - // === MÉTHODES UTILITAIRES === - - /** Vérifie si le créneau est valide (heure fin > heure début) */ - public boolean isValide() { - return heureDebut != null && heureFin != null && heureFin.isAfter(heureDebut); - } - - /** Calcule la durée du créneau en minutes */ - public long getDureeMinutes() { - if (!isValide()) return 0; - return java.time.Duration.between(heureDebut, heureFin).toMinutes(); - } - - /** Vérifie si le créneau est disponible à une date donnée */ - public boolean isDisponibleLe(LocalDate date) { - if (!estActif) return false; - - return switch (type) { - case PONCTUEL -> dateSpecifique != null && dateSpecifique.equals(date); - case RECURRENT -> jourSemaine != null && date.getDayOfWeek() == jourSemaine; - case URGENCE, FLEXIBLE -> true; - }; - } - - /** Vérifie si une heure est dans le créneau */ - public boolean contientHeure(LocalTime heure) { - if (!isValide()) return false; - return !heure.isBefore(heureDebut) && !heure.isAfter(heureFin); - } - - /** Retourne le libellé du créneau */ - public String getLibelle() { - StringBuilder sb = new StringBuilder(); - - boolean recurrentAvecJour = type == TypeCreneau.RECURRENT && jourSemaine != null; - boolean ponctuelAvecDate = type == TypeCreneau.PONCTUEL && dateSpecifique != null; - if (recurrentAvecJour) { - sb.append(jourSemaine.name()).append(" "); - } else if (ponctuelAvecDate) { - sb.append(dateSpecifique.toString()).append(" "); - } - - sb.append(heureDebut.toString()).append(" - ").append(heureFin.toString()); - - return sb.toString(); - } -} +package dev.lions.unionflow.server.api.dto.solidarite; + +import jakarta.validation.constraints.*; +import java.time.DayOfWeek; +import java.time.LocalDate; +import java.time.LocalTime; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO pour les créneaux de disponibilité du proposant + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class CreneauDisponibiliteDTO { + + /** Identifiant unique du créneau */ + private String id; + + /** Jour de la semaine (pour créneaux récurrents) */ + private DayOfWeek jourSemaine; + + /** Date spécifique (pour créneaux ponctuels) */ + private LocalDate dateSpecifique; + + /** Heure de début */ + @NotNull(message = "L'heure de début est obligatoire") + private LocalTime heureDebut; + + /** Heure de fin */ + @NotNull(message = "L'heure de fin est obligatoire") + private LocalTime heureFin; + + /** Type de créneau */ + @NotNull(message = "Le type de créneau est obligatoire") + @Builder.Default + private TypeCreneau type = TypeCreneau.RECURRENT; + + /** Indique si le créneau est actif */ + @Builder.Default private Boolean estActif = true; + + /** Fuseau horaire */ + @Builder.Default private String fuseauHoraire = "Africa/Abidjan"; + + /** Commentaires sur le créneau */ + @Size(max = 200, message = "Les commentaires ne peuvent pas dépasser 200 caractères") + private String commentaires; + + /** Priorité du créneau (1 = haute, 5 = basse) */ + @Min(value = 1, message = "La priorité doit être au moins 1") + @Max(value = 5, message = "La priorité ne peut pas dépasser 5") + @Builder.Default + private Integer priorite = 3; + + /** Durée maximale d'intervention en minutes */ + @Min(value = 15, message = "La durée doit être au moins 15 minutes") + @Max(value = 480, message = "La durée ne peut pas dépasser 8 heures") + private Integer dureeMaxMinutes; + + /** Indique si des pauses sont nécessaires */ + @Builder.Default private Boolean pausesNecessaires = false; + + /** Durée des pauses en minutes */ + @Min(value = 5, message = "La durée de pause doit être au moins 5 minutes") + private Integer dureePauseMinutes; + + /** Énumération des types de créneaux */ + public enum TypeCreneau { + RECURRENT("Récurrent"), + PONCTUEL("Ponctuel"), + URGENCE("Urgence"), + FLEXIBLE("Flexible"); + + private final String libelle; + + TypeCreneau(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } + } + + // === MÉTHODES UTILITAIRES === + + /** Vérifie si le créneau est valide (heure fin > heure début) */ + public boolean isValide() { + return heureDebut != null && heureFin != null && heureFin.isAfter(heureDebut); + } + + /** Calcule la durée du créneau en minutes */ + public long getDureeMinutes() { + if (!isValide()) return 0; + return java.time.Duration.between(heureDebut, heureFin).toMinutes(); + } + + /** Vérifie si le créneau est disponible à une date donnée */ + public boolean isDisponibleLe(LocalDate date) { + if (!estActif) return false; + + return switch (type) { + case PONCTUEL -> dateSpecifique != null && dateSpecifique.equals(date); + case RECURRENT -> jourSemaine != null && date.getDayOfWeek() == jourSemaine; + case URGENCE, FLEXIBLE -> true; + }; + } + + /** Vérifie si une heure est dans le créneau */ + public boolean contientHeure(LocalTime heure) { + if (!isValide()) return false; + return !heure.isBefore(heureDebut) && !heure.isAfter(heureFin); + } + + /** Retourne le libellé du créneau */ + public String getLibelle() { + StringBuilder sb = new StringBuilder(); + + boolean recurrentAvecJour = type == TypeCreneau.RECURRENT && jourSemaine != null; + boolean ponctuelAvecDate = type == TypeCreneau.PONCTUEL && dateSpecifique != null; + if (recurrentAvecJour) { + sb.append(jourSemaine.name()).append(" "); + } else if (ponctuelAvecDate) { + sb.append(dateSpecifique.toString()).append(" "); + } + + sb.append(heureDebut.toString()).append(" - ").append(heureFin.toString()); + + return sb.toString(); + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/CritereSelectionDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/CritereSelectionDTO.java index c8b89ac..379a4fc 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/CritereSelectionDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/CritereSelectionDTO.java @@ -1,54 +1,54 @@ -package dev.lions.unionflow.server.api.dto.solidarite; - -import jakarta.validation.constraints.*; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO pour les critères de sélection des bénéficiaires - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class CritereSelectionDTO { - - /** Nom du critère */ - @NotBlank(message = "Le nom du critère est obligatoire") - @Size(max = 100, message = "Le nom ne peut pas dépasser 100 caractères") - private String nom; - - /** Type de critère (age, situation, localisation, etc.) */ - @NotBlank(message = "Le type de critère est obligatoire") - private String type; - - /** Opérateur de comparaison (equals, greater_than, less_than, contains, etc.) */ - @NotBlank(message = "L'opérateur est obligatoire") - private String operateur; - - /** Valeur de référence pour la comparaison */ - @NotBlank(message = "La valeur est obligatoire") - private String valeur; - - /** Valeur maximale (pour les plages) */ - private String valeurMax; - - /** Indique si le critère est obligatoire */ - @Builder.Default private Boolean estObligatoire = false; - - /** Poids du critère dans la sélection (1-10) */ - @Min(value = 1, message = "Le poids doit être au moins 1") - @Max(value = 10, message = "Le poids ne peut pas dépasser 10") - @Builder.Default - private Integer poids = 5; - - /** Description du critère */ - @Size(max = 200, message = "La description ne peut pas dépasser 200 caractères") - private String description; -} +package dev.lions.unionflow.server.api.dto.solidarite; + +import jakarta.validation.constraints.*; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO pour les critères de sélection des bénéficiaires + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class CritereSelectionDTO { + + /** Nom du critère */ + @NotBlank(message = "Le nom du critère est obligatoire") + @Size(max = 100, message = "Le nom ne peut pas dépasser 100 caractères") + private String nom; + + /** Type de critère (age, situation, localisation, etc.) */ + @NotBlank(message = "Le type de critère est obligatoire") + private String type; + + /** Opérateur de comparaison (equals, greater_than, less_than, contains, etc.) */ + @NotBlank(message = "L'opérateur est obligatoire") + private String operateur; + + /** Valeur de référence pour la comparaison */ + @NotBlank(message = "La valeur est obligatoire") + private String valeur; + + /** Valeur maximale (pour les plages) */ + private String valeurMax; + + /** Indique si le critère est obligatoire */ + @Builder.Default private Boolean estObligatoire = false; + + /** Poids du critère dans la sélection (1-10) */ + @Min(value = 1, message = "Le poids doit être au moins 1") + @Max(value = 10, message = "Le poids ne peut pas dépasser 10") + @Builder.Default + private Integer poids = 5; + + /** Description du critère */ + @Size(max = 200, message = "La description ne peut pas dépasser 200 caractères") + private String description; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/HistoriqueStatutDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/HistoriqueStatutDTO.java index 84c8dc5..cb90aa0 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/HistoriqueStatutDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/HistoriqueStatutDTO.java @@ -1,62 +1,62 @@ -package dev.lions.unionflow.server.api.dto.solidarite; - -import dev.lions.unionflow.server.api.enums.solidarite.StatutAide; -import jakarta.validation.constraints.*; -import java.time.LocalDateTime; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO pour l'historique des changements de statut d'une demande d'aide - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class HistoriqueStatutDTO { - - /** Identifiant unique de l'entrée d'historique */ - private String id; - - /** Ancien statut */ - private StatutAide ancienStatut; - - /** Nouveau statut */ - @NotNull(message = "Le nouveau statut est obligatoire") - private StatutAide nouveauStatut; - - /** Date du changement de statut */ - @NotNull(message = "La date de changement est obligatoire") - @Builder.Default - private LocalDateTime dateChangement = LocalDateTime.now(); - - /** Identifiant de la personne qui a effectué le changement */ - @NotBlank(message = "L'identifiant de l'auteur est obligatoire") - private String auteurId; - - /** Nom de la personne qui a effectué le changement */ - private String auteurNom; - - /** Motif du changement de statut */ - @Size(max = 500, message = "Le motif ne peut pas dépasser 500 caractères") - private String motif; - - /** Commentaires additionnels */ - @Size(max = 1000, message = "Les commentaires ne peuvent pas dépasser 1000 caractères") - private String commentaires; - - /** Indique si le changement est automatique (système) */ - @Builder.Default private Boolean estAutomatique = false; - - /** Durée en minutes depuis le statut précédent */ - private Long dureeDepuisPrecedent; - - /** Données additionnelles liées au changement */ - private java.util.Map donneesAdditionnelles; -} +package dev.lions.unionflow.server.api.dto.solidarite; + +import dev.lions.unionflow.server.api.enums.solidarite.StatutAide; +import jakarta.validation.constraints.*; +import java.time.LocalDateTime; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO pour l'historique des changements de statut d'une demande d'aide + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class HistoriqueStatutDTO { + + /** Identifiant unique de l'entrée d'historique */ + private String id; + + /** Ancien statut */ + private StatutAide ancienStatut; + + /** Nouveau statut */ + @NotNull(message = "Le nouveau statut est obligatoire") + private StatutAide nouveauStatut; + + /** Date du changement de statut */ + @NotNull(message = "La date de changement est obligatoire") + @Builder.Default + private LocalDateTime dateChangement = LocalDateTime.now(); + + /** Identifiant de la personne qui a effectué le changement */ + @NotBlank(message = "L'identifiant de l'auteur est obligatoire") + private String auteurId; + + /** Nom de la personne qui a effectué le changement */ + private String auteurNom; + + /** Motif du changement de statut */ + @Size(max = 500, message = "Le motif ne peut pas dépasser 500 caractères") + private String motif; + + /** Commentaires additionnels */ + @Size(max = 1000, message = "Les commentaires ne peuvent pas dépasser 1000 caractères") + private String commentaires; + + /** Indique si le changement est automatique (système) */ + @Builder.Default private Boolean estAutomatique = false; + + /** Durée en minutes depuis le statut précédent */ + private Long dureeDepuisPrecedent; + + /** Données additionnelles liées au changement */ + private java.util.Map donneesAdditionnelles; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/LocalisationDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/LocalisationDTO.java index fb972b7..c8f9442 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/LocalisationDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/LocalisationDTO.java @@ -1,58 +1,58 @@ -package dev.lions.unionflow.server.api.dto.solidarite; - -import jakarta.validation.constraints.*; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO pour les informations de géolocalisation - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class LocalisationDTO { - - /** Latitude */ - @DecimalMin(value = "-90.0", message = "La latitude doit être comprise entre -90 et 90") - @DecimalMax(value = "90.0", message = "La latitude doit être comprise entre -90 et 90") - private Double latitude; - - /** Longitude */ - @DecimalMin(value = "-180.0", message = "La longitude doit être comprise entre -180 et 180") - @DecimalMax(value = "180.0", message = "La longitude doit être comprise entre -180 et 180") - private Double longitude; - - /** Adresse complète */ - @Size(max = 300, message = "L'adresse ne peut pas dépasser 300 caractères") - private String adresseComplete; - - /** Ville */ - @Size(max = 100, message = "La ville ne peut pas dépasser 100 caractères") - private String ville; - - /** Région/Province */ - @Size(max = 100, message = "La région ne peut pas dépasser 100 caractères") - private String region; - - /** Pays */ - @Size(max = 100, message = "Le pays ne peut pas dépasser 100 caractères") - private String pays; - - /** Code postal */ - @Size(max = 20, message = "Le code postal ne peut pas dépasser 20 caractères") - private String codePostal; - - /** Précision de la localisation en mètres */ - @Min(value = 0, message = "La précision doit être positive") - private Double precision; - - /** Indique si la localisation est approximative */ - @Builder.Default private Boolean estApproximative = false; -} +package dev.lions.unionflow.server.api.dto.solidarite; + +import jakarta.validation.constraints.*; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO pour les informations de géolocalisation + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class LocalisationDTO { + + /** Latitude */ + @DecimalMin(value = "-90.0", message = "La latitude doit être comprise entre -90 et 90") + @DecimalMax(value = "90.0", message = "La latitude doit être comprise entre -90 et 90") + private Double latitude; + + /** Longitude */ + @DecimalMin(value = "-180.0", message = "La longitude doit être comprise entre -180 et 180") + @DecimalMax(value = "180.0", message = "La longitude doit être comprise entre -180 et 180") + private Double longitude; + + /** Adresse complète */ + @Size(max = 300, message = "L'adresse ne peut pas dépasser 300 caractères") + private String adresseComplete; + + /** Ville */ + @Size(max = 100, message = "La ville ne peut pas dépasser 100 caractères") + private String ville; + + /** Région/Province */ + @Size(max = 100, message = "La région ne peut pas dépasser 100 caractères") + private String region; + + /** Pays */ + @Size(max = 100, message = "Le pays ne peut pas dépasser 100 caractères") + private String pays; + + /** Code postal */ + @Size(max = 20, message = "Le code postal ne peut pas dépasser 20 caractères") + private String codePostal; + + /** Précision de la localisation en mètres */ + @Min(value = 0, message = "La précision doit être positive") + private Double precision; + + /** Indique si la localisation est approximative */ + @Builder.Default private Boolean estApproximative = false; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/PieceJustificativeDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/PieceJustificativeDTO.java index 3681531..9376710 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/PieceJustificativeDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/PieceJustificativeDTO.java @@ -1,68 +1,68 @@ -package dev.lions.unionflow.server.api.dto.solidarite; - -import jakarta.validation.constraints.*; -import java.time.LocalDateTime; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * DTO pour les pièces justificatives d'une demande d'aide - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class PieceJustificativeDTO { - - /** Identifiant unique de la pièce justificative */ - private String id; - - /** Nom du fichier */ - @NotBlank(message = "Le nom du fichier est obligatoire") - @Size(max = 255, message = "Le nom du fichier ne peut pas dépasser 255 caractères") - private String nomFichier; - - /** Type de pièce justificative */ - @NotBlank(message = "Le type de pièce est obligatoire") - private String typePiece; - - /** Description de la pièce */ - @Size(max = 500, message = "La description ne peut pas dépasser 500 caractères") - private String description; - - /** URL ou chemin d'accès au fichier */ - @NotBlank(message = "L'URL du fichier est obligatoire") - private String urlFichier; - - /** Type MIME du fichier */ - private String typeMime; - - /** Taille du fichier en octets */ - @Min(value = 1, message = "La taille du fichier doit être positive") - private Long tailleFichier; - - /** Indique si la pièce est obligatoire */ - @Builder.Default private Boolean estObligatoire = false; - - /** Indique si la pièce a été vérifiée */ - @Builder.Default private Boolean estVerifiee = false; - - /** Date d'ajout de la pièce */ - @Builder.Default private LocalDateTime dateAjout = LocalDateTime.now(); - - /** Date de vérification */ - private LocalDateTime dateVerification; - - /** Identifiant de la personne qui a vérifié */ - private String verificateurId; - - /** Commentaires sur la vérification */ - @Size(max = 500, message = "Les commentaires ne peuvent pas dépasser 500 caractères") - private String commentairesVerification; -} +package dev.lions.unionflow.server.api.dto.solidarite; + +import jakarta.validation.constraints.*; +import java.time.LocalDateTime; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * DTO pour les pièces justificatives d'une demande d'aide + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class PieceJustificativeDTO { + + /** Identifiant unique de la pièce justificative */ + private String id; + + /** Nom du fichier */ + @NotBlank(message = "Le nom du fichier est obligatoire") + @Size(max = 255, message = "Le nom du fichier ne peut pas dépasser 255 caractères") + private String nomFichier; + + /** Type de pièce justificative */ + @NotBlank(message = "Le type de pièce est obligatoire") + private String typePiece; + + /** Description de la pièce */ + @Size(max = 500, message = "La description ne peut pas dépasser 500 caractères") + private String description; + + /** URL ou chemin d'accès au fichier */ + @NotBlank(message = "L'URL du fichier est obligatoire") + private String urlFichier; + + /** Type MIME du fichier */ + private String typeMime; + + /** Taille du fichier en octets */ + @Min(value = 1, message = "La taille du fichier doit être positive") + private Long tailleFichier; + + /** Indique si la pièce est obligatoire */ + @Builder.Default private Boolean estObligatoire = false; + + /** Indique si la pièce a été vérifiée */ + @Builder.Default private Boolean estVerifiee = false; + + /** Date d'ajout de la pièce */ + @Builder.Default private LocalDateTime dateAjout = LocalDateTime.now(); + + /** Date de vérification */ + private LocalDateTime dateVerification; + + /** Identifiant de la personne qui a vérifié */ + private String verificateurId; + + /** Commentaires sur la vérification */ + @Size(max = 500, message = "Les commentaires ne peuvent pas dépasser 500 caractères") + private String commentairesVerification; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateCommentaireAideRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateCommentaireAideRequest.java index e418a07..e1557ef 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateCommentaireAideRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateCommentaireAideRequest.java @@ -1,25 +1,25 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import java.util.List; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'un commentaire sur une aide. - */ -@Builder -public record CreateCommentaireAideRequest( - @NotBlank(message = "Le contenu du commentaire est obligatoire") @Size(min = 5, max = 2000, message = "Le commentaire doit contenir entre 5 et 2000 caractères") String contenu, - - @NotBlank(message = "Le type de commentaire est obligatoire") String typeCommentaire, - - @NotNull(message = "L'identifiant de l'auteur est obligatoire") UUID auteurId, - - Boolean estPrive, - Boolean estImportant, - UUID commentaireParentId, - List mentionsUtilisateurs) { -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import java.util.List; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'un commentaire sur une aide. + */ +@Builder +public record CreateCommentaireAideRequest( + @NotBlank(message = "Le contenu du commentaire est obligatoire") @Size(min = 5, max = 2000, message = "Le commentaire doit contenir entre 5 et 2000 caractères") String contenu, + + @NotBlank(message = "Le type de commentaire est obligatoire") String typeCommentaire, + + @NotNull(message = "L'identifiant de l'auteur est obligatoire") UUID auteurId, + + Boolean estPrive, + Boolean estImportant, + UUID commentaireParentId, + List mentionsUtilisateurs) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateDemandeAideRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateDemandeAideRequest.java index ded684a..43196be 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateDemandeAideRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateDemandeAideRequest.java @@ -1,46 +1,46 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import dev.lions.unionflow.server.api.dto.solidarite.BeneficiaireAideDTO; -import dev.lions.unionflow.server.api.dto.solidarite.ContactUrgenceDTO; -import dev.lions.unionflow.server.api.dto.solidarite.LocalisationDTO; -import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; -import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; -import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; -import dev.lions.unionflow.server.api.validation.ValidationConstants; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Digits; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Pattern; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.List; -import java.util.Map; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'une demande d'aide. - */ -@Builder -public record CreateDemandeAideRequest( - @NotNull(message = "Le type d'aide est obligatoire.") TypeAide typeAide, - @NotBlank(message = "Le titre" + ValidationConstants.OBLIGATOIRE_MESSAGE) @Size(max = 200) String titre, - @NotBlank(message = "La description" - + ValidationConstants.OBLIGATOIRE_MESSAGE) @Size(max = 2000) String description, - @Size(max = 1000) String justification, - @DecimalMin(value = "0", inclusive = false) @Digits(integer = 12, fraction = 2) BigDecimal montantDemande, - @Pattern(regexp = "^[A-Z]{3}$") String devise, - @NotNull(message = "L'identifiant du demandeur est obligatoire") UUID membreDemandeurId, - @NotNull(message = "L'identifiant de l'organisation est obligatoire") UUID associationId, - PrioriteAide priorite, - List piecesJustificatives, - List beneficiaires, - Map donneesPersonnalisees, - List tags, - Boolean estConfidentielle, - LocalisationDTO localisation, - ContactUrgenceDTO contactUrgence, - LocalDate dateLimite) { -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import dev.lions.unionflow.server.api.dto.solidarite.BeneficiaireAideDTO; +import dev.lions.unionflow.server.api.dto.solidarite.ContactUrgenceDTO; +import dev.lions.unionflow.server.api.dto.solidarite.LocalisationDTO; +import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; +import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; +import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; +import dev.lions.unionflow.server.api.validation.ValidationConstants; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Digits; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Pattern; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.List; +import java.util.Map; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'une demande d'aide. + */ +@Builder +public record CreateDemandeAideRequest( + @NotNull(message = "Le type d'aide est obligatoire.") TypeAide typeAide, + @NotBlank(message = "Le titre" + ValidationConstants.OBLIGATOIRE_MESSAGE) @Size(max = 200) String titre, + @NotBlank(message = "La description" + + ValidationConstants.OBLIGATOIRE_MESSAGE) @Size(max = 2000) String description, + @Size(max = 1000) String justification, + @DecimalMin(value = "0", inclusive = false) @Digits(integer = 12, fraction = 2) BigDecimal montantDemande, + @Pattern(regexp = "^[A-Z]{3}$") String devise, + @NotNull(message = "L'identifiant du demandeur est obligatoire") UUID membreDemandeurId, + @NotNull(message = "L'identifiant de l'organisation est obligatoire") UUID associationId, + PrioriteAide priorite, + List piecesJustificatives, + List beneficiaires, + Map donneesPersonnalisees, + List tags, + Boolean estConfidentielle, + LocalisationDTO localisation, + ContactUrgenceDTO contactUrgence, + LocalDate dateLimite) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateEvaluationAideRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateEvaluationAideRequest.java index 3e0fb5b..c34e18e 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateEvaluationAideRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateEvaluationAideRequest.java @@ -1,45 +1,45 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import dev.lions.unionflow.server.api.enums.solidarite.TypeEvaluation; -import jakarta.validation.constraints.DecimalMax; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import java.util.Map; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'une évaluation d'aide. - */ -@Builder -public record CreateEvaluationAideRequest( - @NotNull(message = "L'identifiant de la demande d'aide est obligatoire") UUID demandeAideId, - - UUID propositionAideId, - - @NotNull(message = "L'identifiant de l'évaluateur est obligatoire") UUID evaluateurId, - - @NotBlank(message = "Le rôle de l'évaluateur est obligatoire") String roleEvaluateur, - - @NotNull(message = "Le type d'évaluation est obligatoire") TypeEvaluation typeEvaluation, - - @NotNull(message = "La note globale est obligatoire") @DecimalMin(value = "1.0", message = "La note doit être au moins 1") @DecimalMax(value = "5.0", message = "La note ne peut pas dépasser 5") Double noteGlobale, - - Map notesDetaillees, - - @NotBlank(message = "Le commentaire est obligatoire") @Size(min = 10, max = 1000, message = "Le commentaire doit contenir entre 10 et 1000 caractères") String commentairePrincipal, - - String pointsPositifs, - String pointsAmelioration, - String recommandations, - Boolean recommande, - Boolean aideUtile, - Boolean problemeResolu, - Double noteDelaiReponse, - Double noteCommunication, - Double noteProfessionnalisme, - Double noteRespectEngagements, - Boolean estAnonyme) { -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import dev.lions.unionflow.server.api.enums.solidarite.TypeEvaluation; +import jakarta.validation.constraints.DecimalMax; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import java.util.Map; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'une évaluation d'aide. + */ +@Builder +public record CreateEvaluationAideRequest( + @NotNull(message = "L'identifiant de la demande d'aide est obligatoire") UUID demandeAideId, + + UUID propositionAideId, + + @NotNull(message = "L'identifiant de l'évaluateur est obligatoire") UUID evaluateurId, + + @NotBlank(message = "Le rôle de l'évaluateur est obligatoire") String roleEvaluateur, + + @NotNull(message = "Le type d'évaluation est obligatoire") TypeEvaluation typeEvaluation, + + @NotNull(message = "La note globale est obligatoire") @DecimalMin(value = "1.0", message = "La note doit être au moins 1") @DecimalMax(value = "5.0", message = "La note ne peut pas dépasser 5") Double noteGlobale, + + Map notesDetaillees, + + @NotBlank(message = "Le commentaire est obligatoire") @Size(min = 10, max = 1000, message = "Le commentaire doit contenir entre 10 et 1000 caractères") String commentairePrincipal, + + String pointsPositifs, + String pointsAmelioration, + String recommandations, + Boolean recommande, + Boolean aideUtile, + Boolean problemeResolu, + Double noteDelaiReponse, + Double noteCommunication, + Double noteProfessionnalisme, + Double noteRespectEngagements, + Boolean estAnonyme) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreatePropositionAideRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreatePropositionAideRequest.java index eb62239..d514dfd 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreatePropositionAideRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreatePropositionAideRequest.java @@ -1,25 +1,25 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; -import java.math.BigDecimal; -import java.time.LocalDateTime; -import lombok.Builder; - -/** - * Requête de création d'une proposition d'aide. - */ -@Builder -public record CreatePropositionAideRequest( - TypeAide typeAide, - String titre, - String description, - String conditions, - BigDecimal montantMaximum, - Integer nombreMaxBeneficiaires, - String devise, - String proposantId, - String organisationId, - String demandeAideId, - LocalDateTime dateExpiration, - Integer delaiReponseHeures) { -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; +import java.math.BigDecimal; +import java.time.LocalDateTime; +import lombok.Builder; + +/** + * Requête de création d'une proposition d'aide. + */ +@Builder +public record CreatePropositionAideRequest( + TypeAide typeAide, + String titre, + String description, + String conditions, + BigDecimal montantMaximum, + Integer nombreMaxBeneficiaires, + String devise, + String proposantId, + String organisationId, + String demandeAideId, + LocalDateTime dateExpiration, + Integer delaiReponseHeures) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateCommentaireAideRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateCommentaireAideRequest.java index 6ea383f..d3da651 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateCommentaireAideRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateCommentaireAideRequest.java @@ -1,18 +1,18 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import jakarta.validation.constraints.Size; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de mise à jour d'un commentaire sur une aide. - */ -@Builder -public record UpdateCommentaireAideRequest( - @Size(min = 5, max = 2000, message = "Le commentaire doit contenir entre 5 et 2000 caractères") String contenu, - - Boolean estPrive, - Boolean estImportant, - Boolean estResolu, - UUID resoluteurId) { -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import jakarta.validation.constraints.Size; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de mise à jour d'un commentaire sur une aide. + */ +@Builder +public record UpdateCommentaireAideRequest( + @Size(min = 5, max = 2000, message = "Le commentaire doit contenir entre 5 et 2000 caractères") String contenu, + + Boolean estPrive, + Boolean estImportant, + Boolean estResolu, + UUID resoluteurId) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateDemandeAideRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateDemandeAideRequest.java index f80bfec..e231602 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateDemandeAideRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateDemandeAideRequest.java @@ -1,44 +1,44 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import dev.lions.unionflow.server.api.dto.solidarite.BeneficiaireAideDTO; -import dev.lions.unionflow.server.api.dto.solidarite.ContactUrgenceDTO; -import dev.lions.unionflow.server.api.dto.solidarite.LocalisationDTO; -import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; -import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; -import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; -import jakarta.validation.constraints.Size; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.List; -import java.util.Map; -import lombok.Builder; - -/** - * Requête de mise à jour d'une demande d'aide. - */ -@Builder -public record UpdateDemandeAideRequest( - TypeAide typeAide, - @Size(max = 200) String titre, - @Size(max = 2000) String description, - @Size(max = 1000) String justification, - BigDecimal montantDemande, - String devise, - PrioriteAide priorite, - List piecesJustificatives, - List beneficiaires, - Map donneesPersonnalisees, - List tags, - Boolean estConfidentielle, - Boolean necessiteSuivi, - LocalisationDTO localisation, - ContactUrgenceDTO contactUrgence, - LocalDate dateLimite, - dev.lions.unionflow.server.api.enums.solidarite.StatutAide statut, - BigDecimal montantApprouve, - String commentairesEvaluateur, - String documentsJoints, - java.time.LocalDateTime dateSoumission, - java.time.LocalDateTime dateEvaluation, - java.time.LocalDateTime dateVersement) { -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import dev.lions.unionflow.server.api.dto.solidarite.BeneficiaireAideDTO; +import dev.lions.unionflow.server.api.dto.solidarite.ContactUrgenceDTO; +import dev.lions.unionflow.server.api.dto.solidarite.LocalisationDTO; +import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; +import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; +import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; +import jakarta.validation.constraints.Size; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.List; +import java.util.Map; +import lombok.Builder; + +/** + * Requête de mise à jour d'une demande d'aide. + */ +@Builder +public record UpdateDemandeAideRequest( + TypeAide typeAide, + @Size(max = 200) String titre, + @Size(max = 2000) String description, + @Size(max = 1000) String justification, + BigDecimal montantDemande, + String devise, + PrioriteAide priorite, + List piecesJustificatives, + List beneficiaires, + Map donneesPersonnalisees, + List tags, + Boolean estConfidentielle, + Boolean necessiteSuivi, + LocalisationDTO localisation, + ContactUrgenceDTO contactUrgence, + LocalDate dateLimite, + dev.lions.unionflow.server.api.enums.solidarite.StatutAide statut, + BigDecimal montantApprouve, + String commentairesEvaluateur, + String documentsJoints, + java.time.LocalDateTime dateSoumission, + java.time.LocalDateTime dateEvaluation, + java.time.LocalDateTime dateVersement) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateEvaluationAideRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateEvaluationAideRequest.java index ffb71db..c4245fb 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateEvaluationAideRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateEvaluationAideRequest.java @@ -1,34 +1,34 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import dev.lions.unionflow.server.api.enums.solidarite.StatutEvaluation; -import jakarta.validation.constraints.DecimalMax; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Size; -import java.util.Map; -import lombok.Builder; - -/** - * Requête de mise à jour d'une évaluation d'aide. - */ -@Builder -public record UpdateEvaluationAideRequest( - @DecimalMin(value = "1.0", message = "La note doit être au moins 1") @DecimalMax(value = "5.0", message = "La note ne peut pas dépasser 5") Double noteGlobale, - - Map notesDetaillees, - - @Size(min = 10, max = 1000, message = "Le commentaire doit contenir entre 10 et 1000 caractères") String commentairePrincipal, - - String pointsPositifs, - String pointsAmelioration, - String recommandations, - Boolean recommande, - Boolean aideUtile, - Boolean problemeResolu, - Double noteDelaiReponse, - Double noteCommunication, - Double noteProfessionnalisme, - Double noteRespectEngagements, - Boolean estPublique, - Boolean estAnonyme, - StatutEvaluation statut) { -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import dev.lions.unionflow.server.api.enums.solidarite.StatutEvaluation; +import jakarta.validation.constraints.DecimalMax; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Size; +import java.util.Map; +import lombok.Builder; + +/** + * Requête de mise à jour d'une évaluation d'aide. + */ +@Builder +public record UpdateEvaluationAideRequest( + @DecimalMin(value = "1.0", message = "La note doit être au moins 1") @DecimalMax(value = "5.0", message = "La note ne peut pas dépasser 5") Double noteGlobale, + + Map notesDetaillees, + + @Size(min = 10, max = 1000, message = "Le commentaire doit contenir entre 10 et 1000 caractères") String commentairePrincipal, + + String pointsPositifs, + String pointsAmelioration, + String recommandations, + Boolean recommande, + Boolean aideUtile, + Boolean problemeResolu, + Double noteDelaiReponse, + Double noteCommunication, + Double noteProfessionnalisme, + Double noteRespectEngagements, + Boolean estPublique, + Boolean estAnonyme, + StatutEvaluation statut) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdatePropositionAideRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdatePropositionAideRequest.java index e69c8cf..1885db3 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdatePropositionAideRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdatePropositionAideRequest.java @@ -1,27 +1,27 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import dev.lions.unionflow.server.api.enums.solidarite.StatutProposition; -import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; -import java.math.BigDecimal; -import java.time.LocalDateTime; -import lombok.Builder; - -/** - * Requête de mise à jour d'une proposition d'aide. - */ -@Builder -public record UpdatePropositionAideRequest( - TypeAide typeAide, - String titre, - String description, - String conditions, - BigDecimal montantMaximum, - Integer nombreMaxBeneficiaires, - String devise, - StatutProposition statut, - Boolean estDisponible, - Boolean estRecurrente, - String frequenceRecurrence, - LocalDateTime dateExpiration, - Integer delaiReponseHeures) { -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import dev.lions.unionflow.server.api.enums.solidarite.StatutProposition; +import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; +import java.math.BigDecimal; +import java.time.LocalDateTime; +import lombok.Builder; + +/** + * Requête de mise à jour d'une proposition d'aide. + */ +@Builder +public record UpdatePropositionAideRequest( + TypeAide typeAide, + String titre, + String description, + String conditions, + BigDecimal montantMaximum, + Integer nombreMaxBeneficiaires, + String devise, + StatutProposition statut, + Boolean estDisponible, + Boolean estRecurrente, + String frequenceRecurrence, + LocalDateTime dateExpiration, + Integer delaiReponseHeures) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/CommentaireAideResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/CommentaireAideResponse.java index fa9de5c..5c114cd 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/CommentaireAideResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/CommentaireAideResponse.java @@ -1,41 +1,41 @@ -package dev.lions.unionflow.server.api.dto.solidarite.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; -import java.time.LocalDateTime; -import java.util.List; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse pour un commentaire sur une aide. - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class CommentaireAideResponse extends BaseResponse { - - private String contenu; - private String typeCommentaire; - private UUID auteurId; - private String auteurNom; - private String auteurRole; - private Boolean estPrive; - private Boolean estImportant; - private UUID commentaireParentId; - private List reponses; - private List piecesJointes; - private List mentionsUtilisateurs; - private Boolean estModifie; - private Integer nombreReactions; - private Boolean estResolu; - private LocalDateTime dateResolution; - private UUID resoluteurId; -} +package dev.lions.unionflow.server.api.dto.solidarite.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; +import java.time.LocalDateTime; +import java.util.List; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse pour un commentaire sur une aide. + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class CommentaireAideResponse extends BaseResponse { + + private String contenu; + private String typeCommentaire; + private UUID auteurId; + private String auteurNom; + private String auteurRole; + private Boolean estPrive; + private Boolean estImportant; + private UUID commentaireParentId; + private List reponses; + private List piecesJointes; + private List mentionsUtilisateurs; + private Boolean estModifie; + private Integer nombreReactions; + private Boolean estResolu; + private LocalDateTime dateResolution; + private UUID resoluteurId; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/DemandeAideResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/DemandeAideResponse.java index 9605c36..a53b271 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/DemandeAideResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/DemandeAideResponse.java @@ -1,171 +1,171 @@ -package dev.lions.unionflow.server.api.dto.solidarite.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import dev.lions.unionflow.server.api.dto.solidarite.BeneficiaireAideDTO; -import dev.lions.unionflow.server.api.dto.solidarite.response.CommentaireAideResponse; -import dev.lions.unionflow.server.api.dto.solidarite.ContactUrgenceDTO; -import dev.lions.unionflow.server.api.dto.solidarite.HistoriqueStatutDTO; -import dev.lions.unionflow.server.api.dto.solidarite.LocalisationDTO; -import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; -import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; -import dev.lions.unionflow.server.api.enums.solidarite.StatutAide; -import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalDateTime; -import java.util.List; -import java.util.Map; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée pour une demande d'aide. - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class DemandeAideResponse extends BaseResponse { - - private String numeroReference; - private TypeAide typeAide; - private String titre; - private String description; - private String justification; - - private BigDecimal montantDemande; - private BigDecimal montantApprouve; - private BigDecimal montantVerse; - private String devise; - - private UUID membreDemandeurId; - private String nomDemandeur; - private String numeroMembreDemandeur; - - private String evaluateurId; - private String evaluateurNom; - private String approvateurId; - private String approvateurNom; - - private UUID associationId; - private String nomAssociation; - - private StatutAide statut; - private PrioriteAide priorite; - - private String motifRejet; - private String commentairesEvaluateur; - - private LocalDateTime dateSoumission; - private LocalDateTime dateLimiteTraitement; - private LocalDateTime dateEvaluation; - private LocalDateTime dateApprobation; - private LocalDateTime dateVersement; - private LocalDateTime dateCloture; - - private List piecesJustificatives; - private List beneficiaires; - private List historiqueStatuts; - private List commentaires; - private Map donneesPersonnalisees; - private List tags; - - private Boolean estConfidentielle; - private Boolean necessiteSuivi; - private Double scorePriorite; - private Integer nombreVues; - - private LocalisationDTO localisation; - private ContactUrgenceDTO contactUrgence; - - private LocalDate dateLimite; - private Boolean justificatifsFournis; - private String documentsJoints; - private LocalDate dateDebutAide; - private LocalDate dateFinAide; - - private UUID membreAidantId; - private String nomAidant; - private String modeVersement; - private String numeroTransaction; - - private UUID rejeteParId; - private String rejetePar; - private LocalDateTime dateRejet; - private String raisonRejet; - - // === MÉTHODES UTILITAIRES === - - public boolean estModifiable() { - return statut != null && statut.permetModification(); - } - - public boolean peutEtreAnnulee() { - return statut != null && statut.permetAnnulation(); - } - - public boolean estUrgente() { - return priorite != null && priorite.isUrgente(); - } - - public boolean estTerminee() { - return statut != null && statut.isEstFinal(); - } - - public boolean estEnSucces() { - return statut != null && statut.isSucces(); - } - - public double getPourcentageAvancement() { - if (statut == null) { - return 0.0; - } - - return switch (statut) { - case BROUILLON -> 5.0; - case SOUMISE -> 10.0; - case EN_ATTENTE -> 20.0; - case EN_COURS_EVALUATION -> 40.0; - case INFORMATIONS_REQUISES -> 35.0; - case APPROUVEE, APPROUVEE_PARTIELLEMENT -> 60.0; - case EN_COURS_TRAITEMENT -> 70.0; - case EN_COURS_VERSEMENT -> 85.0; - case VERSEE, LIVREE, TERMINEE -> 100.0; - case REJETEE, ANNULEE, EXPIREE -> 100.0; - case SUSPENDUE -> 50.0; - case EN_SUIVI -> 95.0; - case CLOTUREE -> 100.0; - }; - } - - public long getDelaiRestantHeures() { - if (dateLimiteTraitement == null) { - return -1; - } - - LocalDateTime maintenant = LocalDateTime.now(); - if (maintenant.isAfter(dateLimiteTraitement)) { - return 0; - } - - return java.time.Duration.between(maintenant, dateLimiteTraitement).toHours(); - } - - public boolean estDelaiDepasse() { - return getDelaiRestantHeures() == 0; - } - - public String getStatutLibelle() { - return statut != null ? statut.getLibelle() : "Non défini"; - } - - public String getPrioriteLibelle() { - return priorite != null ? priorite.getLibelle() : "Normale"; - } -} +package dev.lions.unionflow.server.api.dto.solidarite.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import dev.lions.unionflow.server.api.dto.solidarite.BeneficiaireAideDTO; +import dev.lions.unionflow.server.api.dto.solidarite.response.CommentaireAideResponse; +import dev.lions.unionflow.server.api.dto.solidarite.ContactUrgenceDTO; +import dev.lions.unionflow.server.api.dto.solidarite.HistoriqueStatutDTO; +import dev.lions.unionflow.server.api.dto.solidarite.LocalisationDTO; +import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; +import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; +import dev.lions.unionflow.server.api.enums.solidarite.StatutAide; +import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.util.List; +import java.util.Map; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée pour une demande d'aide. + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class DemandeAideResponse extends BaseResponse { + + private String numeroReference; + private TypeAide typeAide; + private String titre; + private String description; + private String justification; + + private BigDecimal montantDemande; + private BigDecimal montantApprouve; + private BigDecimal montantVerse; + private String devise; + + private UUID membreDemandeurId; + private String nomDemandeur; + private String numeroMembreDemandeur; + + private String evaluateurId; + private String evaluateurNom; + private String approvateurId; + private String approvateurNom; + + private UUID associationId; + private String nomAssociation; + + private StatutAide statut; + private PrioriteAide priorite; + + private String motifRejet; + private String commentairesEvaluateur; + + private LocalDateTime dateSoumission; + private LocalDateTime dateLimiteTraitement; + private LocalDateTime dateEvaluation; + private LocalDateTime dateApprobation; + private LocalDateTime dateVersement; + private LocalDateTime dateCloture; + + private List piecesJustificatives; + private List beneficiaires; + private List historiqueStatuts; + private List commentaires; + private Map donneesPersonnalisees; + private List tags; + + private Boolean estConfidentielle; + private Boolean necessiteSuivi; + private Double scorePriorite; + private Integer nombreVues; + + private LocalisationDTO localisation; + private ContactUrgenceDTO contactUrgence; + + private LocalDate dateLimite; + private Boolean justificatifsFournis; + private String documentsJoints; + private LocalDate dateDebutAide; + private LocalDate dateFinAide; + + private UUID membreAidantId; + private String nomAidant; + private String modeVersement; + private String numeroTransaction; + + private UUID rejeteParId; + private String rejetePar; + private LocalDateTime dateRejet; + private String raisonRejet; + + // === MÉTHODES UTILITAIRES === + + public boolean estModifiable() { + return statut != null && statut.permetModification(); + } + + public boolean peutEtreAnnulee() { + return statut != null && statut.permetAnnulation(); + } + + public boolean estUrgente() { + return priorite != null && priorite.isUrgente(); + } + + public boolean estTerminee() { + return statut != null && statut.isEstFinal(); + } + + public boolean estEnSucces() { + return statut != null && statut.isSucces(); + } + + public double getPourcentageAvancement() { + if (statut == null) { + return 0.0; + } + + return switch (statut) { + case BROUILLON -> 5.0; + case SOUMISE -> 10.0; + case EN_ATTENTE -> 20.0; + case EN_COURS_EVALUATION -> 40.0; + case INFORMATIONS_REQUISES -> 35.0; + case APPROUVEE, APPROUVEE_PARTIELLEMENT -> 60.0; + case EN_COURS_TRAITEMENT -> 70.0; + case EN_COURS_VERSEMENT -> 85.0; + case VERSEE, LIVREE, TERMINEE -> 100.0; + case REJETEE, ANNULEE, EXPIREE -> 100.0; + case SUSPENDUE -> 50.0; + case EN_SUIVI -> 95.0; + case CLOTUREE -> 100.0; + }; + } + + public long getDelaiRestantHeures() { + if (dateLimiteTraitement == null) { + return -1; + } + + LocalDateTime maintenant = LocalDateTime.now(); + if (maintenant.isAfter(dateLimiteTraitement)) { + return 0; + } + + return java.time.Duration.between(maintenant, dateLimiteTraitement).toHours(); + } + + public boolean estDelaiDepasse() { + return getDelaiRestantHeures() == 0; + } + + public String getStatutLibelle() { + return statut != null ? statut.getLibelle() : "Non défini"; + } + + public String getPrioriteLibelle() { + return priorite != null ? priorite.getLibelle() : "Normale"; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/EvaluationAideResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/EvaluationAideResponse.java index b91a13f..aaa37d3 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/EvaluationAideResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/EvaluationAideResponse.java @@ -1,125 +1,125 @@ -package dev.lions.unionflow.server.api.dto.solidarite.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; -import dev.lions.unionflow.server.api.enums.solidarite.StatutEvaluation; -import dev.lions.unionflow.server.api.enums.solidarite.TypeEvaluation; -import java.time.LocalDateTime; -import java.util.List; -import java.util.Map; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée pour une évaluation d'aide. - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class EvaluationAideResponse extends BaseResponse { - - private UUID demandeAideId; - private UUID propositionAideId; - private UUID evaluateurId; - private String evaluateurNom; - private String roleEvaluateur; - private TypeEvaluation typeEvaluation; - private Double noteGlobale; - private Map notesDetaillees; - private String commentairePrincipal; - private String pointsPositifs; - private String pointsAmelioration; - private String recommandations; - private Boolean recommande; - private Boolean aideUtile; - private Boolean problemeResolu; - private Double noteDelaiReponse; - private Double noteCommunication; - private Double noteProfessionnalisme; - private Double noteRespectEngagements; - private Boolean estPublique; - private Boolean estAnonyme; - private Boolean estVerifiee; - private LocalDateTime dateVerification; - private UUID verificateurId; - private List piecesJointes; - private List tags; - private Map donneesAdditionnelles; - private Integer nombreUtile; - private Integer nombreSignalements; - private StatutEvaluation statut; - - // === MÉTHODES UTILITAIRES === - - public Double getNoteMoyenneDetaillees() { - if (notesDetaillees == null || notesDetaillees.isEmpty()) { - return noteGlobale; - } - - return notesDetaillees.values().stream() - .mapToDouble(Double::doubleValue) - .average() - .orElse(noteGlobale != null ? noteGlobale : 0.0); - } - - public boolean isPositive() { - return noteGlobale != null && noteGlobale >= 4.0; - } - - public boolean isNegative() { - return noteGlobale != null && noteGlobale <= 2.0; - } - - public double getScoreQualite() { - double score = noteGlobale != null ? noteGlobale : 0.0; - - if (noteDelaiReponse != null) - score += noteDelaiReponse * 0.1; - if (noteCommunication != null) - score += noteCommunication * 0.1; - if (noteProfessionnalisme != null) - score += noteProfessionnalisme * 0.1; - if (noteRespectEngagements != null) - score += noteRespectEngagements * 0.1; - - if (recommande != null && recommande) - score += 0.2; - if (problemeResolu != null && problemeResolu) - score += 0.3; - - if (nombreSignalements != null && nombreSignalements > 0) - score -= nombreSignalements * 0.1; - - return Math.min(5.0, Math.max(0.0, score)); - } - - public boolean isComplete() { - boolean noteOk = noteGlobale != null; - boolean commentaireNonVide = commentairePrincipal != null && !commentairePrincipal.trim().isEmpty(); - boolean recommandeOk = recommande != null; - boolean aideUtileOk = aideUtile != null; - boolean problemeResoluOk = problemeResolu != null; - return noteOk & commentaireNonVide & recommandeOk & aideUtileOk & problemeResoluOk; - } - - public String getNiveauSatisfaction() { - if (noteGlobale == null) - return "Non évalué"; - - return switch (noteGlobale.intValue()) { - case 5 -> "Excellent"; - case 4 -> "Très bien"; - case 3 -> "Bien"; - case 2 -> "Passable"; - case 1 -> "Insuffisant"; - default -> "Non évalué"; - }; - } -} +package dev.lions.unionflow.server.api.dto.solidarite.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; +import dev.lions.unionflow.server.api.enums.solidarite.StatutEvaluation; +import dev.lions.unionflow.server.api.enums.solidarite.TypeEvaluation; +import java.time.LocalDateTime; +import java.util.List; +import java.util.Map; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée pour une évaluation d'aide. + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class EvaluationAideResponse extends BaseResponse { + + private UUID demandeAideId; + private UUID propositionAideId; + private UUID evaluateurId; + private String evaluateurNom; + private String roleEvaluateur; + private TypeEvaluation typeEvaluation; + private Double noteGlobale; + private Map notesDetaillees; + private String commentairePrincipal; + private String pointsPositifs; + private String pointsAmelioration; + private String recommandations; + private Boolean recommande; + private Boolean aideUtile; + private Boolean problemeResolu; + private Double noteDelaiReponse; + private Double noteCommunication; + private Double noteProfessionnalisme; + private Double noteRespectEngagements; + private Boolean estPublique; + private Boolean estAnonyme; + private Boolean estVerifiee; + private LocalDateTime dateVerification; + private UUID verificateurId; + private List piecesJointes; + private List tags; + private Map donneesAdditionnelles; + private Integer nombreUtile; + private Integer nombreSignalements; + private StatutEvaluation statut; + + // === MÉTHODES UTILITAIRES === + + public Double getNoteMoyenneDetaillees() { + if (notesDetaillees == null || notesDetaillees.isEmpty()) { + return noteGlobale; + } + + return notesDetaillees.values().stream() + .mapToDouble(Double::doubleValue) + .average() + .orElse(noteGlobale != null ? noteGlobale : 0.0); + } + + public boolean isPositive() { + return noteGlobale != null && noteGlobale >= 4.0; + } + + public boolean isNegative() { + return noteGlobale != null && noteGlobale <= 2.0; + } + + public double getScoreQualite() { + double score = noteGlobale != null ? noteGlobale : 0.0; + + if (noteDelaiReponse != null) + score += noteDelaiReponse * 0.1; + if (noteCommunication != null) + score += noteCommunication * 0.1; + if (noteProfessionnalisme != null) + score += noteProfessionnalisme * 0.1; + if (noteRespectEngagements != null) + score += noteRespectEngagements * 0.1; + + if (recommande != null && recommande) + score += 0.2; + if (problemeResolu != null && problemeResolu) + score += 0.3; + + if (nombreSignalements != null && nombreSignalements > 0) + score -= nombreSignalements * 0.1; + + return Math.min(5.0, Math.max(0.0, score)); + } + + public boolean isComplete() { + boolean noteOk = noteGlobale != null; + boolean commentaireNonVide = commentairePrincipal != null && !commentairePrincipal.trim().isEmpty(); + boolean recommandeOk = recommande != null; + boolean aideUtileOk = aideUtile != null; + boolean problemeResoluOk = problemeResolu != null; + return noteOk & commentaireNonVide & recommandeOk & aideUtileOk & problemeResoluOk; + } + + public String getNiveauSatisfaction() { + if (noteGlobale == null) + return "Non évalué"; + + return switch (noteGlobale.intValue()) { + case 5 -> "Excellent"; + case 4 -> "Très bien"; + case 3 -> "Bien"; + case 2 -> "Passable"; + case 1 -> "Insuffisant"; + default -> "Non évalué"; + }; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/PropositionAideResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/PropositionAideResponse.java index 9bb629e..1d540b74 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/PropositionAideResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/solidarite/response/PropositionAideResponse.java @@ -1,99 +1,99 @@ -package dev.lions.unionflow.server.api.dto.solidarite.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import dev.lions.unionflow.server.api.dto.solidarite.ContactProposantDTO; -import dev.lions.unionflow.server.api.dto.solidarite.CreneauDisponibiliteDTO; -import dev.lions.unionflow.server.api.dto.solidarite.CritereSelectionDTO; -import dev.lions.unionflow.server.api.enums.solidarite.StatutProposition; -import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; -import java.math.BigDecimal; -import java.time.LocalDateTime; -import java.util.List; -import java.util.Map; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée pour une proposition d'aide. - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class PropositionAideResponse extends BaseResponse { - - private String numeroReference; - private TypeAide typeAide; - private String titre; - private String description; - private String conditions; - private BigDecimal montantMaximum; - private Integer nombreMaxBeneficiaires; - private String devise; - - private String proposantId; - private String proposantNom; - private String organisationId; - private String demandeAideId; - - private StatutProposition statut; - private Boolean estDisponible; - private Boolean estRecurrente; - private String frequenceRecurrence; - - private LocalDateTime dateExpiration; - private Integer delaiReponseHeures; - - private List criteresSelection; - private List zonesGeographiques; - private List groupesCibles; - private List competencesRessources; - - private ContactProposantDTO contactProposant; - private List creneauxDisponibilite; - private String modeContactPrefere; - - private Integer nombreDemandesTraitees; - private Integer nombreBeneficiairesAides; - private Double montantTotalVerse; - private Double noteMoyenne; - private Integer nombreEvaluations; - - private List tags; - private Map donneesPersonnalisees; - private Boolean estMiseEnAvant; - private Double scorePertinence; - private Integer nombreVues; - private Integer nombreCandidatures; - - // === MÉTHODES UTILITAIRES === - - public boolean isActiveEtDisponible() { - return statut == StatutProposition.ACTIVE && estDisponible && !isExpiree(); - } - - public boolean isExpiree() { - return dateExpiration != null && LocalDateTime.now().isAfter(dateExpiration); - } - - public boolean peutAccepterBeneficiaires() { - return isActiveEtDisponible() && nombreBeneficiairesAides < nombreMaxBeneficiaires; - } - - public double getPourcentageCapaciteUtilisee() { - if (nombreMaxBeneficiaires == null || nombreMaxBeneficiaires == 0) - return 100.0; - return (nombreBeneficiairesAides * 100.0) / nombreMaxBeneficiaires; - } - - public int getPlacesRestantes() { - if (nombreMaxBeneficiaires == null) - return 0; - return Math.max(0, nombreMaxBeneficiaires - (nombreBeneficiairesAides != null ? nombreBeneficiairesAides : 0)); - } -} +package dev.lions.unionflow.server.api.dto.solidarite.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import dev.lions.unionflow.server.api.dto.solidarite.ContactProposantDTO; +import dev.lions.unionflow.server.api.dto.solidarite.CreneauDisponibiliteDTO; +import dev.lions.unionflow.server.api.dto.solidarite.CritereSelectionDTO; +import dev.lions.unionflow.server.api.enums.solidarite.StatutProposition; +import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; +import java.math.BigDecimal; +import java.time.LocalDateTime; +import java.util.List; +import java.util.Map; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée pour une proposition d'aide. + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class PropositionAideResponse extends BaseResponse { + + private String numeroReference; + private TypeAide typeAide; + private String titre; + private String description; + private String conditions; + private BigDecimal montantMaximum; + private Integer nombreMaxBeneficiaires; + private String devise; + + private String proposantId; + private String proposantNom; + private String organisationId; + private String demandeAideId; + + private StatutProposition statut; + private Boolean estDisponible; + private Boolean estRecurrente; + private String frequenceRecurrence; + + private LocalDateTime dateExpiration; + private Integer delaiReponseHeures; + + private List criteresSelection; + private List zonesGeographiques; + private List groupesCibles; + private List competencesRessources; + + private ContactProposantDTO contactProposant; + private List creneauxDisponibilite; + private String modeContactPrefere; + + private Integer nombreDemandesTraitees; + private Integer nombreBeneficiairesAides; + private Double montantTotalVerse; + private Double noteMoyenne; + private Integer nombreEvaluations; + + private List tags; + private Map donneesPersonnalisees; + private Boolean estMiseEnAvant; + private Double scorePertinence; + private Integer nombreVues; + private Integer nombreCandidatures; + + // === MÉTHODES UTILITAIRES === + + public boolean isActiveEtDisponible() { + return statut == StatutProposition.ACTIVE && estDisponible && !isExpiree(); + } + + public boolean isExpiree() { + return dateExpiration != null && LocalDateTime.now().isAfter(dateExpiration); + } + + public boolean peutAccepterBeneficiaires() { + return isActiveEtDisponible() && nombreBeneficiairesAides < nombreMaxBeneficiaires; + } + + public double getPourcentageCapaciteUtilisee() { + if (nombreMaxBeneficiaires == null || nombreMaxBeneficiaires == 0) + return 100.0; + return (nombreBeneficiairesAides * 100.0) / nombreMaxBeneficiaires; + } + + public int getPlacesRestantes() { + if (nombreMaxBeneficiaires == null) + return 0; + return Math.max(0, nombreMaxBeneficiaires - (nombreBeneficiairesAides != null ? nombreBeneficiairesAides : 0)); + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/suggestion/request/CreateSuggestionRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/suggestion/request/CreateSuggestionRequest.java index 29e62ac..5a8600b 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/suggestion/request/CreateSuggestionRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/suggestion/request/CreateSuggestionRequest.java @@ -1,25 +1,25 @@ -package dev.lions.unionflow.server.api.dto.suggestion.request; - -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import java.util.List; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'une suggestion. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreateSuggestionRequest( - @NotNull(message = "L'utilisateur est obligatoire") UUID utilisateurId, - String utilisateurNom, - @NotBlank(message = "Le titre est obligatoire") String titre, - String description, - String justification, - String categorie, - String prioriteEstimee, - List piecesJointes) { -} +package dev.lions.unionflow.server.api.dto.suggestion.request; + +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import java.util.List; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'une suggestion. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreateSuggestionRequest( + @NotNull(message = "L'utilisateur est obligatoire") UUID utilisateurId, + String utilisateurNom, + @NotBlank(message = "Le titre est obligatoire") String titre, + String description, + String justification, + String categorie, + String prioriteEstimee, + List piecesJointes) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/suggestion/request/UpdateSuggestionRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/suggestion/request/UpdateSuggestionRequest.java index fde421c..beaf354 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/suggestion/request/UpdateSuggestionRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/suggestion/request/UpdateSuggestionRequest.java @@ -1,23 +1,23 @@ -package dev.lions.unionflow.server.api.dto.suggestion.request; - -import java.util.List; -import lombok.Builder; - -/** - * Requête de mise à jour d'une suggestion. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record UpdateSuggestionRequest( - String titre, - String description, - String justification, - String categorie, - String prioriteEstimee, - String statut, - String versionCiblee, - List piecesJointes, - String miseAJour) { -} +package dev.lions.unionflow.server.api.dto.suggestion.request; + +import java.util.List; +import lombok.Builder; + +/** + * Requête de mise à jour d'une suggestion. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record UpdateSuggestionRequest( + String titre, + String description, + String justification, + String categorie, + String prioriteEstimee, + String statut, + String versionCiblee, + List piecesJointes, + String miseAJour) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/suggestion/response/SuggestionResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/suggestion/response/SuggestionResponse.java index f087648..46964fa 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/suggestion/response/SuggestionResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/suggestion/response/SuggestionResponse.java @@ -1,44 +1,44 @@ -package dev.lions.unionflow.server.api.dto.suggestion.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.time.LocalDateTime; -import java.util.List; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée d'une suggestion. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class SuggestionResponse extends BaseResponse { - - private UUID utilisateurId; - private String utilisateurNom; - private String titre; - private String description; - private String justification; - private String categorie; - private String prioriteEstimee; - private String statut; - private Integer nbVotes; - private Integer nbCommentaires; - private Integer nbVues; - private LocalDateTime dateSoumission; - private LocalDateTime dateEvaluation; - private LocalDateTime dateImplementation; - private String versionCiblee; - private List piecesJointes; - private String miseAJour; -} +package dev.lions.unionflow.server.api.dto.suggestion.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.time.LocalDateTime; +import java.util.List; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée d'une suggestion. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class SuggestionResponse extends BaseResponse { + + private UUID utilisateurId; + private String utilisateurNom; + private String titre; + private String description; + private String justification; + private String categorie; + private String prioriteEstimee; + private String statut; + private Integer nbVotes; + private Integer nbCommentaires; + private Integer nbVues; + private LocalDateTime dateSoumission; + private LocalDateTime dateEvaluation; + private LocalDateTime dateImplementation; + private String versionCiblee; + private List piecesJointes; + private String miseAJour; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/system/request/UpdateSystemConfigRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/system/request/UpdateSystemConfigRequest.java index 935c5bc..5b79b70 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/system/request/UpdateSystemConfigRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/system/request/UpdateSystemConfigRequest.java @@ -1,64 +1,64 @@ -package dev.lions.unionflow.server.api.dto.system.request; - -import jakarta.validation.constraints.NotNull; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -/** - * Request pour mettre à jour la configuration système - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class UpdateSystemConfigRequest { - - // Configuration générale - private String applicationName; - private String timezone; - private String defaultLanguage; - private Boolean maintenanceMode; - - // Configuration réseau - private Integer networkTimeout; - private Integer maxRetries; - private Integer connectionPoolSize; - - // Configuration sécurité - private Boolean twoFactorAuthEnabled; - private Integer sessionTimeoutMinutes; - private Boolean auditLoggingEnabled; - - // Configuration performance - private Boolean metricsCollectionEnabled; - private Integer metricsIntervalSeconds; - private Boolean performanceOptimizationEnabled; - - // Configuration backup - private Boolean autoBackupEnabled; - private String backupFrequency; // HOURLY, DAILY, WEEKLY - private Integer backupRetentionDays; - - // Configuration logs - private String logLevel; // TRACE, DEBUG, INFO, WARN, ERROR, CRITICAL - private Integer logRetentionDays; - private Boolean detailedLoggingEnabled; - private Boolean logCompressionEnabled; - - // Configuration monitoring - private Boolean realTimeMonitoringEnabled; - private Integer monitoringIntervalSeconds; - private Boolean emailAlertsEnabled; - private Boolean pushAlertsEnabled; - - // Configuration alertes - private Boolean cpuHighAlertEnabled; - private Integer cpuThresholdPercent; - private Boolean memoryLowAlertEnabled; - private Integer memoryThresholdPercent; - private Boolean criticalErrorAlertEnabled; - private Boolean connectionFailureAlertEnabled; - private Integer connectionFailureThreshold; -} +package dev.lions.unionflow.server.api.dto.system.request; + +import jakarta.validation.constraints.NotNull; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +/** + * Request pour mettre à jour la configuration système + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class UpdateSystemConfigRequest { + + // Configuration générale + private String applicationName; + private String timezone; + private String defaultLanguage; + private Boolean maintenanceMode; + + // Configuration réseau + private Integer networkTimeout; + private Integer maxRetries; + private Integer connectionPoolSize; + + // Configuration sécurité + private Boolean twoFactorAuthEnabled; + private Integer sessionTimeoutMinutes; + private Boolean auditLoggingEnabled; + + // Configuration performance + private Boolean metricsCollectionEnabled; + private Integer metricsIntervalSeconds; + private Boolean performanceOptimizationEnabled; + + // Configuration backup + private Boolean autoBackupEnabled; + private String backupFrequency; // HOURLY, DAILY, WEEKLY + private Integer backupRetentionDays; + + // Configuration logs + private String logLevel; // TRACE, DEBUG, INFO, WARN, ERROR, CRITICAL + private Integer logRetentionDays; + private Boolean detailedLoggingEnabled; + private Boolean logCompressionEnabled; + + // Configuration monitoring + private Boolean realTimeMonitoringEnabled; + private Integer monitoringIntervalSeconds; + private Boolean emailAlertsEnabled; + private Boolean pushAlertsEnabled; + + // Configuration alertes + private Boolean cpuHighAlertEnabled; + private Integer cpuThresholdPercent; + private Boolean memoryLowAlertEnabled; + private Integer memoryThresholdPercent; + private Boolean criticalErrorAlertEnabled; + private Boolean connectionFailureAlertEnabled; + private Integer connectionFailureThreshold; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/system/response/CacheStatsResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/system/response/CacheStatsResponse.java index 734f237..01ee3be 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/system/response/CacheStatsResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/system/response/CacheStatsResponse.java @@ -1,44 +1,44 @@ -package dev.lions.unionflow.server.api.dto.system.response; - -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.time.LocalDateTime; -import java.util.Map; - -/** - * Response contenant les statistiques du cache système - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class CacheStatsResponse { - - private Long totalSizeBytes; - private String totalSizeFormatted; // ex: "2.3 GB" - private Integer totalEntries; - private Double hitRate; // pourcentage (0-100) - private Long hits; - private Long misses; - private LocalDateTime lastCleared; - - // Statistiques par cache - private Map caches; - - @Data - @Builder - @NoArgsConstructor - @AllArgsConstructor - public static class CacheEntry { - private String name; - private Long sizeBytes; - private Integer entries; - private Double hitRate; - private Long hits; - private Long misses; - private LocalDateTime lastAccessed; - } -} +package dev.lions.unionflow.server.api.dto.system.response; + +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.time.LocalDateTime; +import java.util.Map; + +/** + * Response contenant les statistiques du cache système + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class CacheStatsResponse { + + private Long totalSizeBytes; + private String totalSizeFormatted; // ex: "2.3 GB" + private Integer totalEntries; + private Double hitRate; // pourcentage (0-100) + private Long hits; + private Long misses; + private LocalDateTime lastCleared; + + // Statistiques par cache + private Map caches; + + @Data + @Builder + @NoArgsConstructor + @AllArgsConstructor + public static class CacheEntry { + private String name; + private Long sizeBytes; + private Integer entries; + private Double hitRate; + private Long hits; + private Long misses; + private LocalDateTime lastAccessed; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/system/response/SystemConfigResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/system/response/SystemConfigResponse.java index 078c2ca..c355d72 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/system/response/SystemConfigResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/system/response/SystemConfigResponse.java @@ -1,72 +1,72 @@ -package dev.lions.unionflow.server.api.dto.system.response; - -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.time.LocalDateTime; - -/** - * Response contenant la configuration système complète - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class SystemConfigResponse { - - // Configuration générale - private String applicationName; - private String timezone; - private String defaultLanguage; - private Boolean maintenanceMode; - private String version; - private LocalDateTime lastUpdated; - - // Configuration réseau - private Integer networkTimeout; - private Integer maxRetries; - private Integer connectionPoolSize; - - // Configuration sécurité - private Boolean twoFactorAuthEnabled; - private Integer sessionTimeoutMinutes; - private Boolean auditLoggingEnabled; - - // Configuration performance - private Boolean metricsCollectionEnabled; - private Integer metricsIntervalSeconds; - private Boolean performanceOptimizationEnabled; - - // Configuration backup - private Boolean autoBackupEnabled; - private String backupFrequency; - private Integer backupRetentionDays; - private LocalDateTime lastBackup; - - // Configuration logs - private String logLevel; - private Integer logRetentionDays; - private Boolean detailedLoggingEnabled; - private Boolean logCompressionEnabled; - - // Configuration monitoring - private Boolean realTimeMonitoringEnabled; - private Integer monitoringIntervalSeconds; - private Boolean emailAlertsEnabled; - private Boolean pushAlertsEnabled; - - // Configuration alertes - private Boolean cpuHighAlertEnabled; - private Integer cpuThresholdPercent; - private Boolean memoryLowAlertEnabled; - private Integer memoryThresholdPercent; - private Boolean criticalErrorAlertEnabled; - private Boolean connectionFailureAlertEnabled; - private Integer connectionFailureThreshold; - - // Statut système - private String systemStatus; // OPERATIONAL, DEGRADED, DOWN - private Long uptime; // en millisecondes -} +package dev.lions.unionflow.server.api.dto.system.response; + +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.time.LocalDateTime; + +/** + * Response contenant la configuration système complète + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class SystemConfigResponse { + + // Configuration générale + private String applicationName; + private String timezone; + private String defaultLanguage; + private Boolean maintenanceMode; + private String version; + private LocalDateTime lastUpdated; + + // Configuration réseau + private Integer networkTimeout; + private Integer maxRetries; + private Integer connectionPoolSize; + + // Configuration sécurité + private Boolean twoFactorAuthEnabled; + private Integer sessionTimeoutMinutes; + private Boolean auditLoggingEnabled; + + // Configuration performance + private Boolean metricsCollectionEnabled; + private Integer metricsIntervalSeconds; + private Boolean performanceOptimizationEnabled; + + // Configuration backup + private Boolean autoBackupEnabled; + private String backupFrequency; + private Integer backupRetentionDays; + private LocalDateTime lastBackup; + + // Configuration logs + private String logLevel; + private Integer logRetentionDays; + private Boolean detailedLoggingEnabled; + private Boolean logCompressionEnabled; + + // Configuration monitoring + private Boolean realTimeMonitoringEnabled; + private Integer monitoringIntervalSeconds; + private Boolean emailAlertsEnabled; + private Boolean pushAlertsEnabled; + + // Configuration alertes + private Boolean cpuHighAlertEnabled; + private Integer cpuThresholdPercent; + private Boolean memoryLowAlertEnabled; + private Integer memoryThresholdPercent; + private Boolean criticalErrorAlertEnabled; + private Boolean connectionFailureAlertEnabled; + private Integer connectionFailureThreshold; + + // Statut système + private String systemStatus; // OPERATIONAL, DEGRADED, DOWN + private Long uptime; // en millisecondes +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/system/response/SystemTestResultResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/system/response/SystemTestResultResponse.java index 12df543..7fa2ce1 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/system/response/SystemTestResultResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/system/response/SystemTestResultResponse.java @@ -1,25 +1,25 @@ -package dev.lions.unionflow.server.api.dto.system.response; - -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; - -import java.time.LocalDateTime; - -/** - * Response pour les résultats de test système (email, database, etc.) - */ -@Data -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class SystemTestResultResponse { - - private String testType; // EMAIL, DATABASE, NETWORK, CACHE - private Boolean success; - private String message; - private Long responseTimeMs; - private LocalDateTime testedAt; - private String details; -} +package dev.lions.unionflow.server.api.dto.system.response; + +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; + +import java.time.LocalDateTime; + +/** + * Response pour les résultats de test système (email, database, etc.) + */ +@Data +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class SystemTestResultResponse { + + private String testType; // EMAIL, DATABASE, NETWORK, CACHE + private Boolean success; + private String message; + private Long responseTimeMs; + private LocalDateTime testedAt; + private String details; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/ticket/request/CreateTicketRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/ticket/request/CreateTicketRequest.java index cdca3fe..70595ed 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/ticket/request/CreateTicketRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/ticket/request/CreateTicketRequest.java @@ -1,29 +1,29 @@ -package dev.lions.unionflow.server.api.dto.ticket.request; - -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import jakarta.validation.constraints.Size; -import java.util.List; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de création d'un ticket de support. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record CreateTicketRequest( - @NotNull(message = "L'ID de l'utilisateur est obligatoire") UUID utilisateurId, - - @NotBlank(message = "Le sujet est obligatoire") @Size(max = 200) String sujet, - - @NotBlank(message = "La description est obligatoire") @Size(max = 2000) String description, - - @NotBlank(message = "La catégorie est obligatoire") String categorie, - - @NotBlank(message = "La priorité est obligatoire") String priorite, - - List piecesJointes) { -} +package dev.lions.unionflow.server.api.dto.ticket.request; + +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Size; +import java.util.List; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de création d'un ticket de support. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record CreateTicketRequest( + @NotNull(message = "L'ID de l'utilisateur est obligatoire") UUID utilisateurId, + + @NotBlank(message = "Le sujet est obligatoire") @Size(max = 200) String sujet, + + @NotBlank(message = "La description est obligatoire") @Size(max = 2000) String description, + + @NotBlank(message = "La catégorie est obligatoire") String categorie, + + @NotBlank(message = "La priorité est obligatoire") String priorite, + + List piecesJointes) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/ticket/request/UpdateTicketRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/ticket/request/UpdateTicketRequest.java index 665d529..b0c33c4 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/ticket/request/UpdateTicketRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/ticket/request/UpdateTicketRequest.java @@ -1,24 +1,24 @@ -package dev.lions.unionflow.server.api.dto.ticket.request; - -import jakarta.validation.constraints.Size; -import java.util.List; -import java.util.UUID; -import lombok.Builder; - -/** - * Requête de mise à jour d'un ticket de support. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Builder -public record UpdateTicketRequest( - @Size(max = 200) String sujet, - @Size(max = 2000) String description, - String categorie, - String priorite, - String statut, - UUID agentId, - String resolution, - List piecesJointes) { -} +package dev.lions.unionflow.server.api.dto.ticket.request; + +import jakarta.validation.constraints.Size; +import java.util.List; +import java.util.UUID; +import lombok.Builder; + +/** + * Requête de mise à jour d'un ticket de support. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Builder +public record UpdateTicketRequest( + @Size(max = 200) String sujet, + @Size(max = 2000) String description, + String categorie, + String priorite, + String statut, + UUID agentId, + String resolution, + List piecesJointes) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/ticket/response/TicketResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/ticket/response/TicketResponse.java index 226ef3b..50adebf 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/ticket/response/TicketResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/ticket/response/TicketResponse.java @@ -1,51 +1,51 @@ -package dev.lions.unionflow.server.api.dto.ticket.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.time.LocalDateTime; -import java.util.List; -import java.util.UUID; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse détaillée d'un ticket de support. - * - * @author UnionFlow Team - * @version 1.0 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class TicketResponse extends BaseResponse { - - private String numeroTicket; - private UUID utilisateurId; - private String sujet; - private String description; - - /** TECHNIQUE, FONCTIONNALITE, UTILISATION, COMPTE, AUTRE */ - private String categorie; - - /** BASSE, NORMALE, HAUTE, URGENTE */ - private String priorite; - - /** OUVERT, EN_COURS, EN_ATTENTE, RESOLU, FERME */ - private String statut; - - private UUID agentId; - private String agentNom; - private LocalDateTime dateDerniereReponse; - private LocalDateTime dateResolution; - private LocalDateTime dateFermeture; - private Integer nbMessages; - private Integer nbFichiers; - private Integer noteSatisfaction; - private String resolution; - private List piecesJointes; -} +package dev.lions.unionflow.server.api.dto.ticket.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.time.LocalDateTime; +import java.util.List; +import java.util.UUID; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse détaillée d'un ticket de support. + * + * @author UnionFlow Team + * @version 1.0 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class TicketResponse extends BaseResponse { + + private String numeroTicket; + private UUID utilisateurId; + private String sujet; + private String description; + + /** TECHNIQUE, FONCTIONNALITE, UTILISATION, COMPTE, AUTRE */ + private String categorie; + + /** BASSE, NORMALE, HAUTE, URGENTE */ + private String priorite; + + /** OUVERT, EN_COURS, EN_ATTENTE, RESOLU, FERME */ + private String statut; + + private UUID agentId; + private String agentNom; + private LocalDateTime dateDerniereReponse; + private LocalDateTime dateResolution; + private LocalDateTime dateFermeture; + private Integer nbMessages; + private Integer nbFichiers; + private Integer noteSatisfaction; + private String resolution; + private List piecesJointes; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/tontine/TontineRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/tontine/TontineRequest.java index f01a78f..a10c6d8 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/tontine/TontineRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/tontine/TontineRequest.java @@ -1,49 +1,49 @@ -package dev.lions.unionflow.server.api.dto.tontine; - -import dev.lions.unionflow.server.api.enums.tontine.FrequenceTour; -import dev.lions.unionflow.server.api.enums.tontine.TypeTontine; -import jakarta.validation.constraints.DecimalMin; -import jakarta.validation.constraints.Min; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -import java.math.BigDecimal; -import java.time.LocalDate; - -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Requête de création/paramétrage d'une tontine") -public class TontineRequest { - - @NotBlank(message = "Le nom de la tontine est obligatoire") - private String nom; - - private String description; - - @NotBlank(message = "L'ID de l'organisation est obligatoire") - private String organisationId; - - @NotNull(message = "Le type de tontine est obligatoire") - private TypeTontine typeTontine; - - @NotNull(message = "La fréquence des tours est obligatoire") - private FrequenceTour frequence; - - @NotNull(message = "La date de début souhaitée est obligatoire") - private LocalDate dateDebutPrevue; - - @Schema(description = "Montant fixe si tontine classique") - @DecimalMin(value = "0.0", message = "Le montant de cotisation ne peut pas être négatif") - private BigDecimal montantMiseParTour; - - @Schema(description = "Le nombre maximum de membres pouvant rejoindre cette tontine (Optionnel)") - @Min(value = 2, message = "Une tontine nécessite au moins 2 membres") - private Integer limiteParticipants; -} +package dev.lions.unionflow.server.api.dto.tontine; + +import dev.lions.unionflow.server.api.enums.tontine.FrequenceTour; +import dev.lions.unionflow.server.api.enums.tontine.TypeTontine; +import jakarta.validation.constraints.DecimalMin; +import jakarta.validation.constraints.Min; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +import java.math.BigDecimal; +import java.time.LocalDate; + +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Requête de création/paramétrage d'une tontine") +public class TontineRequest { + + @NotBlank(message = "Le nom de la tontine est obligatoire") + private String nom; + + private String description; + + @NotBlank(message = "L'ID de l'organisation est obligatoire") + private String organisationId; + + @NotNull(message = "Le type de tontine est obligatoire") + private TypeTontine typeTontine; + + @NotNull(message = "La fréquence des tours est obligatoire") + private FrequenceTour frequence; + + @NotNull(message = "La date de début souhaitée est obligatoire") + private LocalDate dateDebutPrevue; + + @Schema(description = "Montant fixe si tontine classique") + @DecimalMin(value = "0.0", message = "Le montant de cotisation ne peut pas être négatif") + private BigDecimal montantMiseParTour; + + @Schema(description = "Le nombre maximum de membres pouvant rejoindre cette tontine (Optionnel)") + @Min(value = 2, message = "Une tontine nécessite au moins 2 membres") + private Integer limiteParticipants; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/tontine/TontineResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/tontine/TontineResponse.java index 6d09f56..8e92e44 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/tontine/TontineResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/tontine/TontineResponse.java @@ -1,46 +1,46 @@ -package dev.lions.unionflow.server.api.dto.tontine; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.tontine.FrequenceTour; -import dev.lions.unionflow.server.api.enums.tontine.StatutTontine; -import dev.lions.unionflow.server.api.enums.tontine.TypeTontine; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.List; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Réponse contenant la structure d'une tontine") -public class TontineResponse extends BaseDTO { - - private String nom; - private String description; - private String organisationId; - - private TypeTontine typeTontine; - private FrequenceTour frequence; - private StatutTontine statut; - - private LocalDate dateDebutEffective; - private LocalDate dateFinPrevue; - - private BigDecimal montantMiseParTour; - private Integer limiteParticipants; - - @Schema(description = "Statistiques directes : nombre de participants actifs et fonds totaux levés à ce jour") - private Integer nombreParticipantsActuels; - private BigDecimal fondTotalCollecte; - - @Schema(description = "Calendrier généré des tours de cette tontine") - private List calendrierTours; -} +package dev.lions.unionflow.server.api.dto.tontine; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.tontine.FrequenceTour; +import dev.lions.unionflow.server.api.enums.tontine.StatutTontine; +import dev.lions.unionflow.server.api.enums.tontine.TypeTontine; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.List; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Réponse contenant la structure d'une tontine") +public class TontineResponse extends BaseDTO { + + private String nom; + private String description; + private String organisationId; + + private TypeTontine typeTontine; + private FrequenceTour frequence; + private StatutTontine statut; + + private LocalDate dateDebutEffective; + private LocalDate dateFinPrevue; + + private BigDecimal montantMiseParTour; + private Integer limiteParticipants; + + @Schema(description = "Statistiques directes : nombre de participants actifs et fonds totaux levés à ce jour") + private Integer nombreParticipantsActuels; + private BigDecimal fondTotalCollecte; + + @Schema(description = "Calendrier généré des tours de cette tontine") + private List calendrierTours; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/tontine/TourTontineDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/tontine/TourTontineDTO.java index 6e274a0..23d9120 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/tontine/TourTontineDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/tontine/TourTontineDTO.java @@ -1,41 +1,41 @@ -package dev.lions.unionflow.server.api.dto.tontine; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -import java.math.BigDecimal; -import java.time.LocalDate; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Informations d'un tour spécifique d'une tontine rotative") -public class TourTontineDTO extends BaseDTO { - - private String tontineId; - - @Schema(description = "Ordre cronologique (Tour 1, Tour 2...)") - private Integer ordreTour; - - private LocalDate dateOuvertureCotisations; - private LocalDate dateTirageOuRemise; - - @Schema(description = "Montant cible total (Ex: 10 membres x 10 000 = 100 000 cibles)") - private BigDecimal montantCible; - - @Schema(description = "Montant de la cagnotte réellement collectée pour ce tour") - private BigDecimal cagnotteCollectee; - - @Schema(description = "Membre désigné pour remporter ce tour (bénéficiaire de la caisse)") - private String membreBeneficiaireId; - - @Schema(description = "Statut: A_VENIR, EN_COURS, CLOTURE/REMIS") - private String statutInterne; -} +package dev.lions.unionflow.server.api.dto.tontine; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +import java.math.BigDecimal; +import java.time.LocalDate; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Informations d'un tour spécifique d'une tontine rotative") +public class TourTontineDTO extends BaseDTO { + + private String tontineId; + + @Schema(description = "Ordre cronologique (Tour 1, Tour 2...)") + private Integer ordreTour; + + private LocalDate dateOuvertureCotisations; + private LocalDate dateTirageOuRemise; + + @Schema(description = "Montant cible total (Ex: 10 membres x 10 000 = 100 000 cibles)") + private BigDecimal montantCible; + + @Schema(description = "Montant de la cagnotte réellement collectée pour ce tour") + private BigDecimal cagnotteCollectee; + + @Schema(description = "Membre désigné pour remporter ce tour (bénéficiaire de la caisse)") + private String membreBeneficiaireId; + + @Schema(description = "Statut: A_VENIR, EN_COURS, CLOTURE/REMIS") + private String statutInterne; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/user/request/CreateUserRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/user/request/CreateUserRequest.java index db45c63..29ca358 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/user/request/CreateUserRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/user/request/CreateUserRequest.java @@ -1,45 +1,45 @@ -package dev.lions.unionflow.server.api.dto.user.request; - -import jakarta.validation.constraints.Email; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.Size; -import java.util.List; -import java.util.Map; -import lombok.Builder; - -/** - * Requête de création d'un nouvel utilisateur Keycloak. - * - * @param username Nom d'utilisateur unique. - * @param prenom Prénom de l'utilisateur. - * @param nom Nom de l'utilisateur. - * @param email Adresse email (doit être unique). - * @param password Mot de passe initial. - * @param enabled Indique si le compte est activé (par défaut true). - * @param emailVerified Indique si l'email est vérifié (par défaut false). - * @param realmRoles Liste des rôles à assigner. - * @param attributes Attributs personnalisés (optionnel). - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-28 - */ -@Builder -public record CreateUserRequest( - @NotBlank(message = "Le nom d'utilisateur est obligatoire") @Size(min = 3, max = 50) String username, - - @NotBlank(message = "Le prénom est obligatoire") @Size(max = 100) String prenom, - - @NotBlank(message = "Le nom est obligatoire") @Size(max = 100) String nom, - - @NotBlank(message = "L'email est obligatoire") @Email(message = "Format d'email invalide") String email, - - @NotBlank(message = "Le mot de passe est obligatoire") @Size(min = 8, message = "Le mot de passe doit contenir au moins 8 caractères") String password, - - Boolean enabled, - - Boolean emailVerified, - - List realmRoles, - - Map> attributes) { -} +package dev.lions.unionflow.server.api.dto.user.request; + +import jakarta.validation.constraints.Email; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.Size; +import java.util.List; +import java.util.Map; +import lombok.Builder; + +/** + * Requête de création d'un nouvel utilisateur Keycloak. + * + * @param username Nom d'utilisateur unique. + * @param prenom Prénom de l'utilisateur. + * @param nom Nom de l'utilisateur. + * @param email Adresse email (doit être unique). + * @param password Mot de passe initial. + * @param enabled Indique si le compte est activé (par défaut true). + * @param emailVerified Indique si l'email est vérifié (par défaut false). + * @param realmRoles Liste des rôles à assigner. + * @param attributes Attributs personnalisés (optionnel). + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-28 + */ +@Builder +public record CreateUserRequest( + @NotBlank(message = "Le nom d'utilisateur est obligatoire") @Size(min = 3, max = 50) String username, + + @NotBlank(message = "Le prénom est obligatoire") @Size(max = 100) String prenom, + + @NotBlank(message = "Le nom est obligatoire") @Size(max = 100) String nom, + + @NotBlank(message = "L'email est obligatoire") @Email(message = "Format d'email invalide") String email, + + @NotBlank(message = "Le mot de passe est obligatoire") @Size(min = 8, message = "Le mot de passe doit contenir au moins 8 caractères") String password, + + Boolean enabled, + + Boolean emailVerified, + + List realmRoles, + + Map> attributes) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/user/request/UpdateUserRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/user/request/UpdateUserRequest.java index 18a97de..ea9fb2a 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/user/request/UpdateUserRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/user/request/UpdateUserRequest.java @@ -1,38 +1,38 @@ -package dev.lions.unionflow.server.api.dto.user.request; - -import jakarta.validation.constraints.Email; -import jakarta.validation.constraints.Size; -import java.util.List; -import java.util.Map; -import lombok.Builder; - -/** - * Requête de mise à jour d'un utilisateur Keycloak. - * - * @param prenom Prénom de l'utilisateur (optionnel). - * @param nom Nom de l'utilisateur (optionnel). - * @param email Adresse email (optionnel). - * @param enabled Indique si le compte est activé (optionnel). - * @param emailVerified Indique si l'email est vérifié (optionnel). - * @param realmRoles Liste des rôles à assigner (optionnel - écrase les rôles existants si fourni). - * @param attributes Attributs personnalisés (optionnel). - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-28 - */ -@Builder -public record UpdateUserRequest( - @Size(max = 100) String prenom, - - @Size(max = 100) String nom, - - @Email(message = "Format d'email invalide") String email, - - Boolean enabled, - - Boolean emailVerified, - - List realmRoles, - - Map> attributes) { -} +package dev.lions.unionflow.server.api.dto.user.request; + +import jakarta.validation.constraints.Email; +import jakarta.validation.constraints.Size; +import java.util.List; +import java.util.Map; +import lombok.Builder; + +/** + * Requête de mise à jour d'un utilisateur Keycloak. + * + * @param prenom Prénom de l'utilisateur (optionnel). + * @param nom Nom de l'utilisateur (optionnel). + * @param email Adresse email (optionnel). + * @param enabled Indique si le compte est activé (optionnel). + * @param emailVerified Indique si l'email est vérifié (optionnel). + * @param realmRoles Liste des rôles à assigner (optionnel - écrase les rôles existants si fourni). + * @param attributes Attributs personnalisés (optionnel). + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-28 + */ +@Builder +public record UpdateUserRequest( + @Size(max = 100) String prenom, + + @Size(max = 100) String nom, + + @Email(message = "Format d'email invalide") String email, + + Boolean enabled, + + Boolean emailVerified, + + List realmRoles, + + Map> attributes) { +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/user/response/UserResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/user/response/UserResponse.java index 739bd11..339bceb 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/user/response/UserResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/user/response/UserResponse.java @@ -1,52 +1,52 @@ -package dev.lions.unionflow.server.api.dto.user.response; - -import dev.lions.unionflow.server.api.dto.base.BaseResponse; -import java.time.LocalDateTime; -import java.util.List; -import java.util.Map; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.EqualsAndHashCode; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -/** - * Réponse contenant les données d'un utilisateur Keycloak. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-28 - */ -@Getter -@Setter -@Builder -@NoArgsConstructor -@AllArgsConstructor -public class UserResponse extends BaseResponse { - - // ── Identité ─────────────────────────────── - private String username; - private String prenom; - private String nom; - private String email; - private Boolean emailVerified; - - // ── État du compte ───────────────────────── - private Boolean enabled; - private String statut; // ACTIF, INACTIF, SUSPENDU - private LocalDateTime dateCreation; - private LocalDateTime derniereConnexion; - - // ── Rôles et permissions ─────────────────── - private List roles; - private List realmRoles; - private String primaryRole; // Rôle principal - - // ── Attributs personnalisés ──────────────── - private Map> attributes; - - // ── Métadonnées ──────────────────────────── - private Boolean totp; // 2FA activé - private Integer failedLoginAttempts; -} +package dev.lions.unionflow.server.api.dto.user.response; + +import dev.lions.unionflow.server.api.dto.base.BaseResponse; +import java.time.LocalDateTime; +import java.util.List; +import java.util.Map; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.EqualsAndHashCode; +import lombok.Getter; +import lombok.NoArgsConstructor; +import lombok.Setter; + +/** + * Réponse contenant les données d'un utilisateur Keycloak. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-28 + */ +@Getter +@Setter +@Builder +@NoArgsConstructor +@AllArgsConstructor +public class UserResponse extends BaseResponse { + + // ── Identité ─────────────────────────────── + private String username; + private String prenom; + private String nom; + private String email; + private Boolean emailVerified; + + // ── État du compte ───────────────────────── + private Boolean enabled; + private String statut; // ACTIF, INACTIF, SUSPENDU + private LocalDateTime dateCreation; + private LocalDateTime derniereConnexion; + + // ── Rôles et permissions ─────────────────── + private List roles; + private List realmRoles; + private String primaryRole; // Rôle principal + + // ── Attributs personnalisés ──────────────── + private Map> attributes; + + // ── Métadonnées ──────────────────────────── + private Boolean totp; // 2FA activé + private Integer failedLoginAttempts; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/vote/CampagneVoteRequest.java b/src/main/java/dev/lions/unionflow/server/api/dto/vote/CampagneVoteRequest.java index 1c9f2a7..4d37d7c 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/vote/CampagneVoteRequest.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/vote/CampagneVoteRequest.java @@ -1,52 +1,52 @@ -package dev.lions.unionflow.server.api.dto.vote; - -import dev.lions.unionflow.server.api.enums.vote.ModeScrutin; -import dev.lions.unionflow.server.api.enums.vote.TypeVote; -import jakarta.validation.constraints.Future; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.NotNull; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Data; -import lombok.NoArgsConstructor; -import org.eclipse.microprofile.openapi.annotations.media.Schema; - -import java.time.LocalDateTime; - -@Data -@NoArgsConstructor -@AllArgsConstructor -@Builder -@Schema(description = "Requête de création d'une campagne de vote électronique") -public class CampagneVoteRequest { - - @NotBlank(message = "Le titre de la campagne est obligatoire") - private String titre; - - private String descriptionOuResolution; - - @NotBlank(message = "L'ID de l'organisation est obligatoire") - private String organisationId; - - @NotNull(message = "Le type de vote est requis") - private TypeVote typeVote; - - @NotNull(message = "Le mode de scrutin est requis") - private ModeScrutin modeScrutin; - - @NotNull(message = "La date d'ouverture des scrutins est obligatoire") - @Future(message = "L'ouverture des votes doit être une date future") - private LocalDateTime dateOuverture; - - @NotNull(message = "La date de fermeture est obligatoire") - @Future(message = "La fermeture des votes doit être une date future") - private LocalDateTime dateFermeture; - - @Schema(description = "Restreindre le vote aux membres à jour de cotisations (Optionnel)") - @Builder.Default - private Boolean restreindreMembresAJour = true; - - @Schema(description = "Permettre le vote blanc (Optionnel)") - @Builder.Default - private Boolean autoriserVoteBlanc = true; -} +package dev.lions.unionflow.server.api.dto.vote; + +import dev.lions.unionflow.server.api.enums.vote.ModeScrutin; +import dev.lions.unionflow.server.api.enums.vote.TypeVote; +import jakarta.validation.constraints.Future; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Data; +import lombok.NoArgsConstructor; +import org.eclipse.microprofile.openapi.annotations.media.Schema; + +import java.time.LocalDateTime; + +@Data +@NoArgsConstructor +@AllArgsConstructor +@Builder +@Schema(description = "Requête de création d'une campagne de vote électronique") +public class CampagneVoteRequest { + + @NotBlank(message = "Le titre de la campagne est obligatoire") + private String titre; + + private String descriptionOuResolution; + + @NotBlank(message = "L'ID de l'organisation est obligatoire") + private String organisationId; + + @NotNull(message = "Le type de vote est requis") + private TypeVote typeVote; + + @NotNull(message = "Le mode de scrutin est requis") + private ModeScrutin modeScrutin; + + @NotNull(message = "La date d'ouverture des scrutins est obligatoire") + @Future(message = "L'ouverture des votes doit être une date future") + private LocalDateTime dateOuverture; + + @NotNull(message = "La date de fermeture est obligatoire") + @Future(message = "La fermeture des votes doit être une date future") + private LocalDateTime dateFermeture; + + @Schema(description = "Restreindre le vote aux membres à jour de cotisations (Optionnel)") + @Builder.Default + private Boolean restreindreMembresAJour = true; + + @Schema(description = "Permettre le vote blanc (Optionnel)") + @Builder.Default + private Boolean autoriserVoteBlanc = true; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/vote/CampagneVoteResponse.java b/src/main/java/dev/lions/unionflow/server/api/dto/vote/CampagneVoteResponse.java index b03c68f..3cd5ce0 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/vote/CampagneVoteResponse.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/vote/CampagneVoteResponse.java @@ -1,44 +1,44 @@ -package dev.lions.unionflow.server.api.dto.vote; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.vote.ModeScrutin; -import dev.lions.unionflow.server.api.enums.vote.StatutVote; -import dev.lions.unionflow.server.api.enums.vote.TypeVote; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; - -import java.time.LocalDateTime; -import java.util.List; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class CampagneVoteResponse extends BaseDTO { - - private String titre; - private String descriptionOuResolution; - private String organisationId; - - private TypeVote typeVote; - private ModeScrutin modeScrutin; - private StatutVote statut; - - private LocalDateTime dateOuverture; - private LocalDateTime dateFermeture; - - private Boolean restreindreMembresAJour; - private Boolean autoriserVoteBlanc; - - // Statistiques macro pour l'administrateur - private Integer totalElecteursInscrits; - private Integer totalVotantsEffectifs; - private Integer totalVotesBlancsOuNuls; - private Double tauxDeParticipation; - - private List candidatsExposes; -} +package dev.lions.unionflow.server.api.dto.vote; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.vote.ModeScrutin; +import dev.lions.unionflow.server.api.enums.vote.StatutVote; +import dev.lions.unionflow.server.api.enums.vote.TypeVote; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; + +import java.time.LocalDateTime; +import java.util.List; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class CampagneVoteResponse extends BaseDTO { + + private String titre; + private String descriptionOuResolution; + private String organisationId; + + private TypeVote typeVote; + private ModeScrutin modeScrutin; + private StatutVote statut; + + private LocalDateTime dateOuverture; + private LocalDateTime dateFermeture; + + private Boolean restreindreMembresAJour; + private Boolean autoriserVoteBlanc; + + // Statistiques macro pour l'administrateur + private Integer totalElecteursInscrits; + private Integer totalVotantsEffectifs; + private Integer totalVotesBlancsOuNuls; + private Double tauxDeParticipation; + + private List candidatsExposes; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/vote/CandidatDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/vote/CandidatDTO.java index ef61a9c..b6cf871 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/vote/CandidatDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/vote/CandidatDTO.java @@ -1,34 +1,34 @@ -package dev.lions.unionflow.server.api.dto.vote; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import lombok.AllArgsConstructor; -import lombok.Builder; -import lombok.Getter; -import lombok.Setter; -import lombok.NoArgsConstructor; -import java.math.BigDecimal; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -@Builder -public class CandidatDTO extends BaseDTO { - - private String campagneVoteId; - - // Si l'élection concerne une liste ou un individu (ex: "OUI", "NON", "Liste A", - // ou Membre) - private String nomCandidatureOuChoix; - - // Facultatif : si le choix est relié à un membre / un ticket - private String membreIdAssocie; - - private String professionDeFoi; - private String photoUrl; - - // Nombre de voix accumulées (souvent caché tant que StatutVote != - // RESULTATS_PUBLIES) - private Integer nombreDeVoix; - private BigDecimal pourcentageObtenu; -} +package dev.lions.unionflow.server.api.dto.vote; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import lombok.AllArgsConstructor; +import lombok.Builder; +import lombok.Getter; +import lombok.Setter; +import lombok.NoArgsConstructor; +import java.math.BigDecimal; + +@Getter +@Setter +@NoArgsConstructor +@AllArgsConstructor +@Builder +public class CandidatDTO extends BaseDTO { + + private String campagneVoteId; + + // Si l'élection concerne une liste ou un individu (ex: "OUI", "NON", "Liste A", + // ou Membre) + private String nomCandidatureOuChoix; + + // Facultatif : si le choix est relié à un membre / un ticket + private String membreIdAssocie; + + private String professionDeFoi; + private String photoUrl; + + // Nombre de voix accumulées (souvent caché tant que StatutVote != + // RESULTATS_PUBLIES) + private Integer nombreDeVoix; + private BigDecimal pourcentageObtenu; +} diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/wave/CompteWaveDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/wave/CompteWaveDTO.java index 6c5b437..5b51f1e 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/wave/CompteWaveDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/wave/CompteWaveDTO.java @@ -1,53 +1,53 @@ -package dev.lions.unionflow.server.api.dto.wave; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.wave.StatutCompteWave; -import jakarta.validation.constraints.NotBlank; -import jakarta.validation.constraints.Pattern; -import java.time.LocalDateTime; -import java.util.UUID; -import lombok.Getter; -import lombok.Setter; - -/** - * DTO pour la gestion des comptes Wave - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -@Getter -@Setter -public class CompteWaveDTO extends BaseDTO { - - private static final long serialVersionUID = 1L; - - /** Numéro de téléphone Wave */ - @NotBlank(message = "Le numéro de téléphone est obligatoire") - @Pattern( - regexp = "^\\+225[0-9]{8}$", - message = "Le numéro de téléphone Wave doit être au format +225XXXXXXXX") - private String numeroTelephone; - - /** Statut du compte */ - private StatutCompteWave statutCompte; - - /** Identifiant Wave API (encrypté) */ - private String waveAccountId; - - /** Environnement (SANDBOX ou PRODUCTION) */ - private String environnement; - - /** Date de dernière vérification */ - private LocalDateTime dateDerniereVerification; - - /** Commentaires */ - private String commentaire; - - /** ID de l'organisation (si compte d'organisation) */ - private UUID organisationId; - - /** ID du membre (si compte de membre) */ - private UUID membreId; -} - +package dev.lions.unionflow.server.api.dto.wave; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.wave.StatutCompteWave; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.Pattern; +import java.time.LocalDateTime; +import java.util.UUID; +import lombok.Getter; +import lombok.Setter; + +/** + * DTO pour la gestion des comptes Wave + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +@Getter +@Setter +public class CompteWaveDTO extends BaseDTO { + + private static final long serialVersionUID = 1L; + + /** Numéro de téléphone Wave */ + @NotBlank(message = "Le numéro de téléphone est obligatoire") + @Pattern( + regexp = "^\\+225[0-9]{8}$", + message = "Le numéro de téléphone Wave doit être au format +225XXXXXXXX") + private String numeroTelephone; + + /** Statut du compte */ + private StatutCompteWave statutCompte; + + /** Identifiant Wave API (encrypté) */ + private String waveAccountId; + + /** Environnement (SANDBOX ou PRODUCTION) */ + private String environnement; + + /** Date de dernière vérification */ + private LocalDateTime dateDerniereVerification; + + /** Commentaires */ + private String commentaire; + + /** ID de l'organisation (si compte d'organisation) */ + private UUID organisationId; + + /** ID du membre (si compte de membre) */ + private UUID membreId; +} + diff --git a/src/main/java/dev/lions/unionflow/server/api/dto/wave/TransactionWaveDTO.java b/src/main/java/dev/lions/unionflow/server/api/dto/wave/TransactionWaveDTO.java index 6d62848..1e6e8e5 100644 --- a/src/main/java/dev/lions/unionflow/server/api/dto/wave/TransactionWaveDTO.java +++ b/src/main/java/dev/lions/unionflow/server/api/dto/wave/TransactionWaveDTO.java @@ -1,87 +1,87 @@ -package dev.lions.unionflow.server.api.dto.wave; - -import dev.lions.unionflow.server.api.dto.base.BaseDTO; -import dev.lions.unionflow.server.api.enums.wave.StatutTransactionWave; -import dev.lions.unionflow.server.api.enums.wave.TypeTransactionWave; -import jakarta.validation.constraints.*; -import java.math.BigDecimal; -import java.time.LocalDateTime; -import java.util.UUID; -import lombok.Getter; -import lombok.Setter; - -/** - * DTO pour la gestion des transactions Wave - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -@Getter -@Setter -public class TransactionWaveDTO extends BaseDTO { - - private static final long serialVersionUID = 1L; - - /** Identifiant Wave de la transaction */ - @NotBlank(message = "L'identifiant Wave est obligatoire") - private String waveTransactionId; - - /** Identifiant de requête Wave */ - private String waveRequestId; - - /** Référence Wave */ - private String waveReference; - - /** Type de transaction */ - @NotNull(message = "Le type de transaction est obligatoire") - private TypeTransactionWave typeTransaction; - - /** Statut de la transaction */ - @NotNull(message = "Le statut de la transaction est obligatoire") - private StatutTransactionWave statutTransaction; - - /** Montant de la transaction */ - @NotNull(message = "Le montant est obligatoire") - @DecimalMin(value = "0.0", message = "Le montant doit être positif") - @Digits(integer = 12, fraction = 2) - private BigDecimal montant; - - /** Frais de transaction */ - @DecimalMin(value = "0.0") - @Digits(integer = 10, fraction = 2) - private BigDecimal frais; - - /** Montant net */ - @DecimalMin(value = "0.0") - @Digits(integer = 12, fraction = 2) - private BigDecimal montantNet; - - /** Code devise */ - @NotBlank(message = "Le code devise est obligatoire") - @Pattern(regexp = "^[A-Z]{3}$", message = "Le code devise doit être un code ISO à 3 lettres") - private String codeDevise; - - /** Numéro téléphone payeur */ - private String telephonePayeur; - - /** Numéro téléphone bénéficiaire */ - private String telephoneBeneficiaire; - - /** Métadonnées JSON */ - private String metadonnees; - - /** Nombre de tentatives */ - private Integer nombreTentatives; - - /** Date de dernière tentative */ - private LocalDateTime dateDerniereTentative; - - /** Message d'erreur */ - private String messageErreur; - - /** ID du compte Wave */ - @NotNull(message = "Le compte Wave est obligatoire") - private UUID compteWaveId; -} - +package dev.lions.unionflow.server.api.dto.wave; + +import dev.lions.unionflow.server.api.dto.base.BaseDTO; +import dev.lions.unionflow.server.api.enums.wave.StatutTransactionWave; +import dev.lions.unionflow.server.api.enums.wave.TypeTransactionWave; +import jakarta.validation.constraints.*; +import java.math.BigDecimal; +import java.time.LocalDateTime; +import java.util.UUID; +import lombok.Getter; +import lombok.Setter; + +/** + * DTO pour la gestion des transactions Wave + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +@Getter +@Setter +public class TransactionWaveDTO extends BaseDTO { + + private static final long serialVersionUID = 1L; + + /** Identifiant Wave de la transaction */ + @NotBlank(message = "L'identifiant Wave est obligatoire") + private String waveTransactionId; + + /** Identifiant de requête Wave */ + private String waveRequestId; + + /** Référence Wave */ + private String waveReference; + + /** Type de transaction */ + @NotNull(message = "Le type de transaction est obligatoire") + private TypeTransactionWave typeTransaction; + + /** Statut de la transaction */ + @NotNull(message = "Le statut de la transaction est obligatoire") + private StatutTransactionWave statutTransaction; + + /** Montant de la transaction */ + @NotNull(message = "Le montant est obligatoire") + @DecimalMin(value = "0.0", message = "Le montant doit être positif") + @Digits(integer = 12, fraction = 2) + private BigDecimal montant; + + /** Frais de transaction */ + @DecimalMin(value = "0.0") + @Digits(integer = 10, fraction = 2) + private BigDecimal frais; + + /** Montant net */ + @DecimalMin(value = "0.0") + @Digits(integer = 12, fraction = 2) + private BigDecimal montantNet; + + /** Code devise */ + @NotBlank(message = "Le code devise est obligatoire") + @Pattern(regexp = "^[A-Z]{3}$", message = "Le code devise doit être un code ISO à 3 lettres") + private String codeDevise; + + /** Numéro téléphone payeur */ + private String telephonePayeur; + + /** Numéro téléphone bénéficiaire */ + private String telephoneBeneficiaire; + + /** Métadonnées JSON */ + private String metadonnees; + + /** Nombre de tentatives */ + private Integer nombreTentatives; + + /** Date de dernière tentative */ + private LocalDateTime dateDerniereTentative; + + /** Message d'erreur */ + private String messageErreur; + + /** ID du compte Wave */ + @NotNull(message = "Le compte Wave est obligatoire") + private UUID compteWaveId; +} + diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/abonnement/StatutAbonnement.java b/src/main/java/dev/lions/unionflow/server/api/enums/abonnement/StatutAbonnement.java index 3a6fb52..973d314 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/abonnement/StatutAbonnement.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/abonnement/StatutAbonnement.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.enums.abonnement; - -/** - * Énumération des statuts d'abonnements UnionFlow - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -public enum StatutAbonnement { - ACTIF("Actif"), - SUSPENDU("Suspendu"), - EXPIRE("Expiré"), - ANNULE("Annulé"), - EN_ATTENTE_PAIEMENT("En attente de paiement"); - - private final String libelle; - - StatutAbonnement(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.abonnement; + +/** + * Énumération des statuts d'abonnements UnionFlow + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +public enum StatutAbonnement { + ACTIF("Actif"), + SUSPENDU("Suspendu"), + EXPIRE("Expiré"), + ANNULE("Annulé"), + EN_ATTENTE_PAIEMENT("En attente de paiement"); + + private final String libelle; + + StatutAbonnement(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/abonnement/StatutFormule.java b/src/main/java/dev/lions/unionflow/server/api/enums/abonnement/StatutFormule.java index ca379ce..eb3b3d5 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/abonnement/StatutFormule.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/abonnement/StatutFormule.java @@ -1,25 +1,25 @@ -package dev.lions.unionflow.server.api.enums.abonnement; - -/** - * Énumération des statuts de formules d'abonnement UnionFlow - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -public enum StatutFormule { - ACTIVE("Active"), - INACTIVE("Inactive"), - ARCHIVEE("Archivée"), - BIENTOT_DISPONIBLE("Bientôt Disponible"); - - private final String libelle; - - StatutFormule(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.abonnement; + +/** + * Énumération des statuts de formules d'abonnement UnionFlow + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +public enum StatutFormule { + ACTIVE("Active"), + INACTIVE("Inactive"), + ARCHIVEE("Archivée"), + BIENTOT_DISPONIBLE("Bientôt Disponible"); + + private final String libelle; + + StatutFormule(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/abonnement/StatutSouscription.java b/src/main/java/dev/lions/unionflow/server/api/enums/abonnement/StatutSouscription.java index cb9ba96..4582334 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/abonnement/StatutSouscription.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/abonnement/StatutSouscription.java @@ -1,15 +1,15 @@ -package dev.lions.unionflow.server.api.enums.abonnement; - -public enum StatutSouscription { - EN_ATTENTE("En attente de validation"), - ACTIVE("Active"), - EXPIREE("Expirée"), - SUSPENDUE("Suspendue — quota dépassé ou impayé"), - RESILIEE("Résiliée"); - - private final String libelle; - - StatutSouscription(String libelle) { this.libelle = libelle; } - - public String getLibelle() { return libelle; } -} +package dev.lions.unionflow.server.api.enums.abonnement; + +public enum StatutSouscription { + EN_ATTENTE("En attente de validation"), + ACTIVE("Active"), + EXPIREE("Expirée"), + SUSPENDUE("Suspendue — quota dépassé ou impayé"), + RESILIEE("Résiliée"); + + private final String libelle; + + StatutSouscription(String libelle) { this.libelle = libelle; } + + public String getLibelle() { return libelle; } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/agricole/StatutCampagneAgricole.java b/src/main/java/dev/lions/unionflow/server/api/enums/agricole/StatutCampagneAgricole.java index 06ed5ee..664ebb4 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/agricole/StatutCampagneAgricole.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/agricole/StatutCampagneAgricole.java @@ -1,20 +1,20 @@ -package dev.lions.unionflow.server.api.enums.agricole; - -public enum StatutCampagneAgricole { - PREPARATION("Distribution des intrants et semences"), - LABOUR_SEMIS("Saison des semis et du labour"), - ENTRETIEN("Croissance et traitement phytosanitaire"), - RECOLTE("Saison des récoltes"), - COMMERCIALISATION("Stockage et vente des coopérateurs"), - CLOTUREE("Campagne soldée"); - - private final String libelle; - - StatutCampagneAgricole(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.agricole; + +public enum StatutCampagneAgricole { + PREPARATION("Distribution des intrants et semences"), + LABOUR_SEMIS("Saison des semis et du labour"), + ENTRETIEN("Croissance et traitement phytosanitaire"), + RECOLTE("Saison des récoltes"), + COMMERCIALISATION("Stockage et vente des coopérateurs"), + CLOTUREE("Campagne soldée"); + + private final String libelle; + + StatutCampagneAgricole(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/analytics/FormatExport.java b/src/main/java/dev/lions/unionflow/server/api/enums/analytics/FormatExport.java index c93a6a9..084047a 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/analytics/FormatExport.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/analytics/FormatExport.java @@ -1,257 +1,257 @@ -package dev.lions.unionflow.server.api.enums.analytics; - -/** - * Énumération des formats d'export disponibles pour les rapports et données analytics - * - *

Cette énumération définit les différents formats dans lesquels les données peuvent être - * exportées depuis l'application UnionFlow. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -public enum FormatExport { - - // === FORMATS DOCUMENTS === - PDF("PDF", "pdf", "application/pdf", "Portable Document Format", true, true), - WORD( - "Word", - "docx", - "application/vnd.openxmlformats-officedocument.wordprocessingml.document", - "Microsoft Word", - true, - false), - - // === FORMATS TABLEURS === - EXCEL( - "Excel", - "xlsx", - "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet", - "Microsoft Excel", - true, - true), - CSV("CSV", "csv", "text/csv", "Comma Separated Values", false, true), - - // === FORMATS DONNÉES === - JSON("JSON", "json", "application/json", "JavaScript Object Notation", false, true), - XML("XML", "xml", "application/xml", "eXtensible Markup Language", false, false), - - // === FORMATS IMAGES === - PNG("PNG", "png", "image/png", "Portable Network Graphics", true, false), - JPEG("JPEG", "jpg", "image/jpeg", "Joint Photographic Experts Group", true, false), - SVG("SVG", "svg", "image/svg+xml", "Scalable Vector Graphics", true, false), - - // === FORMATS SPÉCIALISÉS === - POWERPOINT( - "PowerPoint", - "pptx", - "application/vnd.openxmlformats-officedocument.presentationml.presentation", - "Microsoft PowerPoint", - true, - false), - HTML("HTML", "html", "text/html", "HyperText Markup Language", true, false); - - private final String libelle; - private final String extension; - private final String mimeType; - private final String description; - private final boolean supporteGraphiques; - private final boolean supporteGrandesQuantitesDonnees; - - /** - * Constructeur de l'énumération FormatExport - * - * @param libelle Le libellé affiché à l'utilisateur - * @param extension L'extension de fichier - * @param mimeType Le type MIME du format - * @param description La description du format - * @param supporteGraphiques true si le format supporte les graphiques - * @param supporteGrandesQuantitesDonnees true si le format supporte de grandes quantités de - * données - */ - FormatExport( - String libelle, - String extension, - String mimeType, - String description, - boolean supporteGraphiques, - boolean supporteGrandesQuantitesDonnees) { - this.libelle = libelle; - this.extension = extension; - this.mimeType = mimeType; - this.description = description; - this.supporteGraphiques = supporteGraphiques; - this.supporteGrandesQuantitesDonnees = supporteGrandesQuantitesDonnees; - } - - /** - * Retourne le libellé du format - * - * @return Le libellé affiché à l'utilisateur - */ - public String getLibelle() { - return libelle; - } - - /** - * Retourne l'extension de fichier - * - * @return L'extension sans le point (ex: "pdf", "xlsx") - */ - public String getExtension() { - return extension; - } - - /** - * Retourne le type MIME du format - * - * @return Le type MIME complet - */ - public String getMimeType() { - return mimeType; - } - - /** - * Retourne la description du format - * - * @return La description complète du format - */ - public String getDescription() { - return description; - } - - /** - * Vérifie si le format supporte les graphiques - * - * @return true si le format peut inclure des graphiques - */ - public boolean supporteGraphiques() { - return supporteGraphiques; - } - - /** - * Vérifie si le format supporte de grandes quantités de données - * - * @return true si le format peut gérer de gros volumes de données - */ - public boolean supporteGrandesQuantitesDonnees() { - return supporteGrandesQuantitesDonnees; - } - - /** - * Vérifie si le format est adapté aux rapports exécutifs - * - * @return true si le format convient aux rapports de direction - */ - public boolean isFormatExecutif() { - return this == PDF || this == POWERPOINT || this == WORD; - } - - /** - * Vérifie si le format est adapté à l'analyse de données - * - * @return true si le format convient à l'analyse de données - */ - public boolean isFormatAnalyse() { - return this == EXCEL || this == CSV || this == JSON; - } - - /** - * Vérifie si le format est adapté au partage web - * - * @return true si le format convient au partage sur le web - */ - public boolean isFormatWeb() { - return this == HTML || this == PNG || this == SVG || this == JSON; - } - - /** - * Retourne l'icône appropriée pour le format - * - * @return L'icône Material Design - */ - public String getIcone() { - return switch (this) { - case PDF -> "picture_as_pdf"; - case WORD -> "description"; - case EXCEL -> "table_chart"; - case CSV -> "grid_on"; - case JSON -> "code"; - case XML -> "code"; - case PNG, JPEG -> "image"; - case SVG -> "vector_image"; - case POWERPOINT -> "slideshow"; - case HTML -> "web"; - }; - } - - /** - * Retourne la couleur appropriée pour le format - * - * @return Le code couleur hexadécimal - */ - public String getCouleur() { - return switch (this) { - case PDF -> "#FF5722"; // Rouge-orange - case WORD -> "#2196F3"; // Bleu - case EXCEL -> "#4CAF50"; // Vert - case CSV -> "#607D8B"; // Bleu gris - case JSON -> "#FF9800"; // Orange - case XML -> "#795548"; // Marron - case PNG, JPEG -> "#E91E63"; // Rose - case SVG -> "#9C27B0"; // Violet - case POWERPOINT -> "#FF5722"; // Rouge-orange - case HTML -> "#00BCD4"; // Cyan - }; - } - - /** - * Génère un nom de fichier avec l'extension appropriée - * - * @param nomBase Le nom de base du fichier - * @return Le nom de fichier complet avec extension - */ - public String genererNomFichier(String nomBase) { - return nomBase + "." + extension; - } - - /** - * Retourne la taille maximale recommandée pour ce format (en MB) - * - * @return La taille maximale en mégaoctets - */ - public int getTailleMaximaleRecommandee() { - return switch (this) { - case PDF, WORD, POWERPOINT -> 50; // 50 MB pour les documents - case EXCEL -> 100; // 100 MB pour Excel - case CSV, JSON, XML -> 200; // 200 MB pour les données - case PNG, JPEG -> 10; // 10 MB pour les images - case SVG, HTML -> 5; // 5 MB pour les formats légers - }; - } - - /** - * Vérifie si le format nécessite un traitement spécial - * - * @return true si le format nécessite un traitement particulier - */ - public boolean necessiteTraitementSpecial() { - return this == PDF || this == EXCEL || this == POWERPOINT || this == WORD; - } - - /** - * Retourne les formats recommandés pour un type de rapport donné - * - * @param typeRapport Le type de rapport (executif, analytique, technique) - * @return Un tableau des formats recommandés - */ - public static FormatExport[] getFormatsRecommandes(String typeRapport) { - return switch (typeRapport.toLowerCase()) { - case "executif" -> new FormatExport[] {PDF, POWERPOINT, WORD}; - case "analytique" -> new FormatExport[] {EXCEL, CSV, JSON, PDF}; - case "technique" -> new FormatExport[] {JSON, XML, CSV, HTML}; - case "partage" -> new FormatExport[] {PDF, PNG, HTML}; - default -> new FormatExport[] {PDF, EXCEL, CSV}; - }; - } -} +package dev.lions.unionflow.server.api.enums.analytics; + +/** + * Énumération des formats d'export disponibles pour les rapports et données analytics + * + *

Cette énumération définit les différents formats dans lesquels les données peuvent être + * exportées depuis l'application UnionFlow. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +public enum FormatExport { + + // === FORMATS DOCUMENTS === + PDF("PDF", "pdf", "application/pdf", "Portable Document Format", true, true), + WORD( + "Word", + "docx", + "application/vnd.openxmlformats-officedocument.wordprocessingml.document", + "Microsoft Word", + true, + false), + + // === FORMATS TABLEURS === + EXCEL( + "Excel", + "xlsx", + "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet", + "Microsoft Excel", + true, + true), + CSV("CSV", "csv", "text/csv", "Comma Separated Values", false, true), + + // === FORMATS DONNÉES === + JSON("JSON", "json", "application/json", "JavaScript Object Notation", false, true), + XML("XML", "xml", "application/xml", "eXtensible Markup Language", false, false), + + // === FORMATS IMAGES === + PNG("PNG", "png", "image/png", "Portable Network Graphics", true, false), + JPEG("JPEG", "jpg", "image/jpeg", "Joint Photographic Experts Group", true, false), + SVG("SVG", "svg", "image/svg+xml", "Scalable Vector Graphics", true, false), + + // === FORMATS SPÉCIALISÉS === + POWERPOINT( + "PowerPoint", + "pptx", + "application/vnd.openxmlformats-officedocument.presentationml.presentation", + "Microsoft PowerPoint", + true, + false), + HTML("HTML", "html", "text/html", "HyperText Markup Language", true, false); + + private final String libelle; + private final String extension; + private final String mimeType; + private final String description; + private final boolean supporteGraphiques; + private final boolean supporteGrandesQuantitesDonnees; + + /** + * Constructeur de l'énumération FormatExport + * + * @param libelle Le libellé affiché à l'utilisateur + * @param extension L'extension de fichier + * @param mimeType Le type MIME du format + * @param description La description du format + * @param supporteGraphiques true si le format supporte les graphiques + * @param supporteGrandesQuantitesDonnees true si le format supporte de grandes quantités de + * données + */ + FormatExport( + String libelle, + String extension, + String mimeType, + String description, + boolean supporteGraphiques, + boolean supporteGrandesQuantitesDonnees) { + this.libelle = libelle; + this.extension = extension; + this.mimeType = mimeType; + this.description = description; + this.supporteGraphiques = supporteGraphiques; + this.supporteGrandesQuantitesDonnees = supporteGrandesQuantitesDonnees; + } + + /** + * Retourne le libellé du format + * + * @return Le libellé affiché à l'utilisateur + */ + public String getLibelle() { + return libelle; + } + + /** + * Retourne l'extension de fichier + * + * @return L'extension sans le point (ex: "pdf", "xlsx") + */ + public String getExtension() { + return extension; + } + + /** + * Retourne le type MIME du format + * + * @return Le type MIME complet + */ + public String getMimeType() { + return mimeType; + } + + /** + * Retourne la description du format + * + * @return La description complète du format + */ + public String getDescription() { + return description; + } + + /** + * Vérifie si le format supporte les graphiques + * + * @return true si le format peut inclure des graphiques + */ + public boolean supporteGraphiques() { + return supporteGraphiques; + } + + /** + * Vérifie si le format supporte de grandes quantités de données + * + * @return true si le format peut gérer de gros volumes de données + */ + public boolean supporteGrandesQuantitesDonnees() { + return supporteGrandesQuantitesDonnees; + } + + /** + * Vérifie si le format est adapté aux rapports exécutifs + * + * @return true si le format convient aux rapports de direction + */ + public boolean isFormatExecutif() { + return this == PDF || this == POWERPOINT || this == WORD; + } + + /** + * Vérifie si le format est adapté à l'analyse de données + * + * @return true si le format convient à l'analyse de données + */ + public boolean isFormatAnalyse() { + return this == EXCEL || this == CSV || this == JSON; + } + + /** + * Vérifie si le format est adapté au partage web + * + * @return true si le format convient au partage sur le web + */ + public boolean isFormatWeb() { + return this == HTML || this == PNG || this == SVG || this == JSON; + } + + /** + * Retourne l'icône appropriée pour le format + * + * @return L'icône Material Design + */ + public String getIcone() { + return switch (this) { + case PDF -> "picture_as_pdf"; + case WORD -> "description"; + case EXCEL -> "table_chart"; + case CSV -> "grid_on"; + case JSON -> "code"; + case XML -> "code"; + case PNG, JPEG -> "image"; + case SVG -> "vector_image"; + case POWERPOINT -> "slideshow"; + case HTML -> "web"; + }; + } + + /** + * Retourne la couleur appropriée pour le format + * + * @return Le code couleur hexadécimal + */ + public String getCouleur() { + return switch (this) { + case PDF -> "#FF5722"; // Rouge-orange + case WORD -> "#2196F3"; // Bleu + case EXCEL -> "#4CAF50"; // Vert + case CSV -> "#607D8B"; // Bleu gris + case JSON -> "#FF9800"; // Orange + case XML -> "#795548"; // Marron + case PNG, JPEG -> "#E91E63"; // Rose + case SVG -> "#9C27B0"; // Violet + case POWERPOINT -> "#FF5722"; // Rouge-orange + case HTML -> "#00BCD4"; // Cyan + }; + } + + /** + * Génère un nom de fichier avec l'extension appropriée + * + * @param nomBase Le nom de base du fichier + * @return Le nom de fichier complet avec extension + */ + public String genererNomFichier(String nomBase) { + return nomBase + "." + extension; + } + + /** + * Retourne la taille maximale recommandée pour ce format (en MB) + * + * @return La taille maximale en mégaoctets + */ + public int getTailleMaximaleRecommandee() { + return switch (this) { + case PDF, WORD, POWERPOINT -> 50; // 50 MB pour les documents + case EXCEL -> 100; // 100 MB pour Excel + case CSV, JSON, XML -> 200; // 200 MB pour les données + case PNG, JPEG -> 10; // 10 MB pour les images + case SVG, HTML -> 5; // 5 MB pour les formats légers + }; + } + + /** + * Vérifie si le format nécessite un traitement spécial + * + * @return true si le format nécessite un traitement particulier + */ + public boolean necessiteTraitementSpecial() { + return this == PDF || this == EXCEL || this == POWERPOINT || this == WORD; + } + + /** + * Retourne les formats recommandés pour un type de rapport donné + * + * @param typeRapport Le type de rapport (executif, analytique, technique) + * @return Un tableau des formats recommandés + */ + public static FormatExport[] getFormatsRecommandes(String typeRapport) { + return switch (typeRapport.toLowerCase()) { + case "executif" -> new FormatExport[] {PDF, POWERPOINT, WORD}; + case "analytique" -> new FormatExport[] {EXCEL, CSV, JSON, PDF}; + case "technique" -> new FormatExport[] {JSON, XML, CSV, HTML}; + case "partage" -> new FormatExport[] {PDF, PNG, HTML}; + default -> new FormatExport[] {PDF, EXCEL, CSV}; + }; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/analytics/PeriodeAnalyse.java b/src/main/java/dev/lions/unionflow/server/api/enums/analytics/PeriodeAnalyse.java index 899353d..563a26f 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/analytics/PeriodeAnalyse.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/analytics/PeriodeAnalyse.java @@ -1,226 +1,226 @@ -package dev.lions.unionflow.server.api.enums.analytics; - -import java.time.LocalDateTime; -import java.time.temporal.ChronoUnit; - -/** - * Énumération des périodes d'analyse disponibles pour les métriques et rapports - * - *

Cette énumération définit les différentes périodes temporelles qui peuvent être utilisées pour - * analyser les données et générer des rapports. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -public enum PeriodeAnalyse { - - // === PÉRIODES COURTES === - AUJOURD_HUI("Aujourd'hui", "today", 1, ChronoUnit.DAYS), - HIER("Hier", "yesterday", 1, ChronoUnit.DAYS), - CETTE_SEMAINE("Cette semaine", "this_week", 7, ChronoUnit.DAYS), - SEMAINE_DERNIERE("Semaine dernière", "last_week", 7, ChronoUnit.DAYS), - - // === PÉRIODES MENSUELLES === - CE_MOIS("Ce mois", "this_month", 1, ChronoUnit.MONTHS), - MOIS_DERNIER("Mois dernier", "last_month", 1, ChronoUnit.MONTHS), - TROIS_DERNIERS_MOIS("3 derniers mois", "last_3_months", 3, ChronoUnit.MONTHS), - SIX_DERNIERS_MOIS("6 derniers mois", "last_6_months", 6, ChronoUnit.MONTHS), - - // === PÉRIODES ANNUELLES === - CETTE_ANNEE("Cette année", "this_year", 1, ChronoUnit.YEARS), - ANNEE_DERNIERE("Année dernière", "last_year", 1, ChronoUnit.YEARS), - DEUX_DERNIERES_ANNEES("2 dernières années", "last_2_years", 2, ChronoUnit.YEARS), - - // === PÉRIODES PERSONNALISÉES === - SEPT_DERNIERS_JOURS("7 derniers jours", "last_7_days", 7, ChronoUnit.DAYS), - TRENTE_DERNIERS_JOURS("30 derniers jours", "last_30_days", 30, ChronoUnit.DAYS), - QUATRE_VINGT_DIX_DERNIERS_JOURS("90 derniers jours", "last_90_days", 90, ChronoUnit.DAYS), - - // === PÉRIODES SPÉCIALES === - DEPUIS_CREATION("Depuis la création", "since_creation", 0, ChronoUnit.FOREVER), - PERIODE_PERSONNALISEE("Période personnalisée", "custom", 0, ChronoUnit.DAYS); - - private final String libelle; - private final String code; - private final int duree; - private final ChronoUnit unite; - - /** - * Constructeur de l'énumération PeriodeAnalyse - * - * @param libelle Le libellé affiché à l'utilisateur - * @param code Le code technique de la période - * @param duree La durée de la période - * @param unite L'unité de temps (jours, mois, années) - */ - PeriodeAnalyse(String libelle, String code, int duree, ChronoUnit unite) { - this.libelle = libelle; - this.code = code; - this.duree = duree; - this.unite = unite; - } - - /** - * Retourne le libellé de la période - * - * @return Le libellé affiché à l'utilisateur - */ - public String getLibelle() { - return libelle; - } - - /** - * Retourne le code technique de la période - * - * @return Le code technique - */ - public String getCode() { - return code; - } - - /** - * Retourne la durée de la période - * - * @return La durée numérique - */ - public int getDuree() { - return duree; - } - - /** - * Retourne l'unité de temps de la période - * - * @return L'unité de temps (ChronoUnit) - */ - public ChronoUnit getUnite() { - return unite; - } - - /** - * Calcule la date de début pour cette période - * - * @return La date de début de la période - */ - public LocalDateTime getDateDebut() { - LocalDateTime maintenant = LocalDateTime.now(); - - return switch (this) { - case AUJOURD_HUI -> maintenant.toLocalDate().atStartOfDay(); - case HIER -> maintenant.minusDays(1).toLocalDate().atStartOfDay(); - case CETTE_SEMAINE -> - maintenant - .minusDays(maintenant.getDayOfWeek().getValue() - 1) - .toLocalDate() - .atStartOfDay(); - case SEMAINE_DERNIERE -> - maintenant - .minusDays(maintenant.getDayOfWeek().getValue() + 6) - .toLocalDate() - .atStartOfDay(); - case CE_MOIS -> maintenant.withDayOfMonth(1).toLocalDate().atStartOfDay(); - case MOIS_DERNIER -> maintenant.minusMonths(1).withDayOfMonth(1).toLocalDate().atStartOfDay(); - case CETTE_ANNEE -> maintenant.withDayOfYear(1).toLocalDate().atStartOfDay(); - case ANNEE_DERNIERE -> maintenant.minusYears(1).withDayOfYear(1).toLocalDate().atStartOfDay(); - case DEPUIS_CREATION -> LocalDateTime.of(2020, 1, 1, 0, 0); // Date de création d'UnionFlow - case PERIODE_PERSONNALISEE -> maintenant; // À définir par l'utilisateur - default -> maintenant.minus(duree, unite).toLocalDate().atStartOfDay(); - }; - } - - /** - * Calcule la date de fin pour cette période - * - * @return La date de fin de la période - */ - public LocalDateTime getDateFin() { - LocalDateTime maintenant = LocalDateTime.now(); - - return switch (this) { - case AUJOURD_HUI -> maintenant.toLocalDate().atTime(23, 59, 59); - case HIER -> maintenant.minusDays(1).toLocalDate().atTime(23, 59, 59); - case CETTE_SEMAINE -> maintenant.toLocalDate().atTime(23, 59, 59); - case SEMAINE_DERNIERE -> - maintenant - .minusDays(maintenant.getDayOfWeek().getValue()) - .toLocalDate() - .atTime(23, 59, 59); - case CE_MOIS -> maintenant.toLocalDate().atTime(23, 59, 59); - case MOIS_DERNIER -> - maintenant.withDayOfMonth(1).minusDays(1).toLocalDate().atTime(23, 59, 59); - case CETTE_ANNEE -> maintenant.toLocalDate().atTime(23, 59, 59); - case ANNEE_DERNIERE -> - maintenant.withDayOfYear(1).minusDays(1).toLocalDate().atTime(23, 59, 59); - case DEPUIS_CREATION, PERIODE_PERSONNALISEE -> maintenant; - default -> maintenant.toLocalDate().atTime(23, 59, 59); - }; - } - - /** - * Vérifie si la période est une période courte (moins d'un mois) - * - * @return true si la période est courte - */ - public boolean isPeriodeCourte() { - return this == AUJOURD_HUI - || this == HIER - || this == CETTE_SEMAINE - || this == SEMAINE_DERNIERE - || this == SEPT_DERNIERS_JOURS; - } - - /** - * Vérifie si la période est une période longue (plus d'un an) - * - * @return true si la période est longue - */ - public boolean isPeriodeLongue() { - return this == CETTE_ANNEE - || this == ANNEE_DERNIERE - || this == DEUX_DERNIERES_ANNEES - || this == DEPUIS_CREATION; - } - - /** - * Vérifie si la période est personnalisable - * - * @return true si la période peut être personnalisée - */ - public boolean isPersonnalisable() { - return this == PERIODE_PERSONNALISEE; - } - - /** - * Retourne l'intervalle de regroupement recommandé pour cette période - * - * @return L'intervalle de regroupement (jour, semaine, mois) - */ - public String getIntervalleRegroupement() { - return switch (this) { - case AUJOURD_HUI, HIER -> "heure"; - case CETTE_SEMAINE, SEMAINE_DERNIERE, SEPT_DERNIERS_JOURS -> "jour"; - case CE_MOIS, MOIS_DERNIER, TRENTE_DERNIERS_JOURS -> "jour"; - case TROIS_DERNIERS_MOIS, SIX_DERNIERS_MOIS, QUATRE_VINGT_DIX_DERNIERS_JOURS -> "semaine"; - case CETTE_ANNEE, ANNEE_DERNIERE, DEUX_DERNIERES_ANNEES -> "mois"; - case DEPUIS_CREATION -> "annee"; - default -> "jour"; - }; - } - - /** - * Retourne le format de date approprié pour cette période - * - * @return Le format de date (dd/MM, MM/yyyy, etc.) - */ - public String getFormatDate() { - return switch (this) { - case AUJOURD_HUI, HIER -> "HH:mm"; - case CETTE_SEMAINE, SEMAINE_DERNIERE, SEPT_DERNIERS_JOURS -> "dd/MM"; - case CE_MOIS, MOIS_DERNIER, TRENTE_DERNIERS_JOURS -> "dd/MM"; - case TROIS_DERNIERS_MOIS, SIX_DERNIERS_MOIS, QUATRE_VINGT_DIX_DERNIERS_JOURS -> "dd/MM"; - case CETTE_ANNEE, ANNEE_DERNIERE -> "MM/yyyy"; - case DEUX_DERNIERES_ANNEES, DEPUIS_CREATION -> "yyyy"; - default -> "dd/MM/yyyy"; - }; - } -} +package dev.lions.unionflow.server.api.enums.analytics; + +import java.time.LocalDateTime; +import java.time.temporal.ChronoUnit; + +/** + * Énumération des périodes d'analyse disponibles pour les métriques et rapports + * + *

Cette énumération définit les différentes périodes temporelles qui peuvent être utilisées pour + * analyser les données et générer des rapports. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +public enum PeriodeAnalyse { + + // === PÉRIODES COURTES === + AUJOURD_HUI("Aujourd'hui", "today", 1, ChronoUnit.DAYS), + HIER("Hier", "yesterday", 1, ChronoUnit.DAYS), + CETTE_SEMAINE("Cette semaine", "this_week", 7, ChronoUnit.DAYS), + SEMAINE_DERNIERE("Semaine dernière", "last_week", 7, ChronoUnit.DAYS), + + // === PÉRIODES MENSUELLES === + CE_MOIS("Ce mois", "this_month", 1, ChronoUnit.MONTHS), + MOIS_DERNIER("Mois dernier", "last_month", 1, ChronoUnit.MONTHS), + TROIS_DERNIERS_MOIS("3 derniers mois", "last_3_months", 3, ChronoUnit.MONTHS), + SIX_DERNIERS_MOIS("6 derniers mois", "last_6_months", 6, ChronoUnit.MONTHS), + + // === PÉRIODES ANNUELLES === + CETTE_ANNEE("Cette année", "this_year", 1, ChronoUnit.YEARS), + ANNEE_DERNIERE("Année dernière", "last_year", 1, ChronoUnit.YEARS), + DEUX_DERNIERES_ANNEES("2 dernières années", "last_2_years", 2, ChronoUnit.YEARS), + + // === PÉRIODES PERSONNALISÉES === + SEPT_DERNIERS_JOURS("7 derniers jours", "last_7_days", 7, ChronoUnit.DAYS), + TRENTE_DERNIERS_JOURS("30 derniers jours", "last_30_days", 30, ChronoUnit.DAYS), + QUATRE_VINGT_DIX_DERNIERS_JOURS("90 derniers jours", "last_90_days", 90, ChronoUnit.DAYS), + + // === PÉRIODES SPÉCIALES === + DEPUIS_CREATION("Depuis la création", "since_creation", 0, ChronoUnit.FOREVER), + PERIODE_PERSONNALISEE("Période personnalisée", "custom", 0, ChronoUnit.DAYS); + + private final String libelle; + private final String code; + private final int duree; + private final ChronoUnit unite; + + /** + * Constructeur de l'énumération PeriodeAnalyse + * + * @param libelle Le libellé affiché à l'utilisateur + * @param code Le code technique de la période + * @param duree La durée de la période + * @param unite L'unité de temps (jours, mois, années) + */ + PeriodeAnalyse(String libelle, String code, int duree, ChronoUnit unite) { + this.libelle = libelle; + this.code = code; + this.duree = duree; + this.unite = unite; + } + + /** + * Retourne le libellé de la période + * + * @return Le libellé affiché à l'utilisateur + */ + public String getLibelle() { + return libelle; + } + + /** + * Retourne le code technique de la période + * + * @return Le code technique + */ + public String getCode() { + return code; + } + + /** + * Retourne la durée de la période + * + * @return La durée numérique + */ + public int getDuree() { + return duree; + } + + /** + * Retourne l'unité de temps de la période + * + * @return L'unité de temps (ChronoUnit) + */ + public ChronoUnit getUnite() { + return unite; + } + + /** + * Calcule la date de début pour cette période + * + * @return La date de début de la période + */ + public LocalDateTime getDateDebut() { + LocalDateTime maintenant = LocalDateTime.now(); + + return switch (this) { + case AUJOURD_HUI -> maintenant.toLocalDate().atStartOfDay(); + case HIER -> maintenant.minusDays(1).toLocalDate().atStartOfDay(); + case CETTE_SEMAINE -> + maintenant + .minusDays(maintenant.getDayOfWeek().getValue() - 1) + .toLocalDate() + .atStartOfDay(); + case SEMAINE_DERNIERE -> + maintenant + .minusDays(maintenant.getDayOfWeek().getValue() + 6) + .toLocalDate() + .atStartOfDay(); + case CE_MOIS -> maintenant.withDayOfMonth(1).toLocalDate().atStartOfDay(); + case MOIS_DERNIER -> maintenant.minusMonths(1).withDayOfMonth(1).toLocalDate().atStartOfDay(); + case CETTE_ANNEE -> maintenant.withDayOfYear(1).toLocalDate().atStartOfDay(); + case ANNEE_DERNIERE -> maintenant.minusYears(1).withDayOfYear(1).toLocalDate().atStartOfDay(); + case DEPUIS_CREATION -> LocalDateTime.of(2020, 1, 1, 0, 0); // Date de création d'UnionFlow + case PERIODE_PERSONNALISEE -> maintenant; // À définir par l'utilisateur + default -> maintenant.minus(duree, unite).toLocalDate().atStartOfDay(); + }; + } + + /** + * Calcule la date de fin pour cette période + * + * @return La date de fin de la période + */ + public LocalDateTime getDateFin() { + LocalDateTime maintenant = LocalDateTime.now(); + + return switch (this) { + case AUJOURD_HUI -> maintenant.toLocalDate().atTime(23, 59, 59); + case HIER -> maintenant.minusDays(1).toLocalDate().atTime(23, 59, 59); + case CETTE_SEMAINE -> maintenant.toLocalDate().atTime(23, 59, 59); + case SEMAINE_DERNIERE -> + maintenant + .minusDays(maintenant.getDayOfWeek().getValue()) + .toLocalDate() + .atTime(23, 59, 59); + case CE_MOIS -> maintenant.toLocalDate().atTime(23, 59, 59); + case MOIS_DERNIER -> + maintenant.withDayOfMonth(1).minusDays(1).toLocalDate().atTime(23, 59, 59); + case CETTE_ANNEE -> maintenant.toLocalDate().atTime(23, 59, 59); + case ANNEE_DERNIERE -> + maintenant.withDayOfYear(1).minusDays(1).toLocalDate().atTime(23, 59, 59); + case DEPUIS_CREATION, PERIODE_PERSONNALISEE -> maintenant; + default -> maintenant.toLocalDate().atTime(23, 59, 59); + }; + } + + /** + * Vérifie si la période est une période courte (moins d'un mois) + * + * @return true si la période est courte + */ + public boolean isPeriodeCourte() { + return this == AUJOURD_HUI + || this == HIER + || this == CETTE_SEMAINE + || this == SEMAINE_DERNIERE + || this == SEPT_DERNIERS_JOURS; + } + + /** + * Vérifie si la période est une période longue (plus d'un an) + * + * @return true si la période est longue + */ + public boolean isPeriodeLongue() { + return this == CETTE_ANNEE + || this == ANNEE_DERNIERE + || this == DEUX_DERNIERES_ANNEES + || this == DEPUIS_CREATION; + } + + /** + * Vérifie si la période est personnalisable + * + * @return true si la période peut être personnalisée + */ + public boolean isPersonnalisable() { + return this == PERIODE_PERSONNALISEE; + } + + /** + * Retourne l'intervalle de regroupement recommandé pour cette période + * + * @return L'intervalle de regroupement (jour, semaine, mois) + */ + public String getIntervalleRegroupement() { + return switch (this) { + case AUJOURD_HUI, HIER -> "heure"; + case CETTE_SEMAINE, SEMAINE_DERNIERE, SEPT_DERNIERS_JOURS -> "jour"; + case CE_MOIS, MOIS_DERNIER, TRENTE_DERNIERS_JOURS -> "jour"; + case TROIS_DERNIERS_MOIS, SIX_DERNIERS_MOIS, QUATRE_VINGT_DIX_DERNIERS_JOURS -> "semaine"; + case CETTE_ANNEE, ANNEE_DERNIERE, DEUX_DERNIERES_ANNEES -> "mois"; + case DEPUIS_CREATION -> "annee"; + default -> "jour"; + }; + } + + /** + * Retourne le format de date approprié pour cette période + * + * @return Le format de date (dd/MM, MM/yyyy, etc.) + */ + public String getFormatDate() { + return switch (this) { + case AUJOURD_HUI, HIER -> "HH:mm"; + case CETTE_SEMAINE, SEMAINE_DERNIERE, SEPT_DERNIERS_JOURS -> "dd/MM"; + case CE_MOIS, MOIS_DERNIER, TRENTE_DERNIERS_JOURS -> "dd/MM"; + case TROIS_DERNIERS_MOIS, SIX_DERNIERS_MOIS, QUATRE_VINGT_DIX_DERNIERS_JOURS -> "dd/MM"; + case CETTE_ANNEE, ANNEE_DERNIERE -> "MM/yyyy"; + case DEUX_DERNIERES_ANNEES, DEPUIS_CREATION -> "yyyy"; + default -> "dd/MM/yyyy"; + }; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/analytics/TypeMetrique.java b/src/main/java/dev/lions/unionflow/server/api/enums/analytics/TypeMetrique.java index 1f382cd..725ce3b 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/analytics/TypeMetrique.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/analytics/TypeMetrique.java @@ -1,187 +1,187 @@ -package dev.lions.unionflow.server.api.enums.analytics; - -/** - * Énumération des types de métriques disponibles dans le système analytics UnionFlow - * - *

Cette énumération définit les différents types de métriques qui peuvent être calculées et - * affichées dans les tableaux de bord et rapports. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -public enum TypeMetrique { - - // === MÉTRIQUES MEMBRES === - NOMBRE_MEMBRES_ACTIFS("Nombre de membres actifs", "membres", "count"), - NOMBRE_MEMBRES_INACTIFS("Nombre de membres inactifs", "membres", "count"), - TAUX_CROISSANCE_MEMBRES("Taux de croissance des membres", "membres", "percentage"), - MOYENNE_AGE_MEMBRES("Âge moyen des membres", "membres", "average"), - REPARTITION_GENRE_MEMBRES("Répartition par genre", "membres", "distribution"), - - // === MÉTRIQUES FINANCIÈRES === - TOTAL_COTISATIONS_COLLECTEES("Total des cotisations collectées", "finance", "amount"), - COTISATIONS_EN_ATTENTE("Cotisations en attente", "finance", "amount"), - TAUX_RECOUVREMENT_COTISATIONS("Taux de recouvrement", "finance", "percentage"), - MOYENNE_COTISATION_MEMBRE("Cotisation moyenne par membre", "finance", "average"), - EVOLUTION_REVENUS_MENSUELLE("Évolution des revenus mensuels", "finance", "trend"), - - // === MÉTRIQUES ÉVÉNEMENTS === - NOMBRE_EVENEMENTS_ORGANISES("Nombre d'événements organisés", "evenements", "count"), - TAUX_PARTICIPATION_EVENEMENTS("Taux de participation aux événements", "evenements", "percentage"), - MOYENNE_PARTICIPANTS_EVENEMENT("Moyenne de participants par événement", "evenements", "average"), - EVENEMENTS_ANNULES("Événements annulés", "evenements", "count"), - SATISFACTION_EVENEMENTS("Satisfaction des événements", "evenements", "rating"), - - // === MÉTRIQUES SOLIDARITÉ === - NOMBRE_DEMANDES_AIDE("Nombre de demandes d'aide", "solidarite", "count"), - MONTANT_AIDES_ACCORDEES("Montant des aides accordées", "solidarite", "amount"), - TAUX_APPROBATION_AIDES("Taux d'approbation des aides", "solidarite", "percentage"), - DELAI_TRAITEMENT_DEMANDES("Délai moyen de traitement", "solidarite", "duration"), - IMPACT_SOCIAL_MESURE("Impact social mesuré", "solidarite", "score"), - - // === MÉTRIQUES ENGAGEMENT === - TAUX_CONNEXION_MOBILE("Taux de connexion mobile", "engagement", "percentage"), - FREQUENCE_UTILISATION_APP("Fréquence d'utilisation de l'app", "engagement", "frequency"), - ACTIONS_UTILISATEUR_JOUR("Actions utilisateur par jour", "engagement", "count"), - RETENTION_UTILISATEURS("Rétention des utilisateurs", "engagement", "percentage"), - NPS_SATISFACTION("Net Promoter Score", "engagement", "score"), - - // === MÉTRIQUES ORGANISATIONNELLES === - NOMBRE_ORGANISATIONS_ACTIVES("Organisations actives", "organisation", "count"), - TAUX_CROISSANCE_ORGANISATIONS("Croissance des organisations", "organisation", "percentage"), - MOYENNE_MEMBRES_PAR_ORGANISATION("Membres moyens par organisation", "organisation", "average"), - ORGANISATIONS_PREMIUM("Organisations premium", "organisation", "count"), - CHURN_RATE_ORGANISATIONS("Taux de désabonnement", "organisation", "percentage"), - - // === MÉTRIQUES TECHNIQUES === - TEMPS_REPONSE_API("Temps de réponse API", "technique", "duration"), - TAUX_DISPONIBILITE_SYSTEME("Taux de disponibilité", "technique", "percentage"), - NOMBRE_ERREURS_SYSTEME("Nombre d'erreurs système", "technique", "count"), - UTILISATION_STOCKAGE("Utilisation du stockage", "technique", "size"), - PERFORMANCE_MOBILE("Performance mobile", "technique", "score"); - - private final String libelle; - private final String categorie; - private final String typeValeur; - - /** - * Constructeur de l'énumération TypeMetrique - * - * @param libelle Le libellé affiché à l'utilisateur - * @param categorie La catégorie de la métrique - * @param typeValeur Le type de valeur (count, percentage, amount, etc.) - */ - TypeMetrique(String libelle, String categorie, String typeValeur) { - this.libelle = libelle; - this.categorie = categorie; - this.typeValeur = typeValeur; - } - - /** - * Retourne le libellé de la métrique - * - * @return Le libellé affiché à l'utilisateur - */ - public String getLibelle() { - return libelle; - } - - /** - * Retourne la catégorie de la métrique - * - * @return La catégorie (membres, finance, evenements, etc.) - */ - public String getCategorie() { - return categorie; - } - - /** - * Retourne le type de valeur de la métrique - * - * @return Le type de valeur (count, percentage, amount, etc.) - */ - public String getTypeValeur() { - return typeValeur; - } - - /** - * Vérifie si la métrique est de type financier - * - * @return true si la métrique concerne les finances - */ - public boolean isFinanciere() { - return "finance".equals(this.categorie); - } - - /** - * Vérifie si la métrique est de type pourcentage - * - * @return true si la métrique est un pourcentage - */ - public boolean isPourcentage() { - return "percentage".equals(this.typeValeur); - } - - /** - * Vérifie si la métrique est de type compteur - * - * @return true si la métrique est un compteur - */ - public boolean isCompteur() { - return "count".equals(this.typeValeur); - } - - /** - * Retourne l'unité de mesure appropriée pour la métrique - * - * @return L'unité de mesure (%, XOF, jours, etc.) - */ - public String getUnite() { - return switch (this.typeValeur) { - case "percentage" -> "%"; - case "amount" -> "XOF"; - case "duration" -> "jours"; - case "size" -> "MB"; - case "frequency" -> "/jour"; - case "rating", "score" -> "/10"; - default -> ""; - }; - } - - /** - * Retourne l'icône appropriée pour la métrique - * - * @return L'icône Material Design - */ - public String getIcone() { - return switch (this.categorie) { - case "membres" -> "people"; - case "finance" -> "attach_money"; - case "evenements" -> "event"; - case "solidarite" -> "favorite"; - case "engagement" -> "trending_up"; - case "organisation" -> "business"; - case "technique" -> "settings"; - default -> "analytics"; - }; - } - - /** - * Retourne la couleur appropriée pour la métrique - * - * @return Le code couleur hexadécimal - */ - public String getCouleur() { - return switch (this.categorie) { - case "membres" -> "#2196F3"; // Bleu - case "finance" -> "#4CAF50"; // Vert - case "evenements" -> "#FF9800"; // Orange - case "solidarite" -> "#E91E63"; // Rose - case "engagement" -> "#9C27B0"; // Violet - case "organisation" -> "#607D8B"; // Bleu gris - case "technique" -> "#795548"; // Marron - default -> "#757575"; // Gris - }; - } -} +package dev.lions.unionflow.server.api.enums.analytics; + +/** + * Énumération des types de métriques disponibles dans le système analytics UnionFlow + * + *

Cette énumération définit les différents types de métriques qui peuvent être calculées et + * affichées dans les tableaux de bord et rapports. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +public enum TypeMetrique { + + // === MÉTRIQUES MEMBRES === + NOMBRE_MEMBRES_ACTIFS("Nombre de membres actifs", "membres", "count"), + NOMBRE_MEMBRES_INACTIFS("Nombre de membres inactifs", "membres", "count"), + TAUX_CROISSANCE_MEMBRES("Taux de croissance des membres", "membres", "percentage"), + MOYENNE_AGE_MEMBRES("Âge moyen des membres", "membres", "average"), + REPARTITION_GENRE_MEMBRES("Répartition par genre", "membres", "distribution"), + + // === MÉTRIQUES FINANCIÈRES === + TOTAL_COTISATIONS_COLLECTEES("Total des cotisations collectées", "finance", "amount"), + COTISATIONS_EN_ATTENTE("Cotisations en attente", "finance", "amount"), + TAUX_RECOUVREMENT_COTISATIONS("Taux de recouvrement", "finance", "percentage"), + MOYENNE_COTISATION_MEMBRE("Cotisation moyenne par membre", "finance", "average"), + EVOLUTION_REVENUS_MENSUELLE("Évolution des revenus mensuels", "finance", "trend"), + + // === MÉTRIQUES ÉVÉNEMENTS === + NOMBRE_EVENEMENTS_ORGANISES("Nombre d'événements organisés", "evenements", "count"), + TAUX_PARTICIPATION_EVENEMENTS("Taux de participation aux événements", "evenements", "percentage"), + MOYENNE_PARTICIPANTS_EVENEMENT("Moyenne de participants par événement", "evenements", "average"), + EVENEMENTS_ANNULES("Événements annulés", "evenements", "count"), + SATISFACTION_EVENEMENTS("Satisfaction des événements", "evenements", "rating"), + + // === MÉTRIQUES SOLIDARITÉ === + NOMBRE_DEMANDES_AIDE("Nombre de demandes d'aide", "solidarite", "count"), + MONTANT_AIDES_ACCORDEES("Montant des aides accordées", "solidarite", "amount"), + TAUX_APPROBATION_AIDES("Taux d'approbation des aides", "solidarite", "percentage"), + DELAI_TRAITEMENT_DEMANDES("Délai moyen de traitement", "solidarite", "duration"), + IMPACT_SOCIAL_MESURE("Impact social mesuré", "solidarite", "score"), + + // === MÉTRIQUES ENGAGEMENT === + TAUX_CONNEXION_MOBILE("Taux de connexion mobile", "engagement", "percentage"), + FREQUENCE_UTILISATION_APP("Fréquence d'utilisation de l'app", "engagement", "frequency"), + ACTIONS_UTILISATEUR_JOUR("Actions utilisateur par jour", "engagement", "count"), + RETENTION_UTILISATEURS("Rétention des utilisateurs", "engagement", "percentage"), + NPS_SATISFACTION("Net Promoter Score", "engagement", "score"), + + // === MÉTRIQUES ORGANISATIONNELLES === + NOMBRE_ORGANISATIONS_ACTIVES("Organisations actives", "organisation", "count"), + TAUX_CROISSANCE_ORGANISATIONS("Croissance des organisations", "organisation", "percentage"), + MOYENNE_MEMBRES_PAR_ORGANISATION("Membres moyens par organisation", "organisation", "average"), + ORGANISATIONS_PREMIUM("Organisations premium", "organisation", "count"), + CHURN_RATE_ORGANISATIONS("Taux de désabonnement", "organisation", "percentage"), + + // === MÉTRIQUES TECHNIQUES === + TEMPS_REPONSE_API("Temps de réponse API", "technique", "duration"), + TAUX_DISPONIBILITE_SYSTEME("Taux de disponibilité", "technique", "percentage"), + NOMBRE_ERREURS_SYSTEME("Nombre d'erreurs système", "technique", "count"), + UTILISATION_STOCKAGE("Utilisation du stockage", "technique", "size"), + PERFORMANCE_MOBILE("Performance mobile", "technique", "score"); + + private final String libelle; + private final String categorie; + private final String typeValeur; + + /** + * Constructeur de l'énumération TypeMetrique + * + * @param libelle Le libellé affiché à l'utilisateur + * @param categorie La catégorie de la métrique + * @param typeValeur Le type de valeur (count, percentage, amount, etc.) + */ + TypeMetrique(String libelle, String categorie, String typeValeur) { + this.libelle = libelle; + this.categorie = categorie; + this.typeValeur = typeValeur; + } + + /** + * Retourne le libellé de la métrique + * + * @return Le libellé affiché à l'utilisateur + */ + public String getLibelle() { + return libelle; + } + + /** + * Retourne la catégorie de la métrique + * + * @return La catégorie (membres, finance, evenements, etc.) + */ + public String getCategorie() { + return categorie; + } + + /** + * Retourne le type de valeur de la métrique + * + * @return Le type de valeur (count, percentage, amount, etc.) + */ + public String getTypeValeur() { + return typeValeur; + } + + /** + * Vérifie si la métrique est de type financier + * + * @return true si la métrique concerne les finances + */ + public boolean isFinanciere() { + return "finance".equals(this.categorie); + } + + /** + * Vérifie si la métrique est de type pourcentage + * + * @return true si la métrique est un pourcentage + */ + public boolean isPourcentage() { + return "percentage".equals(this.typeValeur); + } + + /** + * Vérifie si la métrique est de type compteur + * + * @return true si la métrique est un compteur + */ + public boolean isCompteur() { + return "count".equals(this.typeValeur); + } + + /** + * Retourne l'unité de mesure appropriée pour la métrique + * + * @return L'unité de mesure (%, XOF, jours, etc.) + */ + public String getUnite() { + return switch (this.typeValeur) { + case "percentage" -> "%"; + case "amount" -> "XOF"; + case "duration" -> "jours"; + case "size" -> "MB"; + case "frequency" -> "/jour"; + case "rating", "score" -> "/10"; + default -> ""; + }; + } + + /** + * Retourne l'icône appropriée pour la métrique + * + * @return L'icône Material Design + */ + public String getIcone() { + return switch (this.categorie) { + case "membres" -> "people"; + case "finance" -> "attach_money"; + case "evenements" -> "event"; + case "solidarite" -> "favorite"; + case "engagement" -> "trending_up"; + case "organisation" -> "business"; + case "technique" -> "settings"; + default -> "analytics"; + }; + } + + /** + * Retourne la couleur appropriée pour la métrique + * + * @return Le code couleur hexadécimal + */ + public String getCouleur() { + return switch (this.categorie) { + case "membres" -> "#2196F3"; // Bleu + case "finance" -> "#4CAF50"; // Vert + case "evenements" -> "#FF9800"; // Orange + case "solidarite" -> "#E91E63"; // Rose + case "engagement" -> "#9C27B0"; // Violet + case "organisation" -> "#607D8B"; // Bleu gris + case "technique" -> "#795548"; // Marron + default -> "#757575"; // Gris + }; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/audit/PorteeAudit.java b/src/main/java/dev/lions/unionflow/server/api/enums/audit/PorteeAudit.java index 5313135..8e8e68f 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/audit/PorteeAudit.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/audit/PorteeAudit.java @@ -1,12 +1,12 @@ -package dev.lions.unionflow.server.api.enums.audit; - -public enum PorteeAudit { - ORGANISATION("Visible par le manager de l'organisation sur ses propres données"), - PLATEFORME("Visible uniquement par le Super Admin UnionFlow — audit global"); - - private final String libelle; - - PorteeAudit(String libelle) { this.libelle = libelle; } - - public String getLibelle() { return libelle; } -} +package dev.lions.unionflow.server.api.enums.audit; + +public enum PorteeAudit { + ORGANISATION("Visible par le manager de l'organisation sur ses propres données"), + PLATEFORME("Visible uniquement par le Super Admin UnionFlow — audit global"); + + private final String libelle; + + PorteeAudit(String libelle) { this.libelle = libelle; } + + public String getLibelle() { return libelle; } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/ayantdroit/LienParente.java b/src/main/java/dev/lions/unionflow/server/api/enums/ayantdroit/LienParente.java index 1389b58..990386e 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/ayantdroit/LienParente.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/ayantdroit/LienParente.java @@ -1,20 +1,20 @@ -package dev.lions.unionflow.server.api.enums.ayantdroit; - -public enum LienParente { - CONJOINT("Conjoint(e) légal(e)"), - ENFANT("Enfant"), - PARENT("Père ou Mère"), - FRATRIE("Frère ou Sœur"), - TUTEUR_LEGAL("Tuteur ou Tutrice légal(e)"), - AUTRE("Autre bénéficiaire désigné"); - - private final String libelle; - - LienParente(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.ayantdroit; + +public enum LienParente { + CONJOINT("Conjoint(e) légal(e)"), + ENFANT("Enfant"), + PARENT("Père ou Mère"), + FRATRIE("Frère ou Sœur"), + TUTEUR_LEGAL("Tuteur ou Tutrice légal(e)"), + AUTRE("Autre bénéficiaire désigné"); + + private final String libelle; + + LienParente(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/ayantdroit/StatutAyantDroit.java b/src/main/java/dev/lions/unionflow/server/api/enums/ayantdroit/StatutAyantDroit.java index cb5bc64..55fdbd7 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/ayantdroit/StatutAyantDroit.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/ayantdroit/StatutAyantDroit.java @@ -1,20 +1,20 @@ -package dev.lions.unionflow.server.api.enums.ayantdroit; - -public enum StatutAyantDroit { - EN_ATTENTE("En attente de validation documentaire"), - ACTIF("Actif et couvert"), - INACTIF("Inactif (Couverture suspendue)"), - REJETE("Dossier rejeté"), - DECEDE("Déclaré décédé"), - MAJORITE_ATTEINTE("Majorité atteinte (Sortie du statut Enfant)"); - - private final String libelle; - - StatutAyantDroit(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.ayantdroit; + +public enum StatutAyantDroit { + EN_ATTENTE("En attente de validation documentaire"), + ACTIF("Actif et couvert"), + INACTIF("Inactif (Couverture suspendue)"), + REJETE("Dossier rejeté"), + DECEDE("Déclaré décédé"), + MAJORITE_ATTEINTE("Majorité atteinte (Sortie du statut Enfant)"); + + private final String libelle; + + StatutAyantDroit(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/collectefonds/StatutCampagneCollecte.java b/src/main/java/dev/lions/unionflow/server/api/enums/collectefonds/StatutCampagneCollecte.java index e270968..07555e4 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/collectefonds/StatutCampagneCollecte.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/collectefonds/StatutCampagneCollecte.java @@ -1,19 +1,19 @@ -package dev.lions.unionflow.server.api.enums.collectefonds; - -public enum StatutCampagneCollecte { - BROUILLON("Paramétrage de la page de don en cours"), - EN_COURS("Active et ouverte aux dons"), - ATTEINTE("Objectif financier atteint (Optionnel de fermer)"), - EXPIREE("Date de fin de campagne dépassée"), - SUSPENDUE("Suspendue temporairement"); - - private final String libelle; - - StatutCampagneCollecte(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.collectefonds; + +public enum StatutCampagneCollecte { + BROUILLON("Paramétrage de la page de don en cours"), + EN_COURS("Active et ouverte aux dons"), + ATTEINTE("Objectif financier atteint (Optionnel de fermer)"), + EXPIREE("Date de fin de campagne dépassée"), + SUSPENDUE("Suspendue temporairement"); + + private final String libelle; + + StatutCampagneCollecte(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/communication/ConversationType.java b/src/main/java/dev/lions/unionflow/server/api/enums/communication/ConversationType.java index 1429c45..6939d6a 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/communication/ConversationType.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/communication/ConversationType.java @@ -1,30 +1,30 @@ -package dev.lions.unionflow.server.api.enums.communication; - -/** - * Type de conversation dans le système de messagerie - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-16 - */ -public enum ConversationType { - /** - * Conversation individuelle (1-1) - */ - INDIVIDUAL, - - /** - * Conversation de groupe - */ - GROUP, - - /** - * Canal broadcast (lecture seule pour la plupart) - */ - BROADCAST, - - /** - * Canal d'annonces organisation - */ - ANNOUNCEMENT -} +package dev.lions.unionflow.server.api.enums.communication; + +/** + * Type de conversation dans le système de messagerie + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-16 + */ +public enum ConversationType { + /** + * Conversation individuelle (1-1) + */ + INDIVIDUAL, + + /** + * Conversation de groupe + */ + GROUP, + + /** + * Canal broadcast (lecture seule pour la plupart) + */ + BROADCAST, + + /** + * Canal d'annonces organisation + */ + ANNOUNCEMENT +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/communication/MessagePriority.java b/src/main/java/dev/lions/unionflow/server/api/enums/communication/MessagePriority.java index d6578d8..898eb93 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/communication/MessagePriority.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/communication/MessagePriority.java @@ -1,25 +1,25 @@ -package dev.lions.unionflow.server.api.enums.communication; - -/** - * Priorité du message - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-16 - */ -public enum MessagePriority { - /** - * Priorité normale - */ - NORMAL, - - /** - * Priorité élevée (important) - */ - HIGH, - - /** - * Priorité urgente (critique) - */ - URGENT -} +package dev.lions.unionflow.server.api.enums.communication; + +/** + * Priorité du message + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-16 + */ +public enum MessagePriority { + /** + * Priorité normale + */ + NORMAL, + + /** + * Priorité élevée (important) + */ + HIGH, + + /** + * Priorité urgente (critique) + */ + URGENT +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/communication/MessageStatus.java b/src/main/java/dev/lions/unionflow/server/api/enums/communication/MessageStatus.java index 8f35701..0917bf7 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/communication/MessageStatus.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/communication/MessageStatus.java @@ -1,30 +1,30 @@ -package dev.lions.unionflow.server.api.enums.communication; - -/** - * Statut de lecture du message - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-16 - */ -public enum MessageStatus { - /** - * Envoyé mais non lu - */ - SENT, - - /** - * Livré (reçu par le serveur) - */ - DELIVERED, - - /** - * Lu par le destinataire - */ - READ, - - /** - * Échec d'envoi - */ - FAILED -} +package dev.lions.unionflow.server.api.enums.communication; + +/** + * Statut de lecture du message + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-16 + */ +public enum MessageStatus { + /** + * Envoyé mais non lu + */ + SENT, + + /** + * Livré (reçu par le serveur) + */ + DELIVERED, + + /** + * Lu par le destinataire + */ + READ, + + /** + * Échec d'envoi + */ + FAILED +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/communication/MessageType.java b/src/main/java/dev/lions/unionflow/server/api/enums/communication/MessageType.java index 24ae80c..70d5b83 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/communication/MessageType.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/communication/MessageType.java @@ -1,30 +1,30 @@ -package dev.lions.unionflow.server.api.enums.communication; - -/** - * Type de message - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-16 - */ -public enum MessageType { - /** - * Message individuel (membre à membre) - */ - INDIVIDUAL, - - /** - * Broadcast organisation (OrgAdmin → tous) - */ - BROADCAST, - - /** - * Message ciblé par rôle (Moderator → groupe) - */ - TARGETED, - - /** - * Notification système - */ - SYSTEM -} +package dev.lions.unionflow.server.api.enums.communication; + +/** + * Type de message + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-16 + */ +public enum MessageType { + /** + * Message individuel (membre à membre) + */ + INDIVIDUAL, + + /** + * Broadcast organisation (OrgAdmin → tous) + */ + BROADCAST, + + /** + * Message ciblé par rôle (Moderator → groupe) + */ + TARGETED, + + /** + * Notification système + */ + SYSTEM +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeCompteComptable.java b/src/main/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeCompteComptable.java index 8001190..d1d3916 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeCompteComptable.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeCompteComptable.java @@ -1,28 +1,28 @@ -package dev.lions.unionflow.server.api.enums.comptabilite; - -/** - * Énumération des types de comptes comptables - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -public enum TypeCompteComptable { - ACTIF("Actif"), - PASSIF("Passif"), - CHARGES("Charges"), - PRODUITS("Produits"), - TRESORERIE("Trésorerie"), - AUTRE("Autre"); - - private final String libelle; - - TypeCompteComptable(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} - +package dev.lions.unionflow.server.api.enums.comptabilite; + +/** + * Énumération des types de comptes comptables + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +public enum TypeCompteComptable { + ACTIF("Actif"), + PASSIF("Passif"), + CHARGES("Charges"), + PRODUITS("Produits"), + TRESORERIE("Trésorerie"), + AUTRE("Autre"); + + private final String libelle; + + TypeCompteComptable(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} + diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeJournalComptable.java b/src/main/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeJournalComptable.java index 804499a..51fd063 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeJournalComptable.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeJournalComptable.java @@ -1,27 +1,27 @@ -package dev.lions.unionflow.server.api.enums.comptabilite; - -/** - * Énumération des types de journaux comptables - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -public enum TypeJournalComptable { - ACHATS("Achats"), - VENTES("Ventes"), - BANQUE("Banque"), - CAISSE("Caisse"), - OD("Opérations Diverses"); - - private final String libelle; - - TypeJournalComptable(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} - +package dev.lions.unionflow.server.api.enums.comptabilite; + +/** + * Énumération des types de journaux comptables + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +public enum TypeJournalComptable { + ACHATS("Achats"), + VENTES("Ventes"), + BANQUE("Banque"), + CAISSE("Caisse"), + OD("Opérations Diverses"); + + private final String libelle; + + TypeJournalComptable(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} + diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/culte/TypeDonReligieux.java b/src/main/java/dev/lions/unionflow/server/api/enums/culte/TypeDonReligieux.java index 7c377a8..7c68e86 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/culte/TypeDonReligieux.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/culte/TypeDonReligieux.java @@ -1,19 +1,19 @@ -package dev.lions.unionflow.server.api.enums.culte; - -public enum TypeDonReligieux { - QUETE_ORDINAIRE("Quête ordinaire de l'office religieux"), - DIME("Obligation ou Dîme régulière"), - ZAKAT("Zakat (Aumône légale)"), - OFFRANDE_SPECIALE("Offrande spéciale d'action de grâce"), - INTENTION_PRIERE("Participation pour intention de prière"); - - private final String libelle; - - TypeDonReligieux(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.culte; + +public enum TypeDonReligieux { + QUETE_ORDINAIRE("Quête ordinaire de l'office religieux"), + DIME("Obligation ou Dîme régulière"), + ZAKAT("Zakat (Aumône légale)"), + OFFRANDE_SPECIALE("Offrande spéciale d'action de grâce"), + INTENTION_PRIERE("Participation pour intention de prière"); + + private final String libelle; + + TypeDonReligieux(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/document/TypeDocument.java b/src/main/java/dev/lions/unionflow/server/api/enums/document/TypeDocument.java index d38d34f..0eaf648 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/document/TypeDocument.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/document/TypeDocument.java @@ -1,31 +1,31 @@ -package dev.lions.unionflow.server.api.enums.document; - -/** - * Énumération des types de documents - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -public enum TypeDocument { - IDENTITE("Pièce d'Identité"), - JUSTIFICATIF_DOMICILE("Justificatif de Domicile"), - PIECE_JUSTIFICATIVE("Pièce Justificative"), - PHOTO("Photo"), - CONTRAT("Contrat"), - FACTURE("Facture"), - RECU("Reçu"), - RAPPORT("Rapport"), - AUTRE("Autre"); - - private final String libelle; - - TypeDocument(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} - +package dev.lions.unionflow.server.api.enums.document; + +/** + * Énumération des types de documents + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +public enum TypeDocument { + IDENTITE("Pièce d'Identité"), + JUSTIFICATIF_DOMICILE("Justificatif de Domicile"), + PIECE_JUSTIFICATIVE("Pièce Justificative"), + PHOTO("Photo"), + CONTRAT("Contrat"), + FACTURE("Facture"), + RECU("Reçu"), + RAPPORT("Rapport"), + AUTRE("Autre"); + + private final String libelle; + + TypeDocument(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} + diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/evenement/PrioriteEvenement.java b/src/main/java/dev/lions/unionflow/server/api/enums/evenement/PrioriteEvenement.java index 57c9349..9c93b48 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/evenement/PrioriteEvenement.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/evenement/PrioriteEvenement.java @@ -1,159 +1,159 @@ -package dev.lions.unionflow.server.api.enums.evenement; - -/** - * Énumération des priorités d'événements dans UnionFlow - * - *

Cette énumération définit les niveaux de priorité pour les événements, permettant de prioriser - * l'affichage et les notifications selon l'importance. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-09-21 - */ -public enum PrioriteEvenement { - CRITIQUE( - "Critique", - "critical", - 1, - "Événement critique nécessitant une attention immédiate", - "#F44336", - "priority_high", - true, - true), - - HAUTE( - "Haute", - "high", - 2, - "Événement de haute priorité", - "#FF9800", - "keyboard_arrow_up", - true, - false), - - NORMALE( - "Normale", "normal", 3, "Événement de priorité normale", "#2196F3", "remove", false, false), - - BASSE( - "Basse", - "low", - 4, - "Événement de priorité basse", - "#4CAF50", - "keyboard_arrow_down", - false, - false); - - private final String libelle; - private final String code; - private final int niveau; - private final String description; - private final String couleur; - private final String icone; - private final boolean notificationImmediate; - private final boolean escaladeAutomatique; - - PrioriteEvenement( - String libelle, - String code, - int niveau, - String description, - String couleur, - String icone, - boolean notificationImmediate, - boolean escaladeAutomatique) { - this.libelle = libelle; - this.code = code; - this.niveau = niveau; - this.description = description; - this.couleur = couleur; - this.icone = icone; - this.notificationImmediate = notificationImmediate; - this.escaladeAutomatique = escaladeAutomatique; - } - - // === GETTERS === - - public String getLibelle() { - return libelle; - } - - public String getCode() { - return code; - } - - public int getNiveau() { - return niveau; - } - - public String getDescription() { - return description; - } - - public String getCouleur() { - return couleur; - } - - public String getIcone() { - return icone; - } - - public boolean isNotificationImmediate() { - return notificationImmediate; - } - - public boolean isEscaladeAutomatique() { - return escaladeAutomatique; - } - - // === MÉTHODES UTILITAIRES === - - /** Vérifie si la priorité est élevée (critique ou haute) */ - public boolean isElevee() { - return this == CRITIQUE || this == HAUTE; - } - - /** Vérifie si la priorité nécessite une attention immédiate */ - public boolean isUrgente() { - return this == CRITIQUE || this == HAUTE; - } - - /** Compare deux priorités */ - public boolean isSuperieurA(PrioriteEvenement autre) { - return this.niveau < autre.niveau; // Plus le niveau est bas, plus la priorité est haute - } - - /** Retourne les priorités élevées */ - public static java.util.List getPrioritesElevees() { - return java.util.Arrays.stream(values()) - .filter(PrioriteEvenement::isElevee) - .collect(java.util.stream.Collectors.toList()); - } - - /** Retourne les priorités urgentes */ - public static java.util.List getPrioritesUrgentes() { - return java.util.Arrays.stream(values()) - .filter(PrioriteEvenement::isUrgente) - .collect(java.util.stream.Collectors.toList()); - } - - /** Détermine la priorité basée sur le type d'événement */ - public static PrioriteEvenement determinerPriorite(TypeEvenementMetier typeEvenement) { - return switch (typeEvenement) { - case ASSEMBLEE_GENERALE -> HAUTE; - case REUNION_BUREAU -> HAUTE; - case ACTION_CARITATIVE -> NORMALE; - case FORMATION -> NORMALE; - case CONFERENCE -> NORMALE; - case ACTIVITE_SOCIALE -> BASSE; - case ATELIER -> BASSE; - case CEREMONIE -> NORMALE; - case AUTRE -> NORMALE; - }; - } - - /** Retourne la priorité par défaut */ - public static PrioriteEvenement getDefaut() { - return NORMALE; - } -} +package dev.lions.unionflow.server.api.enums.evenement; + +/** + * Énumération des priorités d'événements dans UnionFlow + * + *

Cette énumération définit les niveaux de priorité pour les événements, permettant de prioriser + * l'affichage et les notifications selon l'importance. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-09-21 + */ +public enum PrioriteEvenement { + CRITIQUE( + "Critique", + "critical", + 1, + "Événement critique nécessitant une attention immédiate", + "#F44336", + "priority_high", + true, + true), + + HAUTE( + "Haute", + "high", + 2, + "Événement de haute priorité", + "#FF9800", + "keyboard_arrow_up", + true, + false), + + NORMALE( + "Normale", "normal", 3, "Événement de priorité normale", "#2196F3", "remove", false, false), + + BASSE( + "Basse", + "low", + 4, + "Événement de priorité basse", + "#4CAF50", + "keyboard_arrow_down", + false, + false); + + private final String libelle; + private final String code; + private final int niveau; + private final String description; + private final String couleur; + private final String icone; + private final boolean notificationImmediate; + private final boolean escaladeAutomatique; + + PrioriteEvenement( + String libelle, + String code, + int niveau, + String description, + String couleur, + String icone, + boolean notificationImmediate, + boolean escaladeAutomatique) { + this.libelle = libelle; + this.code = code; + this.niveau = niveau; + this.description = description; + this.couleur = couleur; + this.icone = icone; + this.notificationImmediate = notificationImmediate; + this.escaladeAutomatique = escaladeAutomatique; + } + + // === GETTERS === + + public String getLibelle() { + return libelle; + } + + public String getCode() { + return code; + } + + public int getNiveau() { + return niveau; + } + + public String getDescription() { + return description; + } + + public String getCouleur() { + return couleur; + } + + public String getIcone() { + return icone; + } + + public boolean isNotificationImmediate() { + return notificationImmediate; + } + + public boolean isEscaladeAutomatique() { + return escaladeAutomatique; + } + + // === MÉTHODES UTILITAIRES === + + /** Vérifie si la priorité est élevée (critique ou haute) */ + public boolean isElevee() { + return this == CRITIQUE || this == HAUTE; + } + + /** Vérifie si la priorité nécessite une attention immédiate */ + public boolean isUrgente() { + return this == CRITIQUE || this == HAUTE; + } + + /** Compare deux priorités */ + public boolean isSuperieurA(PrioriteEvenement autre) { + return this.niveau < autre.niveau; // Plus le niveau est bas, plus la priorité est haute + } + + /** Retourne les priorités élevées */ + public static java.util.List getPrioritesElevees() { + return java.util.Arrays.stream(values()) + .filter(PrioriteEvenement::isElevee) + .collect(java.util.stream.Collectors.toList()); + } + + /** Retourne les priorités urgentes */ + public static java.util.List getPrioritesUrgentes() { + return java.util.Arrays.stream(values()) + .filter(PrioriteEvenement::isUrgente) + .collect(java.util.stream.Collectors.toList()); + } + + /** Détermine la priorité basée sur le type d'événement */ + public static PrioriteEvenement determinerPriorite(TypeEvenementMetier typeEvenement) { + return switch (typeEvenement) { + case ASSEMBLEE_GENERALE -> HAUTE; + case REUNION_BUREAU -> HAUTE; + case ACTION_CARITATIVE -> NORMALE; + case FORMATION -> NORMALE; + case CONFERENCE -> NORMALE; + case ACTIVITE_SOCIALE -> BASSE; + case ATELIER -> BASSE; + case CEREMONIE -> NORMALE; + case AUTRE -> NORMALE; + }; + } + + /** Retourne la priorité par défaut */ + public static PrioriteEvenement getDefaut() { + return NORMALE; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/evenement/StatutEvenement.java b/src/main/java/dev/lions/unionflow/server/api/enums/evenement/StatutEvenement.java index 9018cfa..1516b4a 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/evenement/StatutEvenement.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/evenement/StatutEvenement.java @@ -1,233 +1,233 @@ -package dev.lions.unionflow.server.api.enums.evenement; - -/** - * Énumération des statuts d'événements dans UnionFlow - * - *

Cette énumération définit les différents états qu'un événement peut avoir tout au long de son - * cycle de vie, de la planification à la clôture. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-09-21 - */ -public enum StatutEvenement { - - // === STATUTS DE PLANIFICATION === - PLANIFIE( - "Planifié", - "planned", - "L'événement est planifié et en préparation", - "#2196F3", - "event", - false, - false), - - CONFIRME( - "Confirmé", - "confirmed", - "L'événement est confirmé et les inscriptions sont ouvertes", - "#4CAF50", - "event_available", - false, - false), - - // === STATUTS D'EXÉCUTION === - EN_COURS( - "En cours", - "ongoing", - "L'événement est actuellement en cours", - "#FF9800", - "play_circle", - false, - false), - - // === STATUTS FINAUX === - TERMINE( - "Terminé", - "completed", - "L'événement s'est terminé avec succès", - "#4CAF50", - "check_circle", - true, - false), - - ANNULE("Annulé", "cancelled", "L'événement a été annulé", "#F44336", "cancel", true, true), - - REPORTE( - "Reporté", - "postponed", - "L'événement a été reporté à une date ultérieure", - "#FF5722", - "schedule", - false, - false); - - private final String libelle; - private final String code; - private final String description; - private final String couleur; - private final String icone; - private final boolean estFinal; - private final boolean estEchec; - - StatutEvenement( - String libelle, - String code, - String description, - String couleur, - String icone, - boolean estFinal, - boolean estEchec) { - this.libelle = libelle; - this.code = code; - this.description = description; - this.couleur = couleur; - this.icone = icone; - this.estFinal = estFinal; - this.estEchec = estEchec; - } - - // === GETTERS === - - public String getLibelle() { - return libelle; - } - - public String getCode() { - return code; - } - - public String getDescription() { - return description; - } - - public String getCouleur() { - return couleur; - } - - public String getIcone() { - return icone; - } - - public boolean isEstFinal() { - return estFinal; - } - - public boolean isEstEchec() { - return estEchec; - } - - // === MÉTHODES UTILITAIRES === - - /** Vérifie si l'événement peut être modifié */ - public boolean permetModification() { - return switch (this) { - case PLANIFIE, CONFIRME, REPORTE -> true; - case EN_COURS, TERMINE, ANNULE -> false; - }; - } - - /** Vérifie si l'événement peut être annulé */ - public boolean permetAnnulation() { - return switch (this) { - case PLANIFIE, CONFIRME, EN_COURS, REPORTE -> true; - case TERMINE, ANNULE -> false; - }; - } - - /** Vérifie si l'événement est en cours d'exécution */ - public boolean isEnCours() { - return this == EN_COURS; - } - - /** Vérifie si l'événement est terminé avec succès */ - public boolean isSucces() { - return this == TERMINE; - } - - /** Retourne les statuts finaux */ - public static java.util.List getStatutsFinaux() { - return java.util.Arrays.stream(values()) - .filter(StatutEvenement::isEstFinal) - .collect(java.util.stream.Collectors.toList()); - } - - /** Retourne les statuts d'échec */ - public static java.util.List getStatutsEchec() { - return java.util.Arrays.stream(values()) - .filter(StatutEvenement::isEstEchec) - .collect(java.util.stream.Collectors.toList()); - } - - /** Vérifie si la transition vers un autre statut est valide */ - public boolean peutTransitionnerVers(StatutEvenement nouveauStatut) { - if (this == nouveauStatut) return false; - if (estFinal && nouveauStatut != REPORTE) return false; - - return switch (this) { - case PLANIFIE -> - nouveauStatut == CONFIRME || nouveauStatut == ANNULE || nouveauStatut == REPORTE; - case CONFIRME -> - nouveauStatut == EN_COURS || nouveauStatut == ANNULE || nouveauStatut == REPORTE; - case EN_COURS -> nouveauStatut == TERMINE || nouveauStatut == ANNULE; - case REPORTE -> nouveauStatut == PLANIFIE || nouveauStatut == ANNULE; - default -> false; - }; - } - - /** Retourne le niveau de priorité pour l'affichage */ - public int getNiveauPriorite() { - return switch (this) { - case EN_COURS -> 1; - case CONFIRME -> 2; - case PLANIFIE -> 3; - case REPORTE -> 4; - case TERMINE -> 5; - case ANNULE -> 6; - }; - } - - // === MÉTHODES STATIQUES === - - /** Retourne les statuts actifs (non finaux) */ - public static StatutEvenement[] getStatutsActifs() { - return new StatutEvenement[] {PLANIFIE, CONFIRME, EN_COURS, REPORTE}; - } - - /** Trouve un statut par son code */ - public static StatutEvenement fromCode(String code) { - if (code == null || code.trim().isEmpty()) { - return null; - } - for (StatutEvenement statut : values()) { - if (statut.code.equals(code)) { - return statut; - } - } - return null; - } - - /** Trouve un statut par son libellé */ - public static StatutEvenement fromLibelle(String libelle) { - if (libelle == null || libelle.trim().isEmpty()) { - return null; - } - for (StatutEvenement statut : values()) { - if (statut.libelle.equals(libelle)) { - return statut; - } - } - return null; - } - - /** Retourne les transitions possibles depuis ce statut */ - public StatutEvenement[] getTransitionsPossibles() { - return switch (this) { - case PLANIFIE -> new StatutEvenement[] {CONFIRME, ANNULE, REPORTE}; - case CONFIRME -> new StatutEvenement[] {EN_COURS, ANNULE, REPORTE}; - case EN_COURS -> new StatutEvenement[] {TERMINE, ANNULE}; - case REPORTE -> new StatutEvenement[] {PLANIFIE, CONFIRME, ANNULE}; - case TERMINE, ANNULE -> new StatutEvenement[] {}; // Aucune transition possible - }; - } -} +package dev.lions.unionflow.server.api.enums.evenement; + +/** + * Énumération des statuts d'événements dans UnionFlow + * + *

Cette énumération définit les différents états qu'un événement peut avoir tout au long de son + * cycle de vie, de la planification à la clôture. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-09-21 + */ +public enum StatutEvenement { + + // === STATUTS DE PLANIFICATION === + PLANIFIE( + "Planifié", + "planned", + "L'événement est planifié et en préparation", + "#2196F3", + "event", + false, + false), + + CONFIRME( + "Confirmé", + "confirmed", + "L'événement est confirmé et les inscriptions sont ouvertes", + "#4CAF50", + "event_available", + false, + false), + + // === STATUTS D'EXÉCUTION === + EN_COURS( + "En cours", + "ongoing", + "L'événement est actuellement en cours", + "#FF9800", + "play_circle", + false, + false), + + // === STATUTS FINAUX === + TERMINE( + "Terminé", + "completed", + "L'événement s'est terminé avec succès", + "#4CAF50", + "check_circle", + true, + false), + + ANNULE("Annulé", "cancelled", "L'événement a été annulé", "#F44336", "cancel", true, true), + + REPORTE( + "Reporté", + "postponed", + "L'événement a été reporté à une date ultérieure", + "#FF5722", + "schedule", + false, + false); + + private final String libelle; + private final String code; + private final String description; + private final String couleur; + private final String icone; + private final boolean estFinal; + private final boolean estEchec; + + StatutEvenement( + String libelle, + String code, + String description, + String couleur, + String icone, + boolean estFinal, + boolean estEchec) { + this.libelle = libelle; + this.code = code; + this.description = description; + this.couleur = couleur; + this.icone = icone; + this.estFinal = estFinal; + this.estEchec = estEchec; + } + + // === GETTERS === + + public String getLibelle() { + return libelle; + } + + public String getCode() { + return code; + } + + public String getDescription() { + return description; + } + + public String getCouleur() { + return couleur; + } + + public String getIcone() { + return icone; + } + + public boolean isEstFinal() { + return estFinal; + } + + public boolean isEstEchec() { + return estEchec; + } + + // === MÉTHODES UTILITAIRES === + + /** Vérifie si l'événement peut être modifié */ + public boolean permetModification() { + return switch (this) { + case PLANIFIE, CONFIRME, REPORTE -> true; + case EN_COURS, TERMINE, ANNULE -> false; + }; + } + + /** Vérifie si l'événement peut être annulé */ + public boolean permetAnnulation() { + return switch (this) { + case PLANIFIE, CONFIRME, EN_COURS, REPORTE -> true; + case TERMINE, ANNULE -> false; + }; + } + + /** Vérifie si l'événement est en cours d'exécution */ + public boolean isEnCours() { + return this == EN_COURS; + } + + /** Vérifie si l'événement est terminé avec succès */ + public boolean isSucces() { + return this == TERMINE; + } + + /** Retourne les statuts finaux */ + public static java.util.List getStatutsFinaux() { + return java.util.Arrays.stream(values()) + .filter(StatutEvenement::isEstFinal) + .collect(java.util.stream.Collectors.toList()); + } + + /** Retourne les statuts d'échec */ + public static java.util.List getStatutsEchec() { + return java.util.Arrays.stream(values()) + .filter(StatutEvenement::isEstEchec) + .collect(java.util.stream.Collectors.toList()); + } + + /** Vérifie si la transition vers un autre statut est valide */ + public boolean peutTransitionnerVers(StatutEvenement nouveauStatut) { + if (this == nouveauStatut) return false; + if (estFinal && nouveauStatut != REPORTE) return false; + + return switch (this) { + case PLANIFIE -> + nouveauStatut == CONFIRME || nouveauStatut == ANNULE || nouveauStatut == REPORTE; + case CONFIRME -> + nouveauStatut == EN_COURS || nouveauStatut == ANNULE || nouveauStatut == REPORTE; + case EN_COURS -> nouveauStatut == TERMINE || nouveauStatut == ANNULE; + case REPORTE -> nouveauStatut == PLANIFIE || nouveauStatut == ANNULE; + default -> false; + }; + } + + /** Retourne le niveau de priorité pour l'affichage */ + public int getNiveauPriorite() { + return switch (this) { + case EN_COURS -> 1; + case CONFIRME -> 2; + case PLANIFIE -> 3; + case REPORTE -> 4; + case TERMINE -> 5; + case ANNULE -> 6; + }; + } + + // === MÉTHODES STATIQUES === + + /** Retourne les statuts actifs (non finaux) */ + public static StatutEvenement[] getStatutsActifs() { + return new StatutEvenement[] {PLANIFIE, CONFIRME, EN_COURS, REPORTE}; + } + + /** Trouve un statut par son code */ + public static StatutEvenement fromCode(String code) { + if (code == null || code.trim().isEmpty()) { + return null; + } + for (StatutEvenement statut : values()) { + if (statut.code.equals(code)) { + return statut; + } + } + return null; + } + + /** Trouve un statut par son libellé */ + public static StatutEvenement fromLibelle(String libelle) { + if (libelle == null || libelle.trim().isEmpty()) { + return null; + } + for (StatutEvenement statut : values()) { + if (statut.libelle.equals(libelle)) { + return statut; + } + } + return null; + } + + /** Retourne les transitions possibles depuis ce statut */ + public StatutEvenement[] getTransitionsPossibles() { + return switch (this) { + case PLANIFIE -> new StatutEvenement[] {CONFIRME, ANNULE, REPORTE}; + case CONFIRME -> new StatutEvenement[] {EN_COURS, ANNULE, REPORTE}; + case EN_COURS -> new StatutEvenement[] {TERMINE, ANNULE}; + case REPORTE -> new StatutEvenement[] {PLANIFIE, CONFIRME, ANNULE}; + case TERMINE, ANNULE -> new StatutEvenement[] {}; // Aucune transition possible + }; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/evenement/TypeEvenementMetier.java b/src/main/java/dev/lions/unionflow/server/api/enums/evenement/TypeEvenementMetier.java index bb70b36..170e0c0 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/evenement/TypeEvenementMetier.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/evenement/TypeEvenementMetier.java @@ -1,30 +1,30 @@ -package dev.lions.unionflow.server.api.enums.evenement; - -/** - * Énumération des types d'événements métier dans UnionFlow - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -public enum TypeEvenementMetier { - ASSEMBLEE_GENERALE("Assemblée Générale"), - FORMATION("Formation"), - ACTIVITE_SOCIALE("Activité Sociale"), - ACTION_CARITATIVE("Action Caritative"), - REUNION_BUREAU("Réunion de Bureau"), - CONFERENCE("Conférence"), - ATELIER("Atelier"), - CEREMONIE("Cérémonie"), - AUTRE("Autre"); - - private final String libelle; - - TypeEvenementMetier(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.evenement; + +/** + * Énumération des types d'événements métier dans UnionFlow + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +public enum TypeEvenementMetier { + ASSEMBLEE_GENERALE("Assemblée Générale"), + FORMATION("Formation"), + ACTIVITE_SOCIALE("Activité Sociale"), + ACTION_CARITATIVE("Action Caritative"), + REUNION_BUREAU("Réunion de Bureau"), + CONFERENCE("Conférence"), + ATELIER("Atelier"), + CEREMONIE("Cérémonie"), + AUTRE("Autre"); + + private final String libelle; + + TypeEvenementMetier(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/finance/StatutCotisation.java b/src/main/java/dev/lions/unionflow/server/api/enums/finance/StatutCotisation.java index 9e4768e..94868bb 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/finance/StatutCotisation.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/finance/StatutCotisation.java @@ -1,27 +1,27 @@ -package dev.lions.unionflow.server.api.enums.finance; - -/** - * Énumération des statuts de cotisations dans UnionFlow - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -public enum StatutCotisation { - EN_ATTENTE("En attente"), - PAYEE("Payée"), - PARTIELLEMENT_PAYEE("Partiellement payée"), - EN_RETARD("En retard"), - ANNULEE("Annulée"), - REMBOURSEE("Remboursée"); - - private final String libelle; - - StatutCotisation(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.finance; + +/** + * Énumération des statuts de cotisations dans UnionFlow + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +public enum StatutCotisation { + EN_ATTENTE("En attente"), + PAYEE("Payée"), + PARTIELLEMENT_PAYEE("Partiellement payée"), + EN_RETARD("En retard"), + ANNULEE("Annulée"), + REMBOURSEE("Remboursée"); + + private final String libelle; + + StatutCotisation(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/formuleabonnement/StatutFormule.java b/src/main/java/dev/lions/unionflow/server/api/enums/formuleabonnement/StatutFormule.java index e943ca5..0e75b83 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/formuleabonnement/StatutFormule.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/formuleabonnement/StatutFormule.java @@ -1,21 +1,21 @@ -package dev.lions.unionflow.server.api.enums.formuleabonnement; - -/** - * Statuts des formules d'abonnement. - */ -public enum StatutFormule { - ACTIVE("Active"), - INACTIVE("Inactive"), - ARCHIVEE("Archivée"), - BIENTOT_DISPONIBLE("Bientôt Disponible"); - - private final String libelle; - - StatutFormule(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.formuleabonnement; + +/** + * Statuts des formules d'abonnement. + */ +public enum StatutFormule { + ACTIVE("Active"), + INACTIVE("Inactive"), + ARCHIVEE("Archivée"), + BIENTOT_DISPONIBLE("Bientôt Disponible"); + + private final String libelle; + + StatutFormule(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/formuleabonnement/TypeFormule.java b/src/main/java/dev/lions/unionflow/server/api/enums/formuleabonnement/TypeFormule.java index aef4eb5..8712b03 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/formuleabonnement/TypeFormule.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/formuleabonnement/TypeFormule.java @@ -1,21 +1,21 @@ -package dev.lions.unionflow.server.api.enums.formuleabonnement; - -/** - * Types de formules d'abonnement disponibles. - */ -public enum TypeFormule { - BASIC("Formule Basique"), - STANDARD("Formule Standard"), - PREMIUM("Formule Premium"), - ENTERPRISE("Formule Entreprise"); - - private final String libelle; - - TypeFormule(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.formuleabonnement; + +/** + * Types de formules d'abonnement disponibles. + */ +public enum TypeFormule { + BASIC("Formule Basique"), + STANDARD("Formule Standard"), + PREMIUM("Formule Premium"), + ENTERPRISE("Formule Entreprise"); + + private final String libelle; + + TypeFormule(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/gouvernance/NiveauEchelon.java b/src/main/java/dev/lions/unionflow/server/api/enums/gouvernance/NiveauEchelon.java index 0d7552e..0a8eef0 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/gouvernance/NiveauEchelon.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/gouvernance/NiveauEchelon.java @@ -1,18 +1,18 @@ -package dev.lions.unionflow.server.api.enums.gouvernance; - -public enum NiveauEchelon { - SIEGE_MONDIAL("Siège / Direction Globale"), - NATIONAL("Fédération ou Bureau National"), - REGIONAL("Ligue ou Section Régionale/Départementale"), - LOCAL("Antenne / Cellule de base locale"); - - private final String libelle; - - NiveauEchelon(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.gouvernance; + +public enum NiveauEchelon { + SIEGE_MONDIAL("Siège / Direction Globale"), + NATIONAL("Fédération ou Bureau National"), + REGIONAL("Ligue ou Section Régionale/Départementale"), + LOCAL("Antenne / Cellule de base locale"); + + private final String libelle; + + NiveauEchelon(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/membre/LienParente.java b/src/main/java/dev/lions/unionflow/server/api/enums/membre/LienParente.java index 3b02848..f54b1f2 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/membre/LienParente.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/membre/LienParente.java @@ -1,14 +1,14 @@ -package dev.lions.unionflow.server.api.enums.membre; - -public enum LienParente { - CONJOINT("Conjoint(e)"), - ENFANT("Enfant"), - PARENT("Parent"), - AUTRE("Autre"); - - private final String libelle; - - LienParente(String libelle) { this.libelle = libelle; } - - public String getLibelle() { return libelle; } -} +package dev.lions.unionflow.server.api.enums.membre; + +public enum LienParente { + CONJOINT("Conjoint(e)"), + ENFANT("Enfant"), + PARENT("Parent"), + AUTRE("Autre"); + + private final String libelle; + + LienParente(String libelle) { this.libelle = libelle; } + + public String getLibelle() { return libelle; } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/membre/NiveauVigilanceKyc.java b/src/main/java/dev/lions/unionflow/server/api/enums/membre/NiveauVigilanceKyc.java index ef50f6c..580deee 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/membre/NiveauVigilanceKyc.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/membre/NiveauVigilanceKyc.java @@ -1,22 +1,22 @@ -package dev.lions.unionflow.server.api.enums.membre; - -/** - * Niveau de vigilance KYC (Know Your Customer) pour la LCB-FT. - * Détermine l'exigence d'identification et de justification des opérations. - */ -public enum NiveauVigilanceKyc { - /** Vigilance simplifiée — identification de base */ - SIMPLIFIE("Vigilance simplifiée"), - /** Vigilance renforcée — justifications et pièces supplémentaires requises */ - RENFORCE("Vigilance renforcée"); - - private final String libelle; - - NiveauVigilanceKyc(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.membre; + +/** + * Niveau de vigilance KYC (Know Your Customer) pour la LCB-FT. + * Détermine l'exigence d'identification et de justification des opérations. + */ +public enum NiveauVigilanceKyc { + /** Vigilance simplifiée — identification de base */ + SIMPLIFIE("Vigilance simplifiée"), + /** Vigilance renforcée — justifications et pièces supplémentaires requises */ + RENFORCE("Vigilance renforcée"); + + private final String libelle; + + NiveauVigilanceKyc(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/membre/StatutCompteUtilisateur.java b/src/main/java/dev/lions/unionflow/server/api/enums/membre/StatutCompteUtilisateur.java index 37c91c9..7f2d81c 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/membre/StatutCompteUtilisateur.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/membre/StatutCompteUtilisateur.java @@ -1,14 +1,14 @@ -package dev.lions.unionflow.server.api.enums.membre; - -public enum StatutCompteUtilisateur { - EN_ATTENTE_VALIDATION("En attente — inscription soumise, validation admin requise"), - ACTIF("Actif — peut se connecter"), - SUSPENDU("Suspendu — accès bloqué temporairement"), - DESACTIVE("Désactivé — compte supprimé logiquement"); - - private final String libelle; - - StatutCompteUtilisateur(String libelle) { this.libelle = libelle; } - - public String getLibelle() { return libelle; } -} +package dev.lions.unionflow.server.api.enums.membre; + +public enum StatutCompteUtilisateur { + EN_ATTENTE_VALIDATION("En attente — inscription soumise, validation admin requise"), + ACTIF("Actif — peut se connecter"), + SUSPENDU("Suspendu — accès bloqué temporairement"), + DESACTIVE("Désactivé — compte supprimé logiquement"); + + private final String libelle; + + StatutCompteUtilisateur(String libelle) { this.libelle = libelle; } + + public String getLibelle() { return libelle; } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/membre/StatutKyc.java b/src/main/java/dev/lions/unionflow/server/api/enums/membre/StatutKyc.java index 8772498..b5b094e 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/membre/StatutKyc.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/membre/StatutKyc.java @@ -1,25 +1,25 @@ -package dev.lions.unionflow.server.api.enums.membre; - -/** - * Statut de la vérification d'identité (KYC) d'un membre — LCB-FT. - */ -public enum StatutKyc { - /** Identité non encore vérifiée */ - NON_VERIFIE("Non vérifié"), - /** Vérification en cours */ - EN_COURS("En cours"), - /** Identité vérifiée — éligible aux opérations */ - VERIFIE("Vérifié"), - /** Vérification refusée ou dossier incomplet */ - REFUSE("Refusé"); - - private final String libelle; - - StatutKyc(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.membre; + +/** + * Statut de la vérification d'identité (KYC) d'un membre — LCB-FT. + */ +public enum StatutKyc { + /** Identité non encore vérifiée */ + NON_VERIFIE("Non vérifié"), + /** Vérification en cours */ + EN_COURS("En cours"), + /** Identité vérifiée — éligible aux opérations */ + VERIFIE("Vérifié"), + /** Vérification refusée ou dossier incomplet */ + REFUSE("Refusé"); + + private final String libelle; + + StatutKyc(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/membre/StatutMembre.java b/src/main/java/dev/lions/unionflow/server/api/enums/membre/StatutMembre.java index 955f50f..8fbcaba 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/membre/StatutMembre.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/membre/StatutMembre.java @@ -1,31 +1,31 @@ -package dev.lions.unionflow.server.api.enums.membre; - -/** - * Énumération des statuts de membres dans UnionFlow - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -public enum StatutMembre { - INVITE("Invité — en attente d'acceptation"), - EN_ATTENTE_VALIDATION("En attente de validation"), - ACTIF("Actif"), - INACTIF("Inactif — cotisations en retard"), - SUSPENDU("Suspendu — décision disciplinaire"), - DEMISSIONNAIRE("Démissionnaire"), - RADIE("Radié — exclusion définitive"), - HONORAIRE("Honoraire — sans cotisation obligatoire"), - DECEDE("Décédé — archivage / gestion ayants droit"), - ARCHIVE("Archivé — données conservées, accès révoqué"); - - private final String libelle; - - StatutMembre(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.membre; + +/** + * Énumération des statuts de membres dans UnionFlow + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +public enum StatutMembre { + INVITE("Invité — en attente d'acceptation"), + EN_ATTENTE_VALIDATION("En attente de validation"), + ACTIF("Actif"), + INACTIF("Inactif — cotisations en retard"), + SUSPENDU("Suspendu — décision disciplinaire"), + DEMISSIONNAIRE("Démissionnaire"), + RADIE("Radié — exclusion définitive"), + HONORAIRE("Honoraire — sans cotisation obligatoire"), + DECEDE("Décédé — archivage / gestion ayants droit"), + ARCHIVE("Archivé — données conservées, accès révoqué"); + + private final String libelle; + + StatutMembre(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/module/TypeModule.java b/src/main/java/dev/lions/unionflow/server/api/enums/module/TypeModule.java index 5a09218..46131ae 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/module/TypeModule.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/module/TypeModule.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.enums.module; - -public enum TypeModule { - COTISATIONS("Gestion des cotisations"), - EVENEMENTS("Gestion des événements"), - SOLIDARITE("Fonds de solidarité"), - COMPTABILITE("Comptabilité simplifiée OHADA"), - DOCUMENTS("Gestion documentaire — 1 Go max"), - NOTIFICATIONS("Notifications multi-canal"), - CREDIT_EPARGNE("Épargne & crédit MEC"), - AYANTS_DROIT("Gestion ayants droit — mutuelles santé"), - TONTINE("Tontine / épargne rotative"), - ONG_PROJETS("Projets humanitaires / ONG"), - COOP_AGRICOLE("Coopérative agricole"), - VOTE_INTERNE("Vote interne électronique"), - COLLECTE_FONDS("Collecte de fonds"), - REGISTRE_PROFESSIONNEL("Registre officiel membres agréés"), - CULTES_RELIGIEUX("Gestion cultes et dîmes"), - GOUVERNANCE_MULTI("Gouvernance multi-niveaux"); - - private final String libelle; - - TypeModule(String libelle) { this.libelle = libelle; } - - public String getLibelle() { return libelle; } -} +package dev.lions.unionflow.server.api.enums.module; + +public enum TypeModule { + COTISATIONS("Gestion des cotisations"), + EVENEMENTS("Gestion des événements"), + SOLIDARITE("Fonds de solidarité"), + COMPTABILITE("Comptabilité simplifiée OHADA"), + DOCUMENTS("Gestion documentaire — 1 Go max"), + NOTIFICATIONS("Notifications multi-canal"), + CREDIT_EPARGNE("Épargne & crédit MEC"), + AYANTS_DROIT("Gestion ayants droit — mutuelles santé"), + TONTINE("Tontine / épargne rotative"), + ONG_PROJETS("Projets humanitaires / ONG"), + COOP_AGRICOLE("Coopérative agricole"), + VOTE_INTERNE("Vote interne électronique"), + COLLECTE_FONDS("Collecte de fonds"), + REGISTRE_PROFESSIONNEL("Registre officiel membres agréés"), + CULTES_RELIGIEUX("Gestion cultes et dîmes"), + GOUVERNANCE_MULTI("Gouvernance multi-niveaux"); + + private final String libelle; + + TypeModule(String libelle) { this.libelle = libelle; } + + public String getLibelle() { return libelle; } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutDemandeCredit.java b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutDemandeCredit.java index 17a8622..6b0a121 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutDemandeCredit.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutDemandeCredit.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.credit; - -/** - * Cycle de vie global d'une demande de financement. - */ -public enum StatutDemandeCredit { - BROUILLON("Brouillon / En constitution"), - SOUMISE("Soumise (Attente analyse)"), - EN_EVALUATION("En cours d'étude par le comité"), - INFORMATIONS_REQUISES("Informations complémenaires requises"), - APPROUVEE("Approuvée (Attente déblocage)"), - REJETEE("Rejetée par le comité"), - DECAISSEE("Décaissement effectué / En cours de remboursement"), - SOLDEE("Crédit totalement remboursé et soldé"), - EN_CONTENTIEUX("En défaut de paiement / Contentieux juridique"); - - private final String libelle; - - StatutDemandeCredit(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.credit; + +/** + * Cycle de vie global d'une demande de financement. + */ +public enum StatutDemandeCredit { + BROUILLON("Brouillon / En constitution"), + SOUMISE("Soumise (Attente analyse)"), + EN_EVALUATION("En cours d'étude par le comité"), + INFORMATIONS_REQUISES("Informations complémenaires requises"), + APPROUVEE("Approuvée (Attente déblocage)"), + REJETEE("Rejetée par le comité"), + DECAISSEE("Décaissement effectué / En cours de remboursement"), + SOLDEE("Crédit totalement remboursé et soldé"), + EN_CONTENTIEUX("En défaut de paiement / Contentieux juridique"); + + private final String libelle; + + StatutDemandeCredit(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutEcheanceCredit.java b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutEcheanceCredit.java index c6fefc3..39b9445 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutEcheanceCredit.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutEcheanceCredit.java @@ -1,25 +1,25 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.credit; - -/** - * Évolution temporelle d'une traite ou d'une échéance prévue au tableau - * d'amortissement. - */ -public enum StatutEcheanceCredit { - A_VENIR("Échéance à venir"), - EXIGIBLE("Échéance exigible ce jour"), - PAYEE("Intégralement payée"), - PAYEE_PARTIELLEMENT("Partiellement payée"), - EN_RETARD("En retard de paiement"), - IMPAYEE("Déclarée impayée / Recouvrement"), - RESTRUCTUREE("Échéance restructurée / reportée"); - - private final String libelle; - - StatutEcheanceCredit(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.credit; + +/** + * Évolution temporelle d'une traite ou d'une échéance prévue au tableau + * d'amortissement. + */ +public enum StatutEcheanceCredit { + A_VENIR("Échéance à venir"), + EXIGIBLE("Échéance exigible ce jour"), + PAYEE("Intégralement payée"), + PAYEE_PARTIELLEMENT("Partiellement payée"), + EN_RETARD("En retard de paiement"), + IMPAYEE("Déclarée impayée / Recouvrement"), + RESTRUCTUREE("Échéance restructurée / reportée"); + + private final String libelle; + + StatutEcheanceCredit(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeCredit.java b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeCredit.java index 40f8a8a..acdd6e2 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeCredit.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeCredit.java @@ -1,24 +1,24 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.credit; - -/** - * Types de produits de crédit ou de financement. - */ -public enum TypeCredit { - CONSOMMATION("Crédit à la consommation"), - IMMOBILIER("Crédit immobilier / Construction"), - PROFESSIONNEL("Financement d'activité génératrice de revenus (AGR)"), - AGRICOLE("Campagne agricole / Matériel"), - SCOLAIRE("Crédit scolaire / Études"), - URGENCE("Prêt d'urgence (Santé, Social)"), - DECOUVERT("Découvert autorisé"); - - private final String libelle; - - TypeCredit(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.credit; + +/** + * Types de produits de crédit ou de financement. + */ +public enum TypeCredit { + CONSOMMATION("Crédit à la consommation"), + IMMOBILIER("Crédit immobilier / Construction"), + PROFESSIONNEL("Financement d'activité génératrice de revenus (AGR)"), + AGRICOLE("Campagne agricole / Matériel"), + SCOLAIRE("Crédit scolaire / Études"), + URGENCE("Prêt d'urgence (Santé, Social)"), + DECOUVERT("Découvert autorisé"); + + private final String libelle; + + TypeCredit(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeGarantie.java b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeGarantie.java index 546b11f..7f38a14 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeGarantie.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeGarantie.java @@ -1,22 +1,22 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.credit; - -/** - * Types de garanties apportées pour sécuriser un crédit. - */ -public enum TypeGarantie { - EPARGNE_BLOQUEE("Fonds bloqués sur compte d'épargne (Nantissement)"), - CAUTION_SOLIDAIRE("Avaliseurs / Cautions solidaires (Membres phys.)"), - MATERIELLE("Garantie sur équipement / Véhicule"), - IMMOBILIERE("Hypothèque / Titre foncier"), - FOND_GARANTIE("Fonds de garantie externe (ex. FONGIP)"); - - private final String libelle; - - TypeGarantie(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.credit; + +/** + * Types de garanties apportées pour sécuriser un crédit. + */ +public enum TypeGarantie { + EPARGNE_BLOQUEE("Fonds bloqués sur compte d'épargne (Nantissement)"), + CAUTION_SOLIDAIRE("Avaliseurs / Cautions solidaires (Membres phys.)"), + MATERIELLE("Garantie sur équipement / Véhicule"), + IMMOBILIERE("Hypothèque / Titre foncier"), + FOND_GARANTIE("Fonds de garantie externe (ex. FONGIP)"); + + private final String libelle; + + TypeGarantie(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/StatutCompteEpargne.java b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/StatutCompteEpargne.java index a8ee174..0ffe772 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/StatutCompteEpargne.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/StatutCompteEpargne.java @@ -1,22 +1,22 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.epargne; - -/** - * Statuts possibles pour un compte d'épargne. - */ -public enum StatutCompteEpargne { - ACTIF("Actif et fonctionnel"), - INACTIF("Inactif (sans mouvement prolongé)"), - BLOQUE("Bloqué (saisie, garantie, ou décision CA)"), - EN_CLOTURE("En cours de clôture"), - CLOTURE("Clôturé"); - - private final String libelle; - - StatutCompteEpargne(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.epargne; + +/** + * Statuts possibles pour un compte d'épargne. + */ +public enum StatutCompteEpargne { + ACTIF("Actif et fonctionnel"), + INACTIF("Inactif (sans mouvement prolongé)"), + BLOQUE("Bloqué (saisie, garantie, ou décision CA)"), + EN_CLOTURE("En cours de clôture"), + CLOTURE("Clôturé"); + + private final String libelle; + + StatutCompteEpargne(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeCompteEpargne.java b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeCompteEpargne.java index c1fd53b..3553c6d 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeCompteEpargne.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeCompteEpargne.java @@ -1,22 +1,22 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.epargne; - -/** - * Types de comptes d'épargne gérés par la mutuelle. - */ -public enum TypeCompteEpargne { - COURANT("Compte courant / de transit"), - EPARGNE_LIBRE("Épargne libre / classique"), - EPARGNE_BLOQUEE("Épargne bloquée (Garantie de crédit)"), - DEPOT_A_TERME("Dépôt à terme (DAT)"), - EPARGNE_PROJET("Épargne projet / tontine"); - - private final String libelle; - - TypeCompteEpargne(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.epargne; + +/** + * Types de comptes d'épargne gérés par la mutuelle. + */ +public enum TypeCompteEpargne { + COURANT("Compte courant / de transit"), + EPARGNE_LIBRE("Épargne libre / classique"), + EPARGNE_BLOQUEE("Épargne bloquée (Garantie de crédit)"), + DEPOT_A_TERME("Dépôt à terme (DAT)"), + EPARGNE_PROJET("Épargne projet / tontine"); + + private final String libelle; + + TypeCompteEpargne(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeTransactionEpargne.java b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeTransactionEpargne.java index 4d456bf..6af6413 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeTransactionEpargne.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeTransactionEpargne.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.epargne; - -/** - * Nature opérationnelle des transactions d'épargne - */ -public enum TypeTransactionEpargne { - DEPOT("Dépôt sur le compte"), - RETRAIT("Retrait d'espèces"), - TRANSFERT_ENTRANT("Virement/Transfert entrant"), - TRANSFERT_SORTANT("Virement/Transfert sortant"), - PAIEMENT_INTERETS("Paiement des intérêts créditeurs"), - PRELEVEMENT_FRAIS("Prélèvement de frais de tenue de compte"), - RETENUE_GARANTIE("Gel/Retenue pour garantie de prêt"), - LIBERATION_GARANTIE("Libération de fonds de garantie"), - REMBOURSEMENT_CREDIT("Remboursement d'une échéance de crédit"); - - private final String libelle; - - TypeTransactionEpargne(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.epargne; + +/** + * Nature opérationnelle des transactions d'épargne + */ +public enum TypeTransactionEpargne { + DEPOT("Dépôt sur le compte"), + RETRAIT("Retrait d'espèces"), + TRANSFERT_ENTRANT("Virement/Transfert entrant"), + TRANSFERT_SORTANT("Virement/Transfert sortant"), + PAIEMENT_INTERETS("Paiement des intérêts créditeurs"), + PRELEVEMENT_FRAIS("Prélèvement de frais de tenue de compte"), + RETENUE_GARANTIE("Gel/Retenue pour garantie de prêt"), + LIBERATION_GARANTIE("Libération de fonds de garantie"), + REMBOURSEMENT_CREDIT("Remboursement d'une échéance de crédit"); + + private final String libelle; + + TypeTransactionEpargne(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/notification/CanalNotification.java b/src/main/java/dev/lions/unionflow/server/api/enums/notification/CanalNotification.java index 97b552c..e6b948c 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/notification/CanalNotification.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/notification/CanalNotification.java @@ -1,467 +1,467 @@ -package dev.lions.unionflow.server.api.enums.notification; - -/** - * Énumération des canaux de notification pour Android et iOS - * - *

Cette énumération définit les différents canaux de notification utilisés pour organiser et - * prioriser les notifications push dans UnionFlow. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -public enum CanalNotification { - - // === CANAUX PAR PRIORITÉ === - URGENT_CHANNEL( - "urgent", - "Notifications urgentes", - "Alertes critiques nécessitant une action immédiate", - 5, - true, - true, - true, - "urgent", - "#F44336"), - - ERROR_CHANNEL( - "error", - "Erreurs système", - "Notifications d'erreurs et de problèmes techniques", - 4, - true, - true, - false, - "error", - "#F44336"), - - WARNING_CHANNEL( - "warning", - "Avertissements", - "Notifications d'avertissement et d'attention", - 4, - true, - true, - false, - "warning", - "#FF9800"), - - IMPORTANT_CHANNEL( - "important", - "Notifications importantes", - "Informations importantes à ne pas manquer", - 4, - true, - true, - false, - "important", - "#FF5722"), - - REMINDER_CHANNEL( - "reminder", - "Rappels", - "Rappels d'événements, cotisations et échéances", - 3, - true, - true, - false, - "reminder", - "#2196F3"), - - SUCCESS_CHANNEL( - "success", - "Confirmations", - "Notifications de succès et confirmations", - 2, - false, - false, - false, - "success", - "#4CAF50"), - - CELEBRATION_CHANNEL( - "celebration", - "Célébrations", - "Anniversaires, félicitations et événements joyeux", - 2, - false, - false, - false, - "celebration", - "#FF9800"), - - DEFAULT_CHANNEL( - "default", - "Notifications générales", - "Notifications d'information générale", - 2, - false, - false, - false, - "info", - "#2196F3"), - - // === CANAUX PAR CATÉGORIE === - EVENTS_CHANNEL( - "events", - "Événements", - "Notifications liées aux événements et activités", - 3, - true, - false, - false, - "event", - "#2196F3"), - - PAYMENTS_CHANNEL( - "payments", - "Paiements", - "Notifications de cotisations et paiements", - 4, - true, - true, - false, - "payment", - "#4CAF50"), - - SOLIDARITY_CHANNEL( - "solidarity", - "Solidarité", - "Notifications d'aide et de solidarité", - 3, - true, - false, - false, - "help", - "#E91E63"), - - MEMBERS_CHANNEL( - "members", - "Membres", - "Notifications concernant les membres", - 2, - false, - false, - false, - "people", - "#2196F3"), - - ORGANIZATION_CHANNEL( - "organization", - "Organisation", - "Annonces et informations organisationnelles", - 3, - true, - false, - false, - "business", - "#2196F3"), - - SYSTEM_CHANNEL( - "system", - "Système", - "Notifications système et maintenance", - 2, - false, - false, - false, - "settings", - "#607D8B"), - - MESSAGES_CHANNEL( - "messages", - "Messages", - "Messages privés et communications", - 3, - true, - false, - false, - "message", - "#2196F3"), - - LOCATION_CHANNEL( - "location", - "Géolocalisation", - "Notifications basées sur la localisation", - 2, - false, - false, - false, - "location_on", - "#4CAF50"); - - private final String id; - private final String nom; - private final String description; - private final int importance; - private final boolean sonActive; - private final boolean vibrationActive; - private final boolean lumiereLED; - private final String typeDefaut; - private final String couleur; - - /** - * Constructeur de l'énumération CanalNotification - * - * @param id L'identifiant unique du canal - * @param nom Le nom affiché du canal - * @param description La description du canal - * @param importance Le niveau d'importance (1=Min, 2=Low, 3=Default, 4=High, 5=Max) - * @param sonActive true si le son est activé par défaut - * @param vibrationActive true si la vibration est activée par défaut - * @param lumiereLED true si la lumière LED est activée par défaut - * @param typeDefaut Le type de notification par défaut pour ce canal - * @param couleur La couleur hexadécimale du canal - */ - CanalNotification( - String id, - String nom, - String description, - int importance, - boolean sonActive, - boolean vibrationActive, - boolean lumiereLED, - String typeDefaut, - String couleur) { - this.id = id; - this.nom = nom; - this.description = description; - this.importance = importance; - this.sonActive = sonActive; - this.vibrationActive = vibrationActive; - this.lumiereLED = lumiereLED; - this.typeDefaut = typeDefaut; - this.couleur = couleur; - } - - /** - * Retourne l'identifiant du canal - * - * @return L'ID unique du canal - */ - public String getId() { - return id; - } - - /** - * Retourne le nom du canal - * - * @return Le nom affiché du canal - */ - public String getNom() { - return nom; - } - - /** - * Retourne la description du canal - * - * @return La description détaillée du canal - */ - public String getDescription() { - return description; - } - - /** - * Retourne le niveau d'importance - * - * @return Le niveau d'importance (1-5) - */ - public int getImportance() { - return importance; - } - - /** - * Vérifie si le son est activé par défaut - * - * @return true si le son est activé - */ - public boolean isSonActive() { - return sonActive; - } - - /** - * Vérifie si la vibration est activée par défaut - * - * @return true si la vibration est activée - */ - public boolean isVibrationActive() { - return vibrationActive; - } - - /** - * Vérifie si la lumière LED est activée par défaut - * - * @return true si la lumière LED est activée - */ - public boolean isLumiereLED() { - return lumiereLED; - } - - /** - * Retourne le type de notification par défaut - * - * @return Le type par défaut pour ce canal - */ - public String getTypeDefaut() { - return typeDefaut; - } - - /** - * Retourne la couleur du canal - * - * @return Le code couleur hexadécimal - */ - public String getCouleur() { - return couleur; - } - - /** - * Vérifie si le canal est critique - * - * @return true si le canal a une importance élevée (4-5) - */ - public boolean isCritique() { - return importance >= 4; - } - - /** - * Vérifie si le canal est silencieux par défaut - * - * @return true si le canal n'émet ni son ni vibration - */ - public boolean isSilencieux() { - boolean pasDeSon = !sonActive; - boolean pasDeVibration = !vibrationActive; - return pasDeSon & pasDeVibration; - } - - /** - * Retourne le niveau d'importance Android - * - * @return Le niveau d'importance pour Android (IMPORTANCE_MIN à IMPORTANCE_MAX) - */ - public String getImportanceAndroid() { - return switch (importance) { - case 1 -> "IMPORTANCE_MIN"; - case 2 -> "IMPORTANCE_LOW"; - case 3 -> "IMPORTANCE_DEFAULT"; - case 4 -> "IMPORTANCE_HIGH"; - case 5 -> "IMPORTANCE_MAX"; - default -> "IMPORTANCE_DEFAULT"; - }; - } - - /** - * Retourne la priorité iOS - * - * @return La priorité pour iOS (low ou high) - */ - public String getPrioriteIOS() { - return importance >= 4 ? "high" : "low"; - } - - /** - * Retourne le son par défaut pour le canal - * - * @return Le nom du fichier son ou "default" - */ - public String getSonDefaut() { - return switch (this) { - case URGENT_CHANNEL -> "urgent_sound.mp3"; - case ERROR_CHANNEL -> "error_sound.mp3"; - case WARNING_CHANNEL -> "warning_sound.mp3"; - case IMPORTANT_CHANNEL -> "important_sound.mp3"; - case REMINDER_CHANNEL -> "reminder_sound.mp3"; - case SUCCESS_CHANNEL -> "success_sound.mp3"; - case CELEBRATION_CHANNEL -> "celebration_sound.mp3"; - default -> "default"; - }; - } - - /** - * Retourne le pattern de vibration - * - * @return Le pattern de vibration en millisecondes - */ - public long[] getPatternVibration() { - return switch (this) { - case URGENT_CHANNEL -> new long[] {0, 500, 200, 500, 200, 500}; // Triple vibration - case ERROR_CHANNEL -> new long[] {0, 1000, 500, 1000}; // Double vibration longue - case WARNING_CHANNEL -> new long[] {0, 300, 200, 300}; // Double vibration courte - case IMPORTANT_CHANNEL -> new long[] {0, 500, 100, 200}; // Vibration distinctive - case REMINDER_CHANNEL -> new long[] {0, 200, 100, 200}; // Vibration douce - default -> new long[] {0, 250}; // Vibration simple - }; - } - - /** - * Vérifie si le canal peut être désactivé par l'utilisateur - * - * @return true si l'utilisateur peut désactiver ce canal - */ - public boolean peutEtreDesactive() { - return this != URGENT_CHANNEL && this != ERROR_CHANNEL; - } - - /** - * Retourne la durée de vie par défaut des notifications de ce canal - * - * @return La durée de vie en millisecondes - */ - public long getDureeVieMs() { - return switch (this) { - case URGENT_CHANNEL -> 3600000L; // 1 heure - case ERROR_CHANNEL -> 86400000L; // 24 heures - case WARNING_CHANNEL -> 172800000L; // 48 heures - case IMPORTANT_CHANNEL -> 259200000L; // 72 heures - case REMINDER_CHANNEL -> 86400000L; // 24 heures - case SUCCESS_CHANNEL -> 172800000L; // 48 heures - case CELEBRATION_CHANNEL -> 259200000L; // 72 heures - default -> 604800000L; // 1 semaine - }; - } - - /** - * Trouve un canal par son ID - * - * @param id L'identifiant du canal - * @return Le canal correspondant ou DEFAULT_CHANNEL si non trouvé - */ - public static CanalNotification parId(String id) { - for (CanalNotification canal : values()) { - if (canal.getId().equals(id)) { - return canal; - } - } - return DEFAULT_CHANNEL; - } - - /** - * Retourne tous les canaux critiques - * - * @return Un tableau des canaux critiques - */ - public static CanalNotification[] getCanauxCritiques() { - return new CanalNotification[] { - URGENT_CHANNEL, ERROR_CHANNEL, WARNING_CHANNEL, IMPORTANT_CHANNEL - }; - } - - /** - * Retourne tous les canaux par catégorie - * - * @return Un tableau des canaux catégoriels - */ - public static CanalNotification[] getCanauxCategories() { - return new CanalNotification[] { - EVENTS_CHANNEL, - PAYMENTS_CHANNEL, - SOLIDARITY_CHANNEL, - MEMBERS_CHANNEL, - ORGANIZATION_CHANNEL, - SYSTEM_CHANNEL, - MESSAGES_CHANNEL, - LOCATION_CHANNEL - }; - } -} +package dev.lions.unionflow.server.api.enums.notification; + +/** + * Énumération des canaux de notification pour Android et iOS + * + *

Cette énumération définit les différents canaux de notification utilisés pour organiser et + * prioriser les notifications push dans UnionFlow. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +public enum CanalNotification { + + // === CANAUX PAR PRIORITÉ === + URGENT_CHANNEL( + "urgent", + "Notifications urgentes", + "Alertes critiques nécessitant une action immédiate", + 5, + true, + true, + true, + "urgent", + "#F44336"), + + ERROR_CHANNEL( + "error", + "Erreurs système", + "Notifications d'erreurs et de problèmes techniques", + 4, + true, + true, + false, + "error", + "#F44336"), + + WARNING_CHANNEL( + "warning", + "Avertissements", + "Notifications d'avertissement et d'attention", + 4, + true, + true, + false, + "warning", + "#FF9800"), + + IMPORTANT_CHANNEL( + "important", + "Notifications importantes", + "Informations importantes à ne pas manquer", + 4, + true, + true, + false, + "important", + "#FF5722"), + + REMINDER_CHANNEL( + "reminder", + "Rappels", + "Rappels d'événements, cotisations et échéances", + 3, + true, + true, + false, + "reminder", + "#2196F3"), + + SUCCESS_CHANNEL( + "success", + "Confirmations", + "Notifications de succès et confirmations", + 2, + false, + false, + false, + "success", + "#4CAF50"), + + CELEBRATION_CHANNEL( + "celebration", + "Célébrations", + "Anniversaires, félicitations et événements joyeux", + 2, + false, + false, + false, + "celebration", + "#FF9800"), + + DEFAULT_CHANNEL( + "default", + "Notifications générales", + "Notifications d'information générale", + 2, + false, + false, + false, + "info", + "#2196F3"), + + // === CANAUX PAR CATÉGORIE === + EVENTS_CHANNEL( + "events", + "Événements", + "Notifications liées aux événements et activités", + 3, + true, + false, + false, + "event", + "#2196F3"), + + PAYMENTS_CHANNEL( + "payments", + "Paiements", + "Notifications de cotisations et paiements", + 4, + true, + true, + false, + "payment", + "#4CAF50"), + + SOLIDARITY_CHANNEL( + "solidarity", + "Solidarité", + "Notifications d'aide et de solidarité", + 3, + true, + false, + false, + "help", + "#E91E63"), + + MEMBERS_CHANNEL( + "members", + "Membres", + "Notifications concernant les membres", + 2, + false, + false, + false, + "people", + "#2196F3"), + + ORGANIZATION_CHANNEL( + "organization", + "Organisation", + "Annonces et informations organisationnelles", + 3, + true, + false, + false, + "business", + "#2196F3"), + + SYSTEM_CHANNEL( + "system", + "Système", + "Notifications système et maintenance", + 2, + false, + false, + false, + "settings", + "#607D8B"), + + MESSAGES_CHANNEL( + "messages", + "Messages", + "Messages privés et communications", + 3, + true, + false, + false, + "message", + "#2196F3"), + + LOCATION_CHANNEL( + "location", + "Géolocalisation", + "Notifications basées sur la localisation", + 2, + false, + false, + false, + "location_on", + "#4CAF50"); + + private final String id; + private final String nom; + private final String description; + private final int importance; + private final boolean sonActive; + private final boolean vibrationActive; + private final boolean lumiereLED; + private final String typeDefaut; + private final String couleur; + + /** + * Constructeur de l'énumération CanalNotification + * + * @param id L'identifiant unique du canal + * @param nom Le nom affiché du canal + * @param description La description du canal + * @param importance Le niveau d'importance (1=Min, 2=Low, 3=Default, 4=High, 5=Max) + * @param sonActive true si le son est activé par défaut + * @param vibrationActive true si la vibration est activée par défaut + * @param lumiereLED true si la lumière LED est activée par défaut + * @param typeDefaut Le type de notification par défaut pour ce canal + * @param couleur La couleur hexadécimale du canal + */ + CanalNotification( + String id, + String nom, + String description, + int importance, + boolean sonActive, + boolean vibrationActive, + boolean lumiereLED, + String typeDefaut, + String couleur) { + this.id = id; + this.nom = nom; + this.description = description; + this.importance = importance; + this.sonActive = sonActive; + this.vibrationActive = vibrationActive; + this.lumiereLED = lumiereLED; + this.typeDefaut = typeDefaut; + this.couleur = couleur; + } + + /** + * Retourne l'identifiant du canal + * + * @return L'ID unique du canal + */ + public String getId() { + return id; + } + + /** + * Retourne le nom du canal + * + * @return Le nom affiché du canal + */ + public String getNom() { + return nom; + } + + /** + * Retourne la description du canal + * + * @return La description détaillée du canal + */ + public String getDescription() { + return description; + } + + /** + * Retourne le niveau d'importance + * + * @return Le niveau d'importance (1-5) + */ + public int getImportance() { + return importance; + } + + /** + * Vérifie si le son est activé par défaut + * + * @return true si le son est activé + */ + public boolean isSonActive() { + return sonActive; + } + + /** + * Vérifie si la vibration est activée par défaut + * + * @return true si la vibration est activée + */ + public boolean isVibrationActive() { + return vibrationActive; + } + + /** + * Vérifie si la lumière LED est activée par défaut + * + * @return true si la lumière LED est activée + */ + public boolean isLumiereLED() { + return lumiereLED; + } + + /** + * Retourne le type de notification par défaut + * + * @return Le type par défaut pour ce canal + */ + public String getTypeDefaut() { + return typeDefaut; + } + + /** + * Retourne la couleur du canal + * + * @return Le code couleur hexadécimal + */ + public String getCouleur() { + return couleur; + } + + /** + * Vérifie si le canal est critique + * + * @return true si le canal a une importance élevée (4-5) + */ + public boolean isCritique() { + return importance >= 4; + } + + /** + * Vérifie si le canal est silencieux par défaut + * + * @return true si le canal n'émet ni son ni vibration + */ + public boolean isSilencieux() { + boolean pasDeSon = !sonActive; + boolean pasDeVibration = !vibrationActive; + return pasDeSon & pasDeVibration; + } + + /** + * Retourne le niveau d'importance Android + * + * @return Le niveau d'importance pour Android (IMPORTANCE_MIN à IMPORTANCE_MAX) + */ + public String getImportanceAndroid() { + return switch (importance) { + case 1 -> "IMPORTANCE_MIN"; + case 2 -> "IMPORTANCE_LOW"; + case 3 -> "IMPORTANCE_DEFAULT"; + case 4 -> "IMPORTANCE_HIGH"; + case 5 -> "IMPORTANCE_MAX"; + default -> "IMPORTANCE_DEFAULT"; + }; + } + + /** + * Retourne la priorité iOS + * + * @return La priorité pour iOS (low ou high) + */ + public String getPrioriteIOS() { + return importance >= 4 ? "high" : "low"; + } + + /** + * Retourne le son par défaut pour le canal + * + * @return Le nom du fichier son ou "default" + */ + public String getSonDefaut() { + return switch (this) { + case URGENT_CHANNEL -> "urgent_sound.mp3"; + case ERROR_CHANNEL -> "error_sound.mp3"; + case WARNING_CHANNEL -> "warning_sound.mp3"; + case IMPORTANT_CHANNEL -> "important_sound.mp3"; + case REMINDER_CHANNEL -> "reminder_sound.mp3"; + case SUCCESS_CHANNEL -> "success_sound.mp3"; + case CELEBRATION_CHANNEL -> "celebration_sound.mp3"; + default -> "default"; + }; + } + + /** + * Retourne le pattern de vibration + * + * @return Le pattern de vibration en millisecondes + */ + public long[] getPatternVibration() { + return switch (this) { + case URGENT_CHANNEL -> new long[] {0, 500, 200, 500, 200, 500}; // Triple vibration + case ERROR_CHANNEL -> new long[] {0, 1000, 500, 1000}; // Double vibration longue + case WARNING_CHANNEL -> new long[] {0, 300, 200, 300}; // Double vibration courte + case IMPORTANT_CHANNEL -> new long[] {0, 500, 100, 200}; // Vibration distinctive + case REMINDER_CHANNEL -> new long[] {0, 200, 100, 200}; // Vibration douce + default -> new long[] {0, 250}; // Vibration simple + }; + } + + /** + * Vérifie si le canal peut être désactivé par l'utilisateur + * + * @return true si l'utilisateur peut désactiver ce canal + */ + public boolean peutEtreDesactive() { + return this != URGENT_CHANNEL && this != ERROR_CHANNEL; + } + + /** + * Retourne la durée de vie par défaut des notifications de ce canal + * + * @return La durée de vie en millisecondes + */ + public long getDureeVieMs() { + return switch (this) { + case URGENT_CHANNEL -> 3600000L; // 1 heure + case ERROR_CHANNEL -> 86400000L; // 24 heures + case WARNING_CHANNEL -> 172800000L; // 48 heures + case IMPORTANT_CHANNEL -> 259200000L; // 72 heures + case REMINDER_CHANNEL -> 86400000L; // 24 heures + case SUCCESS_CHANNEL -> 172800000L; // 48 heures + case CELEBRATION_CHANNEL -> 259200000L; // 72 heures + default -> 604800000L; // 1 semaine + }; + } + + /** + * Trouve un canal par son ID + * + * @param id L'identifiant du canal + * @return Le canal correspondant ou DEFAULT_CHANNEL si non trouvé + */ + public static CanalNotification parId(String id) { + for (CanalNotification canal : values()) { + if (canal.getId().equals(id)) { + return canal; + } + } + return DEFAULT_CHANNEL; + } + + /** + * Retourne tous les canaux critiques + * + * @return Un tableau des canaux critiques + */ + public static CanalNotification[] getCanauxCritiques() { + return new CanalNotification[] { + URGENT_CHANNEL, ERROR_CHANNEL, WARNING_CHANNEL, IMPORTANT_CHANNEL + }; + } + + /** + * Retourne tous les canaux par catégorie + * + * @return Un tableau des canaux catégoriels + */ + public static CanalNotification[] getCanauxCategories() { + return new CanalNotification[] { + EVENTS_CHANNEL, + PAYMENTS_CHANNEL, + SOLIDARITY_CHANNEL, + MEMBERS_CHANNEL, + ORGANIZATION_CHANNEL, + SYSTEM_CHANNEL, + MESSAGES_CHANNEL, + LOCATION_CHANNEL + }; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/notification/PrioriteNotification.java b/src/main/java/dev/lions/unionflow/server/api/enums/notification/PrioriteNotification.java index 3a7f6ef..c899015 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/notification/PrioriteNotification.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/notification/PrioriteNotification.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.enums.notification; - -/** - * Énumération des priorités de notifications - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -public enum PrioriteNotification { - CRITIQUE("Critique"), - HAUTE("Haute"), - NORMALE("Normale"), - BASSE("Basse"); - - private final String libelle; - - PrioriteNotification(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} - +package dev.lions.unionflow.server.api.enums.notification; + +/** + * Énumération des priorités de notifications + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +public enum PrioriteNotification { + CRITIQUE("Critique"), + HAUTE("Haute"), + NORMALE("Normale"), + BASSE("Basse"); + + private final String libelle; + + PrioriteNotification(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} + diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/notification/StatutNotification.java b/src/main/java/dev/lions/unionflow/server/api/enums/notification/StatutNotification.java index a913c3c..0b9a7cc 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/notification/StatutNotification.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/notification/StatutNotification.java @@ -1,459 +1,459 @@ -package dev.lions.unionflow.server.api.enums.notification; - -/** - * Énumération des statuts de notification dans UnionFlow - * - *

Cette énumération définit les différents états qu'une notification peut avoir tout au long de - * son cycle de vie, de la création à l'archivage. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -public enum StatutNotification { - - // === STATUTS DE CRÉATION === - BROUILLON( - "Brouillon", - "draft", - "La notification est en cours de création", - "edit", - "#9E9E9E", - false, - false), - - PROGRAMMEE( - "Programmée", - "scheduled", - "La notification est programmée pour envoi ultérieur", - "schedule", - "#FF9800", - false, - false), - - EN_ATTENTE( - "En attente", - "pending", - "La notification est en attente d'envoi", - "hourglass_empty", - "#FF9800", - false, - false), - - // === STATUTS D'ENVOI === - EN_COURS_ENVOI( - "En cours d'envoi", - "sending", - "La notification est en cours d'envoi", - "send", - "#2196F3", - false, - false), - - ENVOYEE( - "Envoyée", - "sent", - "La notification a été envoyée avec succès", - "check_circle", - "#4CAF50", - true, - false), - - ECHEC_ENVOI( - "Échec d'envoi", - "failed", - "L'envoi de la notification a échoué", - "error", - "#F44336", - true, - true), - - PARTIELLEMENT_ENVOYEE( - "Partiellement envoyée", - "partial", - "La notification a été envoyée à certains destinataires seulement", - "warning", - "#FF9800", - true, - true), - - // === STATUTS DE RÉCEPTION === - RECUE( - "Reçue", - "received", - "La notification a été reçue par l'appareil", - "download_done", - "#4CAF50", - true, - false), - - AFFICHEE( - "Affichée", - "displayed", - "La notification a été affichée à l'utilisateur", - "visibility", - "#2196F3", - true, - false), - - OUVERTE( - "Ouverte", - "opened", - "L'utilisateur a ouvert la notification", - "open_in_new", - "#4CAF50", - true, - false), - - IGNOREE( - "Ignorée", - "ignored", - "La notification a été ignorée par l'utilisateur", - "visibility_off", - "#9E9E9E", - true, - false), - - // === STATUTS D'INTERACTION === - LUE( - "Lue", - "read", - "La notification a été lue par l'utilisateur", - "mark_email_read", - "#4CAF50", - true, - false), - - NON_LUE( - "Non lue", - "unread", - "La notification n'a pas encore été lue", - "mark_email_unread", - "#FF9800", - true, - false), - - MARQUEE_IMPORTANTE( - "Marquée importante", - "starred", - "L'utilisateur a marqué la notification comme importante", - "star", - "#FF9800", - true, - false), - - ACTION_EXECUTEE( - "Action exécutée", - "action_done", - "L'utilisateur a exécuté l'action demandée", - "task_alt", - "#4CAF50", - true, - false), - - // === STATUTS DE GESTION === - SUPPRIMEE( - "Supprimée", - "deleted", - "La notification a été supprimée par l'utilisateur", - "delete", - "#F44336", - false, - false), - - ARCHIVEE( - "Archivée", "archived", "La notification a été archivée", "archive", "#9E9E9E", false, false), - - EXPIREE( - "Expirée", - "expired", - "La notification a dépassé sa durée de vie", - "schedule", - "#9E9E9E", - false, - false), - - ANNULEE( - "Annulée", - "cancelled", - "L'envoi de la notification a été annulé", - "cancel", - "#F44336", - false, - true), - - // === STATUTS D'ERREUR === - ERREUR_TECHNIQUE( - "Erreur technique", - "error", - "Une erreur technique a empêché le traitement", - "bug_report", - "#F44336", - false, - true), - - DESTINATAIRE_INVALIDE( - "Destinataire invalide", - "invalid_recipient", - "Le destinataire n'est pas valide", - "person_off", - "#F44336", - false, - true), - - TOKEN_INVALIDE( - "Token invalide", - "invalid_token", - "Le token FCM du destinataire est invalide", - "key_off", - "#F44336", - false, - true), - - QUOTA_DEPASSE( - "Quota dépassé", - "quota_exceeded", - "Le quota d'envoi a été dépassé", - "block", - "#F44336", - false, - true); - - private final String libelle; - private final String code; - private final String description; - private final String icone; - private final String couleur; - private final boolean visibleUtilisateur; - private final boolean necessiteAttention; - - /** - * Constructeur de l'énumération StatutNotification - * - * @param libelle Le libellé affiché à l'utilisateur - * @param code Le code technique du statut - * @param description La description détaillée du statut - * @param icone L'icône Material Design - * @param couleur La couleur hexadécimale - * @param visibleUtilisateur true si visible à l'utilisateur final - * @param necessiteAttention true si le statut nécessite une attention particulière - */ - StatutNotification( - String libelle, - String code, - String description, - String icone, - String couleur, - boolean visibleUtilisateur, - boolean necessiteAttention) { - this.libelle = libelle; - this.code = code; - this.description = description; - this.icone = icone; - this.couleur = couleur; - this.visibleUtilisateur = visibleUtilisateur; - this.necessiteAttention = necessiteAttention; - } - - /** - * Retourne le libellé du statut - * - * @return Le libellé affiché à l'utilisateur - */ - public String getLibelle() { - return libelle; - } - - /** - * Retourne le code technique du statut - * - * @return Le code technique - */ - public String getCode() { - return code; - } - - /** - * Retourne la description du statut - * - * @return La description détaillée - */ - public String getDescription() { - return description; - } - - /** - * Retourne l'icône du statut - * - * @return L'icône Material Design - */ - public String getIcone() { - return icone; - } - - /** - * Retourne la couleur du statut - * - * @return Le code couleur hexadécimal - */ - public String getCouleur() { - return couleur; - } - - /** - * Vérifie si le statut est visible à l'utilisateur final - * - * @return true si visible à l'utilisateur - */ - public boolean isVisibleUtilisateur() { - return visibleUtilisateur; - } - - /** - * Vérifie si le statut nécessite une attention particulière - * - * @return true si le statut nécessite attention - */ - public boolean isNecessiteAttention() { - return necessiteAttention; - } - - /** - * Vérifie si le statut indique un succès - * - * @return true si le statut indique un succès - */ - public boolean isSucces() { - return this == ENVOYEE - || this == RECUE - || this == AFFICHEE - || this == OUVERTE - || this == LUE - || this == ACTION_EXECUTEE; - } - - /** - * Vérifie si le statut indique une erreur - * - * @return true si le statut indique une erreur - */ - public boolean isErreur() { - return this == ECHEC_ENVOI - || this == ERREUR_TECHNIQUE - || this == DESTINATAIRE_INVALIDE - || this == TOKEN_INVALIDE - || this == QUOTA_DEPASSE; - } - - /** - * Vérifie si le statut indique un état en cours - * - * @return true si le statut indique un traitement en cours - */ - public boolean isEnCours() { - return this == PROGRAMMEE || this == EN_ATTENTE || this == EN_COURS_ENVOI; - } - - /** - * Vérifie si le statut indique un état final - * - * @return true si le statut est final (pas de transition possible) - */ - public boolean isFinal() { - return this == SUPPRIMEE - || this == ARCHIVEE - || this == EXPIREE - || this == ANNULEE - || isErreur(); - } - - /** - * Vérifie si le statut permet la modification - * - * @return true si la notification peut encore être modifiée - */ - public boolean permetModification() { - return this == BROUILLON || this == PROGRAMMEE; - } - - /** - * Vérifie si le statut permet l'annulation - * - * @return true si la notification peut être annulée - */ - public boolean permetAnnulation() { - return this == PROGRAMMEE || this == EN_ATTENTE; - } - - /** - * Retourne la priorité d'affichage du statut - * - * @return La priorité (1=haute, 5=basse) - */ - public int getPrioriteAffichage() { - if (isErreur()) return 1; - if (necessiteAttention) return 2; - if (isEnCours()) return 3; - if (isSucces()) return 4; - return 5; - } - - /** - * Retourne les statuts suivants possibles - * - * @return Un tableau des statuts de transition possibles - */ - public StatutNotification[] getStatutsSuivantsPossibles() { - return switch (this) { - case BROUILLON -> new StatutNotification[] {PROGRAMMEE, EN_ATTENTE, ANNULEE}; - case PROGRAMMEE -> new StatutNotification[] {EN_ATTENTE, EN_COURS_ENVOI, ANNULEE}; - case EN_ATTENTE -> new StatutNotification[] {EN_COURS_ENVOI, ECHEC_ENVOI, ANNULEE}; - case EN_COURS_ENVOI -> new StatutNotification[] {ENVOYEE, PARTIELLEMENT_ENVOYEE, ECHEC_ENVOI}; - case ENVOYEE -> new StatutNotification[] {RECUE, ECHEC_ENVOI}; - case RECUE -> new StatutNotification[] {AFFICHEE, IGNOREE}; - case AFFICHEE -> new StatutNotification[] {OUVERTE, LUE, NON_LUE, IGNOREE}; - case OUVERTE -> new StatutNotification[] {LUE, ACTION_EXECUTEE, MARQUEE_IMPORTANTE}; - case NON_LUE -> new StatutNotification[] {LUE, OUVERTE, SUPPRIMEE, ARCHIVEE}; - case LUE -> - new StatutNotification[] {ACTION_EXECUTEE, MARQUEE_IMPORTANTE, SUPPRIMEE, ARCHIVEE}; - default -> new StatutNotification[] {}; - }; - } - - /** - * Trouve un statut par son code - * - * @param code Le code du statut - * @return Le statut correspondant ou null si non trouvé - */ - public static StatutNotification parCode(String code) { - for (StatutNotification statut : values()) { - if (statut.getCode().equals(code)) { - return statut; - } - } - return null; - } - - /** - * Retourne tous les statuts visibles à l'utilisateur - * - * @return Un tableau des statuts visibles - */ - public static StatutNotification[] getStatutsVisibles() { - return java.util.Arrays.stream(values()) - .filter(StatutNotification::isVisibleUtilisateur) - .toArray(StatutNotification[]::new); - } - - /** - * Retourne tous les statuts d'erreur - * - * @return Un tableau des statuts d'erreur - */ - public static StatutNotification[] getStatutsErreur() { - return java.util.Arrays.stream(values()) - .filter(StatutNotification::isErreur) - .toArray(StatutNotification[]::new); - } -} +package dev.lions.unionflow.server.api.enums.notification; + +/** + * Énumération des statuts de notification dans UnionFlow + * + *

Cette énumération définit les différents états qu'une notification peut avoir tout au long de + * son cycle de vie, de la création à l'archivage. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +public enum StatutNotification { + + // === STATUTS DE CRÉATION === + BROUILLON( + "Brouillon", + "draft", + "La notification est en cours de création", + "edit", + "#9E9E9E", + false, + false), + + PROGRAMMEE( + "Programmée", + "scheduled", + "La notification est programmée pour envoi ultérieur", + "schedule", + "#FF9800", + false, + false), + + EN_ATTENTE( + "En attente", + "pending", + "La notification est en attente d'envoi", + "hourglass_empty", + "#FF9800", + false, + false), + + // === STATUTS D'ENVOI === + EN_COURS_ENVOI( + "En cours d'envoi", + "sending", + "La notification est en cours d'envoi", + "send", + "#2196F3", + false, + false), + + ENVOYEE( + "Envoyée", + "sent", + "La notification a été envoyée avec succès", + "check_circle", + "#4CAF50", + true, + false), + + ECHEC_ENVOI( + "Échec d'envoi", + "failed", + "L'envoi de la notification a échoué", + "error", + "#F44336", + true, + true), + + PARTIELLEMENT_ENVOYEE( + "Partiellement envoyée", + "partial", + "La notification a été envoyée à certains destinataires seulement", + "warning", + "#FF9800", + true, + true), + + // === STATUTS DE RÉCEPTION === + RECUE( + "Reçue", + "received", + "La notification a été reçue par l'appareil", + "download_done", + "#4CAF50", + true, + false), + + AFFICHEE( + "Affichée", + "displayed", + "La notification a été affichée à l'utilisateur", + "visibility", + "#2196F3", + true, + false), + + OUVERTE( + "Ouverte", + "opened", + "L'utilisateur a ouvert la notification", + "open_in_new", + "#4CAF50", + true, + false), + + IGNOREE( + "Ignorée", + "ignored", + "La notification a été ignorée par l'utilisateur", + "visibility_off", + "#9E9E9E", + true, + false), + + // === STATUTS D'INTERACTION === + LUE( + "Lue", + "read", + "La notification a été lue par l'utilisateur", + "mark_email_read", + "#4CAF50", + true, + false), + + NON_LUE( + "Non lue", + "unread", + "La notification n'a pas encore été lue", + "mark_email_unread", + "#FF9800", + true, + false), + + MARQUEE_IMPORTANTE( + "Marquée importante", + "starred", + "L'utilisateur a marqué la notification comme importante", + "star", + "#FF9800", + true, + false), + + ACTION_EXECUTEE( + "Action exécutée", + "action_done", + "L'utilisateur a exécuté l'action demandée", + "task_alt", + "#4CAF50", + true, + false), + + // === STATUTS DE GESTION === + SUPPRIMEE( + "Supprimée", + "deleted", + "La notification a été supprimée par l'utilisateur", + "delete", + "#F44336", + false, + false), + + ARCHIVEE( + "Archivée", "archived", "La notification a été archivée", "archive", "#9E9E9E", false, false), + + EXPIREE( + "Expirée", + "expired", + "La notification a dépassé sa durée de vie", + "schedule", + "#9E9E9E", + false, + false), + + ANNULEE( + "Annulée", + "cancelled", + "L'envoi de la notification a été annulé", + "cancel", + "#F44336", + false, + true), + + // === STATUTS D'ERREUR === + ERREUR_TECHNIQUE( + "Erreur technique", + "error", + "Une erreur technique a empêché le traitement", + "bug_report", + "#F44336", + false, + true), + + DESTINATAIRE_INVALIDE( + "Destinataire invalide", + "invalid_recipient", + "Le destinataire n'est pas valide", + "person_off", + "#F44336", + false, + true), + + TOKEN_INVALIDE( + "Token invalide", + "invalid_token", + "Le token FCM du destinataire est invalide", + "key_off", + "#F44336", + false, + true), + + QUOTA_DEPASSE( + "Quota dépassé", + "quota_exceeded", + "Le quota d'envoi a été dépassé", + "block", + "#F44336", + false, + true); + + private final String libelle; + private final String code; + private final String description; + private final String icone; + private final String couleur; + private final boolean visibleUtilisateur; + private final boolean necessiteAttention; + + /** + * Constructeur de l'énumération StatutNotification + * + * @param libelle Le libellé affiché à l'utilisateur + * @param code Le code technique du statut + * @param description La description détaillée du statut + * @param icone L'icône Material Design + * @param couleur La couleur hexadécimale + * @param visibleUtilisateur true si visible à l'utilisateur final + * @param necessiteAttention true si le statut nécessite une attention particulière + */ + StatutNotification( + String libelle, + String code, + String description, + String icone, + String couleur, + boolean visibleUtilisateur, + boolean necessiteAttention) { + this.libelle = libelle; + this.code = code; + this.description = description; + this.icone = icone; + this.couleur = couleur; + this.visibleUtilisateur = visibleUtilisateur; + this.necessiteAttention = necessiteAttention; + } + + /** + * Retourne le libellé du statut + * + * @return Le libellé affiché à l'utilisateur + */ + public String getLibelle() { + return libelle; + } + + /** + * Retourne le code technique du statut + * + * @return Le code technique + */ + public String getCode() { + return code; + } + + /** + * Retourne la description du statut + * + * @return La description détaillée + */ + public String getDescription() { + return description; + } + + /** + * Retourne l'icône du statut + * + * @return L'icône Material Design + */ + public String getIcone() { + return icone; + } + + /** + * Retourne la couleur du statut + * + * @return Le code couleur hexadécimal + */ + public String getCouleur() { + return couleur; + } + + /** + * Vérifie si le statut est visible à l'utilisateur final + * + * @return true si visible à l'utilisateur + */ + public boolean isVisibleUtilisateur() { + return visibleUtilisateur; + } + + /** + * Vérifie si le statut nécessite une attention particulière + * + * @return true si le statut nécessite attention + */ + public boolean isNecessiteAttention() { + return necessiteAttention; + } + + /** + * Vérifie si le statut indique un succès + * + * @return true si le statut indique un succès + */ + public boolean isSucces() { + return this == ENVOYEE + || this == RECUE + || this == AFFICHEE + || this == OUVERTE + || this == LUE + || this == ACTION_EXECUTEE; + } + + /** + * Vérifie si le statut indique une erreur + * + * @return true si le statut indique une erreur + */ + public boolean isErreur() { + return this == ECHEC_ENVOI + || this == ERREUR_TECHNIQUE + || this == DESTINATAIRE_INVALIDE + || this == TOKEN_INVALIDE + || this == QUOTA_DEPASSE; + } + + /** + * Vérifie si le statut indique un état en cours + * + * @return true si le statut indique un traitement en cours + */ + public boolean isEnCours() { + return this == PROGRAMMEE || this == EN_ATTENTE || this == EN_COURS_ENVOI; + } + + /** + * Vérifie si le statut indique un état final + * + * @return true si le statut est final (pas de transition possible) + */ + public boolean isFinal() { + return this == SUPPRIMEE + || this == ARCHIVEE + || this == EXPIREE + || this == ANNULEE + || isErreur(); + } + + /** + * Vérifie si le statut permet la modification + * + * @return true si la notification peut encore être modifiée + */ + public boolean permetModification() { + return this == BROUILLON || this == PROGRAMMEE; + } + + /** + * Vérifie si le statut permet l'annulation + * + * @return true si la notification peut être annulée + */ + public boolean permetAnnulation() { + return this == PROGRAMMEE || this == EN_ATTENTE; + } + + /** + * Retourne la priorité d'affichage du statut + * + * @return La priorité (1=haute, 5=basse) + */ + public int getPrioriteAffichage() { + if (isErreur()) return 1; + if (necessiteAttention) return 2; + if (isEnCours()) return 3; + if (isSucces()) return 4; + return 5; + } + + /** + * Retourne les statuts suivants possibles + * + * @return Un tableau des statuts de transition possibles + */ + public StatutNotification[] getStatutsSuivantsPossibles() { + return switch (this) { + case BROUILLON -> new StatutNotification[] {PROGRAMMEE, EN_ATTENTE, ANNULEE}; + case PROGRAMMEE -> new StatutNotification[] {EN_ATTENTE, EN_COURS_ENVOI, ANNULEE}; + case EN_ATTENTE -> new StatutNotification[] {EN_COURS_ENVOI, ECHEC_ENVOI, ANNULEE}; + case EN_COURS_ENVOI -> new StatutNotification[] {ENVOYEE, PARTIELLEMENT_ENVOYEE, ECHEC_ENVOI}; + case ENVOYEE -> new StatutNotification[] {RECUE, ECHEC_ENVOI}; + case RECUE -> new StatutNotification[] {AFFICHEE, IGNOREE}; + case AFFICHEE -> new StatutNotification[] {OUVERTE, LUE, NON_LUE, IGNOREE}; + case OUVERTE -> new StatutNotification[] {LUE, ACTION_EXECUTEE, MARQUEE_IMPORTANTE}; + case NON_LUE -> new StatutNotification[] {LUE, OUVERTE, SUPPRIMEE, ARCHIVEE}; + case LUE -> + new StatutNotification[] {ACTION_EXECUTEE, MARQUEE_IMPORTANTE, SUPPRIMEE, ARCHIVEE}; + default -> new StatutNotification[] {}; + }; + } + + /** + * Trouve un statut par son code + * + * @param code Le code du statut + * @return Le statut correspondant ou null si non trouvé + */ + public static StatutNotification parCode(String code) { + for (StatutNotification statut : values()) { + if (statut.getCode().equals(code)) { + return statut; + } + } + return null; + } + + /** + * Retourne tous les statuts visibles à l'utilisateur + * + * @return Un tableau des statuts visibles + */ + public static StatutNotification[] getStatutsVisibles() { + return java.util.Arrays.stream(values()) + .filter(StatutNotification::isVisibleUtilisateur) + .toArray(StatutNotification[]::new); + } + + /** + * Retourne tous les statuts d'erreur + * + * @return Un tableau des statuts d'erreur + */ + public static StatutNotification[] getStatutsErreur() { + return java.util.Arrays.stream(values()) + .filter(StatutNotification::isErreur) + .toArray(StatutNotification[]::new); + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/notification/TypeNotification.java b/src/main/java/dev/lions/unionflow/server/api/enums/notification/TypeNotification.java index 71429ab..4fdd4d2 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/notification/TypeNotification.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/notification/TypeNotification.java @@ -1,32 +1,32 @@ -package dev.lions.unionflow.server.api.enums.notification; - -/** - * Énumération des types de notifications - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -public enum TypeNotification { - EMAIL("Email"), - SMS("SMS"), - PUSH("Push Notification"), - IN_APP("Notification In-App"), - SYSTEME("Notification Système"); - - private final String libelle; - - TypeNotification(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } - - /** Vérifie si ce type de notification est activé par défaut */ - public boolean isActiveeParDefaut() { - // Par défaut, tous les types sont activés sauf SYSTEME - return this != SYSTEME; - } -} +package dev.lions.unionflow.server.api.enums.notification; + +/** + * Énumération des types de notifications + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +public enum TypeNotification { + EMAIL("Email"), + SMS("SMS"), + PUSH("Push Notification"), + IN_APP("Notification In-App"), + SYSTEME("Notification Système"); + + private final String libelle; + + TypeNotification(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } + + /** Vérifie si ce type de notification est activé par défaut */ + public boolean isActiveeParDefaut() { + // Par défaut, tous les types sont activés sauf SYSTEME + return this != SYSTEME; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/ong/StatutProjetOng.java b/src/main/java/dev/lions/unionflow/server/api/enums/ong/StatutProjetOng.java index 419322b..ee22702 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/ong/StatutProjetOng.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/ong/StatutProjetOng.java @@ -1,19 +1,19 @@ -package dev.lions.unionflow.server.api.enums.ong; - -public enum StatutProjetOng { - EN_ETUDE("Étude de faisabilité / Évaluation"), - FINANCEMENT("En recherche de financements"), - EN_COURS("Déploiement opérationnel sur le terrain"), - EVALUE("Opérations terminées, en cours d'évaluation"), - CLOTURE("Projet définitivement clôturé"); - - private final String libelle; - - StatutProjetOng(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.ong; + +public enum StatutProjetOng { + EN_ETUDE("Étude de faisabilité / Évaluation"), + FINANCEMENT("En recherche de financements"), + EN_COURS("Déploiement opérationnel sur le terrain"), + EVALUE("Opérations terminées, en cours d'évaluation"), + CLOTURE("Projet définitivement clôturé"); + + private final String libelle; + + StatutProjetOng(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/organisation/StatutOrganisation.java b/src/main/java/dev/lions/unionflow/server/api/enums/organisation/StatutOrganisation.java index 74aa9dd..8aa2dca 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/organisation/StatutOrganisation.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/organisation/StatutOrganisation.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.enums.organisation; - -/** - * Énumération des statuts d'organisations dans UnionFlow - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -public enum StatutOrganisation { - ACTIVE("Active"), - INACTIVE("Inactive"), - SUSPENDUE("Suspendue"), - EN_CREATION("En Création"), - DISSOUTE("Dissoute"); - - private final String libelle; - - StatutOrganisation(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.organisation; + +/** + * Énumération des statuts d'organisations dans UnionFlow + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +public enum StatutOrganisation { + ACTIVE("Active"), + INACTIVE("Inactive"), + SUSPENDUE("Suspendue"), + EN_CREATION("En Création"), + DISSOUTE("Dissoute"); + + private final String libelle; + + StatutOrganisation(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/MethodePaiement.java b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/MethodePaiement.java index 6661358..4322909 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/MethodePaiement.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/MethodePaiement.java @@ -1,39 +1,39 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -/** - * Énumération des méthodes de paiement dans UnionFlow - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -public enum MethodePaiement { - WAVE_MOBILE_MONEY("Wave Mobile Money"), - ORANGE_MONEY("Orange Money"), - MTN_MOBILE_MONEY("MTN Mobile Money"), - MOOV_MONEY("Moov Money"), - VIREMENT_BANCAIRE("Virement Bancaire"), - CARTE_BANCAIRE("Carte Bancaire"), - ESPECES("Espèces"), - CHEQUE("Chèque"), - AUTRE("Autre"); - - private final String libelle; - - MethodePaiement(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } - - /** Vérifie si c'est une méthode de mobile money */ - public boolean isMobileMoney() { - return this == WAVE_MOBILE_MONEY - || this == ORANGE_MONEY - || this == MTN_MOBILE_MONEY - || this == MOOV_MONEY; - } -} - +package dev.lions.unionflow.server.api.enums.paiement; + +/** + * Énumération des méthodes de paiement dans UnionFlow + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +public enum MethodePaiement { + WAVE_MOBILE_MONEY("Wave Mobile Money"), + ORANGE_MONEY("Orange Money"), + MTN_MOBILE_MONEY("MTN Mobile Money"), + MOOV_MONEY("Moov Money"), + VIREMENT_BANCAIRE("Virement Bancaire"), + CARTE_BANCAIRE("Carte Bancaire"), + ESPECES("Espèces"), + CHEQUE("Chèque"), + AUTRE("Autre"); + + private final String libelle; + + MethodePaiement(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } + + /** Vérifie si c'est une méthode de mobile money */ + public boolean isMobileMoney() { + return this == WAVE_MOBILE_MONEY + || this == ORANGE_MONEY + || this == MTN_MOBILE_MONEY + || this == MOOV_MONEY; + } +} + diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutIntentionPaiement.java b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutIntentionPaiement.java index d4c761e..70e45a3 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutIntentionPaiement.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutIntentionPaiement.java @@ -1,15 +1,15 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -public enum StatutIntentionPaiement { - INITIEE("Initiée — en attente d'appel Wave"), - EN_COURS("En cours — membre en train de confirmer dans Wave"), - COMPLETEE("Complétée — webhook Wave reçu et validé"), - EXPIREE("Expirée — TTL 30 min dépassé"), - ECHOUEE("Échouée — erreur Wave ou annulation"); - - private final String libelle; - - StatutIntentionPaiement(String libelle) { this.libelle = libelle; } - - public String getLibelle() { return libelle; } -} +package dev.lions.unionflow.server.api.enums.paiement; + +public enum StatutIntentionPaiement { + INITIEE("Initiée — en attente d'appel Wave"), + EN_COURS("En cours — membre en train de confirmer dans Wave"), + COMPLETEE("Complétée — webhook Wave reçu et validé"), + EXPIREE("Expirée — TTL 30 min dépassé"), + ECHOUEE("Échouée — erreur Wave ou annulation"); + + private final String libelle; + + StatutIntentionPaiement(String libelle) { this.libelle = libelle; } + + public String getLibelle() { return libelle; } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutPaiement.java b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutPaiement.java index 7522a5b..a2b8076 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutPaiement.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutPaiement.java @@ -1,38 +1,38 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -/** - * Énumération des statuts de paiement dans UnionFlow - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -public enum StatutPaiement { - EN_ATTENTE("En Attente"), - EN_COURS("En Cours"), - VALIDE("Validé"), - ECHOUE("Échoué"), - ANNULE("Annulé"), - REMBOURSE("Remboursé"); - - private final String libelle; - - StatutPaiement(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } - - /** Vérifie si le paiement est finalisé (ne peut plus changer) */ - public boolean isFinalise() { - return this == VALIDE || this == ECHOUE || this == ANNULE || this == REMBOURSE; - } - - /** Vérifie si le paiement est en cours de traitement */ - public boolean isEnTraitement() { - return this == EN_ATTENTE || this == EN_COURS; - } -} - +package dev.lions.unionflow.server.api.enums.paiement; + +/** + * Énumération des statuts de paiement dans UnionFlow + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +public enum StatutPaiement { + EN_ATTENTE("En Attente"), + EN_COURS("En Cours"), + VALIDE("Validé"), + ECHOUE("Échoué"), + ANNULE("Annulé"), + REMBOURSE("Remboursé"); + + private final String libelle; + + StatutPaiement(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } + + /** Vérifie si le paiement est finalisé (ne peut plus changer) */ + public boolean isFinalise() { + return this == VALIDE || this == ECHOUE || this == ANNULE || this == REMBOURSE; + } + + /** Vérifie si le paiement est en cours de traitement */ + public boolean isEnTraitement() { + return this == EN_ATTENTE || this == EN_COURS; + } +} + diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutSession.java b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutSession.java index 9c14092..2ce352e 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutSession.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutSession.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -/** - * Énumération des statuts de sessions de paiement Wave Money - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -public enum StatutSession { - PENDING("En attente"), - COMPLETED("Complétée"), - CANCELLED("Annulée"), - EXPIRED("Expirée"), - FAILED("Échouée"); - - private final String libelle; - - StatutSession(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.paiement; + +/** + * Énumération des statuts de sessions de paiement Wave Money + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +public enum StatutSession { + PENDING("En attente"), + COMPLETED("Complétée"), + CANCELLED("Annulée"), + EXPIRED("Expirée"), + FAILED("Échouée"); + + private final String libelle; + + StatutSession(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutTraitement.java b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutTraitement.java index 6f6fd1a..26b6a98 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutTraitement.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/StatutTraitement.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -/** - * Énumération des statuts de traitement des webhooks Wave Money - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -public enum StatutTraitement { - RECU("Reçu"), - EN_COURS("En cours de traitement"), - TRAITE("Traité avec succès"), - ECHEC("Échec de traitement"), - IGNORE("Ignoré"); - - private final String libelle; - - StatutTraitement(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.paiement; + +/** + * Énumération des statuts de traitement des webhooks Wave Money + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +public enum StatutTraitement { + RECU("Reçu"), + EN_COURS("En cours de traitement"), + TRAITE("Traité avec succès"), + ECHEC("Échec de traitement"), + IGNORE("Ignoré"); + + private final String libelle; + + StatutTraitement(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/TypeEvenement.java b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/TypeEvenement.java index 6baaa1d..6bb6d29 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/TypeEvenement.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/TypeEvenement.java @@ -1,44 +1,44 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -/** - * Énumération des types d'événements Wave Money pour les webhooks - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -public enum TypeEvenement { - CHECKOUT_COMPLETE("checkout.complete"), - CHECKOUT_CANCELLED("checkout.cancelled"), - CHECKOUT_EXPIRED("checkout.expired"), - PAYOUT_COMPLETE("payout.complete"), - PAYOUT_FAILED("payout.failed"), - BALANCE_UPDATED("balance.updated"), - TRANSACTION_CREATED("transaction.created"), - TRANSACTION_UPDATED("transaction.updated"); - - private final String codeWave; - - TypeEvenement(String codeWave) { - this.codeWave = codeWave; - } - - public String getCodeWave() { - return codeWave; - } - - /** - * Trouve un type d'événement par son code Wave - * - * @param code Le code Wave - * @return Le type d'événement correspondant ou null si non trouvé - */ - public static TypeEvenement fromCode(String code) { - for (TypeEvenement type : values()) { - if (type.codeWave.equals(code)) { - return type; - } - } - return null; - } -} +package dev.lions.unionflow.server.api.enums.paiement; + +/** + * Énumération des types d'événements Wave Money pour les webhooks + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +public enum TypeEvenement { + CHECKOUT_COMPLETE("checkout.complete"), + CHECKOUT_CANCELLED("checkout.cancelled"), + CHECKOUT_EXPIRED("checkout.expired"), + PAYOUT_COMPLETE("payout.complete"), + PAYOUT_FAILED("payout.failed"), + BALANCE_UPDATED("balance.updated"), + TRANSACTION_CREATED("transaction.created"), + TRANSACTION_UPDATED("transaction.updated"); + + private final String codeWave; + + TypeEvenement(String codeWave) { + this.codeWave = codeWave; + } + + public String getCodeWave() { + return codeWave; + } + + /** + * Trouve un type d'événement par son code Wave + * + * @param code Le code Wave + * @return Le type d'événement correspondant ou null si non trouvé + */ + public static TypeEvenement fromCode(String code) { + for (TypeEvenement type : values()) { + if (type.codeWave.equals(code)) { + return type; + } + } + return null; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/TypeObjetIntentionPaiement.java b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/TypeObjetIntentionPaiement.java index f77a8a8..0c72b89 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/paiement/TypeObjetIntentionPaiement.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/paiement/TypeObjetIntentionPaiement.java @@ -1,17 +1,17 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -public enum TypeObjetIntentionPaiement { - COTISATION("Cotisation membre"), - ADHESION("Frais d'adhésion"), - EVENEMENT("Participation événement"), - ABONNEMENT_UNIONFLOW("Abonnement forfait UnionFlow"), - DEPOT_EPARGNE("Dépôt compte épargne"), - RETRAIT_EPARGNE("Retrait compte épargne"), - CREDIT_REMBOURSEMENT("Remboursement crédit"); - - private final String libelle; - - TypeObjetIntentionPaiement(String libelle) { this.libelle = libelle; } - - public String getLibelle() { return libelle; } -} +package dev.lions.unionflow.server.api.enums.paiement; + +public enum TypeObjetIntentionPaiement { + COTISATION("Cotisation membre"), + ADHESION("Frais d'adhésion"), + EVENEMENT("Participation événement"), + ABONNEMENT_UNIONFLOW("Abonnement forfait UnionFlow"), + DEPOT_EPARGNE("Dépôt compte épargne"), + RETRAIT_EPARGNE("Retrait compte épargne"), + CREDIT_REMBOURSEMENT("Remboursement crédit"); + + private final String libelle; + + TypeObjetIntentionPaiement(String libelle) { this.libelle = libelle; } + + public String getLibelle() { return libelle; } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/registre/StatutAgrement.java b/src/main/java/dev/lions/unionflow/server/api/enums/registre/StatutAgrement.java index d86b185..79a7010 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/registre/StatutAgrement.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/registre/StatutAgrement.java @@ -1,18 +1,18 @@ -package dev.lions.unionflow.server.api.enums.registre; - -public enum StatutAgrement { - PROVISOIRE("Agréé provisoirement sous condition"), - VALIDE("Agréé - Dossier complet et vérifié"), - SUSPENDU("Agrément temporairement suspendu"), - RETRETIRE("Agrément définitivement radié"); - - private final String libelle; - - StatutAgrement(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.registre; + +public enum StatutAgrement { + PROVISOIRE("Agréé provisoirement sous condition"), + VALIDE("Agréé - Dossier complet et vérifié"), + SUSPENDU("Agrément temporairement suspendu"), + RETRETIRE("Agrément définitivement radié"); + + private final String libelle; + + StatutAgrement(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/PrioriteAide.java b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/PrioriteAide.java index 431caf4..1e739d0 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/PrioriteAide.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/PrioriteAide.java @@ -1,268 +1,268 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -/** - * Énumération des priorités d'aide dans le système de solidarité - * - *

Cette énumération définit les niveaux de priorité pour les demandes d'aide, permettant de - * prioriser le traitement selon l'urgence de la situation. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -public enum PrioriteAide { - CRITIQUE( - "Critique", - "critical", - 1, - "Situation critique nécessitant une intervention immédiate", - "#F44336", - "emergency", - 24, - true, - true), - - URGENTE( - "Urgente", - "urgent", - 2, - "Situation urgente nécessitant une réponse rapide", - "#FF5722", - "priority_high", - 72, - true, - false), - - ELEVEE( - "Élevée", - "high", - 3, - "Priorité élevée, traitement dans les meilleurs délais", - "#FF9800", - "keyboard_arrow_up", - 168, - false, - false), - - NORMALE( - "Normale", - "normal", - 4, - "Priorité normale, traitement selon les délais standards", - "#2196F3", - "remove", - 336, - false, - false), - - FAIBLE( - "Faible", - "low", - 5, - "Priorité faible, traitement quand les ressources le permettent", - "#4CAF50", - "keyboard_arrow_down", - 720, - false, - false); - - private final String libelle; - private final String code; - private final int niveau; - private final String description; - private final String couleur; - private final String icone; - private final int delaiTraitementHeures; - private final boolean notificationImmediate; - private final boolean escaladeAutomatique; - - PrioriteAide( - String libelle, - String code, - int niveau, - String description, - String couleur, - String icone, - int delaiTraitementHeures, - boolean notificationImmediate, - boolean escaladeAutomatique) { - this.libelle = libelle; - this.code = code; - this.niveau = niveau; - this.description = description; - this.couleur = couleur; - this.icone = icone; - this.delaiTraitementHeures = delaiTraitementHeures; - this.notificationImmediate = notificationImmediate; - this.escaladeAutomatique = escaladeAutomatique; - } - - // === GETTERS === - - public String getLibelle() { - return libelle; - } - - public String getCode() { - return code; - } - - public int getNiveau() { - return niveau; - } - - public String getDescription() { - return description; - } - - public String getCouleur() { - return couleur; - } - - public String getIcone() { - return icone; - } - - public int getDelaiTraitementHeures() { - return delaiTraitementHeures; - } - - public boolean isNotificationImmediate() { - return notificationImmediate; - } - - public boolean isEscaladeAutomatique() { - return escaladeAutomatique; - } - - // === MÉTHODES UTILITAIRES === - - /** Vérifie si la priorité est critique ou urgente */ - public boolean isUrgente() { - return this == CRITIQUE || this == URGENTE; - } - - /** Vérifie si la priorité nécessite un traitement immédiat */ - public boolean necessiteTraitementImmediat() { - return niveau <= 2; - } - - /** Retourne la date limite de traitement */ - public java.time.LocalDateTime getDateLimiteTraitement() { - return java.time.LocalDateTime.now().plusHours(delaiTraitementHeures); - } - - /** Retourne la priorité suivante (escalade) */ - public PrioriteAide getPrioriteEscalade() { - return switch (this) { - case FAIBLE -> NORMALE; - case NORMALE -> ELEVEE; - case ELEVEE -> URGENTE; - case URGENTE -> CRITIQUE; - case CRITIQUE -> CRITIQUE; // Déjà au maximum - }; - } - - /** Détermine la priorité basée sur le type d'aide */ - public static PrioriteAide determinerPriorite(TypeAide typeAide) { - if (typeAide.isUrgent()) { - return switch (typeAide) { - case AIDE_FINANCIERE_URGENTE, AIDE_FRAIS_MEDICAUX -> CRITIQUE; - case HEBERGEMENT_URGENCE, AIDE_ALIMENTAIRE -> URGENTE; - default -> ELEVEE; - }; - } - - if (typeAide.getPriorite().equals("important")) { - return ELEVEE; - } - - return NORMALE; - } - - /** Retourne les priorités urgentes */ - public static java.util.List getPrioritesUrgentes() { - return java.util.Arrays.stream(values()) - .filter(PrioriteAide::isUrgente) - .collect(java.util.stream.Collectors.toList()); - } - - /** Retourne les priorités par niveau croissant */ - public static java.util.List getParNiveauCroissant() { - return java.util.Arrays.stream(values()) - .sorted(java.util.Comparator.comparingInt(PrioriteAide::getNiveau)) - .collect(java.util.stream.Collectors.toList()); - } - - /** Retourne les priorités par niveau décroissant */ - public static java.util.List getParNiveauDecroissant() { - return java.util.Arrays.stream(values()) - .sorted(java.util.Comparator.comparingInt(PrioriteAide::getNiveau).reversed()) - .collect(java.util.stream.Collectors.toList()); - } - - /** Trouve la priorité par code */ - public static PrioriteAide parCode(String code) { - return java.util.Arrays.stream(values()) - .filter(p -> p.getCode().equals(code)) - .findFirst() - .orElse(NORMALE); - } - - /** Calcule le score de priorité (plus bas = plus prioritaire) */ - public double getScorePriorite() { - double score = niveau; - - // Bonus pour notification immédiate - if (notificationImmediate) score -= 0.5; - - // Bonus pour escalade automatique - if (escaladeAutomatique) score -= 0.3; - - // Malus pour délai long - if (delaiTraitementHeures > 168) score += 0.2; - - return score; - } - - /** Vérifie si le délai de traitement est dépassé */ - public boolean isDelaiDepasse(java.time.LocalDateTime dateCreation) { - return isDelaiDepasse(dateCreation, java.time.LocalDateTime.now()); - } - - /** Vérifie si le délai de traitement est dépassé (version avec date de référence) */ - public boolean isDelaiDepasse(java.time.LocalDateTime dateCreation, java.time.LocalDateTime maintenant) { - java.time.LocalDateTime dateLimite = dateCreation.plusHours(delaiTraitementHeures); - // Utilise isAfter strictement : le délai est dépassé seulement si on est APRÈS la limite - // Si on est exactement à la limite, le délai n'est pas encore dépassé - return maintenant.isAfter(dateLimite); - } - - /** Calcule le pourcentage de temps écoulé */ - public double getPourcentageTempsEcoule(java.time.LocalDateTime dateCreation) { - java.time.LocalDateTime maintenant = java.time.LocalDateTime.now(); - java.time.LocalDateTime dateLimite = dateCreation.plusHours(delaiTraitementHeures); - - long dureeTotal = java.time.Duration.between(dateCreation, dateLimite).toMinutes(); - long dureeEcoulee = java.time.Duration.between(dateCreation, maintenant).toMinutes(); - - if (dureeTotal <= 0) return 100.0; - - return Math.min(100.0, (dureeEcoulee * 100.0) / dureeTotal); - } - - /** Retourne le message d'alerte selon le temps écoulé */ - public String getMessageAlerte(java.time.LocalDateTime dateCreation) { - double pourcentage = getPourcentageTempsEcoule(dateCreation); - - if (pourcentage >= 100) { - return "Délai de traitement dépassé !"; - } else if (pourcentage >= 80) { - return "Délai de traitement bientôt dépassé"; - } else if (pourcentage >= 60) { - return "Plus de la moitié du délai écoulé"; - } - - return null; - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +/** + * Énumération des priorités d'aide dans le système de solidarité + * + *

Cette énumération définit les niveaux de priorité pour les demandes d'aide, permettant de + * prioriser le traitement selon l'urgence de la situation. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +public enum PrioriteAide { + CRITIQUE( + "Critique", + "critical", + 1, + "Situation critique nécessitant une intervention immédiate", + "#F44336", + "emergency", + 24, + true, + true), + + URGENTE( + "Urgente", + "urgent", + 2, + "Situation urgente nécessitant une réponse rapide", + "#FF5722", + "priority_high", + 72, + true, + false), + + ELEVEE( + "Élevée", + "high", + 3, + "Priorité élevée, traitement dans les meilleurs délais", + "#FF9800", + "keyboard_arrow_up", + 168, + false, + false), + + NORMALE( + "Normale", + "normal", + 4, + "Priorité normale, traitement selon les délais standards", + "#2196F3", + "remove", + 336, + false, + false), + + FAIBLE( + "Faible", + "low", + 5, + "Priorité faible, traitement quand les ressources le permettent", + "#4CAF50", + "keyboard_arrow_down", + 720, + false, + false); + + private final String libelle; + private final String code; + private final int niveau; + private final String description; + private final String couleur; + private final String icone; + private final int delaiTraitementHeures; + private final boolean notificationImmediate; + private final boolean escaladeAutomatique; + + PrioriteAide( + String libelle, + String code, + int niveau, + String description, + String couleur, + String icone, + int delaiTraitementHeures, + boolean notificationImmediate, + boolean escaladeAutomatique) { + this.libelle = libelle; + this.code = code; + this.niveau = niveau; + this.description = description; + this.couleur = couleur; + this.icone = icone; + this.delaiTraitementHeures = delaiTraitementHeures; + this.notificationImmediate = notificationImmediate; + this.escaladeAutomatique = escaladeAutomatique; + } + + // === GETTERS === + + public String getLibelle() { + return libelle; + } + + public String getCode() { + return code; + } + + public int getNiveau() { + return niveau; + } + + public String getDescription() { + return description; + } + + public String getCouleur() { + return couleur; + } + + public String getIcone() { + return icone; + } + + public int getDelaiTraitementHeures() { + return delaiTraitementHeures; + } + + public boolean isNotificationImmediate() { + return notificationImmediate; + } + + public boolean isEscaladeAutomatique() { + return escaladeAutomatique; + } + + // === MÉTHODES UTILITAIRES === + + /** Vérifie si la priorité est critique ou urgente */ + public boolean isUrgente() { + return this == CRITIQUE || this == URGENTE; + } + + /** Vérifie si la priorité nécessite un traitement immédiat */ + public boolean necessiteTraitementImmediat() { + return niveau <= 2; + } + + /** Retourne la date limite de traitement */ + public java.time.LocalDateTime getDateLimiteTraitement() { + return java.time.LocalDateTime.now().plusHours(delaiTraitementHeures); + } + + /** Retourne la priorité suivante (escalade) */ + public PrioriteAide getPrioriteEscalade() { + return switch (this) { + case FAIBLE -> NORMALE; + case NORMALE -> ELEVEE; + case ELEVEE -> URGENTE; + case URGENTE -> CRITIQUE; + case CRITIQUE -> CRITIQUE; // Déjà au maximum + }; + } + + /** Détermine la priorité basée sur le type d'aide */ + public static PrioriteAide determinerPriorite(TypeAide typeAide) { + if (typeAide.isUrgent()) { + return switch (typeAide) { + case AIDE_FINANCIERE_URGENTE, AIDE_FRAIS_MEDICAUX -> CRITIQUE; + case HEBERGEMENT_URGENCE, AIDE_ALIMENTAIRE -> URGENTE; + default -> ELEVEE; + }; + } + + if (typeAide.getPriorite().equals("important")) { + return ELEVEE; + } + + return NORMALE; + } + + /** Retourne les priorités urgentes */ + public static java.util.List getPrioritesUrgentes() { + return java.util.Arrays.stream(values()) + .filter(PrioriteAide::isUrgente) + .collect(java.util.stream.Collectors.toList()); + } + + /** Retourne les priorités par niveau croissant */ + public static java.util.List getParNiveauCroissant() { + return java.util.Arrays.stream(values()) + .sorted(java.util.Comparator.comparingInt(PrioriteAide::getNiveau)) + .collect(java.util.stream.Collectors.toList()); + } + + /** Retourne les priorités par niveau décroissant */ + public static java.util.List getParNiveauDecroissant() { + return java.util.Arrays.stream(values()) + .sorted(java.util.Comparator.comparingInt(PrioriteAide::getNiveau).reversed()) + .collect(java.util.stream.Collectors.toList()); + } + + /** Trouve la priorité par code */ + public static PrioriteAide parCode(String code) { + return java.util.Arrays.stream(values()) + .filter(p -> p.getCode().equals(code)) + .findFirst() + .orElse(NORMALE); + } + + /** Calcule le score de priorité (plus bas = plus prioritaire) */ + public double getScorePriorite() { + double score = niveau; + + // Bonus pour notification immédiate + if (notificationImmediate) score -= 0.5; + + // Bonus pour escalade automatique + if (escaladeAutomatique) score -= 0.3; + + // Malus pour délai long + if (delaiTraitementHeures > 168) score += 0.2; + + return score; + } + + /** Vérifie si le délai de traitement est dépassé */ + public boolean isDelaiDepasse(java.time.LocalDateTime dateCreation) { + return isDelaiDepasse(dateCreation, java.time.LocalDateTime.now()); + } + + /** Vérifie si le délai de traitement est dépassé (version avec date de référence) */ + public boolean isDelaiDepasse(java.time.LocalDateTime dateCreation, java.time.LocalDateTime maintenant) { + java.time.LocalDateTime dateLimite = dateCreation.plusHours(delaiTraitementHeures); + // Utilise isAfter strictement : le délai est dépassé seulement si on est APRÈS la limite + // Si on est exactement à la limite, le délai n'est pas encore dépassé + return maintenant.isAfter(dateLimite); + } + + /** Calcule le pourcentage de temps écoulé */ + public double getPourcentageTempsEcoule(java.time.LocalDateTime dateCreation) { + java.time.LocalDateTime maintenant = java.time.LocalDateTime.now(); + java.time.LocalDateTime dateLimite = dateCreation.plusHours(delaiTraitementHeures); + + long dureeTotal = java.time.Duration.between(dateCreation, dateLimite).toMinutes(); + long dureeEcoulee = java.time.Duration.between(dateCreation, maintenant).toMinutes(); + + if (dureeTotal <= 0) return 100.0; + + return Math.min(100.0, (dureeEcoulee * 100.0) / dureeTotal); + } + + /** Retourne le message d'alerte selon le temps écoulé */ + public String getMessageAlerte(java.time.LocalDateTime dateCreation) { + double pourcentage = getPourcentageTempsEcoule(dateCreation); + + if (pourcentage >= 100) { + return "Délai de traitement dépassé !"; + } else if (pourcentage >= 80) { + return "Délai de traitement bientôt dépassé"; + } else if (pourcentage >= 60) { + return "Plus de la moitié du délai écoulé"; + } + + return null; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutAide.java b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutAide.java index 1d9ae11..356eb12 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutAide.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutAide.java @@ -1,298 +1,298 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -/** - * Énumération des statuts d'aide dans le système de solidarité - * - *

Cette énumération définit les différents statuts qu'une demande d'aide peut avoir tout au long - * de son cycle de vie. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -public enum StatutAide { - - // === STATUTS INITIAUX === - BROUILLON( - "Brouillon", - "draft", - "La demande est en cours de rédaction", - "#9E9E9E", - "edit", - false, - false), - SOUMISE( - "Soumise", - "submitted", - "La demande a été soumise et attend validation", - "#FF9800", - "send", - false, - false), - - // === STATUTS D'ÉVALUATION === - EN_ATTENTE( - "En attente", - "pending", - "La demande est en attente d'évaluation", - "#2196F3", - "hourglass_empty", - false, - false), - EN_COURS_EVALUATION( - "En cours d'évaluation", - "under_review", - "La demande est en cours d'évaluation", - "#FF9800", - "rate_review", - false, - false), - INFORMATIONS_REQUISES( - "Informations requises", - "info_required", - "Des informations complémentaires sont requises", - "#FF5722", - "info", - false, - false), - - // === STATUTS DE DÉCISION === - APPROUVEE( - "Approuvée", - "approved", - "La demande a été approuvée", - "#4CAF50", - "check_circle", - true, - false), - APPROUVEE_PARTIELLEMENT( - "Approuvée partiellement", - "partially_approved", - "La demande a été approuvée partiellement", - "#8BC34A", - "check_circle_outline", - true, - false), - REJETEE("Rejetée", "rejected", "La demande a été rejetée", "#F44336", "cancel", true, true), - - // === STATUTS DE TRAITEMENT === - EN_COURS_TRAITEMENT( - "En cours de traitement", - "processing", - "La demande approuvée est en cours de traitement", - "#9C27B0", - "settings", - false, - false), - EN_COURS_VERSEMENT( - "En cours de versement", - "payment_processing", - "Le versement est en cours", - "#3F51B5", - "payment", - false, - false), - - // === STATUTS FINAUX === - VERSEE("Versée", "paid", "L'aide a été versée avec succès", "#4CAF50", "paid", true, false), - LIVREE( - "Livrée", - "delivered", - "L'aide matérielle a été livrée", - "#4CAF50", - "local_shipping", - true, - false), - TERMINEE( - "Terminée", - "completed", - "L'aide a été fournie avec succès", - "#4CAF50", - "done_all", - true, - false), - - // === STATUTS D'EXCEPTION === - ANNULEE("Annulée", "cancelled", "La demande a été annulée", "#9E9E9E", "cancel", true, true), - SUSPENDUE( - "Suspendue", - "suspended", - "La demande a été suspendue temporairement", - "#FF5722", - "pause_circle", - false, - false), - EXPIREE("Expirée", "expired", "La demande a expiré", "#795548", "schedule", true, true), - - // === STATUTS DE SUIVI === - EN_SUIVI( - "En suivi", - "follow_up", - "L'aide fait l'objet d'un suivi", - "#607D8B", - "track_changes", - false, - false), - CLOTUREE("Clôturée", "closed", "Le dossier d'aide est clôturé", "#9E9E9E", "folder", true, false); - - private final String libelle; - private final String code; - private final String description; - private final String couleur; - private final String icone; - private final boolean estFinal; - private final boolean estEchec; - - StatutAide( - String libelle, - String code, - String description, - String couleur, - String icone, - boolean estFinal, - boolean estEchec) { - this.libelle = libelle; - this.code = code; - this.description = description; - this.couleur = couleur; - this.icone = icone; - this.estFinal = estFinal; - this.estEchec = estEchec; - } - - // === GETTERS === - - public String getLibelle() { - return libelle; - } - - public String getCode() { - return code; - } - - public String getDescription() { - return description; - } - - public String getCouleur() { - return couleur; - } - - public String getIcone() { - return icone; - } - - public boolean isEstFinal() { - return estFinal; - } - - public boolean isEstEchec() { - return estEchec; - } - - // === MÉTHODES UTILITAIRES === - - /** Vérifie si le statut indique un succès */ - public boolean isSucces() { - return this == VERSEE || this == LIVREE || this == TERMINEE; - } - - /** Vérifie si le statut est en cours de traitement */ - public boolean isEnCours() { - return this == EN_COURS_EVALUATION || this == EN_COURS_TRAITEMENT || this == EN_COURS_VERSEMENT; - } - - /** Vérifie si le statut permet la modification */ - public boolean permetModification() { - return this == BROUILLON || this == INFORMATIONS_REQUISES; - } - - /** Vérifie si le statut permet l'annulation (les deux conditions sont évaluées pour couverture) */ - public boolean permetAnnulation() { - boolean nonFinal = !estFinal; - boolean pasAnnulee = (this != ANNULEE); - return nonFinal & pasAnnulee; - } - - /** Retourne les statuts finaux */ - public static java.util.List getStatutsFinaux() { - return java.util.Arrays.stream(values()) - .filter(StatutAide::isEstFinal) - .collect(java.util.stream.Collectors.toList()); - } - - /** Retourne les statuts d'échec */ - public static java.util.List getStatutsEchec() { - return java.util.Arrays.stream(values()) - .filter(StatutAide::isEstEchec) - .collect(java.util.stream.Collectors.toList()); - } - - /** Retourne les statuts de succès */ - public static java.util.List getStatutsSucces() { - return java.util.Arrays.stream(values()) - .filter(StatutAide::isSucces) - .collect(java.util.stream.Collectors.toList()); - } - - /** Retourne les statuts en cours */ - public static java.util.List getStatutsEnCours() { - return java.util.Arrays.stream(values()) - .filter(StatutAide::isEnCours) - .collect(java.util.stream.Collectors.toList()); - } - - /** Vérifie si la transition vers un autre statut est valide */ - public boolean peutTransitionnerVers(StatutAide nouveauStatut) { - // Règles de transition simplifiées - if (this == nouveauStatut) return false; - - // Les statuts finaux ne peuvent transitionner que vers EN_SUIVI - // Exception : APPROUVEE et APPROUVEE_PARTIELLEMENT peuvent transitionner vers EN_COURS_TRAITEMENT ou SUSPENDUE - // car ce sont des statuts de décision qui doivent permettre le démarrage du traitement - if (estFinal - && this != APPROUVEE - && this != APPROUVEE_PARTIELLEMENT - && nouveauStatut != EN_SUIVI) { - return false; - } - - return switch (this) { - case BROUILLON -> nouveauStatut == SOUMISE || nouveauStatut == ANNULEE; - case SOUMISE -> nouveauStatut == EN_ATTENTE || nouveauStatut == ANNULEE; - case EN_ATTENTE -> nouveauStatut == EN_COURS_EVALUATION || nouveauStatut == ANNULEE; - case EN_COURS_EVALUATION -> - nouveauStatut == APPROUVEE - || nouveauStatut == APPROUVEE_PARTIELLEMENT - || nouveauStatut == REJETEE - || nouveauStatut == INFORMATIONS_REQUISES - || nouveauStatut == SUSPENDUE; - case INFORMATIONS_REQUISES -> - nouveauStatut == EN_COURS_EVALUATION || nouveauStatut == ANNULEE; - case APPROUVEE, APPROUVEE_PARTIELLEMENT -> - nouveauStatut == EN_COURS_TRAITEMENT || nouveauStatut == SUSPENDUE; - case EN_COURS_TRAITEMENT -> - nouveauStatut == EN_COURS_VERSEMENT - || nouveauStatut == LIVREE - || nouveauStatut == TERMINEE - || nouveauStatut == SUSPENDUE; - case EN_COURS_VERSEMENT -> nouveauStatut == VERSEE || nouveauStatut == SUSPENDUE; - case SUSPENDUE -> nouveauStatut == EN_COURS_EVALUATION || nouveauStatut == ANNULEE; - default -> false; - }; - } - - /** Retourne le niveau de priorité pour l'affichage */ - public int getNiveauPriorite() { - return switch (this) { - case INFORMATIONS_REQUISES -> 1; - case EN_COURS_EVALUATION, EN_COURS_TRAITEMENT, EN_COURS_VERSEMENT -> 2; - case APPROUVEE, APPROUVEE_PARTIELLEMENT -> 3; - case EN_ATTENTE, SOUMISE -> 4; - case SUSPENDUE -> 5; - case BROUILLON -> 6; - case EN_SUIVI -> 7; - default -> 8; // Statuts finaux - }; - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +/** + * Énumération des statuts d'aide dans le système de solidarité + * + *

Cette énumération définit les différents statuts qu'une demande d'aide peut avoir tout au long + * de son cycle de vie. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +public enum StatutAide { + + // === STATUTS INITIAUX === + BROUILLON( + "Brouillon", + "draft", + "La demande est en cours de rédaction", + "#9E9E9E", + "edit", + false, + false), + SOUMISE( + "Soumise", + "submitted", + "La demande a été soumise et attend validation", + "#FF9800", + "send", + false, + false), + + // === STATUTS D'ÉVALUATION === + EN_ATTENTE( + "En attente", + "pending", + "La demande est en attente d'évaluation", + "#2196F3", + "hourglass_empty", + false, + false), + EN_COURS_EVALUATION( + "En cours d'évaluation", + "under_review", + "La demande est en cours d'évaluation", + "#FF9800", + "rate_review", + false, + false), + INFORMATIONS_REQUISES( + "Informations requises", + "info_required", + "Des informations complémentaires sont requises", + "#FF5722", + "info", + false, + false), + + // === STATUTS DE DÉCISION === + APPROUVEE( + "Approuvée", + "approved", + "La demande a été approuvée", + "#4CAF50", + "check_circle", + true, + false), + APPROUVEE_PARTIELLEMENT( + "Approuvée partiellement", + "partially_approved", + "La demande a été approuvée partiellement", + "#8BC34A", + "check_circle_outline", + true, + false), + REJETEE("Rejetée", "rejected", "La demande a été rejetée", "#F44336", "cancel", true, true), + + // === STATUTS DE TRAITEMENT === + EN_COURS_TRAITEMENT( + "En cours de traitement", + "processing", + "La demande approuvée est en cours de traitement", + "#9C27B0", + "settings", + false, + false), + EN_COURS_VERSEMENT( + "En cours de versement", + "payment_processing", + "Le versement est en cours", + "#3F51B5", + "payment", + false, + false), + + // === STATUTS FINAUX === + VERSEE("Versée", "paid", "L'aide a été versée avec succès", "#4CAF50", "paid", true, false), + LIVREE( + "Livrée", + "delivered", + "L'aide matérielle a été livrée", + "#4CAF50", + "local_shipping", + true, + false), + TERMINEE( + "Terminée", + "completed", + "L'aide a été fournie avec succès", + "#4CAF50", + "done_all", + true, + false), + + // === STATUTS D'EXCEPTION === + ANNULEE("Annulée", "cancelled", "La demande a été annulée", "#9E9E9E", "cancel", true, true), + SUSPENDUE( + "Suspendue", + "suspended", + "La demande a été suspendue temporairement", + "#FF5722", + "pause_circle", + false, + false), + EXPIREE("Expirée", "expired", "La demande a expiré", "#795548", "schedule", true, true), + + // === STATUTS DE SUIVI === + EN_SUIVI( + "En suivi", + "follow_up", + "L'aide fait l'objet d'un suivi", + "#607D8B", + "track_changes", + false, + false), + CLOTUREE("Clôturée", "closed", "Le dossier d'aide est clôturé", "#9E9E9E", "folder", true, false); + + private final String libelle; + private final String code; + private final String description; + private final String couleur; + private final String icone; + private final boolean estFinal; + private final boolean estEchec; + + StatutAide( + String libelle, + String code, + String description, + String couleur, + String icone, + boolean estFinal, + boolean estEchec) { + this.libelle = libelle; + this.code = code; + this.description = description; + this.couleur = couleur; + this.icone = icone; + this.estFinal = estFinal; + this.estEchec = estEchec; + } + + // === GETTERS === + + public String getLibelle() { + return libelle; + } + + public String getCode() { + return code; + } + + public String getDescription() { + return description; + } + + public String getCouleur() { + return couleur; + } + + public String getIcone() { + return icone; + } + + public boolean isEstFinal() { + return estFinal; + } + + public boolean isEstEchec() { + return estEchec; + } + + // === MÉTHODES UTILITAIRES === + + /** Vérifie si le statut indique un succès */ + public boolean isSucces() { + return this == VERSEE || this == LIVREE || this == TERMINEE; + } + + /** Vérifie si le statut est en cours de traitement */ + public boolean isEnCours() { + return this == EN_COURS_EVALUATION || this == EN_COURS_TRAITEMENT || this == EN_COURS_VERSEMENT; + } + + /** Vérifie si le statut permet la modification */ + public boolean permetModification() { + return this == BROUILLON || this == INFORMATIONS_REQUISES; + } + + /** Vérifie si le statut permet l'annulation (les deux conditions sont évaluées pour couverture) */ + public boolean permetAnnulation() { + boolean nonFinal = !estFinal; + boolean pasAnnulee = (this != ANNULEE); + return nonFinal & pasAnnulee; + } + + /** Retourne les statuts finaux */ + public static java.util.List getStatutsFinaux() { + return java.util.Arrays.stream(values()) + .filter(StatutAide::isEstFinal) + .collect(java.util.stream.Collectors.toList()); + } + + /** Retourne les statuts d'échec */ + public static java.util.List getStatutsEchec() { + return java.util.Arrays.stream(values()) + .filter(StatutAide::isEstEchec) + .collect(java.util.stream.Collectors.toList()); + } + + /** Retourne les statuts de succès */ + public static java.util.List getStatutsSucces() { + return java.util.Arrays.stream(values()) + .filter(StatutAide::isSucces) + .collect(java.util.stream.Collectors.toList()); + } + + /** Retourne les statuts en cours */ + public static java.util.List getStatutsEnCours() { + return java.util.Arrays.stream(values()) + .filter(StatutAide::isEnCours) + .collect(java.util.stream.Collectors.toList()); + } + + /** Vérifie si la transition vers un autre statut est valide */ + public boolean peutTransitionnerVers(StatutAide nouveauStatut) { + // Règles de transition simplifiées + if (this == nouveauStatut) return false; + + // Les statuts finaux ne peuvent transitionner que vers EN_SUIVI + // Exception : APPROUVEE et APPROUVEE_PARTIELLEMENT peuvent transitionner vers EN_COURS_TRAITEMENT ou SUSPENDUE + // car ce sont des statuts de décision qui doivent permettre le démarrage du traitement + if (estFinal + && this != APPROUVEE + && this != APPROUVEE_PARTIELLEMENT + && nouveauStatut != EN_SUIVI) { + return false; + } + + return switch (this) { + case BROUILLON -> nouveauStatut == SOUMISE || nouveauStatut == ANNULEE; + case SOUMISE -> nouveauStatut == EN_ATTENTE || nouveauStatut == ANNULEE; + case EN_ATTENTE -> nouveauStatut == EN_COURS_EVALUATION || nouveauStatut == ANNULEE; + case EN_COURS_EVALUATION -> + nouveauStatut == APPROUVEE + || nouveauStatut == APPROUVEE_PARTIELLEMENT + || nouveauStatut == REJETEE + || nouveauStatut == INFORMATIONS_REQUISES + || nouveauStatut == SUSPENDUE; + case INFORMATIONS_REQUISES -> + nouveauStatut == EN_COURS_EVALUATION || nouveauStatut == ANNULEE; + case APPROUVEE, APPROUVEE_PARTIELLEMENT -> + nouveauStatut == EN_COURS_TRAITEMENT || nouveauStatut == SUSPENDUE; + case EN_COURS_TRAITEMENT -> + nouveauStatut == EN_COURS_VERSEMENT + || nouveauStatut == LIVREE + || nouveauStatut == TERMINEE + || nouveauStatut == SUSPENDUE; + case EN_COURS_VERSEMENT -> nouveauStatut == VERSEE || nouveauStatut == SUSPENDUE; + case SUSPENDUE -> nouveauStatut == EN_COURS_EVALUATION || nouveauStatut == ANNULEE; + default -> false; + }; + } + + /** Retourne le niveau de priorité pour l'affichage */ + public int getNiveauPriorite() { + return switch (this) { + case INFORMATIONS_REQUISES -> 1; + case EN_COURS_EVALUATION, EN_COURS_TRAITEMENT, EN_COURS_VERSEMENT -> 2; + case APPROUVEE, APPROUVEE_PARTIELLEMENT -> 3; + case EN_ATTENTE, SOUMISE -> 4; + case SUSPENDUE -> 5; + case BROUILLON -> 6; + case EN_SUIVI -> 7; + default -> 8; // Statuts finaux + }; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutEvaluation.java b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutEvaluation.java index 2187061..e838ffd 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutEvaluation.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutEvaluation.java @@ -1,21 +1,21 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -import lombok.Getter; - -/** - * Énumération des statuts d'évaluation - */ -@Getter -public enum StatutEvaluation { - BROUILLON("Brouillon"), - ACTIVE("Active"), - MASQUEE("Masquée"), - SIGNALEE("Signalée"), - SUPPRIMEE("Supprimée"); - - private final String libelle; - - StatutEvaluation(String libelle) { - this.libelle = libelle; - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +import lombok.Getter; + +/** + * Énumération des statuts d'évaluation + */ +@Getter +public enum StatutEvaluation { + BROUILLON("Brouillon"), + ACTIVE("Active"), + MASQUEE("Masquée"), + SIGNALEE("Signalée"), + SUPPRIMEE("Supprimée"); + + private final String libelle; + + StatutEvaluation(String libelle) { + this.libelle = libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutProposition.java b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutProposition.java index 1ba97ef..8dbccca 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutProposition.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutProposition.java @@ -1,22 +1,22 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -import lombok.Getter; - -/** - * Énumération des statuts d'une proposition d'aide. - */ -@Getter -public enum StatutProposition { - BROUILLON("Brouillon"), - ACTIVE("Active"), - SUSPENDUE("Suspendue"), - EXPIREE("Expirée"), - TERMINEE("Terminée"), - ANNULEE("Annulée"); - - private final String libelle; - - StatutProposition(String libelle) { - this.libelle = libelle; - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +import lombok.Getter; + +/** + * Énumération des statuts d'une proposition d'aide. + */ +@Getter +public enum StatutProposition { + BROUILLON("Brouillon"), + ACTIVE("Active"), + SUSPENDUE("Suspendue"), + EXPIREE("Expirée"), + TERMINEE("Terminée"), + ANNULEE("Annulée"); + + private final String libelle; + + StatutProposition(String libelle) { + this.libelle = libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutValidationEtape.java b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutValidationEtape.java index 37dffc0..d4a8fbc 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutValidationEtape.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/StatutValidationEtape.java @@ -1,15 +1,15 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -public enum StatutValidationEtape { - EN_ATTENTE("En attente du valideur"), - APPROUVEE("Approuvée"), - REJETEE("Rejetée"), - DELEGUEE("Déléguée — véto désactivé par supérieur, tracé BCEAO/OHADA"), - EXPIREE("Expirée — délai SLA dépassé"); - - private final String libelle; - - StatutValidationEtape(String libelle) { this.libelle = libelle; } - - public String getLibelle() { return libelle; } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +public enum StatutValidationEtape { + EN_ATTENTE("En attente du valideur"), + APPROUVEE("Approuvée"), + REJETEE("Rejetée"), + DELEGUEE("Déléguée — véto désactivé par supérieur, tracé BCEAO/OHADA"), + EXPIREE("Expirée — délai SLA dépassé"); + + private final String libelle; + + StatutValidationEtape(String libelle) { this.libelle = libelle; } + + public String getLibelle() { return libelle; } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/TypeAide.java b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/TypeAide.java index d40bed1..4279af7 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/TypeAide.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/TypeAide.java @@ -1,515 +1,515 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -/** - * Énumération des types d'aide disponibles dans le système de solidarité - * - *

Cette énumération définit les différents types d'aide que les membres peuvent demander ou - * proposer dans le cadre du système de solidarité. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-16 - */ -public enum TypeAide { - - // === AIDE FINANCIÈRE === - AIDE_FINANCIERE_URGENTE( - "Aide financière urgente", - "financiere", - "urgent", - "Aide financière pour situation d'urgence", - "emergency_fund", - "#F44336", - true, - true, - 5000.0, - 50000.0, - 7), - - PRET_SANS_INTERET( - "Prêt sans intérêt", - "financiere", - "important", - "Prêt sans intérêt entre membres", - "account_balance", - "#FF9800", - true, - true, - 10000.0, - 100000.0, - 30), - - AIDE_COTISATION( - "Aide pour cotisation", - "financiere", - "normal", - "Aide pour payer les cotisations", - "payment", - "#2196F3", - true, - false, - 1000.0, - 10000.0, - 14), - - AIDE_FRAIS_MEDICAUX( - "Aide frais médicaux", - "financiere", - "urgent", - "Aide pour frais médicaux et hospitaliers", - "medical_services", - "#E91E63", - true, - true, - 5000.0, - 200000.0, - 7), - - AIDE_FRAIS_SCOLARITE( - "Aide frais de scolarité", - "financiere", - "important", - "Aide pour frais de scolarité des enfants", - "school", - "#9C27B0", - true, - true, - 10000.0, - 100000.0, - 21), - - // === AIDE MATÉRIELLE === - DON_MATERIEL( - "Don de matériel", - "materielle", - "normal", - "Don d'objets, équipements ou matériel", - "inventory", - "#4CAF50", - false, - false, - null, - null, - 14), - - PRET_MATERIEL( - "Prêt de matériel", - "materielle", - "normal", - "Prêt temporaire d'objets ou équipements", - "build", - "#607D8B", - false, - false, - null, - null, - 30), - - AIDE_DEMENAGEMENT( - "Aide déménagement", - "materielle", - "normal", - "Aide pour déménagement (transport, main d'œuvre)", - "local_shipping", - "#795548", - false, - false, - null, - null, - 7), - - AIDE_TRAVAUX( - "Aide travaux", - "materielle", - "normal", - "Aide pour travaux de rénovation ou construction", - "construction", - "#FF5722", - false, - false, - null, - null, - 21), - - // === AIDE PROFESSIONNELLE === - AIDE_RECHERCHE_EMPLOI( - "Aide recherche d'emploi", - "professionnelle", - "important", - "Aide pour recherche d'emploi et CV", - "work", - "#3F51B5", - false, - false, - null, - null, - 30), - - FORMATION_PROFESSIONNELLE( - "Formation professionnelle", - "professionnelle", - "normal", - "Formation et développement des compétences", - "school", - "#009688", - false, - false, - null, - null, - 60), - - CONSEIL_JURIDIQUE( - "Conseil juridique", - "professionnelle", - "important", - "Conseil et assistance juridique", - "gavel", - "#8BC34A", - false, - false, - null, - null, - 14), - - AIDE_CREATION_ENTREPRISE( - "Aide création d'entreprise", - "professionnelle", - "normal", - "Accompagnement création d'entreprise", - "business", - "#CDDC39", - false, - false, - null, - null, - 90), - - // === AIDE SOCIALE === - GARDE_ENFANTS( - "Garde d'enfants", - "sociale", - "normal", - "Garde d'enfants ponctuelle ou régulière", - "child_care", - "#FFC107", - false, - false, - null, - null, - 7), - - AIDE_PERSONNES_AGEES( - "Aide personnes âgées", - "sociale", - "important", - "Aide et accompagnement personnes âgées", - "elderly", - "#FF9800", - false, - false, - null, - null, - 30), - - TRANSPORT( - "Transport", - "sociale", - "normal", - "Aide au transport (covoiturage, accompagnement)", - "directions_car", - "#2196F3", - false, - false, - null, - null, - 7), - - AIDE_ADMINISTRATIVE( - "Aide administrative", - "sociale", - "normal", - "Aide pour démarches administratives", - "description", - "#9E9E9E", - false, - false, - null, - null, - 14), - - // === AIDE D'URGENCE === - HEBERGEMENT_URGENCE( - "Hébergement d'urgence", - "urgence", - "urgent", - "Hébergement temporaire d'urgence", - "home", - "#F44336", - false, - true, - null, - null, - 7), - - AIDE_ALIMENTAIRE( - "Aide alimentaire", - "urgence", - "urgent", - "Aide alimentaire d'urgence", - "restaurant", - "#FF5722", - false, - true, - null, - null, - 3), - - AIDE_VESTIMENTAIRE( - "Aide vestimentaire", - "urgence", - "normal", - "Don de vêtements et accessoires", - "checkroom", - "#795548", - false, - false, - null, - null, - 14), - - // === AIDE SPÉCIALISÉE === - SOUTIEN_PSYCHOLOGIQUE( - "Soutien psychologique", - "specialisee", - "important", - "Soutien et écoute psychologique", - "psychology", - "#E91E63", - false, - true, - null, - null, - 30), - - AIDE_NUMERIQUE( - "Aide numérique", - "specialisee", - "normal", - "Aide pour utilisation outils numériques", - "computer", - "#607D8B", - false, - false, - null, - null, - 14), - - TRADUCTION( - "Traduction", - "specialisee", - "normal", - "Services de traduction et interprétariat", - "translate", - "#9C27B0", - false, - false, - null, - null, - 7), - - AUTRE( - "Autre", - "autre", - "normal", - "Autre type d'aide non catégorisé", - "help", - "#9E9E9E", - false, - false, - null, - null, - 14); - - private final String libelle; - private final String categorie; - private final String priorite; - private final String description; - private final String icone; - private final String couleur; - private final boolean necessiteMontant; - private final boolean necessiteValidation; - private final Double montantMin; - private final Double montantMax; - private final int delaiReponseJours; - - TypeAide( - String libelle, - String categorie, - String priorite, - String description, - String icone, - String couleur, - boolean necessiteMontant, - boolean necessiteValidation, - Double montantMin, - Double montantMax, - int delaiReponseJours) { - this.libelle = libelle; - this.categorie = categorie; - this.priorite = priorite; - this.description = description; - this.icone = icone; - this.couleur = couleur; - this.necessiteMontant = necessiteMontant; - this.necessiteValidation = necessiteValidation; - this.montantMin = montantMin; - this.montantMax = montantMax; - this.delaiReponseJours = delaiReponseJours; - } - - // === GETTERS === - - public String getLibelle() { - return libelle; - } - - public String getCategorie() { - return categorie; - } - - public String getPriorite() { - return priorite; - } - - public String getDescription() { - return description; - } - - public String getIcone() { - return icone; - } - - public String getCouleur() { - return couleur; - } - - public boolean isNecessiteMontant() { - return necessiteMontant; - } - - public boolean isNecessiteValidation() { - return necessiteValidation; - } - - public Double getMontantMin() { - return montantMin; - } - - public Double getMontantMax() { - return montantMax; - } - - public int getDelaiReponseJours() { - return delaiReponseJours; - } - - // === MÉTHODES UTILITAIRES === - - /** Vérifie si le type d'aide est urgent */ - public boolean isUrgent() { - return "urgent".equals(priorite); - } - - /** Vérifie si le type d'aide est financier */ - public boolean isFinancier() { - return "financiere".equals(categorie); - } - - /** Vérifie si le type d'aide est matériel */ - public boolean isMateriel() { - return "materielle".equals(categorie); - } - - /** Vérifie si le montant est dans la fourchette autorisée */ - public boolean isMontantValide(Double montant) { - if (!necessiteMontant || montant == null) return true; - if (montantMin != null && montant < montantMin) return false; - if (montantMax != null && montant > montantMax) return false; - return true; - } - - /** Retourne le niveau de priorité numérique */ - public int getNiveauPriorite() { - return switch (priorite) { - case "urgent" -> 1; - case "important" -> 2; - case "normal" -> 3; - default -> 3; - }; - } - - /** Retourne la date limite de réponse */ - public java.time.LocalDateTime getDateLimiteReponse() { - return java.time.LocalDateTime.now().plusDays(delaiReponseJours); - } - - /** Retourne les types d'aide par catégorie */ - public static java.util.List getParCategorie(String categorie) { - return java.util.Arrays.stream(values()) - .filter(type -> type.getCategorie().equals(categorie)) - .collect(java.util.stream.Collectors.toList()); - } - - /** Retourne les types d'aide urgents */ - public static java.util.List getUrgents() { - return java.util.Arrays.stream(values()) - .filter(TypeAide::isUrgent) - .collect(java.util.stream.Collectors.toList()); - } - - /** Retourne les types d'aide financiers */ - public static java.util.List getFinanciers() { - return java.util.Arrays.stream(values()) - .filter(TypeAide::isFinancier) - .collect(java.util.stream.Collectors.toList()); - } - - /** Retourne les catégories disponibles */ - public static java.util.Set getCategories() { - return java.util.Arrays.stream(values()) - .map(TypeAide::getCategorie) - .collect(java.util.stream.Collectors.toSet()); - } - - /** Retourne le libellé de la catégorie */ - public String getLibelleCategorie() { - return switch (categorie) { - case "financiere" -> "Aide financière"; - case "materielle" -> "Aide matérielle"; - case "professionnelle" -> "Aide professionnelle"; - case "sociale" -> "Aide sociale"; - case "urgence" -> "Aide d'urgence"; - case "specialisee" -> "Aide spécialisée"; - case "autre" -> "Autre"; - default -> categorie; - }; - } - - /** Retourne l'unité du montant si applicable */ - public String getUniteMontant() { - return necessiteMontant ? "FCFA" : null; - } - - /** Retourne le message de validation du montant */ - public String getMessageValidationMontant(Double montant) { - if (!necessiteMontant) return null; - if (montant == null) return "Le montant est obligatoire"; - if (montantMin != null && montant < montantMin) { - return String.format("Le montant minimum est de %.0f FCFA", montantMin); - } - if (montantMax != null && montant > montantMax) { - return String.format("Le montant maximum est de %.0f FCFA", montantMax); - } - return null; - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +/** + * Énumération des types d'aide disponibles dans le système de solidarité + * + *

Cette énumération définit les différents types d'aide que les membres peuvent demander ou + * proposer dans le cadre du système de solidarité. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-16 + */ +public enum TypeAide { + + // === AIDE FINANCIÈRE === + AIDE_FINANCIERE_URGENTE( + "Aide financière urgente", + "financiere", + "urgent", + "Aide financière pour situation d'urgence", + "emergency_fund", + "#F44336", + true, + true, + 5000.0, + 50000.0, + 7), + + PRET_SANS_INTERET( + "Prêt sans intérêt", + "financiere", + "important", + "Prêt sans intérêt entre membres", + "account_balance", + "#FF9800", + true, + true, + 10000.0, + 100000.0, + 30), + + AIDE_COTISATION( + "Aide pour cotisation", + "financiere", + "normal", + "Aide pour payer les cotisations", + "payment", + "#2196F3", + true, + false, + 1000.0, + 10000.0, + 14), + + AIDE_FRAIS_MEDICAUX( + "Aide frais médicaux", + "financiere", + "urgent", + "Aide pour frais médicaux et hospitaliers", + "medical_services", + "#E91E63", + true, + true, + 5000.0, + 200000.0, + 7), + + AIDE_FRAIS_SCOLARITE( + "Aide frais de scolarité", + "financiere", + "important", + "Aide pour frais de scolarité des enfants", + "school", + "#9C27B0", + true, + true, + 10000.0, + 100000.0, + 21), + + // === AIDE MATÉRIELLE === + DON_MATERIEL( + "Don de matériel", + "materielle", + "normal", + "Don d'objets, équipements ou matériel", + "inventory", + "#4CAF50", + false, + false, + null, + null, + 14), + + PRET_MATERIEL( + "Prêt de matériel", + "materielle", + "normal", + "Prêt temporaire d'objets ou équipements", + "build", + "#607D8B", + false, + false, + null, + null, + 30), + + AIDE_DEMENAGEMENT( + "Aide déménagement", + "materielle", + "normal", + "Aide pour déménagement (transport, main d'œuvre)", + "local_shipping", + "#795548", + false, + false, + null, + null, + 7), + + AIDE_TRAVAUX( + "Aide travaux", + "materielle", + "normal", + "Aide pour travaux de rénovation ou construction", + "construction", + "#FF5722", + false, + false, + null, + null, + 21), + + // === AIDE PROFESSIONNELLE === + AIDE_RECHERCHE_EMPLOI( + "Aide recherche d'emploi", + "professionnelle", + "important", + "Aide pour recherche d'emploi et CV", + "work", + "#3F51B5", + false, + false, + null, + null, + 30), + + FORMATION_PROFESSIONNELLE( + "Formation professionnelle", + "professionnelle", + "normal", + "Formation et développement des compétences", + "school", + "#009688", + false, + false, + null, + null, + 60), + + CONSEIL_JURIDIQUE( + "Conseil juridique", + "professionnelle", + "important", + "Conseil et assistance juridique", + "gavel", + "#8BC34A", + false, + false, + null, + null, + 14), + + AIDE_CREATION_ENTREPRISE( + "Aide création d'entreprise", + "professionnelle", + "normal", + "Accompagnement création d'entreprise", + "business", + "#CDDC39", + false, + false, + null, + null, + 90), + + // === AIDE SOCIALE === + GARDE_ENFANTS( + "Garde d'enfants", + "sociale", + "normal", + "Garde d'enfants ponctuelle ou régulière", + "child_care", + "#FFC107", + false, + false, + null, + null, + 7), + + AIDE_PERSONNES_AGEES( + "Aide personnes âgées", + "sociale", + "important", + "Aide et accompagnement personnes âgées", + "elderly", + "#FF9800", + false, + false, + null, + null, + 30), + + TRANSPORT( + "Transport", + "sociale", + "normal", + "Aide au transport (covoiturage, accompagnement)", + "directions_car", + "#2196F3", + false, + false, + null, + null, + 7), + + AIDE_ADMINISTRATIVE( + "Aide administrative", + "sociale", + "normal", + "Aide pour démarches administratives", + "description", + "#9E9E9E", + false, + false, + null, + null, + 14), + + // === AIDE D'URGENCE === + HEBERGEMENT_URGENCE( + "Hébergement d'urgence", + "urgence", + "urgent", + "Hébergement temporaire d'urgence", + "home", + "#F44336", + false, + true, + null, + null, + 7), + + AIDE_ALIMENTAIRE( + "Aide alimentaire", + "urgence", + "urgent", + "Aide alimentaire d'urgence", + "restaurant", + "#FF5722", + false, + true, + null, + null, + 3), + + AIDE_VESTIMENTAIRE( + "Aide vestimentaire", + "urgence", + "normal", + "Don de vêtements et accessoires", + "checkroom", + "#795548", + false, + false, + null, + null, + 14), + + // === AIDE SPÉCIALISÉE === + SOUTIEN_PSYCHOLOGIQUE( + "Soutien psychologique", + "specialisee", + "important", + "Soutien et écoute psychologique", + "psychology", + "#E91E63", + false, + true, + null, + null, + 30), + + AIDE_NUMERIQUE( + "Aide numérique", + "specialisee", + "normal", + "Aide pour utilisation outils numériques", + "computer", + "#607D8B", + false, + false, + null, + null, + 14), + + TRADUCTION( + "Traduction", + "specialisee", + "normal", + "Services de traduction et interprétariat", + "translate", + "#9C27B0", + false, + false, + null, + null, + 7), + + AUTRE( + "Autre", + "autre", + "normal", + "Autre type d'aide non catégorisé", + "help", + "#9E9E9E", + false, + false, + null, + null, + 14); + + private final String libelle; + private final String categorie; + private final String priorite; + private final String description; + private final String icone; + private final String couleur; + private final boolean necessiteMontant; + private final boolean necessiteValidation; + private final Double montantMin; + private final Double montantMax; + private final int delaiReponseJours; + + TypeAide( + String libelle, + String categorie, + String priorite, + String description, + String icone, + String couleur, + boolean necessiteMontant, + boolean necessiteValidation, + Double montantMin, + Double montantMax, + int delaiReponseJours) { + this.libelle = libelle; + this.categorie = categorie; + this.priorite = priorite; + this.description = description; + this.icone = icone; + this.couleur = couleur; + this.necessiteMontant = necessiteMontant; + this.necessiteValidation = necessiteValidation; + this.montantMin = montantMin; + this.montantMax = montantMax; + this.delaiReponseJours = delaiReponseJours; + } + + // === GETTERS === + + public String getLibelle() { + return libelle; + } + + public String getCategorie() { + return categorie; + } + + public String getPriorite() { + return priorite; + } + + public String getDescription() { + return description; + } + + public String getIcone() { + return icone; + } + + public String getCouleur() { + return couleur; + } + + public boolean isNecessiteMontant() { + return necessiteMontant; + } + + public boolean isNecessiteValidation() { + return necessiteValidation; + } + + public Double getMontantMin() { + return montantMin; + } + + public Double getMontantMax() { + return montantMax; + } + + public int getDelaiReponseJours() { + return delaiReponseJours; + } + + // === MÉTHODES UTILITAIRES === + + /** Vérifie si le type d'aide est urgent */ + public boolean isUrgent() { + return "urgent".equals(priorite); + } + + /** Vérifie si le type d'aide est financier */ + public boolean isFinancier() { + return "financiere".equals(categorie); + } + + /** Vérifie si le type d'aide est matériel */ + public boolean isMateriel() { + return "materielle".equals(categorie); + } + + /** Vérifie si le montant est dans la fourchette autorisée */ + public boolean isMontantValide(Double montant) { + if (!necessiteMontant || montant == null) return true; + if (montantMin != null && montant < montantMin) return false; + if (montantMax != null && montant > montantMax) return false; + return true; + } + + /** Retourne le niveau de priorité numérique */ + public int getNiveauPriorite() { + return switch (priorite) { + case "urgent" -> 1; + case "important" -> 2; + case "normal" -> 3; + default -> 3; + }; + } + + /** Retourne la date limite de réponse */ + public java.time.LocalDateTime getDateLimiteReponse() { + return java.time.LocalDateTime.now().plusDays(delaiReponseJours); + } + + /** Retourne les types d'aide par catégorie */ + public static java.util.List getParCategorie(String categorie) { + return java.util.Arrays.stream(values()) + .filter(type -> type.getCategorie().equals(categorie)) + .collect(java.util.stream.Collectors.toList()); + } + + /** Retourne les types d'aide urgents */ + public static java.util.List getUrgents() { + return java.util.Arrays.stream(values()) + .filter(TypeAide::isUrgent) + .collect(java.util.stream.Collectors.toList()); + } + + /** Retourne les types d'aide financiers */ + public static java.util.List getFinanciers() { + return java.util.Arrays.stream(values()) + .filter(TypeAide::isFinancier) + .collect(java.util.stream.Collectors.toList()); + } + + /** Retourne les catégories disponibles */ + public static java.util.Set getCategories() { + return java.util.Arrays.stream(values()) + .map(TypeAide::getCategorie) + .collect(java.util.stream.Collectors.toSet()); + } + + /** Retourne le libellé de la catégorie */ + public String getLibelleCategorie() { + return switch (categorie) { + case "financiere" -> "Aide financière"; + case "materielle" -> "Aide matérielle"; + case "professionnelle" -> "Aide professionnelle"; + case "sociale" -> "Aide sociale"; + case "urgence" -> "Aide d'urgence"; + case "specialisee" -> "Aide spécialisée"; + case "autre" -> "Autre"; + default -> categorie; + }; + } + + /** Retourne l'unité du montant si applicable */ + public String getUniteMontant() { + return necessiteMontant ? "FCFA" : null; + } + + /** Retourne le message de validation du montant */ + public String getMessageValidationMontant(Double montant) { + if (!necessiteMontant) return null; + if (montant == null) return "Le montant est obligatoire"; + if (montantMin != null && montant < montantMin) { + return String.format("Le montant minimum est de %.0f FCFA", montantMin); + } + if (montantMax != null && montant > montantMax) { + return String.format("Le montant maximum est de %.0f FCFA", montantMax); + } + return null; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/TypeEvaluation.java b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/TypeEvaluation.java index 6ea49c0..d437500 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/TypeEvaluation.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/TypeEvaluation.java @@ -1,22 +1,22 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -import lombok.Getter; - -/** - * Énumération des types d'évaluation - */ -@Getter -public enum TypeEvaluation { - SATISFACTION_BENEFICIAIRE("Satisfaction du bénéficiaire"), - EVALUATION_PROPOSANT("Évaluation du proposant"), - EVALUATION_PROCESSUS("Évaluation du processus"), - SUIVI_POST_AIDE("Suivi post-aide"), - EVALUATION_IMPACT("Évaluation d'impact"), - RETOUR_EXPERIENCE("Retour d'expérience"); - - private final String libelle; - - TypeEvaluation(String libelle) { - this.libelle = libelle; - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +import lombok.Getter; + +/** + * Énumération des types d'évaluation + */ +@Getter +public enum TypeEvaluation { + SATISFACTION_BENEFICIAIRE("Satisfaction du bénéficiaire"), + EVALUATION_PROPOSANT("Évaluation du proposant"), + EVALUATION_PROCESSUS("Évaluation du processus"), + SUIVI_POST_AIDE("Suivi post-aide"), + EVALUATION_IMPACT("Évaluation d'impact"), + RETOUR_EXPERIENCE("Retour d'expérience"); + + private final String libelle; + + TypeEvaluation(String libelle) { + this.libelle = libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/TypeWorkflow.java b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/TypeWorkflow.java index a4571cd..a7e131a 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/TypeWorkflow.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/solidarite/TypeWorkflow.java @@ -1,13 +1,13 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -public enum TypeWorkflow { - DEMANDE_AIDE("Workflow demande d'aide solidarité"), - ADHESION("Workflow validation adhésion"), - AUTRE("Workflow personnalisé"); - - private final String libelle; - - TypeWorkflow(String libelle) { this.libelle = libelle; } - - public String getLibelle() { return libelle; } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +public enum TypeWorkflow { + DEMANDE_AIDE("Workflow demande d'aide solidarité"), + ADHESION("Workflow validation adhésion"), + AUTRE("Workflow personnalisé"); + + private final String libelle; + + TypeWorkflow(String libelle) { this.libelle = libelle; } + + public String getLibelle() { return libelle; } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/tontine/FrequenceTour.java b/src/main/java/dev/lions/unionflow/server/api/enums/tontine/FrequenceTour.java index 0db8e47..02f2eb7 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/tontine/FrequenceTour.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/tontine/FrequenceTour.java @@ -1,20 +1,20 @@ -package dev.lions.unionflow.server.api.enums.tontine; - -public enum FrequenceTour { - JOURNALIERE("Chaque jour"), - HEBDOMADAIRE("Chaque semaine"), - DECADE("Tous les 10 jours"), - QUINZAINE("Chaque quinzaine (tous les 15 jours)"), - MENSUELLE("Chaque mois"), - TRIMESTRIELLE("Chaque trimestre"); - - private final String libelle; - - FrequenceTour(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.tontine; + +public enum FrequenceTour { + JOURNALIERE("Chaque jour"), + HEBDOMADAIRE("Chaque semaine"), + DECADE("Tous les 10 jours"), + QUINZAINE("Chaque quinzaine (tous les 15 jours)"), + MENSUELLE("Chaque mois"), + TRIMESTRIELLE("Chaque trimestre"); + + private final String libelle; + + FrequenceTour(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/tontine/StatutTontine.java b/src/main/java/dev/lions/unionflow/server/api/enums/tontine/StatutTontine.java index 2660762..e85efcb 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/tontine/StatutTontine.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/tontine/StatutTontine.java @@ -1,19 +1,19 @@ -package dev.lions.unionflow.server.api.enums.tontine; - -public enum StatutTontine { - PLANIFIEE("En cours de planification / Enrôlement des membres"), - EN_COURS("Active et en cours de déroulement"), - EN_PAUSE("Suspendue temporairement par l'administration"), - CLOTUREE("Terminée avec succès (tous les tours finis)"), - ANNULEE("Annulée avant son terme"); - - private final String libelle; - - StatutTontine(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.tontine; + +public enum StatutTontine { + PLANIFIEE("En cours de planification / Enrôlement des membres"), + EN_COURS("Active et en cours de déroulement"), + EN_PAUSE("Suspendue temporairement par l'administration"), + CLOTUREE("Terminée avec succès (tous les tours finis)"), + ANNULEE("Annulée avant son terme"); + + private final String libelle; + + StatutTontine(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/tontine/TypeTontine.java b/src/main/java/dev/lions/unionflow/server/api/enums/tontine/TypeTontine.java index 65dfa11..76fbefa 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/tontine/TypeTontine.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/tontine/TypeTontine.java @@ -1,17 +1,17 @@ -package dev.lions.unionflow.server.api.enums.tontine; - -public enum TypeTontine { - ROTATIVE_CLASSIQUE("Tontine rotative classique avec cotisations fixes"), - VARIABLE("Tontine à cotisations variables (Vente aux enchères/Mise)"), - ACCUMULATIVE("Tontine accumulative / Caisse de secours"); - - private final String libelle; - - TypeTontine(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.tontine; + +public enum TypeTontine { + ROTATIVE_CLASSIQUE("Tontine rotative classique avec cotisations fixes"), + VARIABLE("Tontine à cotisations variables (Vente aux enchères/Mise)"), + ACCUMULATIVE("Tontine accumulative / Caisse de secours"); + + private final String libelle; + + TypeTontine(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/vote/ModeScrutin.java b/src/main/java/dev/lions/unionflow/server/api/enums/vote/ModeScrutin.java index 13ea052..5972be3 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/vote/ModeScrutin.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/vote/ModeScrutin.java @@ -1,18 +1,18 @@ -package dev.lions.unionflow.server.api.enums.vote; - -public enum ModeScrutin { - MAJORITAIRE_UN_TOUR("Scrutin majoritaire à un seul tour"), - MAJORITAIRE_DEUX_TOURS("Scrutin majoritaire à deux tours"), - PROPORTIONNEL("Scrutin proportionnel de listes"), - BUREAU_CONSENSUEL("Vote d'approbation globale de bureau (OUI/NON)"); - - private final String libelle; - - ModeScrutin(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.vote; + +public enum ModeScrutin { + MAJORITAIRE_UN_TOUR("Scrutin majoritaire à un seul tour"), + MAJORITAIRE_DEUX_TOURS("Scrutin majoritaire à deux tours"), + PROPORTIONNEL("Scrutin proportionnel de listes"), + BUREAU_CONSENSUEL("Vote d'approbation globale de bureau (OUI/NON)"); + + private final String libelle; + + ModeScrutin(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/vote/StatutVote.java b/src/main/java/dev/lions/unionflow/server/api/enums/vote/StatutVote.java index 6d639a9..6937dfd 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/vote/StatutVote.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/vote/StatutVote.java @@ -1,20 +1,20 @@ -package dev.lions.unionflow.server.api.enums.vote; - -public enum StatutVote { - BROUILLON("Paramétrage de la campagne en cours"), - PLANIFIE("Campagne planifiée (pas encore ouverte aux votes)"), - OUVERT("Les membres peuvent voter activement"), - SUSPENDU("Campagne de vote suspendue suite à une contestation"), - CLOTURE("Dispositif de vote fermé (Calcul en cours)"), - RESULTATS_PUBLIES("Résultats définitifs publiés et accessibles"); - - private final String libelle; - - StatutVote(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.vote; + +public enum StatutVote { + BROUILLON("Paramétrage de la campagne en cours"), + PLANIFIE("Campagne planifiée (pas encore ouverte aux votes)"), + OUVERT("Les membres peuvent voter activement"), + SUSPENDU("Campagne de vote suspendue suite à une contestation"), + CLOTURE("Dispositif de vote fermé (Calcul en cours)"), + RESULTATS_PUBLIES("Résultats définitifs publiés et accessibles"); + + private final String libelle; + + StatutVote(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/vote/TypeVote.java b/src/main/java/dev/lions/unionflow/server/api/enums/vote/TypeVote.java index 5b46785..d0b5d4d 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/vote/TypeVote.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/vote/TypeVote.java @@ -1,19 +1,19 @@ -package dev.lions.unionflow.server.api.enums.vote; - -public enum TypeVote { - ELECTION_BUREAU("Élection des membres du bureau exécutif"), - ADOPTION_RESOLUTION("Vote pour ou contre une résolution"), - MODIFICATION_STATUTS("Vote d'amendement des statuts de la mutuelle"), - EXCLUSION_MEMBRE("Vote d'exclusion d'un membre pour manquements"), - REFERENDUM("Référendum interne ou consultation générale"); - - private final String libelle; - - TypeVote(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} +package dev.lions.unionflow.server.api.enums.vote; + +public enum TypeVote { + ELECTION_BUREAU("Élection des membres du bureau exécutif"), + ADOPTION_RESOLUTION("Vote pour ou contre une résolution"), + MODIFICATION_STATUTS("Vote d'amendement des statuts de la mutuelle"), + EXCLUSION_MEMBRE("Vote d'exclusion d'un membre pour manquements"), + REFERENDUM("Référendum interne ou consultation générale"); + + private final String libelle; + + TypeVote(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/wave/StatutCompteWave.java b/src/main/java/dev/lions/unionflow/server/api/enums/wave/StatutCompteWave.java index acbcaae..e4aef95 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/wave/StatutCompteWave.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/wave/StatutCompteWave.java @@ -1,26 +1,26 @@ -package dev.lions.unionflow.server.api.enums.wave; - -/** - * Énumération des statuts de compte Wave - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -public enum StatutCompteWave { - NON_VERIFIE("Non Vérifié"), - VERIFIE("Vérifié"), - SUSPENDU("Suspendu"), - BLOQUE("Bloqué"); - - private final String libelle; - - StatutCompteWave(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} - +package dev.lions.unionflow.server.api.enums.wave; + +/** + * Énumération des statuts de compte Wave + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +public enum StatutCompteWave { + NON_VERIFIE("Non Vérifié"), + VERIFIE("Vérifié"), + SUSPENDU("Suspendu"), + BLOQUE("Bloqué"); + + private final String libelle; + + StatutCompteWave(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} + diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/wave/StatutTransactionWave.java b/src/main/java/dev/lions/unionflow/server/api/enums/wave/StatutTransactionWave.java index 9b54a8e..2db84b0 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/wave/StatutTransactionWave.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/wave/StatutTransactionWave.java @@ -1,34 +1,34 @@ -package dev.lions.unionflow.server.api.enums.wave; - -/** - * Énumération des statuts de transaction Wave - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -public enum StatutTransactionWave { - INITIALISE("Initialisé"), - EN_ATTENTE("En Attente"), - EN_COURS("En Cours"), - REUSSIE("Réussie"), - ECHOUE("Échoué"), - ANNULEE("Annulée"), - EXPIRED("Expiré"); - - private final String libelle; - - StatutTransactionWave(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } - - /** Vérifie si la transaction est finalisée */ - public boolean isFinalise() { - return this == REUSSIE || this == ECHOUE || this == ANNULEE || this == EXPIRED; - } -} - +package dev.lions.unionflow.server.api.enums.wave; + +/** + * Énumération des statuts de transaction Wave + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +public enum StatutTransactionWave { + INITIALISE("Initialisé"), + EN_ATTENTE("En Attente"), + EN_COURS("En Cours"), + REUSSIE("Réussie"), + ECHOUE("Échoué"), + ANNULEE("Annulée"), + EXPIRED("Expiré"); + + private final String libelle; + + StatutTransactionWave(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } + + /** Vérifie si la transaction est finalisée */ + public boolean isFinalise() { + return this == REUSSIE || this == ECHOUE || this == ANNULEE || this == EXPIRED; + } +} + diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/wave/StatutWebhook.java b/src/main/java/dev/lions/unionflow/server/api/enums/wave/StatutWebhook.java index 3d96b71..08761a0 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/wave/StatutWebhook.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/wave/StatutWebhook.java @@ -1,27 +1,27 @@ -package dev.lions.unionflow.server.api.enums.wave; - -/** - * Énumération des statuts de traitement de webhook Wave - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -public enum StatutWebhook { - EN_ATTENTE("En Attente"), - EN_TRAITEMENT("En Traitement"), - TRAITE("Traité"), - ECHOUE("Échoué"), - IGNORE("Ignoré"); - - private final String libelle; - - StatutWebhook(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} - +package dev.lions.unionflow.server.api.enums.wave; + +/** + * Énumération des statuts de traitement de webhook Wave + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +public enum StatutWebhook { + EN_ATTENTE("En Attente"), + EN_TRAITEMENT("En Traitement"), + TRAITE("Traité"), + ECHOUE("Échoué"), + IGNORE("Ignoré"); + + private final String libelle; + + StatutWebhook(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} + diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/wave/TypeEvenementWebhook.java b/src/main/java/dev/lions/unionflow/server/api/enums/wave/TypeEvenementWebhook.java index 336ce3d..417808e 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/wave/TypeEvenementWebhook.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/wave/TypeEvenementWebhook.java @@ -1,29 +1,29 @@ -package dev.lions.unionflow.server.api.enums.wave; - -/** - * Énumération des types d'événements webhook Wave - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -public enum TypeEvenementWebhook { - TRANSACTION_CREATED("Transaction Créée"), - TRANSACTION_COMPLETED("Transaction Complétée"), - TRANSACTION_FAILED("Transaction Échouée"), - TRANSACTION_CANCELLED("Transaction Annulée"), - ACCOUNT_VERIFIED("Compte Vérifié"), - ACCOUNT_SUSPENDED("Compte Suspendu"), - OTHER("Autre"); - - private final String libelle; - - TypeEvenementWebhook(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} - +package dev.lions.unionflow.server.api.enums.wave; + +/** + * Énumération des types d'événements webhook Wave + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +public enum TypeEvenementWebhook { + TRANSACTION_CREATED("Transaction Créée"), + TRANSACTION_COMPLETED("Transaction Complétée"), + TRANSACTION_FAILED("Transaction Échouée"), + TRANSACTION_CANCELLED("Transaction Annulée"), + ACCOUNT_VERIFIED("Compte Vérifié"), + ACCOUNT_SUSPENDED("Compte Suspendu"), + OTHER("Autre"); + + private final String libelle; + + TypeEvenementWebhook(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} + diff --git a/src/main/java/dev/lions/unionflow/server/api/enums/wave/TypeTransactionWave.java b/src/main/java/dev/lions/unionflow/server/api/enums/wave/TypeTransactionWave.java index b57e453..684049f 100644 --- a/src/main/java/dev/lions/unionflow/server/api/enums/wave/TypeTransactionWave.java +++ b/src/main/java/dev/lions/unionflow/server/api/enums/wave/TypeTransactionWave.java @@ -1,27 +1,27 @@ -package dev.lions.unionflow.server.api.enums.wave; - -/** - * Énumération des types de transaction Wave - * - * @author UnionFlow Team - * @version 3.0 - * @since 2025-01-29 - */ -public enum TypeTransactionWave { - DEPOT("Dépôt"), - RETRAIT("Retrait"), - TRANSFERT("Transfert"), - PAIEMENT("Paiement"), - REMBOURSEMENT("Remboursement"); - - private final String libelle; - - TypeTransactionWave(String libelle) { - this.libelle = libelle; - } - - public String getLibelle() { - return libelle; - } -} - +package dev.lions.unionflow.server.api.enums.wave; + +/** + * Énumération des types de transaction Wave + * + * @author UnionFlow Team + * @version 3.0 + * @since 2025-01-29 + */ +public enum TypeTransactionWave { + DEPOT("Dépôt"), + RETRAIT("Retrait"), + TRANSFERT("Transfert"), + PAIEMENT("Paiement"), + REMBOURSEMENT("Remboursement"); + + private final String libelle; + + TypeTransactionWave(String libelle) { + this.libelle = libelle; + } + + public String getLibelle() { + return libelle; + } +} + diff --git a/src/main/java/dev/lions/unionflow/server/api/service/dashboard/DashboardService.java b/src/main/java/dev/lions/unionflow/server/api/service/dashboard/DashboardService.java index febf3b9..1c2c1f2 100644 --- a/src/main/java/dev/lions/unionflow/server/api/service/dashboard/DashboardService.java +++ b/src/main/java/dev/lions/unionflow/server/api/service/dashboard/DashboardService.java @@ -1,59 +1,59 @@ -package dev.lions.unionflow.server.api.service.dashboard; - -import dev.lions.unionflow.server.api.dto.dashboard.DashboardDataResponse; -import dev.lions.unionflow.server.api.dto.dashboard.DashboardStatsResponse; -import dev.lions.unionflow.server.api.dto.dashboard.RecentActivityResponse; -import dev.lions.unionflow.server.api.dto.dashboard.UpcomingEventResponse; - -import java.util.List; - -/** - * Interface de service pour la gestion des données du dashboard - * - *

Cette interface définit le contrat pour récupérer les données du dashboard, - * incluant les statistiques, activités récentes et événements à venir. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-15 - */ -public interface DashboardService { - - /** - * Récupère toutes les données du dashboard pour une organisation et un utilisateur - * - * @param organizationId L'identifiant de l'organisation - * @param userId L'identifiant de l'utilisateur - * @return Les données complètes du dashboard - */ - DashboardDataResponse getDashboardData(String organizationId, String userId); - - /** - * Récupère uniquement les statistiques du dashboard - * - * @param organizationId L'identifiant de l'organisation - * @param userId L'identifiant de l'utilisateur - * @return Les statistiques du dashboard - */ - DashboardStatsResponse getDashboardStats(String organizationId, String userId); - - /** - * Récupère les activités récentes - * - * @param organizationId L'identifiant de l'organisation - * @param userId L'identifiant de l'utilisateur - * @param limit Le nombre maximum d'activités à retourner - * @return La liste des activités récentes - */ - List getRecentActivities(String organizationId, String userId, int limit); - - /** - * Récupère les événements à venir - * - * @param organizationId L'identifiant de l'organisation - * @param userId L'identifiant de l'utilisateur - * @param limit Le nombre maximum d'événements à retourner - * @return La liste des événements à venir - */ - List getUpcomingEvents(String organizationId, String userId, int limit); -} +package dev.lions.unionflow.server.api.service.dashboard; + +import dev.lions.unionflow.server.api.dto.dashboard.DashboardDataResponse; +import dev.lions.unionflow.server.api.dto.dashboard.DashboardStatsResponse; +import dev.lions.unionflow.server.api.dto.dashboard.RecentActivityResponse; +import dev.lions.unionflow.server.api.dto.dashboard.UpcomingEventResponse; + +import java.util.List; + +/** + * Interface de service pour la gestion des données du dashboard + * + *

Cette interface définit le contrat pour récupérer les données du dashboard, + * incluant les statistiques, activités récentes et événements à venir. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-15 + */ +public interface DashboardService { + + /** + * Récupère toutes les données du dashboard pour une organisation et un utilisateur + * + * @param organizationId L'identifiant de l'organisation + * @param userId L'identifiant de l'utilisateur + * @return Les données complètes du dashboard + */ + DashboardDataResponse getDashboardData(String organizationId, String userId); + + /** + * Récupère uniquement les statistiques du dashboard + * + * @param organizationId L'identifiant de l'organisation + * @param userId L'identifiant de l'utilisateur + * @return Les statistiques du dashboard + */ + DashboardStatsResponse getDashboardStats(String organizationId, String userId); + + /** + * Récupère les activités récentes + * + * @param organizationId L'identifiant de l'organisation + * @param userId L'identifiant de l'utilisateur + * @param limit Le nombre maximum d'activités à retourner + * @return La liste des activités récentes + */ + List getRecentActivities(String organizationId, String userId, int limit); + + /** + * Récupère les événements à venir + * + * @param organizationId L'identifiant de l'organisation + * @param userId L'identifiant de l'utilisateur + * @param limit Le nombre maximum d'événements à retourner + * @return La liste des événements à venir + */ + List getUpcomingEvents(String organizationId, String userId, int limit); +} diff --git a/src/main/java/dev/lions/unionflow/server/api/validation/ValidationConstants.java b/src/main/java/dev/lions/unionflow/server/api/validation/ValidationConstants.java index a4f750d..6b31f2c 100644 --- a/src/main/java/dev/lions/unionflow/server/api/validation/ValidationConstants.java +++ b/src/main/java/dev/lions/unionflow/server/api/validation/ValidationConstants.java @@ -1,244 +1,244 @@ -package dev.lions.unionflow.server.api.validation; - -/** - * Constantes pour la validation des DTOs - * - *

Cette classe centralise toutes les contraintes de validation pour assurer la cohérence entre - * les différents DTOs du système. - * - * @author UnionFlow Team - * @version 2.0 - * @since 2025-01-16 - */ -public final class ValidationConstants { - - private ValidationConstants() { - // Classe utilitaire - constructeur privé - } - - // === CONTRAINTES DE TAILLE POUR LES TEXTES === - - /** Titre court (événements, aides, etc.) */ - public static final int TITRE_MIN_LENGTH = 5; - - public static final int TITRE_MAX_LENGTH = 100; - public static final String TITRE_SIZE_MESSAGE = - "Le titre doit contenir entre " - + TITRE_MIN_LENGTH - + " et " - + TITRE_MAX_LENGTH - + " caractères"; - - /** Nom d'organisation */ - public static final int NOM_ORGANISATION_MIN_LENGTH = 2; - - public static final int NOM_ORGANISATION_MAX_LENGTH = 200; - public static final String NOM_ORGANISATION_SIZE_MESSAGE = - "Le nom doit contenir entre " - + NOM_ORGANISATION_MIN_LENGTH - + " et " - + NOM_ORGANISATION_MAX_LENGTH - + " caractères"; - - /** Description standard */ - public static final int DESCRIPTION_MIN_LENGTH = 20; - - public static final int DESCRIPTION_MAX_LENGTH = 2000; - public static final String DESCRIPTION_SIZE_MESSAGE = - "La description doit contenir entre " - + DESCRIPTION_MIN_LENGTH - + " et " - + DESCRIPTION_MAX_LENGTH - + " caractères"; - - /** Description courte (événements) */ - public static final int DESCRIPTION_COURTE_MAX_LENGTH = 1000; - - public static final String DESCRIPTION_COURTE_SIZE_MESSAGE = - "La description ne peut pas dépasser " + DESCRIPTION_COURTE_MAX_LENGTH + " caractères"; - - /** Justification */ - public static final int JUSTIFICATION_MAX_LENGTH = 1000; - - public static final String JUSTIFICATION_SIZE_MESSAGE = - "La justification ne peut pas dépasser " + JUSTIFICATION_MAX_LENGTH + " caractères"; - - /** Commentaires */ - public static final int COMMENTAIRES_MAX_LENGTH = 1000; - - public static final String COMMENTAIRES_SIZE_MESSAGE = - "Les commentaires ne peuvent pas dépasser " + COMMENTAIRES_MAX_LENGTH + " caractères"; - - /** Raison de rejet */ - public static final int RAISON_REJET_MAX_LENGTH = 500; - - public static final String RAISON_REJET_SIZE_MESSAGE = - "La raison du rejet ne peut pas dépasser " + RAISON_REJET_MAX_LENGTH + " caractères"; - - /** Adresse */ - public static final int ADRESSE_MAX_LENGTH = 200; - - public static final String ADRESSE_SIZE_MESSAGE = - "L'adresse ne peut pas dépasser " + ADRESSE_MAX_LENGTH + " caractères"; - - /** Ville, région, quartier */ - public static final int LOCALISATION_MAX_LENGTH = 50; - - public static final String VILLE_SIZE_MESSAGE = - "La ville ne peut pas dépasser " + LOCALISATION_MAX_LENGTH + " caractères"; - public static final String REGION_SIZE_MESSAGE = - "La région ne peut pas dépasser " + LOCALISATION_MAX_LENGTH + " caractères"; - public static final String QUARTIER_SIZE_MESSAGE = - "Le quartier ne peut pas dépasser " + LOCALISATION_MAX_LENGTH + " caractères"; - - /** Rôle */ - public static final int ROLE_MAX_LENGTH = 50; - - public static final String ROLE_SIZE_MESSAGE = - "Le rôle ne peut pas dépasser " + ROLE_MAX_LENGTH + " caractères"; - - /** URL */ - public static final int URL_MAX_LENGTH = 255; - - public static final String URL_SIZE_MESSAGE = - "L'URL ne peut pas dépasser " + URL_MAX_LENGTH + " caractères"; - - /** Email */ - public static final int EMAIL_MAX_LENGTH = 100; - - public static final String EMAIL_SIZE_MESSAGE = - "L'email ne peut pas dépasser " + EMAIL_MAX_LENGTH + " caractères"; - - /** Nom et prénom */ - public static final int NOM_PRENOM_MIN_LENGTH = 2; - - public static final int NOM_PRENOM_MAX_LENGTH = 50; - public static final String NOM_SIZE_MESSAGE = - "Le nom doit contenir entre " - + NOM_PRENOM_MIN_LENGTH - + " et " - + NOM_PRENOM_MAX_LENGTH - + " caractères"; - public static final String PRENOM_SIZE_MESSAGE = - "Le prénom doit contenir entre " - + NOM_PRENOM_MIN_LENGTH - + " et " - + NOM_PRENOM_MAX_LENGTH - + " caractères"; - - // === PATTERNS DE VALIDATION === - - /** Numéro de téléphone international */ - public static final String TELEPHONE_PATTERN = "^\\+?[0-9]{8,15}$"; - - public static final String TELEPHONE_MESSAGE = - "Le numéro de téléphone doit contenir entre 8 et 15 chiffres, avec un indicatif optionnel" - + " (+)"; - - /** Code devise ISO */ - public static final String DEVISE_PATTERN = "^[A-Z]{3}$"; - - public static final String DEVISE_MESSAGE = - "La devise doit être un code ISO à 3 lettres majuscules"; - - /** Numéro de référence aide */ - public static final String REFERENCE_AIDE_PATTERN = "^DA-\\d{4}-\\d{6}$"; - - public static final String REFERENCE_AIDE_MESSAGE = - "Le numéro de référence doit suivre le format DA-YYYY-NNNNNN"; - - /** Numéro de membre */ - public static final String NUMERO_MEMBRE_PATTERN = "^UF-\\d{4}-[A-Z0-9]{8}$"; - - public static final String NUMERO_MEMBRE_MESSAGE = - "Format de numéro de membre invalide (UF-YYYY-XXXXXXXX)"; - - /** Couleur hexadécimale */ - public static final String COULEUR_HEX_PATTERN = "^#[0-9A-Fa-f]{6}$"; - - public static final String COULEUR_HEX_MESSAGE = "Format de couleur invalide (format: #RRGGBB)"; - - // === CONTRAINTES NUMÉRIQUES === - - /** Montant minimum */ - public static final String MONTANT_MIN_VALUE = "0.0"; - - public static final String MONTANT_POSITIF_MESSAGE = "Le montant doit être positif"; - - /** Contraintes pour les montants */ - public static final int MONTANT_INTEGER_DIGITS = 10; - - public static final int MONTANT_FRACTION_DIGITS = 2; - public static final String MONTANT_DIGITS_MESSAGE = - "Le montant doit avoir au maximum " - + MONTANT_INTEGER_DIGITS - + " chiffres entiers et " - + MONTANT_FRACTION_DIGITS - + " décimales"; - - // === MESSAGES D'ERREUR STANDARD === - - public static final String OBLIGATOIRE_MESSAGE = " est obligatoire"; - public static final String EMAIL_FORMAT_MESSAGE = "L'adresse email n'est pas valide"; - public static final String DATE_PASSEE_MESSAGE = "La date doit être dans le passé"; - public static final String DATE_FUTURE_MESSAGE = "La date doit être dans le futur"; - - // === CONTRAINTES SPÉCIFIQUES === - - /** Documents joints */ - public static final int DOCUMENTS_JOINTS_MAX_LENGTH = 1000; - - public static final String DOCUMENTS_JOINTS_SIZE_MESSAGE = - "La liste des documents ne peut pas dépasser " + DOCUMENTS_JOINTS_MAX_LENGTH + " caractères"; - - /** Mode de versement */ - public static final int MODE_VERSEMENT_MAX_LENGTH = 50; - - public static final String MODE_VERSEMENT_SIZE_MESSAGE = - "Le mode de versement ne peut pas dépasser " + MODE_VERSEMENT_MAX_LENGTH + " caractères"; - - /** Numéro de transaction */ - public static final int NUMERO_TRANSACTION_MAX_LENGTH = 100; - - public static final String NUMERO_TRANSACTION_SIZE_MESSAGE = - "Le numéro de transaction ne peut pas dépasser " - + NUMERO_TRANSACTION_MAX_LENGTH - + " caractères"; - - /** Numéro d'enregistrement */ - public static final int NUMERO_ENREGISTREMENT_MAX_LENGTH = 100; - - public static final String NUMERO_ENREGISTREMENT_SIZE_MESSAGE = - "Le numéro d'enregistrement ne peut pas dépasser " - + NUMERO_ENREGISTREMENT_MAX_LENGTH - + " caractères"; - - /** Nom court d'organisation */ - public static final int NOM_COURT_MAX_LENGTH = 50; - - public static final String NOM_COURT_SIZE_MESSAGE = - "Le nom court ne peut pas dépasser " + NOM_COURT_MAX_LENGTH + " caractères"; - - /** Instructions et matériel */ - public static final int INSTRUCTIONS_MAX_LENGTH = 500; - - public static final String INSTRUCTIONS_SIZE_MESSAGE = - "Les instructions ne peuvent pas dépasser " + INSTRUCTIONS_MAX_LENGTH + " caractères"; - - /** Conditions météo */ - public static final int CONDITIONS_METEO_MAX_LENGTH = 100; - - public static final String CONDITIONS_METEO_SIZE_MESSAGE = - "Les conditions météo ne peuvent pas dépasser " + CONDITIONS_METEO_MAX_LENGTH + " caractères"; - - // === LCB-FT / Anti-blanchiment (mutuelles) === - - /** Origine des fonds — libellé court (obligatoire au-dessus du seuil configuré) */ - public static final int ORIGINE_FONDS_MAX_LENGTH = 200; - - public static final String ORIGINE_FONDS_SIZE_MESSAGE = - "L'origine des fonds ne peut pas dépasser " + ORIGINE_FONDS_MAX_LENGTH + " caractères"; - - public static final String ORIGINE_FONDS_OBLIGATOIRE_SEUIL_MESSAGE = - "L'origine des fonds est obligatoire pour les opérations au-dessus du seuil LCB-FT configuré"; -} +package dev.lions.unionflow.server.api.validation; + +/** + * Constantes pour la validation des DTOs + * + *

Cette classe centralise toutes les contraintes de validation pour assurer la cohérence entre + * les différents DTOs du système. + * + * @author UnionFlow Team + * @version 2.0 + * @since 2025-01-16 + */ +public final class ValidationConstants { + + private ValidationConstants() { + // Classe utilitaire - constructeur privé + } + + // === CONTRAINTES DE TAILLE POUR LES TEXTES === + + /** Titre court (événements, aides, etc.) */ + public static final int TITRE_MIN_LENGTH = 5; + + public static final int TITRE_MAX_LENGTH = 100; + public static final String TITRE_SIZE_MESSAGE = + "Le titre doit contenir entre " + + TITRE_MIN_LENGTH + + " et " + + TITRE_MAX_LENGTH + + " caractères"; + + /** Nom d'organisation */ + public static final int NOM_ORGANISATION_MIN_LENGTH = 2; + + public static final int NOM_ORGANISATION_MAX_LENGTH = 200; + public static final String NOM_ORGANISATION_SIZE_MESSAGE = + "Le nom doit contenir entre " + + NOM_ORGANISATION_MIN_LENGTH + + " et " + + NOM_ORGANISATION_MAX_LENGTH + + " caractères"; + + /** Description standard */ + public static final int DESCRIPTION_MIN_LENGTH = 20; + + public static final int DESCRIPTION_MAX_LENGTH = 2000; + public static final String DESCRIPTION_SIZE_MESSAGE = + "La description doit contenir entre " + + DESCRIPTION_MIN_LENGTH + + " et " + + DESCRIPTION_MAX_LENGTH + + " caractères"; + + /** Description courte (événements) */ + public static final int DESCRIPTION_COURTE_MAX_LENGTH = 1000; + + public static final String DESCRIPTION_COURTE_SIZE_MESSAGE = + "La description ne peut pas dépasser " + DESCRIPTION_COURTE_MAX_LENGTH + " caractères"; + + /** Justification */ + public static final int JUSTIFICATION_MAX_LENGTH = 1000; + + public static final String JUSTIFICATION_SIZE_MESSAGE = + "La justification ne peut pas dépasser " + JUSTIFICATION_MAX_LENGTH + " caractères"; + + /** Commentaires */ + public static final int COMMENTAIRES_MAX_LENGTH = 1000; + + public static final String COMMENTAIRES_SIZE_MESSAGE = + "Les commentaires ne peuvent pas dépasser " + COMMENTAIRES_MAX_LENGTH + " caractères"; + + /** Raison de rejet */ + public static final int RAISON_REJET_MAX_LENGTH = 500; + + public static final String RAISON_REJET_SIZE_MESSAGE = + "La raison du rejet ne peut pas dépasser " + RAISON_REJET_MAX_LENGTH + " caractères"; + + /** Adresse */ + public static final int ADRESSE_MAX_LENGTH = 200; + + public static final String ADRESSE_SIZE_MESSAGE = + "L'adresse ne peut pas dépasser " + ADRESSE_MAX_LENGTH + " caractères"; + + /** Ville, région, quartier */ + public static final int LOCALISATION_MAX_LENGTH = 50; + + public static final String VILLE_SIZE_MESSAGE = + "La ville ne peut pas dépasser " + LOCALISATION_MAX_LENGTH + " caractères"; + public static final String REGION_SIZE_MESSAGE = + "La région ne peut pas dépasser " + LOCALISATION_MAX_LENGTH + " caractères"; + public static final String QUARTIER_SIZE_MESSAGE = + "Le quartier ne peut pas dépasser " + LOCALISATION_MAX_LENGTH + " caractères"; + + /** Rôle */ + public static final int ROLE_MAX_LENGTH = 50; + + public static final String ROLE_SIZE_MESSAGE = + "Le rôle ne peut pas dépasser " + ROLE_MAX_LENGTH + " caractères"; + + /** URL */ + public static final int URL_MAX_LENGTH = 255; + + public static final String URL_SIZE_MESSAGE = + "L'URL ne peut pas dépasser " + URL_MAX_LENGTH + " caractères"; + + /** Email */ + public static final int EMAIL_MAX_LENGTH = 100; + + public static final String EMAIL_SIZE_MESSAGE = + "L'email ne peut pas dépasser " + EMAIL_MAX_LENGTH + " caractères"; + + /** Nom et prénom */ + public static final int NOM_PRENOM_MIN_LENGTH = 2; + + public static final int NOM_PRENOM_MAX_LENGTH = 50; + public static final String NOM_SIZE_MESSAGE = + "Le nom doit contenir entre " + + NOM_PRENOM_MIN_LENGTH + + " et " + + NOM_PRENOM_MAX_LENGTH + + " caractères"; + public static final String PRENOM_SIZE_MESSAGE = + "Le prénom doit contenir entre " + + NOM_PRENOM_MIN_LENGTH + + " et " + + NOM_PRENOM_MAX_LENGTH + + " caractères"; + + // === PATTERNS DE VALIDATION === + + /** Numéro de téléphone international */ + public static final String TELEPHONE_PATTERN = "^\\+?[0-9]{8,15}$"; + + public static final String TELEPHONE_MESSAGE = + "Le numéro de téléphone doit contenir entre 8 et 15 chiffres, avec un indicatif optionnel" + + " (+)"; + + /** Code devise ISO */ + public static final String DEVISE_PATTERN = "^[A-Z]{3}$"; + + public static final String DEVISE_MESSAGE = + "La devise doit être un code ISO à 3 lettres majuscules"; + + /** Numéro de référence aide */ + public static final String REFERENCE_AIDE_PATTERN = "^DA-\\d{4}-\\d{6}$"; + + public static final String REFERENCE_AIDE_MESSAGE = + "Le numéro de référence doit suivre le format DA-YYYY-NNNNNN"; + + /** Numéro de membre */ + public static final String NUMERO_MEMBRE_PATTERN = "^UF-\\d{4}-[A-Z0-9]{8}$"; + + public static final String NUMERO_MEMBRE_MESSAGE = + "Format de numéro de membre invalide (UF-YYYY-XXXXXXXX)"; + + /** Couleur hexadécimale */ + public static final String COULEUR_HEX_PATTERN = "^#[0-9A-Fa-f]{6}$"; + + public static final String COULEUR_HEX_MESSAGE = "Format de couleur invalide (format: #RRGGBB)"; + + // === CONTRAINTES NUMÉRIQUES === + + /** Montant minimum */ + public static final String MONTANT_MIN_VALUE = "0.0"; + + public static final String MONTANT_POSITIF_MESSAGE = "Le montant doit être positif"; + + /** Contraintes pour les montants */ + public static final int MONTANT_INTEGER_DIGITS = 10; + + public static final int MONTANT_FRACTION_DIGITS = 2; + public static final String MONTANT_DIGITS_MESSAGE = + "Le montant doit avoir au maximum " + + MONTANT_INTEGER_DIGITS + + " chiffres entiers et " + + MONTANT_FRACTION_DIGITS + + " décimales"; + + // === MESSAGES D'ERREUR STANDARD === + + public static final String OBLIGATOIRE_MESSAGE = " est obligatoire"; + public static final String EMAIL_FORMAT_MESSAGE = "L'adresse email n'est pas valide"; + public static final String DATE_PASSEE_MESSAGE = "La date doit être dans le passé"; + public static final String DATE_FUTURE_MESSAGE = "La date doit être dans le futur"; + + // === CONTRAINTES SPÉCIFIQUES === + + /** Documents joints */ + public static final int DOCUMENTS_JOINTS_MAX_LENGTH = 1000; + + public static final String DOCUMENTS_JOINTS_SIZE_MESSAGE = + "La liste des documents ne peut pas dépasser " + DOCUMENTS_JOINTS_MAX_LENGTH + " caractères"; + + /** Mode de versement */ + public static final int MODE_VERSEMENT_MAX_LENGTH = 50; + + public static final String MODE_VERSEMENT_SIZE_MESSAGE = + "Le mode de versement ne peut pas dépasser " + MODE_VERSEMENT_MAX_LENGTH + " caractères"; + + /** Numéro de transaction */ + public static final int NUMERO_TRANSACTION_MAX_LENGTH = 100; + + public static final String NUMERO_TRANSACTION_SIZE_MESSAGE = + "Le numéro de transaction ne peut pas dépasser " + + NUMERO_TRANSACTION_MAX_LENGTH + + " caractères"; + + /** Numéro d'enregistrement */ + public static final int NUMERO_ENREGISTREMENT_MAX_LENGTH = 100; + + public static final String NUMERO_ENREGISTREMENT_SIZE_MESSAGE = + "Le numéro d'enregistrement ne peut pas dépasser " + + NUMERO_ENREGISTREMENT_MAX_LENGTH + + " caractères"; + + /** Nom court d'organisation */ + public static final int NOM_COURT_MAX_LENGTH = 50; + + public static final String NOM_COURT_SIZE_MESSAGE = + "Le nom court ne peut pas dépasser " + NOM_COURT_MAX_LENGTH + " caractères"; + + /** Instructions et matériel */ + public static final int INSTRUCTIONS_MAX_LENGTH = 500; + + public static final String INSTRUCTIONS_SIZE_MESSAGE = + "Les instructions ne peuvent pas dépasser " + INSTRUCTIONS_MAX_LENGTH + " caractères"; + + /** Conditions météo */ + public static final int CONDITIONS_METEO_MAX_LENGTH = 100; + + public static final String CONDITIONS_METEO_SIZE_MESSAGE = + "Les conditions météo ne peuvent pas dépasser " + CONDITIONS_METEO_MAX_LENGTH + " caractères"; + + // === LCB-FT / Anti-blanchiment (mutuelles) === + + /** Origine des fonds — libellé court (obligatoire au-dessus du seuil configuré) */ + public static final int ORIGINE_FONDS_MAX_LENGTH = 200; + + public static final String ORIGINE_FONDS_SIZE_MESSAGE = + "L'origine des fonds ne peut pas dépasser " + ORIGINE_FONDS_MAX_LENGTH + " caractères"; + + public static final String ORIGINE_FONDS_OBLIGATOIRE_SEUIL_MESSAGE = + "L'origine des fonds est obligatoire pour les opérations au-dessus du seuil LCB-FT configuré"; +} diff --git a/src/main/java/lombok.config b/src/main/java/lombok.config index df71bb6..9d3ccb6 100644 --- a/src/main/java/lombok.config +++ b/src/main/java/lombok.config @@ -1,2 +1,2 @@ -config.stopBubbling = true -lombok.addLombokGeneratedAnnotation = true +config.stopBubbling = true +lombok.addLombokGeneratedAnnotation = true diff --git a/src/test/java/dev/lions/unionflow/server/api/CompilationTest.java b/src/test/java/dev/lions/unionflow/server/api/CompilationTest.java index 3c8b2d6..17c8ef0 100644 --- a/src/test/java/dev/lions/unionflow/server/api/CompilationTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/CompilationTest.java @@ -1,138 +1,138 @@ -package dev.lions.unionflow.server.api; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.dto.evenement.response.EvenementResponse; -import dev.lions.unionflow.server.api.dto.solidarite.response.DemandeAideResponse; -import dev.lions.unionflow.server.api.dto.solidarite.response.PropositionAideResponse; - -import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; -import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; -import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; -import dev.lions.unionflow.server.api.validation.ValidationConstants; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Test de compilation pour vérifier que tous les DTOs compilent correctement - * - * @author UnionFlow Team - * @version 2.0 - * @since 2025-01-16 - */ -@DisplayName("Tests de Compilation") -class CompilationTest { - - @Test - @DisplayName("Test compilation EvenementResponse") - void testCompilationEvenementResponse() { - EvenementResponse evenement = new EvenementResponse(); - evenement.setTitre("Test Formation"); - evenement.setStatut(StatutEvenement.PLANIFIE); - evenement.setPriorite(PrioriteEvenement.NORMALE); - evenement.setTypeEvenement(TypeEvenementMetier.FORMATION); - evenement.setDateDebut(LocalDate.now().plusDays(30)); - - // Test des méthodes métier - assertThat(evenement.estEnCours()).isFalse(); - assertThat(evenement.getStatutLibelle()).isEqualTo("Planifié"); - assertThat(evenement.getTypeEvenementLibelle()).isEqualTo("Formation"); - - // Test des setters - evenement.setStatut(StatutEvenement.CONFIRME); - assertThat(evenement.getStatut()).isEqualTo(StatutEvenement.CONFIRME); - } - - @Test - @DisplayName("Test compilation DemandeAideResponse") - void testCompilationDemandeAideResponse() { - DemandeAideResponse demande = new DemandeAideResponse(); - demande.setTitre("Test Demande"); - demande.setMontantDemande(new BigDecimal("50000")); - - // Test des méthodes métier - assertThat(demande.getId()).isNull(); - assertThat(demande.getVersion()).isNull(); // Unset version is null in BaseResponse - - // Test des setters - demande.setCreePar("testUser"); - assertThat(demande.getCreePar()).isEqualTo("testUser"); - } - - @Test - @DisplayName("Test compilation PropositionAideResponse") - void testCompilationPropositionAideResponse() { - PropositionAideResponse proposition = new PropositionAideResponse(); - proposition.setTitre("Test Proposition"); - proposition.setMontantMaximum(new BigDecimal("100000")); - - // Vérifier que le type est correct - assertThat(proposition.getMontantMaximum()).isInstanceOf(BigDecimal.class); - } - - @Test - @DisplayName("Test compilation ValidationConstants") - void testCompilationValidationConstants() { - // Test que les constantes sont accessibles - assertThat(ValidationConstants.TITRE_MIN_LENGTH).isEqualTo(5); - assertThat(ValidationConstants.TITRE_MAX_LENGTH).isEqualTo(100); - assertThat(ValidationConstants.TELEPHONE_PATTERN).isNotNull(); - assertThat(ValidationConstants.DEVISE_PATTERN).isNotNull(); - } - - @Test - @DisplayName("Test compilation énumérations") - void testCompilationEnumerations() { - // Test StatutEvenement - StatutEvenement statut = StatutEvenement.PLANIFIE; - assertThat(statut.getLibelle()).isEqualTo("Planifié"); - assertThat(statut.permetModification()).isTrue(); - - // Test PrioriteEvenement - PrioriteEvenement priorite = PrioriteEvenement.HAUTE; - assertThat(priorite.getLibelle()).isEqualTo("Haute"); - assertThat(priorite.isUrgente()).isTrue(); // Amélioration TDD : HAUTE est maintenant urgente - - // Test TypeEvenementMetier - TypeEvenementMetier type = TypeEvenementMetier.FORMATION; - assertThat(type.getLibelle()).isEqualTo("Formation"); - } - - @Test - @DisplayName("Test intégration complète") - void testIntegrationComplete() { - // Créer un événement complet - EvenementResponse evenement = new EvenementResponse(); - evenement.setTitre("Formation Leadership"); - evenement.setTypeEvenement(TypeEvenementMetier.FORMATION); - evenement.setDateDebut(LocalDate.now().plusDays(30)); - evenement.setLieu("Centre de Formation"); - evenement.setStatut(StatutEvenement.PLANIFIE); - evenement.setPriorite(PrioriteEvenement.HAUTE); - evenement.setCapaciteMax(50); - evenement.setParticipantsInscrits(0); - evenement.setBudget(new BigDecimal("500000")); - evenement.setCodeDevise("XOF"); - evenement.setAssociationId(UUID.randomUUID()); - - // Vérifier que tout fonctionne - assertThat(evenement.estEnCours()).isFalse(); - assertThat(evenement.estComplet()).isFalse(); - assertThat(evenement.sontInscriptionsOuvertes()).isTrue(); - - // Créer une demande d'aide complète - DemandeAideResponse demande = new DemandeAideResponse(); - demande.setTitre("Aide Médicale Urgente"); - demande.setDescription("Besoin d'aide pour frais médicaux"); - demande.setMontantDemande(new BigDecimal("250000")); - demande.setMembreDemandeurId(UUID.randomUUID()); - demande.setAssociationId(UUID.randomUUID()); - - // Vérifier que tout fonctionne - assertThat(demande.getId()).isNull(); - assertThat(demande.getMontantDemande()).isEqualTo(new BigDecimal("250000")); - } -} +package dev.lions.unionflow.server.api; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.dto.evenement.response.EvenementResponse; +import dev.lions.unionflow.server.api.dto.solidarite.response.DemandeAideResponse; +import dev.lions.unionflow.server.api.dto.solidarite.response.PropositionAideResponse; + +import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; +import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; +import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; +import dev.lions.unionflow.server.api.validation.ValidationConstants; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Test de compilation pour vérifier que tous les DTOs compilent correctement + * + * @author UnionFlow Team + * @version 2.0 + * @since 2025-01-16 + */ +@DisplayName("Tests de Compilation") +class CompilationTest { + + @Test + @DisplayName("Test compilation EvenementResponse") + void testCompilationEvenementResponse() { + EvenementResponse evenement = new EvenementResponse(); + evenement.setTitre("Test Formation"); + evenement.setStatut(StatutEvenement.PLANIFIE); + evenement.setPriorite(PrioriteEvenement.NORMALE); + evenement.setTypeEvenement(TypeEvenementMetier.FORMATION); + evenement.setDateDebut(LocalDate.now().plusDays(30)); + + // Test des méthodes métier + assertThat(evenement.estEnCours()).isFalse(); + assertThat(evenement.getStatutLibelle()).isEqualTo("Planifié"); + assertThat(evenement.getTypeEvenementLibelle()).isEqualTo("Formation"); + + // Test des setters + evenement.setStatut(StatutEvenement.CONFIRME); + assertThat(evenement.getStatut()).isEqualTo(StatutEvenement.CONFIRME); + } + + @Test + @DisplayName("Test compilation DemandeAideResponse") + void testCompilationDemandeAideResponse() { + DemandeAideResponse demande = new DemandeAideResponse(); + demande.setTitre("Test Demande"); + demande.setMontantDemande(new BigDecimal("50000")); + + // Test des méthodes métier + assertThat(demande.getId()).isNull(); + assertThat(demande.getVersion()).isNull(); // Unset version is null in BaseResponse + + // Test des setters + demande.setCreePar("testUser"); + assertThat(demande.getCreePar()).isEqualTo("testUser"); + } + + @Test + @DisplayName("Test compilation PropositionAideResponse") + void testCompilationPropositionAideResponse() { + PropositionAideResponse proposition = new PropositionAideResponse(); + proposition.setTitre("Test Proposition"); + proposition.setMontantMaximum(new BigDecimal("100000")); + + // Vérifier que le type est correct + assertThat(proposition.getMontantMaximum()).isInstanceOf(BigDecimal.class); + } + + @Test + @DisplayName("Test compilation ValidationConstants") + void testCompilationValidationConstants() { + // Test que les constantes sont accessibles + assertThat(ValidationConstants.TITRE_MIN_LENGTH).isEqualTo(5); + assertThat(ValidationConstants.TITRE_MAX_LENGTH).isEqualTo(100); + assertThat(ValidationConstants.TELEPHONE_PATTERN).isNotNull(); + assertThat(ValidationConstants.DEVISE_PATTERN).isNotNull(); + } + + @Test + @DisplayName("Test compilation énumérations") + void testCompilationEnumerations() { + // Test StatutEvenement + StatutEvenement statut = StatutEvenement.PLANIFIE; + assertThat(statut.getLibelle()).isEqualTo("Planifié"); + assertThat(statut.permetModification()).isTrue(); + + // Test PrioriteEvenement + PrioriteEvenement priorite = PrioriteEvenement.HAUTE; + assertThat(priorite.getLibelle()).isEqualTo("Haute"); + assertThat(priorite.isUrgente()).isTrue(); // Amélioration TDD : HAUTE est maintenant urgente + + // Test TypeEvenementMetier + TypeEvenementMetier type = TypeEvenementMetier.FORMATION; + assertThat(type.getLibelle()).isEqualTo("Formation"); + } + + @Test + @DisplayName("Test intégration complète") + void testIntegrationComplete() { + // Créer un événement complet + EvenementResponse evenement = new EvenementResponse(); + evenement.setTitre("Formation Leadership"); + evenement.setTypeEvenement(TypeEvenementMetier.FORMATION); + evenement.setDateDebut(LocalDate.now().plusDays(30)); + evenement.setLieu("Centre de Formation"); + evenement.setStatut(StatutEvenement.PLANIFIE); + evenement.setPriorite(PrioriteEvenement.HAUTE); + evenement.setCapaciteMax(50); + evenement.setParticipantsInscrits(0); + evenement.setBudget(new BigDecimal("500000")); + evenement.setCodeDevise("XOF"); + evenement.setAssociationId(UUID.randomUUID()); + + // Vérifier que tout fonctionne + assertThat(evenement.estEnCours()).isFalse(); + assertThat(evenement.estComplet()).isFalse(); + assertThat(evenement.sontInscriptionsOuvertes()).isTrue(); + + // Créer une demande d'aide complète + DemandeAideResponse demande = new DemandeAideResponse(); + demande.setTitre("Aide Médicale Urgente"); + demande.setDescription("Besoin d'aide pour frais médicaux"); + demande.setMontantDemande(new BigDecimal("250000")); + demande.setMembreDemandeurId(UUID.randomUUID()); + demande.setAssociationId(UUID.randomUUID()); + + // Vérifier que tout fonctionne + assertThat(demande.getId()).isNull(); + assertThat(demande.getMontantDemande()).isEqualTo(new BigDecimal("250000")); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/TestDataFactory.java b/src/test/java/dev/lions/unionflow/server/api/TestDataFactory.java index 3433bd2..8b33910 100644 --- a/src/test/java/dev/lions/unionflow/server/api/TestDataFactory.java +++ b/src/test/java/dev/lions/unionflow/server/api/TestDataFactory.java @@ -1,245 +1,245 @@ -package dev.lions.unionflow.server.api; - -import dev.lions.unionflow.server.api.dto.analytics.AnalyticsDataResponse; -import dev.lions.unionflow.server.api.dto.dashboard.DashboardDataResponse; -import dev.lions.unionflow.server.api.dto.dashboard.DashboardStatsResponse; -import dev.lions.unionflow.server.api.dto.dashboard.RecentActivityResponse; -import dev.lions.unionflow.server.api.dto.dashboard.UpcomingEventResponse; -import dev.lions.unionflow.server.api.dto.membre.request.CreateMembreRequest; -import dev.lions.unionflow.server.api.dto.membre.response.MembreSummaryResponse; -import dev.lions.unionflow.server.api.dto.membre.MembreSearchCriteria; -import dev.lions.unionflow.server.api.dto.membre.MembreSearchResultDTO; -import dev.lions.unionflow.server.api.dto.notification.response.NotificationResponse; -import dev.lions.unionflow.server.api.dto.solidarite.response.CommentaireAideResponse; -import dev.lions.unionflow.server.api.dto.solidarite.response.DemandeAideResponse; -import dev.lions.unionflow.server.api.dto.solidarite.response.EvaluationAideResponse; -import dev.lions.unionflow.server.api.dto.solidarite.response.PropositionAideResponse; -import java.time.LocalDate; -import java.time.LocalDateTime; -import java.util.List; -import java.util.Map; -import java.util.UUID; - -/** - * Factory pour créer des objets de test réutilisables. - * Principe: Write Once, Use Everywhere (WOU) et DRY. - */ -public final class TestDataFactory { - - private TestDataFactory() { - // Utility class - } - - // ===== MEMBRE DTOs ===== - - public static MembreSummaryResponse createMembreSummaryResponse() { - return createMembreSummaryResponse("UF-2025-000001", "Dupont", "Jean", "jean@example.com"); - } - - public static MembreSummaryResponse createMembreSummaryResponse(String numero, String nom, String prenom, - String email) { - return new MembreSummaryResponse( - UUID.randomUUID(), numero, prenom, nom, email, "0102030405", "Profession", "ACTIF", "Actif", "success", true, - List.of("MEMBRE"), null, null, null); - } - - public static CreateMembreRequest createCreateMembreRequest(int age) { - return new CreateMembreRequest( - "Jean", "Dupont", "jean@example.com", "0102030405", "+22501020304", - LocalDate.now().minusYears(age), "Profession", "photo.jpg", "CELIBATAIRE", "Ivoirienne", "CNI", "123456789", - null); // organisationId - optional - } - - // ===== MEMBRE SEARCH CRITERIA ===== - - public static MembreSearchCriteria createMembreSearchCriteria() { - return new MembreSearchCriteria(); - } - - public static MembreSearchCriteria createMembreSearchCriteria(String query) { - MembreSearchCriteria criteria = new MembreSearchCriteria(); - criteria.setQuery(query); - return criteria; - } - - // ===== MEMBRE SEARCH RESULT ===== - - public static MembreSearchResultDTO createMembreSearchResultDTO() { - MembreSearchResultDTO result = new MembreSearchResultDTO(); - result.setMembres(List.of()); - result.setTotalElements(0L); - result.setTotalPages(0); - result.setCurrentPage(0); - result.setPageSize(20); - return result; - } - - public static MembreSearchResultDTO createMembreSearchResultDTO( - List membres, long totalElements, int totalPages, int currentPage) { - MembreSearchResultDTO result = new MembreSearchResultDTO(); - result.setMembres(membres); - result.setTotalElements(totalElements); - result.setTotalPages(totalPages); - result.setCurrentPage(currentPage); - result.setPageSize(20); - result.setNumberOfElements(membres != null ? membres.size() : 0); - result.calculatePaginationFlags(); - return result; - } - - // ===== DASHBOARD DTOs ===== - - public static DashboardStatsResponse createDashboardStatsResponse() { - return DashboardStatsResponse.builder() - .totalMembers(100) - .activeMembers(80) - .totalEvents(50) - .upcomingEvents(10) - .totalContributions(200) - .totalContributionAmount(50000.0) - .pendingRequests(5) - .completedProjects(15) - .monthlyGrowth(5.5) - .engagementRate(0.75) - .lastUpdated(LocalDateTime.now()) - .build(); - } - - public static RecentActivityResponse createRecentActivityResponse() { - return createRecentActivityResponse("member", LocalDateTime.now().minusHours(1)); - } - - public static RecentActivityResponse createRecentActivityResponse(String type, LocalDateTime timestamp) { - return RecentActivityResponse.builder() - .id("act-" + UUID.randomUUID().toString().substring(0, 8)) - .type(type) - .title("Test Activity") - .description("Test Description") - .userName("Test User") - .timestamp(timestamp) - .build(); - } - - public static UpcomingEventResponse createUpcomingEventResponse() { - return createUpcomingEventResponse(LocalDateTime.now().plusDays(1)); - } - - public static UpcomingEventResponse createUpcomingEventResponse(LocalDateTime startDate) { - return UpcomingEventResponse.builder() - .id("event-" + UUID.randomUUID().toString().substring(0, 8)) - .title("Test Event") - .description("Test Description") - .startDate(startDate) - .endDate(startDate != null ? startDate.plusHours(2) : null) - .location("Test Location") - .maxParticipants(100) - .currentParticipants(50) - .status("open") - .build(); - } - - public static DashboardDataResponse createDashboardDataResponse() { - return DashboardDataResponse.builder() - .stats(createDashboardStatsResponse()) - .recentActivities(List.of(createRecentActivityResponse())) - .upcomingEvents(List.of(createUpcomingEventResponse())) - .userPreferences(Map.of("theme", "royal_teal", "language", "fr")) - .organizationId("org-123") - .userId("user-456") - .build(); - } - - // ===== HELPERS POUR DATES ===== - - public static LocalDateTime now() { - return LocalDateTime.now(); - } - - public static LocalDateTime hoursAgo(int hours) { - return now().minusHours(hours); - } - - public static LocalDateTime daysAgo(int days) { - return now().minusDays(days); - } - - public static LocalDateTime daysFromNow(int days) { - return now().plusDays(days); - } - - public static LocalDate date(int year, int month, int day) { - return LocalDate.of(year, month, day); - } - - // ===== NOTIFICATION DTO ===== - - public static NotificationResponse createNotificationResponse() { - NotificationResponse notification = new NotificationResponse(); - notification.setId(UUID.randomUUID()); - notification.setDateCreation(now()); - return notification; - } - - // ===== ANALYTICS DATA DTO ===== - - public static AnalyticsDataResponse createAnalyticsDataResponse() { - return AnalyticsDataResponse.builder() - .dateCalcul(now()) - .dateDebut(now().minusDays(30)) - .dateFin(now()) - .build(); - } - - // ===== SOLIDARITE DTOs ===== - - public static DemandeAideResponse createDemandeAideResponse() { - DemandeAideResponse dto = new DemandeAideResponse(); - dto.setId(UUID.randomUUID()); - dto.setNumeroReference("DA-2025-000001"); - dto.setTypeAide(dev.lions.unionflow.server.api.enums.solidarite.TypeAide.AIDE_FINANCIERE_URGENTE); - dto.setTitre("Aide pour frais médicaux"); - dto.setDescription("Demande d'aide pour couvrir les frais d'hospitalisation"); - dto.setMembreDemandeurId(UUID.randomUUID()); - dto.setNomDemandeur("Jean Dupont"); - dto.setAssociationId(UUID.randomUUID()); - dto.setStatut(dev.lions.unionflow.server.api.enums.solidarite.StatutAide.EN_ATTENTE); - dto.setPriorite(dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide.NORMALE); - return dto; - } - - public static PropositionAideResponse createPropositionAideResponse() { - PropositionAideResponse dto = new PropositionAideResponse(); - dto.setId(UUID.randomUUID()); - dto.setNumeroReference("PA-2025-000001"); - dto.setTypeAide(dev.lions.unionflow.server.api.enums.solidarite.TypeAide.AIDE_FINANCIERE_URGENTE); - dto.setTitre("Proposition d'aide financière"); - dto.setDescription("Je propose une aide financière pour les membres en difficulté"); - dto.setProposantId(UUID.randomUUID().toString()); - dto.setProposantNom("Marie Martin"); - dto.setOrganisationId(UUID.randomUUID().toString()); - return dto; - } - - public static EvaluationAideResponse createEvaluationAideResponse() { - EvaluationAideResponse dto = new EvaluationAideResponse(); - dto.setId(UUID.randomUUID()); - dto.setDemandeAideId(UUID.randomUUID()); - dto.setEvaluateurId(UUID.randomUUID()); - dto.setEvaluateurNom("Évaluateur Test"); - dto.setRoleEvaluateur("beneficiaire"); - dto.setNoteGlobale(4.5); - dto.setCommentairePrincipal("Très satisfait de l'aide reçue"); - dto.setStatut(dev.lions.unionflow.server.api.enums.solidarite.StatutEvaluation.ACTIVE); - return dto; - } - - public static CommentaireAideResponse createCommentaireAideResponse() { - CommentaireAideResponse dto = new CommentaireAideResponse(); - dto.setId(UUID.randomUUID()); - dto.setAuteurId(UUID.randomUUID()); - dto.setAuteurNom("Auteur Test"); - dto.setContenu("Ceci est un commentaire de test"); - dto.setDateCreation(now()); - return dto; - } -} +package dev.lions.unionflow.server.api; + +import dev.lions.unionflow.server.api.dto.analytics.AnalyticsDataResponse; +import dev.lions.unionflow.server.api.dto.dashboard.DashboardDataResponse; +import dev.lions.unionflow.server.api.dto.dashboard.DashboardStatsResponse; +import dev.lions.unionflow.server.api.dto.dashboard.RecentActivityResponse; +import dev.lions.unionflow.server.api.dto.dashboard.UpcomingEventResponse; +import dev.lions.unionflow.server.api.dto.membre.request.CreateMembreRequest; +import dev.lions.unionflow.server.api.dto.membre.response.MembreSummaryResponse; +import dev.lions.unionflow.server.api.dto.membre.MembreSearchCriteria; +import dev.lions.unionflow.server.api.dto.membre.MembreSearchResultDTO; +import dev.lions.unionflow.server.api.dto.notification.response.NotificationResponse; +import dev.lions.unionflow.server.api.dto.solidarite.response.CommentaireAideResponse; +import dev.lions.unionflow.server.api.dto.solidarite.response.DemandeAideResponse; +import dev.lions.unionflow.server.api.dto.solidarite.response.EvaluationAideResponse; +import dev.lions.unionflow.server.api.dto.solidarite.response.PropositionAideResponse; +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.util.List; +import java.util.Map; +import java.util.UUID; + +/** + * Factory pour créer des objets de test réutilisables. + * Principe: Write Once, Use Everywhere (WOU) et DRY. + */ +public final class TestDataFactory { + + private TestDataFactory() { + // Utility class + } + + // ===== MEMBRE DTOs ===== + + public static MembreSummaryResponse createMembreSummaryResponse() { + return createMembreSummaryResponse("UF-2025-000001", "Dupont", "Jean", "jean@example.com"); + } + + public static MembreSummaryResponse createMembreSummaryResponse(String numero, String nom, String prenom, + String email) { + return new MembreSummaryResponse( + UUID.randomUUID(), numero, prenom, nom, email, "0102030405", "Profession", "ACTIF", "Actif", "success", true, + List.of("MEMBRE"), null, null, null); + } + + public static CreateMembreRequest createCreateMembreRequest(int age) { + return new CreateMembreRequest( + "Jean", "Dupont", "jean@example.com", "0102030405", "+22501020304", + LocalDate.now().minusYears(age), "Profession", "photo.jpg", "CELIBATAIRE", "Ivoirienne", "CNI", "123456789", + null); // organisationId - optional + } + + // ===== MEMBRE SEARCH CRITERIA ===== + + public static MembreSearchCriteria createMembreSearchCriteria() { + return new MembreSearchCriteria(); + } + + public static MembreSearchCriteria createMembreSearchCriteria(String query) { + MembreSearchCriteria criteria = new MembreSearchCriteria(); + criteria.setQuery(query); + return criteria; + } + + // ===== MEMBRE SEARCH RESULT ===== + + public static MembreSearchResultDTO createMembreSearchResultDTO() { + MembreSearchResultDTO result = new MembreSearchResultDTO(); + result.setMembres(List.of()); + result.setTotalElements(0L); + result.setTotalPages(0); + result.setCurrentPage(0); + result.setPageSize(20); + return result; + } + + public static MembreSearchResultDTO createMembreSearchResultDTO( + List membres, long totalElements, int totalPages, int currentPage) { + MembreSearchResultDTO result = new MembreSearchResultDTO(); + result.setMembres(membres); + result.setTotalElements(totalElements); + result.setTotalPages(totalPages); + result.setCurrentPage(currentPage); + result.setPageSize(20); + result.setNumberOfElements(membres != null ? membres.size() : 0); + result.calculatePaginationFlags(); + return result; + } + + // ===== DASHBOARD DTOs ===== + + public static DashboardStatsResponse createDashboardStatsResponse() { + return DashboardStatsResponse.builder() + .totalMembers(100) + .activeMembers(80) + .totalEvents(50) + .upcomingEvents(10) + .totalContributions(200) + .totalContributionAmount(50000.0) + .pendingRequests(5) + .completedProjects(15) + .monthlyGrowth(5.5) + .engagementRate(0.75) + .lastUpdated(LocalDateTime.now()) + .build(); + } + + public static RecentActivityResponse createRecentActivityResponse() { + return createRecentActivityResponse("member", LocalDateTime.now().minusHours(1)); + } + + public static RecentActivityResponse createRecentActivityResponse(String type, LocalDateTime timestamp) { + return RecentActivityResponse.builder() + .id("act-" + UUID.randomUUID().toString().substring(0, 8)) + .type(type) + .title("Test Activity") + .description("Test Description") + .userName("Test User") + .timestamp(timestamp) + .build(); + } + + public static UpcomingEventResponse createUpcomingEventResponse() { + return createUpcomingEventResponse(LocalDateTime.now().plusDays(1)); + } + + public static UpcomingEventResponse createUpcomingEventResponse(LocalDateTime startDate) { + return UpcomingEventResponse.builder() + .id("event-" + UUID.randomUUID().toString().substring(0, 8)) + .title("Test Event") + .description("Test Description") + .startDate(startDate) + .endDate(startDate != null ? startDate.plusHours(2) : null) + .location("Test Location") + .maxParticipants(100) + .currentParticipants(50) + .status("open") + .build(); + } + + public static DashboardDataResponse createDashboardDataResponse() { + return DashboardDataResponse.builder() + .stats(createDashboardStatsResponse()) + .recentActivities(List.of(createRecentActivityResponse())) + .upcomingEvents(List.of(createUpcomingEventResponse())) + .userPreferences(Map.of("theme", "royal_teal", "language", "fr")) + .organizationId("org-123") + .userId("user-456") + .build(); + } + + // ===== HELPERS POUR DATES ===== + + public static LocalDateTime now() { + return LocalDateTime.now(); + } + + public static LocalDateTime hoursAgo(int hours) { + return now().minusHours(hours); + } + + public static LocalDateTime daysAgo(int days) { + return now().minusDays(days); + } + + public static LocalDateTime daysFromNow(int days) { + return now().plusDays(days); + } + + public static LocalDate date(int year, int month, int day) { + return LocalDate.of(year, month, day); + } + + // ===== NOTIFICATION DTO ===== + + public static NotificationResponse createNotificationResponse() { + NotificationResponse notification = new NotificationResponse(); + notification.setId(UUID.randomUUID()); + notification.setDateCreation(now()); + return notification; + } + + // ===== ANALYTICS DATA DTO ===== + + public static AnalyticsDataResponse createAnalyticsDataResponse() { + return AnalyticsDataResponse.builder() + .dateCalcul(now()) + .dateDebut(now().minusDays(30)) + .dateFin(now()) + .build(); + } + + // ===== SOLIDARITE DTOs ===== + + public static DemandeAideResponse createDemandeAideResponse() { + DemandeAideResponse dto = new DemandeAideResponse(); + dto.setId(UUID.randomUUID()); + dto.setNumeroReference("DA-2025-000001"); + dto.setTypeAide(dev.lions.unionflow.server.api.enums.solidarite.TypeAide.AIDE_FINANCIERE_URGENTE); + dto.setTitre("Aide pour frais médicaux"); + dto.setDescription("Demande d'aide pour couvrir les frais d'hospitalisation"); + dto.setMembreDemandeurId(UUID.randomUUID()); + dto.setNomDemandeur("Jean Dupont"); + dto.setAssociationId(UUID.randomUUID()); + dto.setStatut(dev.lions.unionflow.server.api.enums.solidarite.StatutAide.EN_ATTENTE); + dto.setPriorite(dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide.NORMALE); + return dto; + } + + public static PropositionAideResponse createPropositionAideResponse() { + PropositionAideResponse dto = new PropositionAideResponse(); + dto.setId(UUID.randomUUID()); + dto.setNumeroReference("PA-2025-000001"); + dto.setTypeAide(dev.lions.unionflow.server.api.enums.solidarite.TypeAide.AIDE_FINANCIERE_URGENTE); + dto.setTitre("Proposition d'aide financière"); + dto.setDescription("Je propose une aide financière pour les membres en difficulté"); + dto.setProposantId(UUID.randomUUID().toString()); + dto.setProposantNom("Marie Martin"); + dto.setOrganisationId(UUID.randomUUID().toString()); + return dto; + } + + public static EvaluationAideResponse createEvaluationAideResponse() { + EvaluationAideResponse dto = new EvaluationAideResponse(); + dto.setId(UUID.randomUUID()); + dto.setDemandeAideId(UUID.randomUUID()); + dto.setEvaluateurId(UUID.randomUUID()); + dto.setEvaluateurNom("Évaluateur Test"); + dto.setRoleEvaluateur("beneficiaire"); + dto.setNoteGlobale(4.5); + dto.setCommentairePrincipal("Très satisfait de l'aide reçue"); + dto.setStatut(dev.lions.unionflow.server.api.enums.solidarite.StatutEvaluation.ACTIVE); + return dto; + } + + public static CommentaireAideResponse createCommentaireAideResponse() { + CommentaireAideResponse dto = new CommentaireAideResponse(); + dto.setId(UUID.randomUUID()); + dto.setAuteurId(UUID.randomUUID()); + dto.setAuteurNom("Auteur Test"); + dto.setContenu("Ceci est un commentaire de test"); + dto.setDateCreation(now()); + return dto; + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/abonnement/request/CreateAbonnementRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/abonnement/request/CreateAbonnementRequestTest.java index c686a9c..a621d16 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/abonnement/request/CreateAbonnementRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/abonnement/request/CreateAbonnementRequestTest.java @@ -1,307 +1,307 @@ -package dev.lions.unionflow.server.api.dto.abonnement.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; -import dev.lions.unionflow.server.api.enums.abonnement.TypePeriodeAbonnement; -import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateAbonnementRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID organisationId = UUID.randomUUID(); - UUID formulaireId = UUID.randomUUID(); - UUID responsableId = UUID.randomUUID(); - LocalDate dateDebut = LocalDate.now(); - LocalDate dateFin = LocalDate.now().plusMonths(12); - LocalDate dateProchainePeriode = LocalDate.now().plusMonths(1); - LocalDate dateFinEssai = LocalDate.now().plusDays(30); - - CreateAbonnementRequest request = CreateAbonnementRequest.builder() - .numeroReference("ABO-2026-TEST1234") - .organisationId(organisationId) - .nomOrganisation("Test Org") - .formulaireId(formulaireId) - .codeFormule("PREMIUM") - .nomFormule("Premium Formula") - .typeFormule(TypeFormule.PREMIUM) - .statut(StatutAbonnement.ACTIF) - .typeAbonnement(TypePeriodeAbonnement.MENSUEL) - .dateDebut(dateDebut) - .dateFin(dateFin) - .dateProchainePeriode(dateProchainePeriode) - .montant(new BigDecimal("10000.00")) - .devise("XOF") - .remise(new BigDecimal("10.00")) - .montantFinal(new BigDecimal("9000.00")) - .renouvellementAutomatique(true) - .periodeEssaiUtilisee(true) - .dateFinEssai(dateFinEssai) - .maxMembres(100) - .nombreMembresActuels(50) - .espaceStockageGB(new BigDecimal("100.00")) - .espaceStockageUtilise(new BigDecimal("25.50")) - .supportTechnique(true) - .niveauSupport("PREMIUM") - .fonctionnalitesAvancees(true) - .apiAccess(true) - .rapportsPersonnalises(true) - .integrationsTierces(true) - .responsableId(responsableId) - .nomResponsable("John Doe") - .emailResponsable("john@example.com") - .telephoneResponsable("+221771234567") - .modePaiementPrefere("WAVE_MONEY") - .numeroPaiementMobile("+221771234567") - .historiquePaiements("Paiements réguliers") - .notes("Notes importantes") - .alertesActivees(true) - .notificationsEmail(true) - .notificationsSMS(true) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroReference()).isEqualTo("ABO-2026-TEST1234"); - assertThat(request.organisationId()).isEqualTo(organisationId); - assertThat(request.nomOrganisation()).isEqualTo("Test Org"); - assertThat(request.formulaireId()).isEqualTo(formulaireId); - assertThat(request.codeFormule()).isEqualTo("PREMIUM"); - assertThat(request.nomFormule()).isEqualTo("Premium Formula"); - assertThat(request.typeFormule()).isEqualTo(TypeFormule.PREMIUM); - assertThat(request.statut()).isEqualTo(StatutAbonnement.ACTIF); - assertThat(request.typeAbonnement()).isEqualTo(TypePeriodeAbonnement.MENSUEL); - assertThat(request.dateDebut()).isEqualTo(dateDebut); - assertThat(request.dateFin()).isEqualTo(dateFin); - assertThat(request.dateProchainePeriode()).isEqualTo(dateProchainePeriode); - assertThat(request.montant()).isEqualByComparingTo(new BigDecimal("10000.00")); - assertThat(request.devise()).isEqualTo("XOF"); - assertThat(request.remise()).isEqualByComparingTo(new BigDecimal("10.00")); - assertThat(request.montantFinal()).isEqualByComparingTo(new BigDecimal("9000.00")); - assertThat(request.renouvellementAutomatique()).isTrue(); - assertThat(request.periodeEssaiUtilisee()).isTrue(); - assertThat(request.dateFinEssai()).isEqualTo(dateFinEssai); - assertThat(request.maxMembres()).isEqualTo(100); - assertThat(request.nombreMembresActuels()).isEqualTo(50); - assertThat(request.espaceStockageGB()).isEqualByComparingTo(new BigDecimal("100.00")); - assertThat(request.espaceStockageUtilise()).isEqualByComparingTo(new BigDecimal("25.50")); - assertThat(request.supportTechnique()).isTrue(); - assertThat(request.niveauSupport()).isEqualTo("PREMIUM"); - assertThat(request.fonctionnalitesAvancees()).isTrue(); - assertThat(request.apiAccess()).isTrue(); - assertThat(request.rapportsPersonnalises()).isTrue(); - assertThat(request.integrationsTierces()).isTrue(); - assertThat(request.responsableId()).isEqualTo(responsableId); - assertThat(request.nomResponsable()).isEqualTo("John Doe"); - assertThat(request.emailResponsable()).isEqualTo("john@example.com"); - assertThat(request.telephoneResponsable()).isEqualTo("+221771234567"); - assertThat(request.modePaiementPrefere()).isEqualTo("WAVE_MONEY"); - assertThat(request.numeroPaiementMobile()).isEqualTo("+221771234567"); - assertThat(request.historiquePaiements()).isEqualTo("Paiements réguliers"); - assertThat(request.notes()).isEqualTo("Notes importantes"); - assertThat(request.alertesActivees()).isTrue(); - assertThat(request.notificationsEmail()).isTrue(); - assertThat(request.notificationsSMS()).isTrue(); - } - - @Test - void testBuilder_MinimalFields() { - UUID organisationId = UUID.randomUUID(); - UUID formulaireId = UUID.randomUUID(); - LocalDate dateDebut = LocalDate.now(); - LocalDate dateFin = LocalDate.now().plusMonths(12); - - CreateAbonnementRequest request = CreateAbonnementRequest.builder() - .numeroReference("ABO-2026-TEST9999") - .organisationId(organisationId) - .formulaireId(formulaireId) - .statut(StatutAbonnement.ACTIF) - .typeAbonnement(TypePeriodeAbonnement.ANNUEL) - .dateDebut(dateDebut) - .dateFin(dateFin) - .montant(new BigDecimal("5000.00")) - .devise("XOF") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroReference()).isEqualTo("ABO-2026-TEST9999"); - assertThat(request.organisationId()).isEqualTo(organisationId); - assertThat(request.formulaireId()).isEqualTo(formulaireId); - assertThat(request.statut()).isEqualTo(StatutAbonnement.ACTIF); - assertThat(request.typeAbonnement()).isEqualTo(TypePeriodeAbonnement.ANNUEL); - assertThat(request.dateDebut()).isEqualTo(dateDebut); - assertThat(request.montant()).isEqualByComparingTo(new BigDecimal("5000.00")); - assertThat(request.devise()).isEqualTo("XOF"); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateAbonnementRequest request = CreateAbonnementRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroReference")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("organisationId")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("formulaireId")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("statut")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeAbonnement")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateDebut")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montant")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); - } - - @Test - void testValidation_InvalidNumeroReference() { - CreateAbonnementRequest request = CreateAbonnementRequest.builder() - .numeroReference("INVALID") - .organisationId(UUID.randomUUID()) - .formulaireId(UUID.randomUUID()) - .statut(StatutAbonnement.ACTIF) - .typeAbonnement(TypePeriodeAbonnement.MENSUEL) - .dateDebut(LocalDate.now()) - .dateFin(LocalDate.now().plusMonths(12)) - .montant(new BigDecimal("1000.00")) - .devise("XOF") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroReference")); - } - - @Test - void testValidation_InvalidDevise() { - CreateAbonnementRequest request = CreateAbonnementRequest.builder() - .numeroReference("ABO-2026-TEST1234") - .organisationId(UUID.randomUUID()) - .formulaireId(UUID.randomUUID()) - .statut(StatutAbonnement.ACTIF) - .typeAbonnement(TypePeriodeAbonnement.MENSUEL) - .dateDebut(LocalDate.now()) - .dateFin(LocalDate.now().plusMonths(12)) - .montant(new BigDecimal("1000.00")) - .devise("INVALID") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); - } - - @Test - void testValidation_MontantZero() { - CreateAbonnementRequest request = CreateAbonnementRequest.builder() - .numeroReference("ABO-2026-TEST1234") - .organisationId(UUID.randomUUID()) - .formulaireId(UUID.randomUUID()) - .statut(StatutAbonnement.ACTIF) - .typeAbonnement(TypePeriodeAbonnement.MENSUEL) - .dateDebut(LocalDate.now()) - .dateFin(LocalDate.now().plusMonths(12)) - .montant(BigDecimal.ZERO) - .devise("XOF") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montant")); - } - - @Test - void testValidation_ValidFields() { - CreateAbonnementRequest request = CreateAbonnementRequest.builder() - .numeroReference("ABO-2026-TEST1234") - .organisationId(UUID.randomUUID()) - .formulaireId(UUID.randomUUID()) - .statut(StatutAbonnement.ACTIF) - .typeAbonnement(TypePeriodeAbonnement.MENSUEL) - .dateDebut(LocalDate.now()) - .dateFin(LocalDate.now().plusMonths(12)) - .montant(new BigDecimal("1000.00")) - .devise("XOF") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID organisationId = UUID.randomUUID(); - UUID formulaireId = UUID.randomUUID(); - LocalDate dateDebut = LocalDate.now(); - LocalDate dateFin = LocalDate.now().plusMonths(12); - - CreateAbonnementRequest request1 = CreateAbonnementRequest.builder() - .numeroReference("ABO-2026-TEST1234") - .organisationId(organisationId) - .formulaireId(formulaireId) - .statut(StatutAbonnement.ACTIF) - .typeAbonnement(TypePeriodeAbonnement.MENSUEL) - .dateDebut(dateDebut) - .dateFin(dateFin) - .montant(new BigDecimal("1000.00")) - .devise("XOF") - .build(); - - CreateAbonnementRequest request2 = CreateAbonnementRequest.builder() - .numeroReference("ABO-2026-TEST1234") - .organisationId(organisationId) - .formulaireId(formulaireId) - .statut(StatutAbonnement.ACTIF) - .typeAbonnement(TypePeriodeAbonnement.MENSUEL) - .dateDebut(dateDebut) - .dateFin(dateFin) - .montant(new BigDecimal("1000.00")) - .devise("XOF") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateAbonnementRequest request = CreateAbonnementRequest.builder() - .numeroReference("ABO-2026-TEST1234") - .organisationId(UUID.randomUUID()) - .formulaireId(UUID.randomUUID()) - .statut(StatutAbonnement.ACTIF) - .typeAbonnement(TypePeriodeAbonnement.MENSUEL) - .dateDebut(LocalDate.now()) - .dateFin(LocalDate.now().plusMonths(12)) - .montant(new BigDecimal("1000.00")) - .devise("XOF") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateAbonnementRequest"); - assertThat(toString).contains("ABO-2026-TEST1234"); - assertThat(toString).contains("ACTIF"); - } -} +package dev.lions.unionflow.server.api.dto.abonnement.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; +import dev.lions.unionflow.server.api.enums.abonnement.TypePeriodeAbonnement; +import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateAbonnementRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID organisationId = UUID.randomUUID(); + UUID formulaireId = UUID.randomUUID(); + UUID responsableId = UUID.randomUUID(); + LocalDate dateDebut = LocalDate.now(); + LocalDate dateFin = LocalDate.now().plusMonths(12); + LocalDate dateProchainePeriode = LocalDate.now().plusMonths(1); + LocalDate dateFinEssai = LocalDate.now().plusDays(30); + + CreateAbonnementRequest request = CreateAbonnementRequest.builder() + .numeroReference("ABO-2026-TEST1234") + .organisationId(organisationId) + .nomOrganisation("Test Org") + .formulaireId(formulaireId) + .codeFormule("PREMIUM") + .nomFormule("Premium Formula") + .typeFormule(TypeFormule.PREMIUM) + .statut(StatutAbonnement.ACTIF) + .typeAbonnement(TypePeriodeAbonnement.MENSUEL) + .dateDebut(dateDebut) + .dateFin(dateFin) + .dateProchainePeriode(dateProchainePeriode) + .montant(new BigDecimal("10000.00")) + .devise("XOF") + .remise(new BigDecimal("10.00")) + .montantFinal(new BigDecimal("9000.00")) + .renouvellementAutomatique(true) + .periodeEssaiUtilisee(true) + .dateFinEssai(dateFinEssai) + .maxMembres(100) + .nombreMembresActuels(50) + .espaceStockageGB(new BigDecimal("100.00")) + .espaceStockageUtilise(new BigDecimal("25.50")) + .supportTechnique(true) + .niveauSupport("PREMIUM") + .fonctionnalitesAvancees(true) + .apiAccess(true) + .rapportsPersonnalises(true) + .integrationsTierces(true) + .responsableId(responsableId) + .nomResponsable("John Doe") + .emailResponsable("john@example.com") + .telephoneResponsable("+221771234567") + .modePaiementPrefere("WAVE_MONEY") + .numeroPaiementMobile("+221771234567") + .historiquePaiements("Paiements réguliers") + .notes("Notes importantes") + .alertesActivees(true) + .notificationsEmail(true) + .notificationsSMS(true) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroReference()).isEqualTo("ABO-2026-TEST1234"); + assertThat(request.organisationId()).isEqualTo(organisationId); + assertThat(request.nomOrganisation()).isEqualTo("Test Org"); + assertThat(request.formulaireId()).isEqualTo(formulaireId); + assertThat(request.codeFormule()).isEqualTo("PREMIUM"); + assertThat(request.nomFormule()).isEqualTo("Premium Formula"); + assertThat(request.typeFormule()).isEqualTo(TypeFormule.PREMIUM); + assertThat(request.statut()).isEqualTo(StatutAbonnement.ACTIF); + assertThat(request.typeAbonnement()).isEqualTo(TypePeriodeAbonnement.MENSUEL); + assertThat(request.dateDebut()).isEqualTo(dateDebut); + assertThat(request.dateFin()).isEqualTo(dateFin); + assertThat(request.dateProchainePeriode()).isEqualTo(dateProchainePeriode); + assertThat(request.montant()).isEqualByComparingTo(new BigDecimal("10000.00")); + assertThat(request.devise()).isEqualTo("XOF"); + assertThat(request.remise()).isEqualByComparingTo(new BigDecimal("10.00")); + assertThat(request.montantFinal()).isEqualByComparingTo(new BigDecimal("9000.00")); + assertThat(request.renouvellementAutomatique()).isTrue(); + assertThat(request.periodeEssaiUtilisee()).isTrue(); + assertThat(request.dateFinEssai()).isEqualTo(dateFinEssai); + assertThat(request.maxMembres()).isEqualTo(100); + assertThat(request.nombreMembresActuels()).isEqualTo(50); + assertThat(request.espaceStockageGB()).isEqualByComparingTo(new BigDecimal("100.00")); + assertThat(request.espaceStockageUtilise()).isEqualByComparingTo(new BigDecimal("25.50")); + assertThat(request.supportTechnique()).isTrue(); + assertThat(request.niveauSupport()).isEqualTo("PREMIUM"); + assertThat(request.fonctionnalitesAvancees()).isTrue(); + assertThat(request.apiAccess()).isTrue(); + assertThat(request.rapportsPersonnalises()).isTrue(); + assertThat(request.integrationsTierces()).isTrue(); + assertThat(request.responsableId()).isEqualTo(responsableId); + assertThat(request.nomResponsable()).isEqualTo("John Doe"); + assertThat(request.emailResponsable()).isEqualTo("john@example.com"); + assertThat(request.telephoneResponsable()).isEqualTo("+221771234567"); + assertThat(request.modePaiementPrefere()).isEqualTo("WAVE_MONEY"); + assertThat(request.numeroPaiementMobile()).isEqualTo("+221771234567"); + assertThat(request.historiquePaiements()).isEqualTo("Paiements réguliers"); + assertThat(request.notes()).isEqualTo("Notes importantes"); + assertThat(request.alertesActivees()).isTrue(); + assertThat(request.notificationsEmail()).isTrue(); + assertThat(request.notificationsSMS()).isTrue(); + } + + @Test + void testBuilder_MinimalFields() { + UUID organisationId = UUID.randomUUID(); + UUID formulaireId = UUID.randomUUID(); + LocalDate dateDebut = LocalDate.now(); + LocalDate dateFin = LocalDate.now().plusMonths(12); + + CreateAbonnementRequest request = CreateAbonnementRequest.builder() + .numeroReference("ABO-2026-TEST9999") + .organisationId(organisationId) + .formulaireId(formulaireId) + .statut(StatutAbonnement.ACTIF) + .typeAbonnement(TypePeriodeAbonnement.ANNUEL) + .dateDebut(dateDebut) + .dateFin(dateFin) + .montant(new BigDecimal("5000.00")) + .devise("XOF") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroReference()).isEqualTo("ABO-2026-TEST9999"); + assertThat(request.organisationId()).isEqualTo(organisationId); + assertThat(request.formulaireId()).isEqualTo(formulaireId); + assertThat(request.statut()).isEqualTo(StatutAbonnement.ACTIF); + assertThat(request.typeAbonnement()).isEqualTo(TypePeriodeAbonnement.ANNUEL); + assertThat(request.dateDebut()).isEqualTo(dateDebut); + assertThat(request.montant()).isEqualByComparingTo(new BigDecimal("5000.00")); + assertThat(request.devise()).isEqualTo("XOF"); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateAbonnementRequest request = CreateAbonnementRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroReference")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("organisationId")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("formulaireId")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("statut")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeAbonnement")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateDebut")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montant")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); + } + + @Test + void testValidation_InvalidNumeroReference() { + CreateAbonnementRequest request = CreateAbonnementRequest.builder() + .numeroReference("INVALID") + .organisationId(UUID.randomUUID()) + .formulaireId(UUID.randomUUID()) + .statut(StatutAbonnement.ACTIF) + .typeAbonnement(TypePeriodeAbonnement.MENSUEL) + .dateDebut(LocalDate.now()) + .dateFin(LocalDate.now().plusMonths(12)) + .montant(new BigDecimal("1000.00")) + .devise("XOF") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroReference")); + } + + @Test + void testValidation_InvalidDevise() { + CreateAbonnementRequest request = CreateAbonnementRequest.builder() + .numeroReference("ABO-2026-TEST1234") + .organisationId(UUID.randomUUID()) + .formulaireId(UUID.randomUUID()) + .statut(StatutAbonnement.ACTIF) + .typeAbonnement(TypePeriodeAbonnement.MENSUEL) + .dateDebut(LocalDate.now()) + .dateFin(LocalDate.now().plusMonths(12)) + .montant(new BigDecimal("1000.00")) + .devise("INVALID") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); + } + + @Test + void testValidation_MontantZero() { + CreateAbonnementRequest request = CreateAbonnementRequest.builder() + .numeroReference("ABO-2026-TEST1234") + .organisationId(UUID.randomUUID()) + .formulaireId(UUID.randomUUID()) + .statut(StatutAbonnement.ACTIF) + .typeAbonnement(TypePeriodeAbonnement.MENSUEL) + .dateDebut(LocalDate.now()) + .dateFin(LocalDate.now().plusMonths(12)) + .montant(BigDecimal.ZERO) + .devise("XOF") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montant")); + } + + @Test + void testValidation_ValidFields() { + CreateAbonnementRequest request = CreateAbonnementRequest.builder() + .numeroReference("ABO-2026-TEST1234") + .organisationId(UUID.randomUUID()) + .formulaireId(UUID.randomUUID()) + .statut(StatutAbonnement.ACTIF) + .typeAbonnement(TypePeriodeAbonnement.MENSUEL) + .dateDebut(LocalDate.now()) + .dateFin(LocalDate.now().plusMonths(12)) + .montant(new BigDecimal("1000.00")) + .devise("XOF") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID organisationId = UUID.randomUUID(); + UUID formulaireId = UUID.randomUUID(); + LocalDate dateDebut = LocalDate.now(); + LocalDate dateFin = LocalDate.now().plusMonths(12); + + CreateAbonnementRequest request1 = CreateAbonnementRequest.builder() + .numeroReference("ABO-2026-TEST1234") + .organisationId(organisationId) + .formulaireId(formulaireId) + .statut(StatutAbonnement.ACTIF) + .typeAbonnement(TypePeriodeAbonnement.MENSUEL) + .dateDebut(dateDebut) + .dateFin(dateFin) + .montant(new BigDecimal("1000.00")) + .devise("XOF") + .build(); + + CreateAbonnementRequest request2 = CreateAbonnementRequest.builder() + .numeroReference("ABO-2026-TEST1234") + .organisationId(organisationId) + .formulaireId(formulaireId) + .statut(StatutAbonnement.ACTIF) + .typeAbonnement(TypePeriodeAbonnement.MENSUEL) + .dateDebut(dateDebut) + .dateFin(dateFin) + .montant(new BigDecimal("1000.00")) + .devise("XOF") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateAbonnementRequest request = CreateAbonnementRequest.builder() + .numeroReference("ABO-2026-TEST1234") + .organisationId(UUID.randomUUID()) + .formulaireId(UUID.randomUUID()) + .statut(StatutAbonnement.ACTIF) + .typeAbonnement(TypePeriodeAbonnement.MENSUEL) + .dateDebut(LocalDate.now()) + .dateFin(LocalDate.now().plusMonths(12)) + .montant(new BigDecimal("1000.00")) + .devise("XOF") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateAbonnementRequest"); + assertThat(toString).contains("ABO-2026-TEST1234"); + assertThat(toString).contains("ACTIF"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/abonnement/request/UpdateAbonnementRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/abonnement/request/UpdateAbonnementRequestTest.java index 67374a3..27af2b9 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/abonnement/request/UpdateAbonnementRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/abonnement/request/UpdateAbonnementRequestTest.java @@ -1,219 +1,219 @@ -package dev.lions.unionflow.server.api.dto.abonnement.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; -import dev.lions.unionflow.server.api.enums.abonnement.TypePeriodeAbonnement; -import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateAbonnementRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID organisationId = UUID.randomUUID(); - UUID formulaireId = UUID.randomUUID(); - UUID responsableId = UUID.randomUUID(); - LocalDate dateDebut = LocalDate.now(); - LocalDate dateFin = LocalDate.now().plusMonths(12); - LocalDate dateProchainePeriode = LocalDate.now().plusMonths(1); - LocalDate dateFinEssai = LocalDate.now().plusDays(30); - - UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() - .numeroReference("ABO-2026-TEST1234") - .organisationId(organisationId) - .nomOrganisation("Test Org") - .formulaireId(formulaireId) - .codeFormule("PREMIUM") - .nomFormule("Premium Formula") - .typeFormule(TypeFormule.PREMIUM) - .statut(StatutAbonnement.ACTIF) - .typeAbonnement(TypePeriodeAbonnement.MENSUEL) - .dateDebut(dateDebut) - .dateFin(dateFin) - .dateProchainePeriode(dateProchainePeriode) - .montant(new BigDecimal("10000.00")) - .devise("XOF") - .remise(new BigDecimal("10.00")) - .montantFinal(new BigDecimal("9000.00")) - .renouvellementAutomatique(true) - .periodeEssaiUtilisee(true) - .dateFinEssai(dateFinEssai) - .maxMembres(100) - .nombreMembresActuels(50) - .espaceStockageGB(new BigDecimal("100.00")) - .espaceStockageUtilise(new BigDecimal("25.50")) - .supportTechnique(true) - .niveauSupport("PREMIUM") - .fonctionnalitesAvancees(true) - .apiAccess(true) - .rapportsPersonnalises(true) - .integrationsTierces(true) - .responsableId(responsableId) - .nomResponsable("John Doe") - .emailResponsable("john@example.com") - .telephoneResponsable("+221771234567") - .modePaiementPrefere("WAVE_MONEY") - .numeroPaiementMobile("+221771234567") - .historiquePaiements("Paiements réguliers") - .notes("Notes importantes") - .alertesActivees(true) - .notificationsEmail(true) - .notificationsSMS(true) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroReference()).isEqualTo("ABO-2026-TEST1234"); - assertThat(request.organisationId()).isEqualTo(organisationId); - assertThat(request.nomOrganisation()).isEqualTo("Test Org"); - assertThat(request.formulaireId()).isEqualTo(formulaireId); - assertThat(request.codeFormule()).isEqualTo("PREMIUM"); - assertThat(request.nomFormule()).isEqualTo("Premium Formula"); - assertThat(request.typeFormule()).isEqualTo(TypeFormule.PREMIUM); - assertThat(request.statut()).isEqualTo(StatutAbonnement.ACTIF); - assertThat(request.typeAbonnement()).isEqualTo(TypePeriodeAbonnement.MENSUEL); - assertThat(request.dateDebut()).isEqualTo(dateDebut); - assertThat(request.dateFin()).isEqualTo(dateFin); - assertThat(request.dateProchainePeriode()).isEqualTo(dateProchainePeriode); - assertThat(request.montant()).isEqualByComparingTo(new BigDecimal("10000.00")); - assertThat(request.devise()).isEqualTo("XOF"); - assertThat(request.remise()).isEqualByComparingTo(new BigDecimal("10.00")); - assertThat(request.montantFinal()).isEqualByComparingTo(new BigDecimal("9000.00")); - assertThat(request.renouvellementAutomatique()).isTrue(); - assertThat(request.periodeEssaiUtilisee()).isTrue(); - assertThat(request.dateFinEssai()).isEqualTo(dateFinEssai); - assertThat(request.maxMembres()).isEqualTo(100); - assertThat(request.nombreMembresActuels()).isEqualTo(50); - assertThat(request.espaceStockageGB()).isEqualByComparingTo(new BigDecimal("100.00")); - assertThat(request.espaceStockageUtilise()).isEqualByComparingTo(new BigDecimal("25.50")); - assertThat(request.supportTechnique()).isTrue(); - assertThat(request.niveauSupport()).isEqualTo("PREMIUM"); - assertThat(request.fonctionnalitesAvancees()).isTrue(); - assertThat(request.apiAccess()).isTrue(); - assertThat(request.rapportsPersonnalises()).isTrue(); - assertThat(request.integrationsTierces()).isTrue(); - assertThat(request.responsableId()).isEqualTo(responsableId); - assertThat(request.nomResponsable()).isEqualTo("John Doe"); - assertThat(request.emailResponsable()).isEqualTo("john@example.com"); - assertThat(request.telephoneResponsable()).isEqualTo("+221771234567"); - assertThat(request.modePaiementPrefere()).isEqualTo("WAVE_MONEY"); - assertThat(request.numeroPaiementMobile()).isEqualTo("+221771234567"); - assertThat(request.historiquePaiements()).isEqualTo("Paiements réguliers"); - assertThat(request.notes()).isEqualTo("Notes importantes"); - assertThat(request.alertesActivees()).isTrue(); - assertThat(request.notificationsEmail()).isTrue(); - assertThat(request.notificationsSMS()).isTrue(); - } - - @Test - void testBuilder_MinimalFields() { - UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() - .statut(StatutAbonnement.SUSPENDU) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.statut()).isEqualTo(StatutAbonnement.SUSPENDU); - } - - @Test - void testValidation_InvalidNumeroReference() { - UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() - .numeroReference("INVALID") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroReference")); - } - - @Test - void testValidation_InvalidDevise() { - UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() - .devise("INVALID") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); - } - - @Test - void testValidation_MontantZero() { - UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() - .montant(BigDecimal.ZERO) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montant")); - } - - @Test - void testValidation_ValidFields() { - UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() - .numeroReference("ABO-2026-TEST1234") - .statut(StatutAbonnement.ACTIF) - .montant(new BigDecimal("1000.00")) - .devise("XOF") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID organisationId = UUID.randomUUID(); - - UpdateAbonnementRequest request1 = UpdateAbonnementRequest.builder() - .numeroReference("ABO-2026-TEST1234") - .organisationId(organisationId) - .statut(StatutAbonnement.ACTIF) - .build(); - - UpdateAbonnementRequest request2 = UpdateAbonnementRequest.builder() - .numeroReference("ABO-2026-TEST1234") - .organisationId(organisationId) - .statut(StatutAbonnement.ACTIF) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() - .numeroReference("ABO-2026-TEST1234") - .statut(StatutAbonnement.ACTIF) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateAbonnementRequest"); - assertThat(toString).contains("ABO-2026-TEST1234"); - assertThat(toString).contains("ACTIF"); - } -} +package dev.lions.unionflow.server.api.dto.abonnement.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; +import dev.lions.unionflow.server.api.enums.abonnement.TypePeriodeAbonnement; +import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateAbonnementRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID organisationId = UUID.randomUUID(); + UUID formulaireId = UUID.randomUUID(); + UUID responsableId = UUID.randomUUID(); + LocalDate dateDebut = LocalDate.now(); + LocalDate dateFin = LocalDate.now().plusMonths(12); + LocalDate dateProchainePeriode = LocalDate.now().plusMonths(1); + LocalDate dateFinEssai = LocalDate.now().plusDays(30); + + UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() + .numeroReference("ABO-2026-TEST1234") + .organisationId(organisationId) + .nomOrganisation("Test Org") + .formulaireId(formulaireId) + .codeFormule("PREMIUM") + .nomFormule("Premium Formula") + .typeFormule(TypeFormule.PREMIUM) + .statut(StatutAbonnement.ACTIF) + .typeAbonnement(TypePeriodeAbonnement.MENSUEL) + .dateDebut(dateDebut) + .dateFin(dateFin) + .dateProchainePeriode(dateProchainePeriode) + .montant(new BigDecimal("10000.00")) + .devise("XOF") + .remise(new BigDecimal("10.00")) + .montantFinal(new BigDecimal("9000.00")) + .renouvellementAutomatique(true) + .periodeEssaiUtilisee(true) + .dateFinEssai(dateFinEssai) + .maxMembres(100) + .nombreMembresActuels(50) + .espaceStockageGB(new BigDecimal("100.00")) + .espaceStockageUtilise(new BigDecimal("25.50")) + .supportTechnique(true) + .niveauSupport("PREMIUM") + .fonctionnalitesAvancees(true) + .apiAccess(true) + .rapportsPersonnalises(true) + .integrationsTierces(true) + .responsableId(responsableId) + .nomResponsable("John Doe") + .emailResponsable("john@example.com") + .telephoneResponsable("+221771234567") + .modePaiementPrefere("WAVE_MONEY") + .numeroPaiementMobile("+221771234567") + .historiquePaiements("Paiements réguliers") + .notes("Notes importantes") + .alertesActivees(true) + .notificationsEmail(true) + .notificationsSMS(true) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroReference()).isEqualTo("ABO-2026-TEST1234"); + assertThat(request.organisationId()).isEqualTo(organisationId); + assertThat(request.nomOrganisation()).isEqualTo("Test Org"); + assertThat(request.formulaireId()).isEqualTo(formulaireId); + assertThat(request.codeFormule()).isEqualTo("PREMIUM"); + assertThat(request.nomFormule()).isEqualTo("Premium Formula"); + assertThat(request.typeFormule()).isEqualTo(TypeFormule.PREMIUM); + assertThat(request.statut()).isEqualTo(StatutAbonnement.ACTIF); + assertThat(request.typeAbonnement()).isEqualTo(TypePeriodeAbonnement.MENSUEL); + assertThat(request.dateDebut()).isEqualTo(dateDebut); + assertThat(request.dateFin()).isEqualTo(dateFin); + assertThat(request.dateProchainePeriode()).isEqualTo(dateProchainePeriode); + assertThat(request.montant()).isEqualByComparingTo(new BigDecimal("10000.00")); + assertThat(request.devise()).isEqualTo("XOF"); + assertThat(request.remise()).isEqualByComparingTo(new BigDecimal("10.00")); + assertThat(request.montantFinal()).isEqualByComparingTo(new BigDecimal("9000.00")); + assertThat(request.renouvellementAutomatique()).isTrue(); + assertThat(request.periodeEssaiUtilisee()).isTrue(); + assertThat(request.dateFinEssai()).isEqualTo(dateFinEssai); + assertThat(request.maxMembres()).isEqualTo(100); + assertThat(request.nombreMembresActuels()).isEqualTo(50); + assertThat(request.espaceStockageGB()).isEqualByComparingTo(new BigDecimal("100.00")); + assertThat(request.espaceStockageUtilise()).isEqualByComparingTo(new BigDecimal("25.50")); + assertThat(request.supportTechnique()).isTrue(); + assertThat(request.niveauSupport()).isEqualTo("PREMIUM"); + assertThat(request.fonctionnalitesAvancees()).isTrue(); + assertThat(request.apiAccess()).isTrue(); + assertThat(request.rapportsPersonnalises()).isTrue(); + assertThat(request.integrationsTierces()).isTrue(); + assertThat(request.responsableId()).isEqualTo(responsableId); + assertThat(request.nomResponsable()).isEqualTo("John Doe"); + assertThat(request.emailResponsable()).isEqualTo("john@example.com"); + assertThat(request.telephoneResponsable()).isEqualTo("+221771234567"); + assertThat(request.modePaiementPrefere()).isEqualTo("WAVE_MONEY"); + assertThat(request.numeroPaiementMobile()).isEqualTo("+221771234567"); + assertThat(request.historiquePaiements()).isEqualTo("Paiements réguliers"); + assertThat(request.notes()).isEqualTo("Notes importantes"); + assertThat(request.alertesActivees()).isTrue(); + assertThat(request.notificationsEmail()).isTrue(); + assertThat(request.notificationsSMS()).isTrue(); + } + + @Test + void testBuilder_MinimalFields() { + UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() + .statut(StatutAbonnement.SUSPENDU) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.statut()).isEqualTo(StatutAbonnement.SUSPENDU); + } + + @Test + void testValidation_InvalidNumeroReference() { + UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() + .numeroReference("INVALID") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroReference")); + } + + @Test + void testValidation_InvalidDevise() { + UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() + .devise("INVALID") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); + } + + @Test + void testValidation_MontantZero() { + UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() + .montant(BigDecimal.ZERO) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montant")); + } + + @Test + void testValidation_ValidFields() { + UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() + .numeroReference("ABO-2026-TEST1234") + .statut(StatutAbonnement.ACTIF) + .montant(new BigDecimal("1000.00")) + .devise("XOF") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID organisationId = UUID.randomUUID(); + + UpdateAbonnementRequest request1 = UpdateAbonnementRequest.builder() + .numeroReference("ABO-2026-TEST1234") + .organisationId(organisationId) + .statut(StatutAbonnement.ACTIF) + .build(); + + UpdateAbonnementRequest request2 = UpdateAbonnementRequest.builder() + .numeroReference("ABO-2026-TEST1234") + .organisationId(organisationId) + .statut(StatutAbonnement.ACTIF) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateAbonnementRequest request = UpdateAbonnementRequest.builder() + .numeroReference("ABO-2026-TEST1234") + .statut(StatutAbonnement.ACTIF) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateAbonnementRequest"); + assertThat(toString).contains("ABO-2026-TEST1234"); + assertThat(toString).contains("ACTIF"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/abonnement/response/AbonnementResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/abonnement/response/AbonnementResponseTest.java index aadce85..a24b287 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/abonnement/response/AbonnementResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/abonnement/response/AbonnementResponseTest.java @@ -1,393 +1,393 @@ -package dev.lions.unionflow.server.api.dto.abonnement.response; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; -import java.time.LocalDate; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour AbonnementResponse. - * Couvre toutes les méthodes utilitaires avec toutes les branches. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-01 - */ -@DisplayName("Tests AbonnementResponse") -class AbonnementResponseTest { - - @Nested - @DisplayName("isExpire") - class IsExpire { - - @Test - @DisplayName("retourne true quand statut EXPIRE") - void testStatutExpire() { - AbonnementResponse response = AbonnementResponse.builder() - .statut(StatutAbonnement.EXPIRE) - .dateFin(LocalDate.now().plusDays(10)) // même avec dateFin dans le futur - .build(); - - assertThat(response.isExpire()).isTrue(); - } - - @Test - @DisplayName("retourne true quand dateFin dans le passé") - void testDateFinPassee() { - AbonnementResponse response = AbonnementResponse.builder() - .statut(StatutAbonnement.ACTIF) // statut != EXPIRE - .dateFin(LocalDate.now().minusDays(5)) - .build(); - - assertThat(response.isExpire()).isTrue(); - } - - @Test - @DisplayName("retourne false quand statut != EXPIRE et dateFin null") - void testStatutActifDateFinNull() { - AbonnementResponse response = AbonnementResponse.builder() - .statut(StatutAbonnement.ACTIF) - .dateFin(null) - .build(); - - assertThat(response.isExpire()).isFalse(); - } - - @Test - @DisplayName("retourne false quand statut != EXPIRE et dateFin future") - void testStatutActifDateFinFuture() { - AbonnementResponse response = AbonnementResponse.builder() - .statut(StatutAbonnement.ACTIF) - .dateFin(LocalDate.now().plusDays(10)) - .build(); - - assertThat(response.isExpire()).isFalse(); - } - } - - @Nested - @DisplayName("isExpirationProche") - class IsExpirationProche { - - @Test - @DisplayName("retourne true quand joursRestants entre 0 et 30") - void testExpirationProche() { - AbonnementResponse response = AbonnementResponse.builder() - .dateFin(LocalDate.now().plusDays(15)) - .build(); - - assertThat(response.isExpirationProche()).isTrue(); - } - - @Test - @DisplayName("retourne false quand joursRestants > 30") - void testExpirationLoin() { - AbonnementResponse response = AbonnementResponse.builder() - .dateFin(LocalDate.now().plusDays(60)) - .build(); - - assertThat(response.isExpirationProche()).isFalse(); - } - - @Test - @DisplayName("retourne false quand joursRestants < 0 (dateFin null)") - void testDateFinNull() { - AbonnementResponse response = AbonnementResponse.builder() - .dateFin(null) - .build(); - - assertThat(response.isExpirationProche()).isFalse(); - } - - @Test - @DisplayName("retourne true quand joursRestants = 0 (déjà expiré)") - void testExpireAujourdhui() { - AbonnementResponse response = AbonnementResponse.builder() - .dateFin(LocalDate.now().minusDays(1)) - .build(); - - assertThat(response.isExpirationProche()).isTrue(); // joursRestants = 0, et 0 >= 0 && 0 <= 30 - } - } - - @Nested - @DisplayName("peutEtreRenouvele") - class PeutEtreRenouvele { - - @Test - @DisplayName("retourne true quand renouvellement auto et non expiré") - void testRenouvellable() { - AbonnementResponse response = AbonnementResponse.builder() - .renouvellementAutomatique(true) - .statut(StatutAbonnement.ACTIF) - .dateFin(LocalDate.now().plusDays(30)) - .build(); - - assertThat(response.peutEtreRenouvele()).isTrue(); - } - - @Test - @DisplayName("retourne false quand renouvellement auto false") - void testRenouvellementAutoFalse() { - AbonnementResponse response = AbonnementResponse.builder() - .renouvellementAutomatique(false) - .statut(StatutAbonnement.ACTIF) - .dateFin(LocalDate.now().plusDays(30)) - .build(); - - assertThat(response.peutEtreRenouvele()).isFalse(); - } - - @Test - @DisplayName("retourne false quand renouvellement auto null") - void testRenouvellementAutoNull() { - AbonnementResponse response = AbonnementResponse.builder() - .renouvellementAutomatique(null) - .statut(StatutAbonnement.ACTIF) - .dateFin(LocalDate.now().plusDays(30)) - .build(); - - assertThat(response.peutEtreRenouvele()).isFalse(); - } - - @Test - @DisplayName("retourne false quand abonnement expiré") - void testExpire() { - AbonnementResponse response = AbonnementResponse.builder() - .renouvellementAutomatique(true) - .statut(StatutAbonnement.EXPIRE) - .dateFin(LocalDate.now().minusDays(10)) - .build(); - - assertThat(response.peutEtreRenouvele()).isFalse(); - } - } - - @Nested - @DisplayName("Autres méthodes utilitaires") - class AutresMethodes { - - @Test - @DisplayName("isActive retourne true pour ACTIF") - void testIsActive() { - AbonnementResponse response = AbonnementResponse.builder() - .statut(StatutAbonnement.ACTIF) - .build(); - - assertThat(response.isActive()).isTrue(); - } - - @Test - @DisplayName("isSuspendu retourne true pour SUSPENDU") - void testIsSuspendu() { - AbonnementResponse response = AbonnementResponse.builder() - .statut(StatutAbonnement.SUSPENDU) - .build(); - - assertThat(response.isSuspendu()).isTrue(); - } - - @Test - @DisplayName("getStatutLibelle retourne le nom du statut") - void testGetStatutLibelle() { - AbonnementResponse response = AbonnementResponse.builder() - .statut(StatutAbonnement.ACTIF) - .build(); - - assertThat(response.getStatutLibelle()).isEqualTo("ACTIF"); - } - - @Test - @DisplayName("getStatutLibelle retourne INCONNU quand statut null") - void testGetStatutLibelleNull() { - AbonnementResponse response = AbonnementResponse.builder() - .statut(null) - .build(); - - assertThat(response.getStatutLibelle()).isEqualTo("INCONNU"); - } - } - - @Nested - @DisplayName("getMembresRestants") - class GetMembresRestants { - - @Test - @DisplayName("retourne 0 quand maxMembres null") - void testMaxMembresNull() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(null) - .nombreMembresActuels(5) - .build(); - - assertThat(response.getMembresRestants()).isEqualTo(0); - } - - @Test - @DisplayName("retourne maxMembres quand nombreMembresActuels null") - void testNombreMembresActuelsNull() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(10) - .nombreMembresActuels(null) - .build(); - - assertThat(response.getMembresRestants()).isEqualTo(10); - } - - @Test - @DisplayName("retourne différence quand actuels < max") - void testMembresRestantsNormal() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(10) - .nombreMembresActuels(7) - .build(); - - assertThat(response.getMembresRestants()).isEqualTo(3); - } - - @Test - @DisplayName("retourne 0 quand actuels >= max") - void testQuotaDepasse() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(10) - .nombreMembresActuels(12) - .build(); - - assertThat(response.getMembresRestants()).isEqualTo(0); - } - } - - @Nested - @DisplayName("isQuotaAtteint") - class IsQuotaAtteint { - - @Test - @DisplayName("retourne false quand maxMembres null") - void testMaxMembresNull() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(null) - .nombreMembresActuels(100) - .build(); - - assertThat(response.isQuotaAtteint()).isFalse(); - } - - @Test - @DisplayName("retourne false quand actuels < max") - void testSousQuota() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(10) - .nombreMembresActuels(7) - .build(); - - assertThat(response.isQuotaAtteint()).isFalse(); - } - - @Test - @DisplayName("retourne true quand actuels = max") - void testQuotaAtteintExact() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(10) - .nombreMembresActuels(10) - .build(); - - assertThat(response.isQuotaAtteint()).isTrue(); - } - - @Test - @DisplayName("retourne true quand actuels > max") - void testQuotaDepasse() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(10) - .nombreMembresActuels(15) - .build(); - - assertThat(response.isQuotaAtteint()).isTrue(); - } - - @Test - @DisplayName("retourne false quand nombreMembresActuels null (défaut 0)") - void testNombreMembresActuelsNull() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(10) - .nombreMembresActuels(null) - .build(); - - assertThat(response.isQuotaAtteint()).isFalse(); - } - } - - @Nested - @DisplayName("getPourcentageUtilisation") - class GetPourcentageUtilisation { - - @Test - @DisplayName("retourne 0 quand maxMembres null") - void testMaxMembresNull() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(null) - .nombreMembresActuels(5) - .build(); - - assertThat(response.getPourcentageUtilisation()).isEqualTo(0); - } - - @Test - @DisplayName("retourne 0 quand maxMembres = 0") - void testMaxMembresZero() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(0) - .nombreMembresActuels(5) - .build(); - - assertThat(response.getPourcentageUtilisation()).isEqualTo(0); - } - - @Test - @DisplayName("retourne 0 quand nombreMembresActuels null (défaut 0)") - void testNombreMembresActuelsNull() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(10) - .nombreMembresActuels(null) - .build(); - - assertThat(response.getPourcentageUtilisation()).isEqualTo(0); - } - - @Test - @DisplayName("calcule pourcentage correct") - void testCalculPourcentage() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(10) - .nombreMembresActuels(7) - .build(); - - assertThat(response.getPourcentageUtilisation()).isEqualTo(70); - } - - @Test - @DisplayName("retourne 100 quand actuels = max") - void testPourcentageCent() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(10) - .nombreMembresActuels(10) - .build(); - - assertThat(response.getPourcentageUtilisation()).isEqualTo(100); - } - - @Test - @DisplayName("retourne > 100 quand actuels > max") - void testPourcentageDepasse() { - AbonnementResponse response = AbonnementResponse.builder() - .maxMembres(10) - .nombreMembresActuels(15) - .build(); - - assertThat(response.getPourcentageUtilisation()).isEqualTo(150); - } - } -} +package dev.lions.unionflow.server.api.dto.abonnement.response; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; +import java.time.LocalDate; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour AbonnementResponse. + * Couvre toutes les méthodes utilitaires avec toutes les branches. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-01 + */ +@DisplayName("Tests AbonnementResponse") +class AbonnementResponseTest { + + @Nested + @DisplayName("isExpire") + class IsExpire { + + @Test + @DisplayName("retourne true quand statut EXPIRE") + void testStatutExpire() { + AbonnementResponse response = AbonnementResponse.builder() + .statut(StatutAbonnement.EXPIRE) + .dateFin(LocalDate.now().plusDays(10)) // même avec dateFin dans le futur + .build(); + + assertThat(response.isExpire()).isTrue(); + } + + @Test + @DisplayName("retourne true quand dateFin dans le passé") + void testDateFinPassee() { + AbonnementResponse response = AbonnementResponse.builder() + .statut(StatutAbonnement.ACTIF) // statut != EXPIRE + .dateFin(LocalDate.now().minusDays(5)) + .build(); + + assertThat(response.isExpire()).isTrue(); + } + + @Test + @DisplayName("retourne false quand statut != EXPIRE et dateFin null") + void testStatutActifDateFinNull() { + AbonnementResponse response = AbonnementResponse.builder() + .statut(StatutAbonnement.ACTIF) + .dateFin(null) + .build(); + + assertThat(response.isExpire()).isFalse(); + } + + @Test + @DisplayName("retourne false quand statut != EXPIRE et dateFin future") + void testStatutActifDateFinFuture() { + AbonnementResponse response = AbonnementResponse.builder() + .statut(StatutAbonnement.ACTIF) + .dateFin(LocalDate.now().plusDays(10)) + .build(); + + assertThat(response.isExpire()).isFalse(); + } + } + + @Nested + @DisplayName("isExpirationProche") + class IsExpirationProche { + + @Test + @DisplayName("retourne true quand joursRestants entre 0 et 30") + void testExpirationProche() { + AbonnementResponse response = AbonnementResponse.builder() + .dateFin(LocalDate.now().plusDays(15)) + .build(); + + assertThat(response.isExpirationProche()).isTrue(); + } + + @Test + @DisplayName("retourne false quand joursRestants > 30") + void testExpirationLoin() { + AbonnementResponse response = AbonnementResponse.builder() + .dateFin(LocalDate.now().plusDays(60)) + .build(); + + assertThat(response.isExpirationProche()).isFalse(); + } + + @Test + @DisplayName("retourne false quand joursRestants < 0 (dateFin null)") + void testDateFinNull() { + AbonnementResponse response = AbonnementResponse.builder() + .dateFin(null) + .build(); + + assertThat(response.isExpirationProche()).isFalse(); + } + + @Test + @DisplayName("retourne true quand joursRestants = 0 (déjà expiré)") + void testExpireAujourdhui() { + AbonnementResponse response = AbonnementResponse.builder() + .dateFin(LocalDate.now().minusDays(1)) + .build(); + + assertThat(response.isExpirationProche()).isTrue(); // joursRestants = 0, et 0 >= 0 && 0 <= 30 + } + } + + @Nested + @DisplayName("peutEtreRenouvele") + class PeutEtreRenouvele { + + @Test + @DisplayName("retourne true quand renouvellement auto et non expiré") + void testRenouvellable() { + AbonnementResponse response = AbonnementResponse.builder() + .renouvellementAutomatique(true) + .statut(StatutAbonnement.ACTIF) + .dateFin(LocalDate.now().plusDays(30)) + .build(); + + assertThat(response.peutEtreRenouvele()).isTrue(); + } + + @Test + @DisplayName("retourne false quand renouvellement auto false") + void testRenouvellementAutoFalse() { + AbonnementResponse response = AbonnementResponse.builder() + .renouvellementAutomatique(false) + .statut(StatutAbonnement.ACTIF) + .dateFin(LocalDate.now().plusDays(30)) + .build(); + + assertThat(response.peutEtreRenouvele()).isFalse(); + } + + @Test + @DisplayName("retourne false quand renouvellement auto null") + void testRenouvellementAutoNull() { + AbonnementResponse response = AbonnementResponse.builder() + .renouvellementAutomatique(null) + .statut(StatutAbonnement.ACTIF) + .dateFin(LocalDate.now().plusDays(30)) + .build(); + + assertThat(response.peutEtreRenouvele()).isFalse(); + } + + @Test + @DisplayName("retourne false quand abonnement expiré") + void testExpire() { + AbonnementResponse response = AbonnementResponse.builder() + .renouvellementAutomatique(true) + .statut(StatutAbonnement.EXPIRE) + .dateFin(LocalDate.now().minusDays(10)) + .build(); + + assertThat(response.peutEtreRenouvele()).isFalse(); + } + } + + @Nested + @DisplayName("Autres méthodes utilitaires") + class AutresMethodes { + + @Test + @DisplayName("isActive retourne true pour ACTIF") + void testIsActive() { + AbonnementResponse response = AbonnementResponse.builder() + .statut(StatutAbonnement.ACTIF) + .build(); + + assertThat(response.isActive()).isTrue(); + } + + @Test + @DisplayName("isSuspendu retourne true pour SUSPENDU") + void testIsSuspendu() { + AbonnementResponse response = AbonnementResponse.builder() + .statut(StatutAbonnement.SUSPENDU) + .build(); + + assertThat(response.isSuspendu()).isTrue(); + } + + @Test + @DisplayName("getStatutLibelle retourne le nom du statut") + void testGetStatutLibelle() { + AbonnementResponse response = AbonnementResponse.builder() + .statut(StatutAbonnement.ACTIF) + .build(); + + assertThat(response.getStatutLibelle()).isEqualTo("ACTIF"); + } + + @Test + @DisplayName("getStatutLibelle retourne INCONNU quand statut null") + void testGetStatutLibelleNull() { + AbonnementResponse response = AbonnementResponse.builder() + .statut(null) + .build(); + + assertThat(response.getStatutLibelle()).isEqualTo("INCONNU"); + } + } + + @Nested + @DisplayName("getMembresRestants") + class GetMembresRestants { + + @Test + @DisplayName("retourne 0 quand maxMembres null") + void testMaxMembresNull() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(null) + .nombreMembresActuels(5) + .build(); + + assertThat(response.getMembresRestants()).isEqualTo(0); + } + + @Test + @DisplayName("retourne maxMembres quand nombreMembresActuels null") + void testNombreMembresActuelsNull() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(10) + .nombreMembresActuels(null) + .build(); + + assertThat(response.getMembresRestants()).isEqualTo(10); + } + + @Test + @DisplayName("retourne différence quand actuels < max") + void testMembresRestantsNormal() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(10) + .nombreMembresActuels(7) + .build(); + + assertThat(response.getMembresRestants()).isEqualTo(3); + } + + @Test + @DisplayName("retourne 0 quand actuels >= max") + void testQuotaDepasse() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(10) + .nombreMembresActuels(12) + .build(); + + assertThat(response.getMembresRestants()).isEqualTo(0); + } + } + + @Nested + @DisplayName("isQuotaAtteint") + class IsQuotaAtteint { + + @Test + @DisplayName("retourne false quand maxMembres null") + void testMaxMembresNull() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(null) + .nombreMembresActuels(100) + .build(); + + assertThat(response.isQuotaAtteint()).isFalse(); + } + + @Test + @DisplayName("retourne false quand actuels < max") + void testSousQuota() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(10) + .nombreMembresActuels(7) + .build(); + + assertThat(response.isQuotaAtteint()).isFalse(); + } + + @Test + @DisplayName("retourne true quand actuels = max") + void testQuotaAtteintExact() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(10) + .nombreMembresActuels(10) + .build(); + + assertThat(response.isQuotaAtteint()).isTrue(); + } + + @Test + @DisplayName("retourne true quand actuels > max") + void testQuotaDepasse() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(10) + .nombreMembresActuels(15) + .build(); + + assertThat(response.isQuotaAtteint()).isTrue(); + } + + @Test + @DisplayName("retourne false quand nombreMembresActuels null (défaut 0)") + void testNombreMembresActuelsNull() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(10) + .nombreMembresActuels(null) + .build(); + + assertThat(response.isQuotaAtteint()).isFalse(); + } + } + + @Nested + @DisplayName("getPourcentageUtilisation") + class GetPourcentageUtilisation { + + @Test + @DisplayName("retourne 0 quand maxMembres null") + void testMaxMembresNull() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(null) + .nombreMembresActuels(5) + .build(); + + assertThat(response.getPourcentageUtilisation()).isEqualTo(0); + } + + @Test + @DisplayName("retourne 0 quand maxMembres = 0") + void testMaxMembresZero() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(0) + .nombreMembresActuels(5) + .build(); + + assertThat(response.getPourcentageUtilisation()).isEqualTo(0); + } + + @Test + @DisplayName("retourne 0 quand nombreMembresActuels null (défaut 0)") + void testNombreMembresActuelsNull() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(10) + .nombreMembresActuels(null) + .build(); + + assertThat(response.getPourcentageUtilisation()).isEqualTo(0); + } + + @Test + @DisplayName("calcule pourcentage correct") + void testCalculPourcentage() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(10) + .nombreMembresActuels(7) + .build(); + + assertThat(response.getPourcentageUtilisation()).isEqualTo(70); + } + + @Test + @DisplayName("retourne 100 quand actuels = max") + void testPourcentageCent() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(10) + .nombreMembresActuels(10) + .build(); + + assertThat(response.getPourcentageUtilisation()).isEqualTo(100); + } + + @Test + @DisplayName("retourne > 100 quand actuels > max") + void testPourcentageDepasse() { + AbonnementResponse response = AbonnementResponse.builder() + .maxMembres(10) + .nombreMembresActuels(15) + .build(); + + assertThat(response.getPourcentageUtilisation()).isEqualTo(150); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/admin/request/CreateAuditLogRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/admin/request/CreateAuditLogRequestTest.java index 91c17c3..0228cc6 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/admin/request/CreateAuditLogRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/admin/request/CreateAuditLogRequestTest.java @@ -1,131 +1,131 @@ -package dev.lions.unionflow.server.api.dto.admin.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.time.LocalDateTime; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateAuditLogRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDateTime dateHeure = LocalDateTime.now(); - - CreateAuditLogRequest request = CreateAuditLogRequest.builder() - .typeAction("CREATE") - .severite("INFO") - .utilisateur("john.doe@example.com") - .role("ROLE_ADMIN") - .module("MEMBRES") - .description("Création d'un nouveau membre") - .details("Membre créé avec succès") - .ipAddress("192.168.1.100") - .userAgent("Mozilla/5.0") - .sessionId("session-123") - .dateHeure(dateHeure) - .donneesAvant("{}") - .donneesApres("{\"nom\":\"Doe\",\"prenom\":\"John\"}") - .entiteId("uuid-123") - .entiteType("MEMBRE") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.typeAction()).isEqualTo("CREATE"); - assertThat(request.severite()).isEqualTo("INFO"); - assertThat(request.utilisateur()).isEqualTo("john.doe@example.com"); - assertThat(request.role()).isEqualTo("ROLE_ADMIN"); - assertThat(request.module()).isEqualTo("MEMBRES"); - assertThat(request.description()).isEqualTo("Création d'un nouveau membre"); - assertThat(request.details()).isEqualTo("Membre créé avec succès"); - assertThat(request.ipAddress()).isEqualTo("192.168.1.100"); - assertThat(request.userAgent()).isEqualTo("Mozilla/5.0"); - assertThat(request.sessionId()).isEqualTo("session-123"); - assertThat(request.dateHeure()).isEqualTo(dateHeure); - assertThat(request.donneesAvant()).isEqualTo("{}"); - assertThat(request.donneesApres()).isEqualTo("{\"nom\":\"Doe\",\"prenom\":\"John\"}"); - assertThat(request.entiteId()).isEqualTo("uuid-123"); - assertThat(request.entiteType()).isEqualTo("MEMBRE"); - } - - @Test - void testBuilder_MinimalFields() { - CreateAuditLogRequest request = CreateAuditLogRequest.builder() - .typeAction("READ") - .utilisateur("user@example.com") - .module("DASHBOARD") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.typeAction()).isEqualTo("READ"); - assertThat(request.utilisateur()).isEqualTo("user@example.com"); - assertThat(request.module()).isEqualTo("DASHBOARD"); - } - - @Test - void testValidation_ValidFields() { - CreateAuditLogRequest request = CreateAuditLogRequest.builder() - .typeAction("UPDATE") - .severite("WARNING") - .utilisateur("admin@example.com") - .module("SETTINGS") - .description("Modification configuration") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - LocalDateTime dateHeure = LocalDateTime.now(); - - CreateAuditLogRequest request1 = CreateAuditLogRequest.builder() - .typeAction("CREATE") - .utilisateur("user@example.com") - .module("TEST") - .dateHeure(dateHeure) - .build(); - - CreateAuditLogRequest request2 = CreateAuditLogRequest.builder() - .typeAction("CREATE") - .utilisateur("user@example.com") - .module("TEST") - .dateHeure(dateHeure) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateAuditLogRequest request = CreateAuditLogRequest.builder() - .typeAction("DELETE") - .utilisateur("admin@example.com") - .module("MEMBRES") - .description("Suppression membre") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateAuditLogRequest"); - assertThat(toString).contains("DELETE"); - assertThat(toString).contains("MEMBRES"); - } -} +package dev.lions.unionflow.server.api.dto.admin.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.time.LocalDateTime; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateAuditLogRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDateTime dateHeure = LocalDateTime.now(); + + CreateAuditLogRequest request = CreateAuditLogRequest.builder() + .typeAction("CREATE") + .severite("INFO") + .utilisateur("john.doe@example.com") + .role("ROLE_ADMIN") + .module("MEMBRES") + .description("Création d'un nouveau membre") + .details("Membre créé avec succès") + .ipAddress("192.168.1.100") + .userAgent("Mozilla/5.0") + .sessionId("session-123") + .dateHeure(dateHeure) + .donneesAvant("{}") + .donneesApres("{\"nom\":\"Doe\",\"prenom\":\"John\"}") + .entiteId("uuid-123") + .entiteType("MEMBRE") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.typeAction()).isEqualTo("CREATE"); + assertThat(request.severite()).isEqualTo("INFO"); + assertThat(request.utilisateur()).isEqualTo("john.doe@example.com"); + assertThat(request.role()).isEqualTo("ROLE_ADMIN"); + assertThat(request.module()).isEqualTo("MEMBRES"); + assertThat(request.description()).isEqualTo("Création d'un nouveau membre"); + assertThat(request.details()).isEqualTo("Membre créé avec succès"); + assertThat(request.ipAddress()).isEqualTo("192.168.1.100"); + assertThat(request.userAgent()).isEqualTo("Mozilla/5.0"); + assertThat(request.sessionId()).isEqualTo("session-123"); + assertThat(request.dateHeure()).isEqualTo(dateHeure); + assertThat(request.donneesAvant()).isEqualTo("{}"); + assertThat(request.donneesApres()).isEqualTo("{\"nom\":\"Doe\",\"prenom\":\"John\"}"); + assertThat(request.entiteId()).isEqualTo("uuid-123"); + assertThat(request.entiteType()).isEqualTo("MEMBRE"); + } + + @Test + void testBuilder_MinimalFields() { + CreateAuditLogRequest request = CreateAuditLogRequest.builder() + .typeAction("READ") + .utilisateur("user@example.com") + .module("DASHBOARD") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.typeAction()).isEqualTo("READ"); + assertThat(request.utilisateur()).isEqualTo("user@example.com"); + assertThat(request.module()).isEqualTo("DASHBOARD"); + } + + @Test + void testValidation_ValidFields() { + CreateAuditLogRequest request = CreateAuditLogRequest.builder() + .typeAction("UPDATE") + .severite("WARNING") + .utilisateur("admin@example.com") + .module("SETTINGS") + .description("Modification configuration") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + LocalDateTime dateHeure = LocalDateTime.now(); + + CreateAuditLogRequest request1 = CreateAuditLogRequest.builder() + .typeAction("CREATE") + .utilisateur("user@example.com") + .module("TEST") + .dateHeure(dateHeure) + .build(); + + CreateAuditLogRequest request2 = CreateAuditLogRequest.builder() + .typeAction("CREATE") + .utilisateur("user@example.com") + .module("TEST") + .dateHeure(dateHeure) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateAuditLogRequest request = CreateAuditLogRequest.builder() + .typeAction("DELETE") + .utilisateur("admin@example.com") + .module("MEMBRES") + .description("Suppression membre") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateAuditLogRequest"); + assertThat(toString).contains("DELETE"); + assertThat(toString).contains("MEMBRES"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/admin/response/AuditLogResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/admin/response/AuditLogResponseTest.java index 4af02c6..0511a5e 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/admin/response/AuditLogResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/admin/response/AuditLogResponseTest.java @@ -1,57 +1,57 @@ -package dev.lions.unionflow.server.api.dto.admin.response; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalDateTime; -import org.junit.jupiter.api.Test; - -class AuditLogResponseTest { - - @Test - void testGettersSetters_AllFields() { - LocalDateTime dateHeure = LocalDateTime.now(); - - AuditLogResponse response = new AuditLogResponse(); - response.setTypeAction("CREATE"); - response.setSeverite("INFO"); - response.setUtilisateur("john.doe"); - response.setRole("ADMIN"); - response.setModule("MEMBRES"); - response.setDescription("Création d'un nouveau membre"); - response.setDetails("Détails complets de l'opération"); - response.setIpAddress("192.168.1.100"); - response.setUserAgent("Mozilla/5.0"); - response.setSessionId("session-123"); - response.setDateHeure(dateHeure); - response.setDonneesAvant(null); - response.setDonneesApres("{\"nom\":\"Doe\"}"); - response.setEntiteId("123e4567-e89b-12d3-a456-426614174000"); - response.setEntiteType("MEMBRE"); - - assertThat(response.getTypeAction()).isEqualTo("CREATE"); - assertThat(response.getSeverite()).isEqualTo("INFO"); - assertThat(response.getUtilisateur()).isEqualTo("john.doe"); - assertThat(response.getRole()).isEqualTo("ADMIN"); - assertThat(response.getModule()).isEqualTo("MEMBRES"); - assertThat(response.getDescription()).isEqualTo("Création d'un nouveau membre"); - assertThat(response.getDetails()).isEqualTo("Détails complets de l'opération"); - assertThat(response.getIpAddress()).isEqualTo("192.168.1.100"); - assertThat(response.getUserAgent()).isEqualTo("Mozilla/5.0"); - assertThat(response.getSessionId()).isEqualTo("session-123"); - assertThat(response.getDateHeure()).isEqualTo(dateHeure); - assertThat(response.getDonneesAvant()).isNull(); - assertThat(response.getDonneesApres()).isEqualTo("{\"nom\":\"Doe\"}"); - assertThat(response.getEntiteId()).isEqualTo("123e4567-e89b-12d3-a456-426614174000"); - assertThat(response.getEntiteType()).isEqualTo("MEMBRE"); - } - - @Test - void testDefaultConstructor() { - AuditLogResponse response = new AuditLogResponse(); - - assertThat(response).isNotNull(); - assertThat(response.getTypeAction()).isNull(); - assertThat(response.getSeverite()).isNull(); - assertThat(response.getUtilisateur()).isNull(); - } -} +package dev.lions.unionflow.server.api.dto.admin.response; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalDateTime; +import org.junit.jupiter.api.Test; + +class AuditLogResponseTest { + + @Test + void testGettersSetters_AllFields() { + LocalDateTime dateHeure = LocalDateTime.now(); + + AuditLogResponse response = new AuditLogResponse(); + response.setTypeAction("CREATE"); + response.setSeverite("INFO"); + response.setUtilisateur("john.doe"); + response.setRole("ADMIN"); + response.setModule("MEMBRES"); + response.setDescription("Création d'un nouveau membre"); + response.setDetails("Détails complets de l'opération"); + response.setIpAddress("192.168.1.100"); + response.setUserAgent("Mozilla/5.0"); + response.setSessionId("session-123"); + response.setDateHeure(dateHeure); + response.setDonneesAvant(null); + response.setDonneesApres("{\"nom\":\"Doe\"}"); + response.setEntiteId("123e4567-e89b-12d3-a456-426614174000"); + response.setEntiteType("MEMBRE"); + + assertThat(response.getTypeAction()).isEqualTo("CREATE"); + assertThat(response.getSeverite()).isEqualTo("INFO"); + assertThat(response.getUtilisateur()).isEqualTo("john.doe"); + assertThat(response.getRole()).isEqualTo("ADMIN"); + assertThat(response.getModule()).isEqualTo("MEMBRES"); + assertThat(response.getDescription()).isEqualTo("Création d'un nouveau membre"); + assertThat(response.getDetails()).isEqualTo("Détails complets de l'opération"); + assertThat(response.getIpAddress()).isEqualTo("192.168.1.100"); + assertThat(response.getUserAgent()).isEqualTo("Mozilla/5.0"); + assertThat(response.getSessionId()).isEqualTo("session-123"); + assertThat(response.getDateHeure()).isEqualTo(dateHeure); + assertThat(response.getDonneesAvant()).isNull(); + assertThat(response.getDonneesApres()).isEqualTo("{\"nom\":\"Doe\"}"); + assertThat(response.getEntiteId()).isEqualTo("123e4567-e89b-12d3-a456-426614174000"); + assertThat(response.getEntiteType()).isEqualTo("MEMBRE"); + } + + @Test + void testDefaultConstructor() { + AuditLogResponse response = new AuditLogResponse(); + + assertThat(response).isNotNull(); + assertThat(response.getTypeAction()).isNull(); + assertThat(response.getSeverite()).isNull(); + assertThat(response.getUtilisateur()).isNull(); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/adresse/request/CreateAdresseRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/adresse/request/CreateAdresseRequestTest.java index df89671..39f34c0 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/adresse/request/CreateAdresseRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/adresse/request/CreateAdresseRequestTest.java @@ -1,269 +1,269 @@ -package dev.lions.unionflow.server.api.dto.adresse.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateAdresseRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID organisationId = UUID.randomUUID(); - - CreateAdresseRequest request = new CreateAdresseRequest( - "DOMICILE", - "123 Rue de la Liberté", - "Appartement 5B", - "12345", - "Dakar", - "Dakar", - "Sénégal", - new BigDecimal("14.716677"), - new BigDecimal("-17.467686"), - true, - "Domicile principal", - "Notes importantes", - organisationId, - null, - null - ); - - assertThat(request).isNotNull(); - assertThat(request.typeAdresse()).isEqualTo("DOMICILE"); - assertThat(request.adresse()).isEqualTo("123 Rue de la Liberté"); - assertThat(request.complementAdresse()).isEqualTo("Appartement 5B"); - assertThat(request.codePostal()).isEqualTo("12345"); - assertThat(request.ville()).isEqualTo("Dakar"); - assertThat(request.region()).isEqualTo("Dakar"); - assertThat(request.pays()).isEqualTo("Sénégal"); - assertThat(request.latitude()).isEqualByComparingTo(new BigDecimal("14.716677")); - assertThat(request.longitude()).isEqualByComparingTo(new BigDecimal("-17.467686")); - assertThat(request.principale()).isTrue(); - assertThat(request.libelle()).isEqualTo("Domicile principal"); - assertThat(request.notes()).isEqualTo("Notes importantes"); - assertThat(request.organisationId()).isEqualTo(organisationId); - } - - @Test - void testBuilder_MinimalFields() { - CreateAdresseRequest request = new CreateAdresseRequest( - "BUREAU", - "456 Avenue du Commerce", - null, - null, - "Thiès", - null, - "Sénégal", - null, - null, - false, - null, - null, - null, - null, - null - ); - - assertThat(request).isNotNull(); - assertThat(request.typeAdresse()).isEqualTo("BUREAU"); - assertThat(request.adresse()).isEqualTo("456 Avenue du Commerce"); - assertThat(request.ville()).isEqualTo("Thiès"); - assertThat(request.pays()).isEqualTo("Sénégal"); - assertThat(request.principale()).isFalse(); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateAdresseRequest request = new CreateAdresseRequest( - null, - null, - null, - null, - null, - null, - null, - null, - null, - null, - null, - null, - null, - null, - null - ); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeAdresse")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("adresse")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ville")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("pays")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("principale")); - } - - @Test - void testValidation_InvalidLatitude() { - CreateAdresseRequest request = new CreateAdresseRequest( - "DOMICILE", - "123 Rue Test", - null, - null, - "Dakar", - null, - "Sénégal", - new BigDecimal("100.0"), - new BigDecimal("0.0"), - true, - null, - null, - null, - null, - null - ); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("latitude")); - } - - @Test - void testValidation_InvalidLongitude() { - CreateAdresseRequest request = new CreateAdresseRequest( - "DOMICILE", - "123 Rue Test", - null, - null, - "Dakar", - null, - "Sénégal", - new BigDecimal("0.0"), - new BigDecimal("200.0"), - true, - null, - null, - null, - null, - null - ); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("longitude")); - } - - @Test - void testValidation_ValidFields() { - CreateAdresseRequest request = new CreateAdresseRequest( - "DOMICILE", - "123 Rue Test", - null, - null, - "Dakar", - null, - "Sénégal", - new BigDecimal("14.716677"), - new BigDecimal("-17.467686"), - true, - null, - null, - null, - null, - null - ); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID orgId = UUID.randomUUID(); - - CreateAdresseRequest request1 = new CreateAdresseRequest( - "DOMICILE", - "123 Rue Test", - null, - null, - "Dakar", - null, - "Sénégal", - null, - null, - true, - null, - null, - orgId, - null, - null - ); - - CreateAdresseRequest request2 = new CreateAdresseRequest( - "DOMICILE", - "123 Rue Test", - null, - null, - "Dakar", - null, - "Sénégal", - null, - null, - true, - null, - null, - orgId, - null, - null - ); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateAdresseRequest request = new CreateAdresseRequest( - "DOMICILE", - "123 Rue Test", - null, - null, - "Dakar", - null, - "Sénégal", - null, - null, - true, - null, - null, - null, - null, - null - ); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateAdresseRequest"); - assertThat(toString).contains("DOMICILE"); - assertThat(toString).contains("Dakar"); - } -} +package dev.lions.unionflow.server.api.dto.adresse.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateAdresseRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID organisationId = UUID.randomUUID(); + + CreateAdresseRequest request = new CreateAdresseRequest( + "DOMICILE", + "123 Rue de la Liberté", + "Appartement 5B", + "12345", + "Dakar", + "Dakar", + "Sénégal", + new BigDecimal("14.716677"), + new BigDecimal("-17.467686"), + true, + "Domicile principal", + "Notes importantes", + organisationId, + null, + null + ); + + assertThat(request).isNotNull(); + assertThat(request.typeAdresse()).isEqualTo("DOMICILE"); + assertThat(request.adresse()).isEqualTo("123 Rue de la Liberté"); + assertThat(request.complementAdresse()).isEqualTo("Appartement 5B"); + assertThat(request.codePostal()).isEqualTo("12345"); + assertThat(request.ville()).isEqualTo("Dakar"); + assertThat(request.region()).isEqualTo("Dakar"); + assertThat(request.pays()).isEqualTo("Sénégal"); + assertThat(request.latitude()).isEqualByComparingTo(new BigDecimal("14.716677")); + assertThat(request.longitude()).isEqualByComparingTo(new BigDecimal("-17.467686")); + assertThat(request.principale()).isTrue(); + assertThat(request.libelle()).isEqualTo("Domicile principal"); + assertThat(request.notes()).isEqualTo("Notes importantes"); + assertThat(request.organisationId()).isEqualTo(organisationId); + } + + @Test + void testBuilder_MinimalFields() { + CreateAdresseRequest request = new CreateAdresseRequest( + "BUREAU", + "456 Avenue du Commerce", + null, + null, + "Thiès", + null, + "Sénégal", + null, + null, + false, + null, + null, + null, + null, + null + ); + + assertThat(request).isNotNull(); + assertThat(request.typeAdresse()).isEqualTo("BUREAU"); + assertThat(request.adresse()).isEqualTo("456 Avenue du Commerce"); + assertThat(request.ville()).isEqualTo("Thiès"); + assertThat(request.pays()).isEqualTo("Sénégal"); + assertThat(request.principale()).isFalse(); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateAdresseRequest request = new CreateAdresseRequest( + null, + null, + null, + null, + null, + null, + null, + null, + null, + null, + null, + null, + null, + null, + null + ); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeAdresse")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("adresse")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ville")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("pays")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("principale")); + } + + @Test + void testValidation_InvalidLatitude() { + CreateAdresseRequest request = new CreateAdresseRequest( + "DOMICILE", + "123 Rue Test", + null, + null, + "Dakar", + null, + "Sénégal", + new BigDecimal("100.0"), + new BigDecimal("0.0"), + true, + null, + null, + null, + null, + null + ); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("latitude")); + } + + @Test + void testValidation_InvalidLongitude() { + CreateAdresseRequest request = new CreateAdresseRequest( + "DOMICILE", + "123 Rue Test", + null, + null, + "Dakar", + null, + "Sénégal", + new BigDecimal("0.0"), + new BigDecimal("200.0"), + true, + null, + null, + null, + null, + null + ); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("longitude")); + } + + @Test + void testValidation_ValidFields() { + CreateAdresseRequest request = new CreateAdresseRequest( + "DOMICILE", + "123 Rue Test", + null, + null, + "Dakar", + null, + "Sénégal", + new BigDecimal("14.716677"), + new BigDecimal("-17.467686"), + true, + null, + null, + null, + null, + null + ); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID orgId = UUID.randomUUID(); + + CreateAdresseRequest request1 = new CreateAdresseRequest( + "DOMICILE", + "123 Rue Test", + null, + null, + "Dakar", + null, + "Sénégal", + null, + null, + true, + null, + null, + orgId, + null, + null + ); + + CreateAdresseRequest request2 = new CreateAdresseRequest( + "DOMICILE", + "123 Rue Test", + null, + null, + "Dakar", + null, + "Sénégal", + null, + null, + true, + null, + null, + orgId, + null, + null + ); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateAdresseRequest request = new CreateAdresseRequest( + "DOMICILE", + "123 Rue Test", + null, + null, + "Dakar", + null, + "Sénégal", + null, + null, + true, + null, + null, + null, + null, + null + ); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateAdresseRequest"); + assertThat(toString).contains("DOMICILE"); + assertThat(toString).contains("Dakar"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/adresse/request/UpdateAdresseRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/adresse/request/UpdateAdresseRequestTest.java index afeaa9d..ecb102f 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/adresse/request/UpdateAdresseRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/adresse/request/UpdateAdresseRequestTest.java @@ -1,232 +1,232 @@ -package dev.lions.unionflow.server.api.dto.adresse.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateAdresseRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID organisationId = UUID.randomUUID(); - - UpdateAdresseRequest request = new UpdateAdresseRequest( - "BUREAU", - "456 Avenue Mise à jour", - "Suite 10", - "54321", - "Thiès", - "Thiès", - "Sénégal", - new BigDecimal("14.800000"), - new BigDecimal("-16.900000"), - false, - "Bureau secondaire", - "Notes mises à jour", - organisationId, - null, - null - ); - - assertThat(request).isNotNull(); - assertThat(request.typeAdresse()).isEqualTo("BUREAU"); - assertThat(request.adresse()).isEqualTo("456 Avenue Mise à jour"); - assertThat(request.complementAdresse()).isEqualTo("Suite 10"); - assertThat(request.codePostal()).isEqualTo("54321"); - assertThat(request.ville()).isEqualTo("Thiès"); - assertThat(request.region()).isEqualTo("Thiès"); - assertThat(request.pays()).isEqualTo("Sénégal"); - assertThat(request.latitude()).isEqualByComparingTo(new BigDecimal("14.800000")); - assertThat(request.longitude()).isEqualByComparingTo(new BigDecimal("-16.900000")); - assertThat(request.principale()).isFalse(); - assertThat(request.libelle()).isEqualTo("Bureau secondaire"); - assertThat(request.notes()).isEqualTo("Notes mises à jour"); - assertThat(request.organisationId()).isEqualTo(organisationId); - } - - @Test - void testBuilder_MinimalFields() { - UpdateAdresseRequest request = new UpdateAdresseRequest( - null, - "Nouvelle adresse", - null, - null, - null, - null, - null, - null, - null, - null, - null, - null, - null, - null, - null - ); - - assertThat(request).isNotNull(); - assertThat(request.adresse()).isEqualTo("Nouvelle adresse"); - } - - @Test - void testValidation_InvalidLatitude() { - UpdateAdresseRequest request = new UpdateAdresseRequest( - null, - null, - null, - null, - null, - null, - null, - new BigDecimal("100.0"), - null, - null, - null, - null, - null, - null, - null - ); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("latitude")); - } - - @Test - void testValidation_InvalidLongitude() { - UpdateAdresseRequest request = new UpdateAdresseRequest( - null, - null, - null, - null, - null, - null, - null, - null, - new BigDecimal("200.0"), - null, - null, - null, - null, - null, - null - ); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("longitude")); - } - - @Test - void testValidation_ValidFields() { - UpdateAdresseRequest request = new UpdateAdresseRequest( - "DOMICILE", - "123 Rue Updated", - null, - null, - "Dakar", - null, - "Sénégal", - new BigDecimal("14.716677"), - new BigDecimal("-17.467686"), - true, - null, - null, - null, - null, - null - ); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UpdateAdresseRequest request1 = new UpdateAdresseRequest( - "BUREAU", - "Test Address", - null, - null, - "Dakar", - null, - "Sénégal", - null, - null, - false, - null, - null, - null, - null, - null - ); - - UpdateAdresseRequest request2 = new UpdateAdresseRequest( - "BUREAU", - "Test Address", - null, - null, - "Dakar", - null, - "Sénégal", - null, - null, - false, - null, - null, - null, - null, - null - ); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateAdresseRequest request = new UpdateAdresseRequest( - "BUREAU", - "Test Address", - null, - null, - "Dakar", - null, - "Sénégal", - null, - null, - false, - null, - null, - null, - null, - null - ); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateAdresseRequest"); - assertThat(toString).contains("BUREAU"); - } -} +package dev.lions.unionflow.server.api.dto.adresse.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateAdresseRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID organisationId = UUID.randomUUID(); + + UpdateAdresseRequest request = new UpdateAdresseRequest( + "BUREAU", + "456 Avenue Mise à jour", + "Suite 10", + "54321", + "Thiès", + "Thiès", + "Sénégal", + new BigDecimal("14.800000"), + new BigDecimal("-16.900000"), + false, + "Bureau secondaire", + "Notes mises à jour", + organisationId, + null, + null + ); + + assertThat(request).isNotNull(); + assertThat(request.typeAdresse()).isEqualTo("BUREAU"); + assertThat(request.adresse()).isEqualTo("456 Avenue Mise à jour"); + assertThat(request.complementAdresse()).isEqualTo("Suite 10"); + assertThat(request.codePostal()).isEqualTo("54321"); + assertThat(request.ville()).isEqualTo("Thiès"); + assertThat(request.region()).isEqualTo("Thiès"); + assertThat(request.pays()).isEqualTo("Sénégal"); + assertThat(request.latitude()).isEqualByComparingTo(new BigDecimal("14.800000")); + assertThat(request.longitude()).isEqualByComparingTo(new BigDecimal("-16.900000")); + assertThat(request.principale()).isFalse(); + assertThat(request.libelle()).isEqualTo("Bureau secondaire"); + assertThat(request.notes()).isEqualTo("Notes mises à jour"); + assertThat(request.organisationId()).isEqualTo(organisationId); + } + + @Test + void testBuilder_MinimalFields() { + UpdateAdresseRequest request = new UpdateAdresseRequest( + null, + "Nouvelle adresse", + null, + null, + null, + null, + null, + null, + null, + null, + null, + null, + null, + null, + null + ); + + assertThat(request).isNotNull(); + assertThat(request.adresse()).isEqualTo("Nouvelle adresse"); + } + + @Test + void testValidation_InvalidLatitude() { + UpdateAdresseRequest request = new UpdateAdresseRequest( + null, + null, + null, + null, + null, + null, + null, + new BigDecimal("100.0"), + null, + null, + null, + null, + null, + null, + null + ); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("latitude")); + } + + @Test + void testValidation_InvalidLongitude() { + UpdateAdresseRequest request = new UpdateAdresseRequest( + null, + null, + null, + null, + null, + null, + null, + null, + new BigDecimal("200.0"), + null, + null, + null, + null, + null, + null + ); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("longitude")); + } + + @Test + void testValidation_ValidFields() { + UpdateAdresseRequest request = new UpdateAdresseRequest( + "DOMICILE", + "123 Rue Updated", + null, + null, + "Dakar", + null, + "Sénégal", + new BigDecimal("14.716677"), + new BigDecimal("-17.467686"), + true, + null, + null, + null, + null, + null + ); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UpdateAdresseRequest request1 = new UpdateAdresseRequest( + "BUREAU", + "Test Address", + null, + null, + "Dakar", + null, + "Sénégal", + null, + null, + false, + null, + null, + null, + null, + null + ); + + UpdateAdresseRequest request2 = new UpdateAdresseRequest( + "BUREAU", + "Test Address", + null, + null, + "Dakar", + null, + "Sénégal", + null, + null, + false, + null, + null, + null, + null, + null + ); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateAdresseRequest request = new UpdateAdresseRequest( + "BUREAU", + "Test Address", + null, + null, + "Dakar", + null, + "Sénégal", + null, + null, + false, + null, + null, + null, + null, + null + ); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateAdresseRequest"); + assertThat(toString).contains("BUREAU"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/adresse/response/AdresseResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/adresse/response/AdresseResponseTest.java index 2ea1434..db9c3c6 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/adresse/response/AdresseResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/adresse/response/AdresseResponseTest.java @@ -1,171 +1,171 @@ -package dev.lions.unionflow.server.api.dto.adresse.response; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.math.BigDecimal; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour AdresseResponse. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-15 - */ -@DisplayName("Tests AdresseResponse") -class AdresseResponseTest { - - @Nested - @DisplayName("Constructeur et getters/setters") - class ConstructeurEtGettersSetters { - - @Test - @DisplayName("Le constructeur par défaut crée une instance") - void testConstructeurParDefaut() { - AdresseResponse response = new AdresseResponse(); - assertThat(response).isNotNull(); - } - - @Test - @DisplayName("Les setters et getters fonctionnent correctement") - void testSettersEtGetters() { - AdresseResponse response = new AdresseResponse(); - UUID id = UUID.randomUUID(); - UUID organisationId = UUID.randomUUID(); - UUID membreId = UUID.randomUUID(); - UUID evenementId = UUID.randomUUID(); - BigDecimal latitude = new BigDecimal("48.8566"); - BigDecimal longitude = new BigDecimal("2.3522"); - - response.setId(id); - response.setTypeAdresse("DOMICILE"); - response.setTypeAdresseLibelle("Adresse de domicile"); - response.setTypeAdresseIcone("home"); - response.setAdresse("123 Rue de la Paix"); - response.setComplementAdresse("Appartement 4B"); - response.setCodePostal("75001"); - response.setVille("Paris"); - response.setRegion("Île-de-France"); - response.setPays("France"); - response.setLatitude(latitude); - response.setLongitude(longitude); - response.setPrincipale(true); - response.setLibelle("Domicile principal"); - response.setNotes("Interphone code 1234"); - response.setOrganisationId(organisationId); - response.setMembreId(membreId); - response.setEvenementId(evenementId); - response.setAdresseComplete("123 Rue de la Paix, 75001 Paris, France"); - - assertThat(response.getId()).isEqualTo(id); - assertThat(response.getTypeAdresse()).isEqualTo("DOMICILE"); - assertThat(response.getTypeAdresseLibelle()).isEqualTo("Adresse de domicile"); - assertThat(response.getTypeAdresseIcone()).isEqualTo("home"); - assertThat(response.getAdresse()).isEqualTo("123 Rue de la Paix"); - assertThat(response.getComplementAdresse()).isEqualTo("Appartement 4B"); - assertThat(response.getCodePostal()).isEqualTo("75001"); - assertThat(response.getVille()).isEqualTo("Paris"); - assertThat(response.getRegion()).isEqualTo("Île-de-France"); - assertThat(response.getPays()).isEqualTo("France"); - assertThat(response.getLatitude()).isEqualTo(latitude); - assertThat(response.getLongitude()).isEqualTo(longitude); - assertThat(response.getPrincipale()).isTrue(); - assertThat(response.getLibelle()).isEqualTo("Domicile principal"); - assertThat(response.getNotes()).isEqualTo("Interphone code 1234"); - assertThat(response.getOrganisationId()).isEqualTo(organisationId); - assertThat(response.getMembreId()).isEqualTo(membreId); - assertThat(response.getEvenementId()).isEqualTo(evenementId); - assertThat(response.getAdresseComplete()).isEqualTo("123 Rue de la Paix, 75001 Paris, France"); - } - - @Test - @DisplayName("Les champs peuvent être null") - void testChampsNull() { - AdresseResponse response = new AdresseResponse(); - - response.setTypeAdresse(null); - response.setLatitude(null); - response.setLongitude(null); - response.setPrincipale(null); - response.setOrganisationId(null); - response.setMembreId(null); - response.setEvenementId(null); - - assertThat(response.getTypeAdresse()).isNull(); - assertThat(response.getLatitude()).isNull(); - assertThat(response.getLongitude()).isNull(); - assertThat(response.getPrincipale()).isNull(); - assertThat(response.getOrganisationId()).isNull(); - assertThat(response.getMembreId()).isNull(); - assertThat(response.getEvenementId()).isNull(); - } - } - - @Nested - @DisplayName("equals et hashCode") - class EqualsEtHashCode { - - @Test - @DisplayName("equals retourne true pour même id") - void testEqualsMemeId() { - UUID id = UUID.randomUUID(); - - AdresseResponse r1 = new AdresseResponse(); - r1.setId(id); - r1.setAdresse("Adresse 1"); - - AdresseResponse r2 = new AdresseResponse(); - r2.setId(id); - r2.setAdresse("Adresse 2"); - - assertThat(r1).isEqualTo(r2); - } - - @Test - @DisplayName("equals retourne false pour ids différents") - void testEqualsIdsDifferents() { - AdresseResponse r1 = new AdresseResponse(); - r1.setId(UUID.randomUUID()); - - AdresseResponse r2 = new AdresseResponse(); - r2.setId(UUID.randomUUID()); - - assertThat(r1).isNotEqualTo(r2); - } - - @Test - @DisplayName("hashCode est basé sur l'id") - void testHashCode() { - UUID id = UUID.randomUUID(); - - AdresseResponse r1 = new AdresseResponse(); - r1.setId(id); - - AdresseResponse r2 = new AdresseResponse(); - r2.setId(id); - - assertThat(r1.hashCode()).isEqualTo(r2.hashCode()); - } - } - - @Nested - @DisplayName("toString") - class ToString { - - @Test - @DisplayName("toString retourne une représentation non-null") - void testToString() { - AdresseResponse response = new AdresseResponse(); - response.setId(UUID.randomUUID()); - response.setAdresse("123 Rue Test"); - response.setVille("Paris"); - - String result = response.toString(); - assertThat(result).isNotNull(); - assertThat(result).contains("AdresseResponse"); - } - } -} +package dev.lions.unionflow.server.api.dto.adresse.response; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.math.BigDecimal; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour AdresseResponse. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-15 + */ +@DisplayName("Tests AdresseResponse") +class AdresseResponseTest { + + @Nested + @DisplayName("Constructeur et getters/setters") + class ConstructeurEtGettersSetters { + + @Test + @DisplayName("Le constructeur par défaut crée une instance") + void testConstructeurParDefaut() { + AdresseResponse response = new AdresseResponse(); + assertThat(response).isNotNull(); + } + + @Test + @DisplayName("Les setters et getters fonctionnent correctement") + void testSettersEtGetters() { + AdresseResponse response = new AdresseResponse(); + UUID id = UUID.randomUUID(); + UUID organisationId = UUID.randomUUID(); + UUID membreId = UUID.randomUUID(); + UUID evenementId = UUID.randomUUID(); + BigDecimal latitude = new BigDecimal("48.8566"); + BigDecimal longitude = new BigDecimal("2.3522"); + + response.setId(id); + response.setTypeAdresse("DOMICILE"); + response.setTypeAdresseLibelle("Adresse de domicile"); + response.setTypeAdresseIcone("home"); + response.setAdresse("123 Rue de la Paix"); + response.setComplementAdresse("Appartement 4B"); + response.setCodePostal("75001"); + response.setVille("Paris"); + response.setRegion("Île-de-France"); + response.setPays("France"); + response.setLatitude(latitude); + response.setLongitude(longitude); + response.setPrincipale(true); + response.setLibelle("Domicile principal"); + response.setNotes("Interphone code 1234"); + response.setOrganisationId(organisationId); + response.setMembreId(membreId); + response.setEvenementId(evenementId); + response.setAdresseComplete("123 Rue de la Paix, 75001 Paris, France"); + + assertThat(response.getId()).isEqualTo(id); + assertThat(response.getTypeAdresse()).isEqualTo("DOMICILE"); + assertThat(response.getTypeAdresseLibelle()).isEqualTo("Adresse de domicile"); + assertThat(response.getTypeAdresseIcone()).isEqualTo("home"); + assertThat(response.getAdresse()).isEqualTo("123 Rue de la Paix"); + assertThat(response.getComplementAdresse()).isEqualTo("Appartement 4B"); + assertThat(response.getCodePostal()).isEqualTo("75001"); + assertThat(response.getVille()).isEqualTo("Paris"); + assertThat(response.getRegion()).isEqualTo("Île-de-France"); + assertThat(response.getPays()).isEqualTo("France"); + assertThat(response.getLatitude()).isEqualTo(latitude); + assertThat(response.getLongitude()).isEqualTo(longitude); + assertThat(response.getPrincipale()).isTrue(); + assertThat(response.getLibelle()).isEqualTo("Domicile principal"); + assertThat(response.getNotes()).isEqualTo("Interphone code 1234"); + assertThat(response.getOrganisationId()).isEqualTo(organisationId); + assertThat(response.getMembreId()).isEqualTo(membreId); + assertThat(response.getEvenementId()).isEqualTo(evenementId); + assertThat(response.getAdresseComplete()).isEqualTo("123 Rue de la Paix, 75001 Paris, France"); + } + + @Test + @DisplayName("Les champs peuvent être null") + void testChampsNull() { + AdresseResponse response = new AdresseResponse(); + + response.setTypeAdresse(null); + response.setLatitude(null); + response.setLongitude(null); + response.setPrincipale(null); + response.setOrganisationId(null); + response.setMembreId(null); + response.setEvenementId(null); + + assertThat(response.getTypeAdresse()).isNull(); + assertThat(response.getLatitude()).isNull(); + assertThat(response.getLongitude()).isNull(); + assertThat(response.getPrincipale()).isNull(); + assertThat(response.getOrganisationId()).isNull(); + assertThat(response.getMembreId()).isNull(); + assertThat(response.getEvenementId()).isNull(); + } + } + + @Nested + @DisplayName("equals et hashCode") + class EqualsEtHashCode { + + @Test + @DisplayName("equals retourne true pour même id") + void testEqualsMemeId() { + UUID id = UUID.randomUUID(); + + AdresseResponse r1 = new AdresseResponse(); + r1.setId(id); + r1.setAdresse("Adresse 1"); + + AdresseResponse r2 = new AdresseResponse(); + r2.setId(id); + r2.setAdresse("Adresse 2"); + + assertThat(r1).isEqualTo(r2); + } + + @Test + @DisplayName("equals retourne false pour ids différents") + void testEqualsIdsDifferents() { + AdresseResponse r1 = new AdresseResponse(); + r1.setId(UUID.randomUUID()); + + AdresseResponse r2 = new AdresseResponse(); + r2.setId(UUID.randomUUID()); + + assertThat(r1).isNotEqualTo(r2); + } + + @Test + @DisplayName("hashCode est basé sur l'id") + void testHashCode() { + UUID id = UUID.randomUUID(); + + AdresseResponse r1 = new AdresseResponse(); + r1.setId(id); + + AdresseResponse r2 = new AdresseResponse(); + r2.setId(id); + + assertThat(r1.hashCode()).isEqualTo(r2.hashCode()); + } + } + + @Nested + @DisplayName("toString") + class ToString { + + @Test + @DisplayName("toString retourne une représentation non-null") + void testToString() { + AdresseResponse response = new AdresseResponse(); + response.setId(UUID.randomUUID()); + response.setAdresse("123 Rue Test"); + response.setVille("Paris"); + + String result = response.toString(); + assertThat(result).isNotNull(); + assertThat(result).contains("AdresseResponse"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/analytics/AnalyticsDataResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/analytics/AnalyticsDataResponseTest.java index 1950e55..f6cdee2 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/analytics/AnalyticsDataResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/analytics/AnalyticsDataResponseTest.java @@ -1,344 +1,344 @@ -package dev.lions.unionflow.server.api.dto.analytics; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.math.BigDecimal; -import java.time.LocalDateTime; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; -import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; - -/** - * Tests unitaires pour AnalyticsDataResponse. - * Couvre getLibelleAffichage, hasEvolutionPositive/Negative, isStable, getTendance, - * isDonneesFiables, isCritique, constructeur 3 args. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests AnalyticsDataResponse") -class AnalyticsDataResponseTest { - - private static final TypeMetrique TYPE = TypeMetrique.NOMBRE_MEMBRES_ACTIFS; - private static final PeriodeAnalyse PERIODE = PeriodeAnalyse.CETTE_SEMAINE; - - @Nested - @DisplayName("getLibelleAffichage") - class GetLibelleAffichage { - - @Test - @DisplayName("retourne typeMetrique.getLibelle() quand libellePersonnalise null") - void testLibelleNull() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()).build(); - assertThat(r.getLibelleAffichage()).isEqualTo(TYPE.getLibelle()); - } - - @Test - @DisplayName("retourne typeMetrique.getLibelle() quand libellePersonnalise vide ou blanc") - void testLibelleVide() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()) - .libellePersonnalise("").build(); - assertThat(r.getLibelleAffichage()).isEqualTo(TYPE.getLibelle()); - r.setLibellePersonnalise(" "); - assertThat(r.getLibelleAffichage()).isEqualTo(TYPE.getLibelle()); - } - - @Test - @DisplayName("retourne libellePersonnalise quand non vide") - void testLibellePersonnalise() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()) - .libellePersonnalise("Mon libellé").build(); - assertThat(r.getLibelleAffichage()).isEqualTo("Mon libellé"); - } - } - - @Nested - @DisplayName("getUnite, getIcone, getCouleur") - class DelegationTypeMetrique { - - @Test - @DisplayName("délèguent à typeMetrique") - void testDelegation() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()).build(); - assertThat(r.getUnite()).isEqualTo(TYPE.getUnite()); - assertThat(r.getIcone()).isEqualTo(TYPE.getIcone()); - assertThat(r.getCouleur()).isEqualTo(TYPE.getCouleur()); - } - } - - @Nested - @DisplayName("hasEvolutionPositive, hasEvolutionNegative, isStable") - class Evolution { - - @Test - @DisplayName("hasEvolutionPositive true quand pourcentageEvolution > 0") - void testEvolutionPositive() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()) - .pourcentageEvolution(BigDecimal.valueOf(5.5)).build(); - assertThat(r.hasEvolutionPositive()).isTrue(); - assertThat(r.hasEvolutionNegative()).isFalse(); - assertThat(r.isStable()).isFalse(); - } - - @Test - @DisplayName("hasEvolutionNegative true quand pourcentageEvolution < 0") - void testEvolutionNegative() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()) - .pourcentageEvolution(BigDecimal.valueOf(-3.2)).build(); - assertThat(r.hasEvolutionNegative()).isTrue(); - assertThat(r.hasEvolutionPositive()).isFalse(); - assertThat(r.isStable()).isFalse(); - } - - @Test - @DisplayName("isStable true quand pourcentageEvolution == 0") - void testStable() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()) - .pourcentageEvolution(BigDecimal.ZERO).build(); - assertThat(r.isStable()).isTrue(); - assertThat(r.hasEvolutionPositive()).isFalse(); - assertThat(r.hasEvolutionNegative()).isFalse(); - } - - @Test - @DisplayName("retournent false / false / false quand pourcentageEvolution null") - void testEvolutionNull() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()).build(); - assertThat(r.hasEvolutionPositive()).isFalse(); - assertThat(r.hasEvolutionNegative()).isFalse(); - assertThat(r.isStable()).isFalse(); - } - } - - @Nested - @DisplayName("getTendance") - class GetTendance { - - @Test - @DisplayName("retourne hausse quand évolution positive") - void testHausse() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()) - .pourcentageEvolution(BigDecimal.ONE).build(); - assertThat(r.getTendance()).isEqualTo("hausse"); - } - - @Test - @DisplayName("retourne baisse quand évolution négative") - void testBaisse() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()) - .pourcentageEvolution(BigDecimal.ONE.negate()).build(); - assertThat(r.getTendance()).isEqualTo("baisse"); - } - - @Test - @DisplayName("retourne stable sinon") - void testStable() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()) - .pourcentageEvolution(BigDecimal.ZERO).build(); - assertThat(r.getTendance()).isEqualTo("stable"); - r.setPourcentageEvolution(null); - assertThat(r.getTendance()).isEqualTo("stable"); - } - } - - @Nested - @DisplayName("isDonneesFiables") - class IsDonneesFiables { - - @Test - @DisplayName("retourne false quand indicateurFiabilite null") - void testNull() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()).build(); - assertThat(r.isDonneesFiables()).isFalse(); - } - - @Test - @DisplayName("retourne true quand indicateurFiabilite >= 80") - void testFiable() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()) - .indicateurFiabilite(new BigDecimal("80.0")).build(); - assertThat(r.isDonneesFiables()).isTrue(); - r.setIndicateurFiabilite(new BigDecimal("95.5")); - assertThat(r.isDonneesFiables()).isTrue(); - } - - @Test - @DisplayName("retourne false quand indicateurFiabilite < 80") - void testNonFiable() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()) - .indicateurFiabilite(new BigDecimal("79.9")).build(); - assertThat(r.isDonneesFiables()).isFalse(); - } - } - - @Nested - @DisplayName("isCritique") - class IsCritique { - - @Test - @DisplayName("retourne false quand niveauPriorite null ou < 4") - void testNonCritique() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()).build(); - assertThat(r.isCritique()).isFalse(); - r.setNiveauPriorite(3); - assertThat(r.isCritique()).isFalse(); - } - - @Test - @DisplayName("retourne true quand niveauPriorite >= 4") - void testCritique() { - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()) - .niveauPriorite(4).build(); - assertThat(r.isCritique()).isTrue(); - r.setNiveauPriorite(5); - assertThat(r.isCritique()).isTrue(); - } - } - - @Nested - @DisplayName("Constructeur 3 arguments") - class Constructeur3Args { - - @Test - @DisplayName("initialise typeMetrique, periodeAnalyse, valeur, dateCalcul, dateDebut, dateFin, défauts") - void testConstructeur() { - AnalyticsDataResponse r = new AnalyticsDataResponse(TYPE, PERIODE, BigDecimal.valueOf(42)); - assertThat(r.getTypeMetrique()).isEqualTo(TYPE); - assertThat(r.getPeriodeAnalyse()).isEqualTo(PERIODE); - assertThat(r.getValeur()).isEqualByComparingTo(BigDecimal.valueOf(42)); - assertThat(r.getDateCalcul()).isNotNull(); - assertThat(r.getDateDebut()).isEqualTo(PERIODE.getDateDebut()); - assertThat(r.getDateFin()).isEqualTo(PERIODE.getDateFin()); - assertThat(r.getTempsReel()).isFalse(); - assertThat(r.getNecessiteMiseAJour()).isFalse(); - assertThat(r.getNiveauPriorite()).isEqualTo(3); - assertThat(r.getIndicateurFiabilite()).isEqualByComparingTo(new BigDecimal("95.0")); - } - } - - @Nested - @DisplayName("Builder et getters") - class BuilderGetters { - - @Test - @DisplayName("champs optionnels accessibles") - void testBuilder() { - UUID orgId = UUID.randomUUID(); - AnalyticsDataResponse r = AnalyticsDataResponse.builder() - .typeMetrique(TYPE) - .periodeAnalyse(PERIODE) - .valeur(BigDecimal.ONE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .dateCalcul(LocalDateTime.now()) - .organisationId(orgId) - .nomOrganisation("Org") - .tempsReel(true) - .necessiteMiseAJour(true).build(); - assertThat(r.getOrganisationId()).isEqualTo(orgId); - assertThat(r.getNomOrganisation()).isEqualTo("Org"); - assertThat(r.getTempsReel()).isTrue(); - assertThat(r.getNecessiteMiseAJour()).isTrue(); - } - } -} +package dev.lions.unionflow.server.api.dto.analytics; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.math.BigDecimal; +import java.time.LocalDateTime; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; +import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; + +/** + * Tests unitaires pour AnalyticsDataResponse. + * Couvre getLibelleAffichage, hasEvolutionPositive/Negative, isStable, getTendance, + * isDonneesFiables, isCritique, constructeur 3 args. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests AnalyticsDataResponse") +class AnalyticsDataResponseTest { + + private static final TypeMetrique TYPE = TypeMetrique.NOMBRE_MEMBRES_ACTIFS; + private static final PeriodeAnalyse PERIODE = PeriodeAnalyse.CETTE_SEMAINE; + + @Nested + @DisplayName("getLibelleAffichage") + class GetLibelleAffichage { + + @Test + @DisplayName("retourne typeMetrique.getLibelle() quand libellePersonnalise null") + void testLibelleNull() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()).build(); + assertThat(r.getLibelleAffichage()).isEqualTo(TYPE.getLibelle()); + } + + @Test + @DisplayName("retourne typeMetrique.getLibelle() quand libellePersonnalise vide ou blanc") + void testLibelleVide() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()) + .libellePersonnalise("").build(); + assertThat(r.getLibelleAffichage()).isEqualTo(TYPE.getLibelle()); + r.setLibellePersonnalise(" "); + assertThat(r.getLibelleAffichage()).isEqualTo(TYPE.getLibelle()); + } + + @Test + @DisplayName("retourne libellePersonnalise quand non vide") + void testLibellePersonnalise() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()) + .libellePersonnalise("Mon libellé").build(); + assertThat(r.getLibelleAffichage()).isEqualTo("Mon libellé"); + } + } + + @Nested + @DisplayName("getUnite, getIcone, getCouleur") + class DelegationTypeMetrique { + + @Test + @DisplayName("délèguent à typeMetrique") + void testDelegation() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()).build(); + assertThat(r.getUnite()).isEqualTo(TYPE.getUnite()); + assertThat(r.getIcone()).isEqualTo(TYPE.getIcone()); + assertThat(r.getCouleur()).isEqualTo(TYPE.getCouleur()); + } + } + + @Nested + @DisplayName("hasEvolutionPositive, hasEvolutionNegative, isStable") + class Evolution { + + @Test + @DisplayName("hasEvolutionPositive true quand pourcentageEvolution > 0") + void testEvolutionPositive() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()) + .pourcentageEvolution(BigDecimal.valueOf(5.5)).build(); + assertThat(r.hasEvolutionPositive()).isTrue(); + assertThat(r.hasEvolutionNegative()).isFalse(); + assertThat(r.isStable()).isFalse(); + } + + @Test + @DisplayName("hasEvolutionNegative true quand pourcentageEvolution < 0") + void testEvolutionNegative() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()) + .pourcentageEvolution(BigDecimal.valueOf(-3.2)).build(); + assertThat(r.hasEvolutionNegative()).isTrue(); + assertThat(r.hasEvolutionPositive()).isFalse(); + assertThat(r.isStable()).isFalse(); + } + + @Test + @DisplayName("isStable true quand pourcentageEvolution == 0") + void testStable() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()) + .pourcentageEvolution(BigDecimal.ZERO).build(); + assertThat(r.isStable()).isTrue(); + assertThat(r.hasEvolutionPositive()).isFalse(); + assertThat(r.hasEvolutionNegative()).isFalse(); + } + + @Test + @DisplayName("retournent false / false / false quand pourcentageEvolution null") + void testEvolutionNull() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()).build(); + assertThat(r.hasEvolutionPositive()).isFalse(); + assertThat(r.hasEvolutionNegative()).isFalse(); + assertThat(r.isStable()).isFalse(); + } + } + + @Nested + @DisplayName("getTendance") + class GetTendance { + + @Test + @DisplayName("retourne hausse quand évolution positive") + void testHausse() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()) + .pourcentageEvolution(BigDecimal.ONE).build(); + assertThat(r.getTendance()).isEqualTo("hausse"); + } + + @Test + @DisplayName("retourne baisse quand évolution négative") + void testBaisse() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()) + .pourcentageEvolution(BigDecimal.ONE.negate()).build(); + assertThat(r.getTendance()).isEqualTo("baisse"); + } + + @Test + @DisplayName("retourne stable sinon") + void testStable() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()) + .pourcentageEvolution(BigDecimal.ZERO).build(); + assertThat(r.getTendance()).isEqualTo("stable"); + r.setPourcentageEvolution(null); + assertThat(r.getTendance()).isEqualTo("stable"); + } + } + + @Nested + @DisplayName("isDonneesFiables") + class IsDonneesFiables { + + @Test + @DisplayName("retourne false quand indicateurFiabilite null") + void testNull() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()).build(); + assertThat(r.isDonneesFiables()).isFalse(); + } + + @Test + @DisplayName("retourne true quand indicateurFiabilite >= 80") + void testFiable() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()) + .indicateurFiabilite(new BigDecimal("80.0")).build(); + assertThat(r.isDonneesFiables()).isTrue(); + r.setIndicateurFiabilite(new BigDecimal("95.5")); + assertThat(r.isDonneesFiables()).isTrue(); + } + + @Test + @DisplayName("retourne false quand indicateurFiabilite < 80") + void testNonFiable() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()) + .indicateurFiabilite(new BigDecimal("79.9")).build(); + assertThat(r.isDonneesFiables()).isFalse(); + } + } + + @Nested + @DisplayName("isCritique") + class IsCritique { + + @Test + @DisplayName("retourne false quand niveauPriorite null ou < 4") + void testNonCritique() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()).build(); + assertThat(r.isCritique()).isFalse(); + r.setNiveauPriorite(3); + assertThat(r.isCritique()).isFalse(); + } + + @Test + @DisplayName("retourne true quand niveauPriorite >= 4") + void testCritique() { + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()) + .niveauPriorite(4).build(); + assertThat(r.isCritique()).isTrue(); + r.setNiveauPriorite(5); + assertThat(r.isCritique()).isTrue(); + } + } + + @Nested + @DisplayName("Constructeur 3 arguments") + class Constructeur3Args { + + @Test + @DisplayName("initialise typeMetrique, periodeAnalyse, valeur, dateCalcul, dateDebut, dateFin, défauts") + void testConstructeur() { + AnalyticsDataResponse r = new AnalyticsDataResponse(TYPE, PERIODE, BigDecimal.valueOf(42)); + assertThat(r.getTypeMetrique()).isEqualTo(TYPE); + assertThat(r.getPeriodeAnalyse()).isEqualTo(PERIODE); + assertThat(r.getValeur()).isEqualByComparingTo(BigDecimal.valueOf(42)); + assertThat(r.getDateCalcul()).isNotNull(); + assertThat(r.getDateDebut()).isEqualTo(PERIODE.getDateDebut()); + assertThat(r.getDateFin()).isEqualTo(PERIODE.getDateFin()); + assertThat(r.getTempsReel()).isFalse(); + assertThat(r.getNecessiteMiseAJour()).isFalse(); + assertThat(r.getNiveauPriorite()).isEqualTo(3); + assertThat(r.getIndicateurFiabilite()).isEqualByComparingTo(new BigDecimal("95.0")); + } + } + + @Nested + @DisplayName("Builder et getters") + class BuilderGetters { + + @Test + @DisplayName("champs optionnels accessibles") + void testBuilder() { + UUID orgId = UUID.randomUUID(); + AnalyticsDataResponse r = AnalyticsDataResponse.builder() + .typeMetrique(TYPE) + .periodeAnalyse(PERIODE) + .valeur(BigDecimal.ONE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .dateCalcul(LocalDateTime.now()) + .organisationId(orgId) + .nomOrganisation("Org") + .tempsReel(true) + .necessiteMiseAJour(true).build(); + assertThat(r.getOrganisationId()).isEqualTo(orgId); + assertThat(r.getNomOrganisation()).isEqualTo("Org"); + assertThat(r.getTempsReel()).isTrue(); + assertThat(r.getNecessiteMiseAJour()).isTrue(); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/analytics/DashboardWidgetResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/analytics/DashboardWidgetResponseTest.java index 371ec4c..6759a80 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/analytics/DashboardWidgetResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/analytics/DashboardWidgetResponseTest.java @@ -1,350 +1,350 @@ -package dev.lions.unionflow.server.api.dto.analytics; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalDateTime; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; -import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; - -/** - * Tests unitaires pour DashboardWidgetResponse. - * Couvre getLibelleMetrique, getUnite, getIconeAffichage, getCouleurAffichage, - * necessiteMiseAJour, isInteractif, isTempsReel, getTailleWidget, isWidgetGrand, - * hasErreursRecentes, getStatutWidget. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests DashboardWidgetResponse") -class DashboardWidgetResponseTest { - - private static DashboardWidgetResponse minimalWidget() { - return DashboardWidgetResponse.builder() - .titre("Widget") - .typeWidget("kpi") - .utilisateurProprietaireId(UUID.randomUUID()) - .positionX(0) - .positionY(0) - .largeur(2) - .hauteur(2).build(); - } - - @Nested - @DisplayName("getLibelleMetrique") - class GetLibelleMetrique { - - @Test - @DisplayName("retourne null quand typeMetrique null") - void testNull() { - DashboardWidgetResponse w = minimalWidget(); - assertThat(w.getLibelleMetrique()).isNull(); - } - - @Test - @DisplayName("retourne typeMetrique.getLibelle() quand défini") - void testLibelle() { - DashboardWidgetResponse w = minimalWidget(); - w.setTypeMetrique(TypeMetrique.NOMBRE_MEMBRES_ACTIFS); - assertThat(w.getLibelleMetrique()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getLibelle()); - } - } - - @Nested - @DisplayName("getUnite") - class GetUnite { - - @Test - @DisplayName("retourne chaîne vide quand typeMetrique null") - void testNull() { - DashboardWidgetResponse w = minimalWidget(); - assertThat(w.getUnite()).isEmpty(); - } - - @Test - @DisplayName("retourne typeMetrique.getUnite() quand défini") - void testUnite() { - DashboardWidgetResponse w = minimalWidget(); - w.setTypeMetrique(TypeMetrique.NOMBRE_MEMBRES_ACTIFS); - assertThat(w.getUnite()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getUnite()); - } - } - - @Nested - @DisplayName("getIconeAffichage") - class GetIconeAffichage { - - @Test - @DisplayName("retourne icone personnalisée si non vide") - void testPersonnalise() { - DashboardWidgetResponse w = minimalWidget(); - w.setIcone("custom_icon"); - assertThat(w.getIconeAffichage()).isEqualTo("custom_icon"); - } - - @Test - @DisplayName("retourne typeMetrique.getIcone() si icone null") - void testTypeMetrique() { - DashboardWidgetResponse w = minimalWidget(); - w.setTypeMetrique(TypeMetrique.NOMBRE_MEMBRES_ACTIFS); - assertThat(w.getIconeAffichage()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getIcone()); - } - - @Test - @DisplayName("retourne dashboard si icone vide et typeMetrique null") - void testDefault() { - DashboardWidgetResponse w = minimalWidget(); - w.setIcone(" "); - assertThat(w.getIconeAffichage()).isEqualTo("dashboard"); - } - - @Test - @DisplayName("retourne dashboard si icone null et typeMetrique null") - void testIconeNullTypeMetriqueNull() { - DashboardWidgetResponse w = minimalWidget(); - w.setIcone(null); - w.setTypeMetrique(null); - assertThat(w.getIconeAffichage()).isEqualTo("dashboard"); - } - } - - @Nested - @DisplayName("getCouleurAffichage") - class GetCouleurAffichage { - - @Test - @DisplayName("retourne couleurPrincipale si non vide") - void testPersonnalise() { - DashboardWidgetResponse w = minimalWidget(); - w.setCouleurPrincipale("#FF0000"); - assertThat(w.getCouleurAffichage()).isEqualTo("#FF0000"); - } - - @Test - @DisplayName("retourne typeMetrique.getCouleur() si couleurPrincipale null") - void testTypeMetrique() { - DashboardWidgetResponse w = minimalWidget(); - w.setTypeMetrique(TypeMetrique.NOMBRE_MEMBRES_ACTIFS); - assertThat(w.getCouleurAffichage()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getCouleur()); - } - - @Test - @DisplayName("retourne #757575 si couleurPrincipale vide et typeMetrique null") - void testDefault() { - DashboardWidgetResponse w = minimalWidget(); - w.setCouleurPrincipale(" "); - assertThat(w.getCouleurAffichage()).isEqualTo("#757575"); - } - - @Test - @DisplayName("retourne #757575 si couleurPrincipale null et typeMetrique null") - void testCouleurNullTypeMetriqueNull() { - DashboardWidgetResponse w = minimalWidget(); - w.setCouleurPrincipale(null); - w.setTypeMetrique(null); - assertThat(w.getCouleurAffichage()).isEqualTo("#757575"); - } - } - - @Nested - @DisplayName("necessiteMiseAJour") - class NecessiteMiseAJour { - - @Test - @DisplayName("retourne true quand miseAJourAutomatique et prochaineMiseAJour dans le passé") - void testTrue() { - DashboardWidgetResponse w = minimalWidget(); - w.setMiseAJourAutomatique(true); - w.setProchaineMiseAJour(LocalDateTime.now().minusMinutes(5)); - assertThat(w.necessiteMiseAJour()).isTrue(); - } - - @Test - @DisplayName("retourne false quand miseAJourAutomatique false") - void testFalseNonAuto() { - DashboardWidgetResponse w = minimalWidget(); - w.setMiseAJourAutomatique(false); - w.setProchaineMiseAJour(LocalDateTime.now().minusMinutes(5)); - assertThat(w.necessiteMiseAJour()).isFalse(); - } - - @Test - @DisplayName("retourne false quand prochaineMiseAJour null ou futur") - void testFalseFutur() { - DashboardWidgetResponse w = minimalWidget(); - w.setMiseAJourAutomatique(true); - w.setProchaineMiseAJour(null); - assertThat(w.necessiteMiseAJour()).isFalse(); - w.setProchaineMiseAJour(LocalDateTime.now().plusHours(1)); - assertThat(w.necessiteMiseAJour()).isFalse(); - } - } - - @Nested - @DisplayName("isInteractif") - class IsInteractif { - - @Test - @DisplayName("retourne true pour chart, table, gauge") - void testInteractif() { - assertThat(DashboardWidgetResponse.builder().titre("x").typeWidget("chart").utilisateurProprietaireId(UUID.randomUUID()).positionX(0).positionY(0).largeur(1).hauteur(1).build().isInteractif()).isTrue(); - DashboardWidgetResponse w = minimalWidget(); - w.setTypeWidget("table"); - assertThat(w.isInteractif()).isTrue(); - w.setTypeWidget("gauge"); - assertThat(w.isInteractif()).isTrue(); - } - - @Test - @DisplayName("retourne false pour kpi, progress, text") - void testNonInteractif() { - DashboardWidgetResponse w = minimalWidget(); - w.setTypeWidget("kpi"); - assertThat(w.isInteractif()).isFalse(); - w.setTypeWidget("text"); - assertThat(w.isInteractif()).isFalse(); - } - } - - @Nested - @DisplayName("isTempsReel") - class IsTempsReel { - - @Test - @DisplayName("retourne true quand frequenceMiseAJourSecondes <= 60") - void testTempsReel() { - DashboardWidgetResponse w = minimalWidget(); - w.setFrequenceMiseAJourSecondes(30); - assertThat(w.isTempsReel()).isTrue(); - w.setFrequenceMiseAJourSecondes(60); - assertThat(w.isTempsReel()).isTrue(); - } - - @Test - @DisplayName("retourne false quand frequenceMiseAJourSecondes > 60 ou null") - void testNonTempsReel() { - DashboardWidgetResponse w = minimalWidget(); - assertThat(w.isTempsReel()).isFalse(); - w.setFrequenceMiseAJourSecondes(300); - assertThat(w.isTempsReel()).isFalse(); - w.setFrequenceMiseAJourSecondes(61); - assertThat(w.isTempsReel()).isFalse(); - } - - @Test - @DisplayName("retourne false quand frequenceMiseAJourSecondes explicitement null") - void testTempsReelFrequenceNull() { - DashboardWidgetResponse w = minimalWidget(); - w.setFrequenceMiseAJourSecondes(30); - w.setFrequenceMiseAJourSecondes(null); - assertThat(w.isTempsReel()).isFalse(); - } - } - - @Nested - @DisplayName("getTailleWidget et isWidgetGrand") - class TailleWidget { - - @Test - @DisplayName("getTailleWidget retourne largeur * hauteur") - void testTaille() { - DashboardWidgetResponse w = minimalWidget(); - w.setLargeur(3); - w.setHauteur(2); - assertThat(w.getTailleWidget()).isEqualTo(6); - } - - @Test - @DisplayName("isWidgetGrand true quand surface > 6") - void testGrand() { - DashboardWidgetResponse w = minimalWidget(); - w.setLargeur(4); - w.setHauteur(2); - assertThat(w.getTailleWidget()).isEqualTo(8); - assertThat(w.isWidgetGrand()).isTrue(); - } - - @Test - @DisplayName("isWidgetGrand false quand surface <= 6") - void testPetit() { - DashboardWidgetResponse w = minimalWidget(); - assertThat(w.getTailleWidget()).isEqualTo(4); - assertThat(w.isWidgetGrand()).isFalse(); - } - } - - @Nested - @DisplayName("hasErreursRecentes et getStatutWidget") - class ErreursEtStatut { - - @Test - @DisplayName("hasErreursRecentes true quand dateDerniereErreur < 24h") - void testErreurRecente() { - DashboardWidgetResponse w = minimalWidget(); - w.setDateDerniereErreur(LocalDateTime.now().minusHours(2)); - assertThat(w.hasErreursRecentes()).isTrue(); - } - - @Test - @DisplayName("hasErreursRecentes false quand dateDerniereErreur null ou > 24h") - void testPasErreurRecente() { - DashboardWidgetResponse w = minimalWidget(); - assertThat(w.hasErreursRecentes()).isFalse(); - w.setDateDerniereErreur(LocalDateTime.now().minusHours(25)); - assertThat(w.hasErreursRecentes()).isFalse(); - } - - @Test - @DisplayName("getStatutWidget retourne erreur si hasErreursRecentes") - void testStatutErreur() { - DashboardWidgetResponse w = minimalWidget(); - w.setDateDerniereErreur(LocalDateTime.now().minusHours(1)); - assertThat(w.getStatutWidget()).isEqualTo("erreur"); - } - - @Test - @DisplayName("getStatutWidget retourne inactif si visible false") - void testStatutInactif() { - DashboardWidgetResponse w = minimalWidget(); - w.setVisible(false); - assertThat(w.getStatutWidget()).isEqualTo("inactif"); - } - - @Test - @DisplayName("getStatutWidget retourne maintenance si tauxErreur > 10") - void testStatutMaintenance() { - DashboardWidgetResponse w = minimalWidget(); - w.setTauxErreur(15.0); - assertThat(w.getStatutWidget()).isEqualTo("maintenance"); - } - - @Test - @DisplayName("getStatutWidget retourne actif sinon") - void testStatutActif() { - DashboardWidgetResponse w = minimalWidget(); - assertThat(w.getStatutWidget()).isEqualTo("actif"); - } - - @Test - @DisplayName("getStatutWidget retourne actif quand tauxErreur non null mais <= 10") - void testStatutActifTauxErreurFaible() { - DashboardWidgetResponse w = minimalWidget(); - w.setTauxErreur(5.0); - w.setVisible(true); - assertThat(w.getStatutWidget()).isEqualTo("actif"); - } - - @Test - @DisplayName("getStatutWidget retourne actif quand tauxErreur explicitement null") - void testStatutActifTauxErreurNull() { - DashboardWidgetResponse w = minimalWidget(); - w.setTauxErreur(15.0); - w.setTauxErreur(null); - assertThat(w.getStatutWidget()).isEqualTo("actif"); - } - } -} +package dev.lions.unionflow.server.api.dto.analytics; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalDateTime; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; +import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; + +/** + * Tests unitaires pour DashboardWidgetResponse. + * Couvre getLibelleMetrique, getUnite, getIconeAffichage, getCouleurAffichage, + * necessiteMiseAJour, isInteractif, isTempsReel, getTailleWidget, isWidgetGrand, + * hasErreursRecentes, getStatutWidget. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests DashboardWidgetResponse") +class DashboardWidgetResponseTest { + + private static DashboardWidgetResponse minimalWidget() { + return DashboardWidgetResponse.builder() + .titre("Widget") + .typeWidget("kpi") + .utilisateurProprietaireId(UUID.randomUUID()) + .positionX(0) + .positionY(0) + .largeur(2) + .hauteur(2).build(); + } + + @Nested + @DisplayName("getLibelleMetrique") + class GetLibelleMetrique { + + @Test + @DisplayName("retourne null quand typeMetrique null") + void testNull() { + DashboardWidgetResponse w = minimalWidget(); + assertThat(w.getLibelleMetrique()).isNull(); + } + + @Test + @DisplayName("retourne typeMetrique.getLibelle() quand défini") + void testLibelle() { + DashboardWidgetResponse w = minimalWidget(); + w.setTypeMetrique(TypeMetrique.NOMBRE_MEMBRES_ACTIFS); + assertThat(w.getLibelleMetrique()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getLibelle()); + } + } + + @Nested + @DisplayName("getUnite") + class GetUnite { + + @Test + @DisplayName("retourne chaîne vide quand typeMetrique null") + void testNull() { + DashboardWidgetResponse w = minimalWidget(); + assertThat(w.getUnite()).isEmpty(); + } + + @Test + @DisplayName("retourne typeMetrique.getUnite() quand défini") + void testUnite() { + DashboardWidgetResponse w = minimalWidget(); + w.setTypeMetrique(TypeMetrique.NOMBRE_MEMBRES_ACTIFS); + assertThat(w.getUnite()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getUnite()); + } + } + + @Nested + @DisplayName("getIconeAffichage") + class GetIconeAffichage { + + @Test + @DisplayName("retourne icone personnalisée si non vide") + void testPersonnalise() { + DashboardWidgetResponse w = minimalWidget(); + w.setIcone("custom_icon"); + assertThat(w.getIconeAffichage()).isEqualTo("custom_icon"); + } + + @Test + @DisplayName("retourne typeMetrique.getIcone() si icone null") + void testTypeMetrique() { + DashboardWidgetResponse w = minimalWidget(); + w.setTypeMetrique(TypeMetrique.NOMBRE_MEMBRES_ACTIFS); + assertThat(w.getIconeAffichage()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getIcone()); + } + + @Test + @DisplayName("retourne dashboard si icone vide et typeMetrique null") + void testDefault() { + DashboardWidgetResponse w = minimalWidget(); + w.setIcone(" "); + assertThat(w.getIconeAffichage()).isEqualTo("dashboard"); + } + + @Test + @DisplayName("retourne dashboard si icone null et typeMetrique null") + void testIconeNullTypeMetriqueNull() { + DashboardWidgetResponse w = minimalWidget(); + w.setIcone(null); + w.setTypeMetrique(null); + assertThat(w.getIconeAffichage()).isEqualTo("dashboard"); + } + } + + @Nested + @DisplayName("getCouleurAffichage") + class GetCouleurAffichage { + + @Test + @DisplayName("retourne couleurPrincipale si non vide") + void testPersonnalise() { + DashboardWidgetResponse w = minimalWidget(); + w.setCouleurPrincipale("#FF0000"); + assertThat(w.getCouleurAffichage()).isEqualTo("#FF0000"); + } + + @Test + @DisplayName("retourne typeMetrique.getCouleur() si couleurPrincipale null") + void testTypeMetrique() { + DashboardWidgetResponse w = minimalWidget(); + w.setTypeMetrique(TypeMetrique.NOMBRE_MEMBRES_ACTIFS); + assertThat(w.getCouleurAffichage()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getCouleur()); + } + + @Test + @DisplayName("retourne #757575 si couleurPrincipale vide et typeMetrique null") + void testDefault() { + DashboardWidgetResponse w = minimalWidget(); + w.setCouleurPrincipale(" "); + assertThat(w.getCouleurAffichage()).isEqualTo("#757575"); + } + + @Test + @DisplayName("retourne #757575 si couleurPrincipale null et typeMetrique null") + void testCouleurNullTypeMetriqueNull() { + DashboardWidgetResponse w = minimalWidget(); + w.setCouleurPrincipale(null); + w.setTypeMetrique(null); + assertThat(w.getCouleurAffichage()).isEqualTo("#757575"); + } + } + + @Nested + @DisplayName("necessiteMiseAJour") + class NecessiteMiseAJour { + + @Test + @DisplayName("retourne true quand miseAJourAutomatique et prochaineMiseAJour dans le passé") + void testTrue() { + DashboardWidgetResponse w = minimalWidget(); + w.setMiseAJourAutomatique(true); + w.setProchaineMiseAJour(LocalDateTime.now().minusMinutes(5)); + assertThat(w.necessiteMiseAJour()).isTrue(); + } + + @Test + @DisplayName("retourne false quand miseAJourAutomatique false") + void testFalseNonAuto() { + DashboardWidgetResponse w = minimalWidget(); + w.setMiseAJourAutomatique(false); + w.setProchaineMiseAJour(LocalDateTime.now().minusMinutes(5)); + assertThat(w.necessiteMiseAJour()).isFalse(); + } + + @Test + @DisplayName("retourne false quand prochaineMiseAJour null ou futur") + void testFalseFutur() { + DashboardWidgetResponse w = minimalWidget(); + w.setMiseAJourAutomatique(true); + w.setProchaineMiseAJour(null); + assertThat(w.necessiteMiseAJour()).isFalse(); + w.setProchaineMiseAJour(LocalDateTime.now().plusHours(1)); + assertThat(w.necessiteMiseAJour()).isFalse(); + } + } + + @Nested + @DisplayName("isInteractif") + class IsInteractif { + + @Test + @DisplayName("retourne true pour chart, table, gauge") + void testInteractif() { + assertThat(DashboardWidgetResponse.builder().titre("x").typeWidget("chart").utilisateurProprietaireId(UUID.randomUUID()).positionX(0).positionY(0).largeur(1).hauteur(1).build().isInteractif()).isTrue(); + DashboardWidgetResponse w = minimalWidget(); + w.setTypeWidget("table"); + assertThat(w.isInteractif()).isTrue(); + w.setTypeWidget("gauge"); + assertThat(w.isInteractif()).isTrue(); + } + + @Test + @DisplayName("retourne false pour kpi, progress, text") + void testNonInteractif() { + DashboardWidgetResponse w = minimalWidget(); + w.setTypeWidget("kpi"); + assertThat(w.isInteractif()).isFalse(); + w.setTypeWidget("text"); + assertThat(w.isInteractif()).isFalse(); + } + } + + @Nested + @DisplayName("isTempsReel") + class IsTempsReel { + + @Test + @DisplayName("retourne true quand frequenceMiseAJourSecondes <= 60") + void testTempsReel() { + DashboardWidgetResponse w = minimalWidget(); + w.setFrequenceMiseAJourSecondes(30); + assertThat(w.isTempsReel()).isTrue(); + w.setFrequenceMiseAJourSecondes(60); + assertThat(w.isTempsReel()).isTrue(); + } + + @Test + @DisplayName("retourne false quand frequenceMiseAJourSecondes > 60 ou null") + void testNonTempsReel() { + DashboardWidgetResponse w = minimalWidget(); + assertThat(w.isTempsReel()).isFalse(); + w.setFrequenceMiseAJourSecondes(300); + assertThat(w.isTempsReel()).isFalse(); + w.setFrequenceMiseAJourSecondes(61); + assertThat(w.isTempsReel()).isFalse(); + } + + @Test + @DisplayName("retourne false quand frequenceMiseAJourSecondes explicitement null") + void testTempsReelFrequenceNull() { + DashboardWidgetResponse w = minimalWidget(); + w.setFrequenceMiseAJourSecondes(30); + w.setFrequenceMiseAJourSecondes(null); + assertThat(w.isTempsReel()).isFalse(); + } + } + + @Nested + @DisplayName("getTailleWidget et isWidgetGrand") + class TailleWidget { + + @Test + @DisplayName("getTailleWidget retourne largeur * hauteur") + void testTaille() { + DashboardWidgetResponse w = minimalWidget(); + w.setLargeur(3); + w.setHauteur(2); + assertThat(w.getTailleWidget()).isEqualTo(6); + } + + @Test + @DisplayName("isWidgetGrand true quand surface > 6") + void testGrand() { + DashboardWidgetResponse w = minimalWidget(); + w.setLargeur(4); + w.setHauteur(2); + assertThat(w.getTailleWidget()).isEqualTo(8); + assertThat(w.isWidgetGrand()).isTrue(); + } + + @Test + @DisplayName("isWidgetGrand false quand surface <= 6") + void testPetit() { + DashboardWidgetResponse w = minimalWidget(); + assertThat(w.getTailleWidget()).isEqualTo(4); + assertThat(w.isWidgetGrand()).isFalse(); + } + } + + @Nested + @DisplayName("hasErreursRecentes et getStatutWidget") + class ErreursEtStatut { + + @Test + @DisplayName("hasErreursRecentes true quand dateDerniereErreur < 24h") + void testErreurRecente() { + DashboardWidgetResponse w = minimalWidget(); + w.setDateDerniereErreur(LocalDateTime.now().minusHours(2)); + assertThat(w.hasErreursRecentes()).isTrue(); + } + + @Test + @DisplayName("hasErreursRecentes false quand dateDerniereErreur null ou > 24h") + void testPasErreurRecente() { + DashboardWidgetResponse w = minimalWidget(); + assertThat(w.hasErreursRecentes()).isFalse(); + w.setDateDerniereErreur(LocalDateTime.now().minusHours(25)); + assertThat(w.hasErreursRecentes()).isFalse(); + } + + @Test + @DisplayName("getStatutWidget retourne erreur si hasErreursRecentes") + void testStatutErreur() { + DashboardWidgetResponse w = minimalWidget(); + w.setDateDerniereErreur(LocalDateTime.now().minusHours(1)); + assertThat(w.getStatutWidget()).isEqualTo("erreur"); + } + + @Test + @DisplayName("getStatutWidget retourne inactif si visible false") + void testStatutInactif() { + DashboardWidgetResponse w = minimalWidget(); + w.setVisible(false); + assertThat(w.getStatutWidget()).isEqualTo("inactif"); + } + + @Test + @DisplayName("getStatutWidget retourne maintenance si tauxErreur > 10") + void testStatutMaintenance() { + DashboardWidgetResponse w = minimalWidget(); + w.setTauxErreur(15.0); + assertThat(w.getStatutWidget()).isEqualTo("maintenance"); + } + + @Test + @DisplayName("getStatutWidget retourne actif sinon") + void testStatutActif() { + DashboardWidgetResponse w = minimalWidget(); + assertThat(w.getStatutWidget()).isEqualTo("actif"); + } + + @Test + @DisplayName("getStatutWidget retourne actif quand tauxErreur non null mais <= 10") + void testStatutActifTauxErreurFaible() { + DashboardWidgetResponse w = minimalWidget(); + w.setTauxErreur(5.0); + w.setVisible(true); + assertThat(w.getStatutWidget()).isEqualTo("actif"); + } + + @Test + @DisplayName("getStatutWidget retourne actif quand tauxErreur explicitement null") + void testStatutActifTauxErreurNull() { + DashboardWidgetResponse w = minimalWidget(); + w.setTauxErreur(15.0); + w.setTauxErreur(null); + assertThat(w.getStatutWidget()).isEqualTo("actif"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/analytics/KPITrendResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/analytics/KPITrendResponseTest.java index 910eb9a..a9ec560 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/analytics/KPITrendResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/analytics/KPITrendResponseTest.java @@ -1,220 +1,220 @@ -package dev.lions.unionflow.server.api.dto.analytics; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.math.BigDecimal; -import java.time.LocalDateTime; -import java.util.List; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; -import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; - -/** - * Tests unitaires pour KPITrendResponse. - * Couvre getLibelleMetrique, getUnite, getIcone, getCouleur, isTendancePositive/Negative/Stable, - * getVolatilite, isPredictionFiable, getNombrePointsDonnees, hasAnomalies. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests KPITrendResponse") -class KPITrendResponseTest { - - private static KPITrendResponse minimalKpi() { - return KPITrendResponse.builder() - .typeMetrique(TypeMetrique.NOMBRE_MEMBRES_ACTIFS) - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .pointsDonnees(List.of()) - .valeurActuelle(BigDecimal.ONE).build(); - } - - @Nested - @DisplayName("getLibelleMetrique, getUnite, getIcone, getCouleur") - class DelegationTypeMetrique { - - @Test - @DisplayName("délèguent à typeMetrique") - void testDelegation() { - KPITrendResponse k = minimalKpi(); - assertThat(k.getLibelleMetrique()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getLibelle()); - assertThat(k.getUnite()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getUnite()); - assertThat(k.getIcone()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getIcone()); - assertThat(k.getCouleur()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getCouleur()); - } - } - - @Nested - @DisplayName("isTendancePositive, isTendanceNegative, isTendanceStable") - class Tendance { - - @Test - @DisplayName("isTendancePositive true quand tendanceGenerale > 0") - void testPositive() { - KPITrendResponse k = minimalKpi(); - k.setTendanceGenerale(BigDecimal.ONE); - assertThat(k.isTendancePositive()).isTrue(); - assertThat(k.isTendanceNegative()).isFalse(); - assertThat(k.isTendanceStable()).isFalse(); - } - - @Test - @DisplayName("isTendanceNegative true quand tendanceGenerale < 0") - void testNegative() { - KPITrendResponse k = minimalKpi(); - k.setTendanceGenerale(BigDecimal.ONE.negate()); - assertThat(k.isTendanceNegative()).isTrue(); - assertThat(k.isTendancePositive()).isFalse(); - assertThat(k.isTendanceStable()).isFalse(); - } - - @Test - @DisplayName("isTendanceStable true quand tendanceGenerale == 0") - void testStable() { - KPITrendResponse k = minimalKpi(); - k.setTendanceGenerale(BigDecimal.ZERO); - assertThat(k.isTendanceStable()).isTrue(); - assertThat(k.isTendancePositive()).isFalse(); - assertThat(k.isTendanceNegative()).isFalse(); - } - - @Test - @DisplayName("toutes false quand tendanceGenerale null") - void testNull() { - KPITrendResponse k = minimalKpi(); - assertThat(k.isTendancePositive()).isFalse(); - assertThat(k.isTendanceNegative()).isFalse(); - assertThat(k.isTendanceStable()).isFalse(); - } - } - - @Nested - @DisplayName("getVolatilite") - class GetVolatilite { - - @Test - @DisplayName("retourne inconnue quand coefficientVariation null") - void testNull() { - KPITrendResponse k = minimalKpi(); - assertThat(k.getVolatilite()).isEqualTo("inconnue"); - } - - @Test - @DisplayName("retourne faible quand cv <= 0.1") - void testFaible() { - KPITrendResponse k = minimalKpi(); - k.setCoefficientVariation(new BigDecimal("0.05")); - assertThat(k.getVolatilite()).isEqualTo("faible"); - k.setCoefficientVariation(new BigDecimal("0.1")); - assertThat(k.getVolatilite()).isEqualTo("faible"); - } - - @Test - @DisplayName("retourne moyenne quand cv <= 0.3 et > 0.1") - void testMoyenne() { - KPITrendResponse k = minimalKpi(); - k.setCoefficientVariation(new BigDecimal("0.2")); - assertThat(k.getVolatilite()).isEqualTo("moyenne"); - k.setCoefficientVariation(new BigDecimal("0.3")); - assertThat(k.getVolatilite()).isEqualTo("moyenne"); - } - - @Test - @DisplayName("retourne élevée quand cv > 0.3") - void testElevee() { - KPITrendResponse k = minimalKpi(); - k.setCoefficientVariation(new BigDecimal("0.5")); - assertThat(k.getVolatilite()).isEqualTo("élevée"); - } - } - - @Nested - @DisplayName("isPredictionFiable") - class IsPredictionFiable { - - @Test - @DisplayName("retourne false quand coefficientCorrelation null ou < 0.7") - void testFalse() { - KPITrendResponse k = minimalKpi(); - assertThat(k.isPredictionFiable()).isFalse(); - k.setCoefficientCorrelation(new BigDecimal("0.5")); - assertThat(k.isPredictionFiable()).isFalse(); - } - - @Test - @DisplayName("retourne true quand coefficientCorrelation >= 0.7") - void testTrue() { - KPITrendResponse k = minimalKpi(); - k.setCoefficientCorrelation(new BigDecimal("0.7")); - assertThat(k.isPredictionFiable()).isTrue(); - k.setCoefficientCorrelation(new BigDecimal("0.95")); - assertThat(k.isPredictionFiable()).isTrue(); - } - } - - @Nested - @DisplayName("getNombrePointsDonnees") - class GetNombrePointsDonnees { - - @Test - @DisplayName("retourne 0 quand pointsDonnees null") - void testNull() { - KPITrendResponse k = KPITrendResponse.builder() - .typeMetrique(TypeMetrique.NOMBRE_MEMBRES_ACTIFS) - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .dateDebut(LocalDateTime.now()) - .dateFin(LocalDateTime.now()) - .valeurActuelle(BigDecimal.ONE) - .pointsDonnees(null).build(); - assertThat(k.getNombrePointsDonnees()).isEqualTo(0); - } - - @Test - @DisplayName("retourne la taille de pointsDonnees") - void testSize() { - KPITrendResponse k = minimalKpi(); - k.setPointsDonnees(List.of( - KPITrendResponse.PointDonneeDTO.builder().date(LocalDateTime.now()).valeur(BigDecimal.ONE).build(), - KPITrendResponse.PointDonneeDTO.builder().date(LocalDateTime.now()).valeur(BigDecimal.TEN).build())); - assertThat(k.getNombrePointsDonnees()).isEqualTo(2); - } - } - - @Nested - @DisplayName("hasAnomalies") - class HasAnomalies { - - @Test - @DisplayName("retourne false quand pointsDonnees null") - void testNull() { - KPITrendResponse k = minimalKpi(); - k.setPointsDonnees(null); - assertThat(k.hasAnomalies()).isFalse(); - } - - @Test - @DisplayName("retourne false quand aucun point anomalie") - void testFalse() { - KPITrendResponse k = minimalKpi(); - assertThat(k.hasAnomalies()).isFalse(); - k.setPointsDonnees(List.of( - KPITrendResponse.PointDonneeDTO.builder().date(LocalDateTime.now()).valeur(BigDecimal.ONE).anomalie(false).build())); - assertThat(k.hasAnomalies()).isFalse(); - } - - @Test - @DisplayName("retourne true quand au moins un point a anomalie true") - void testTrue() { - KPITrendResponse k = minimalKpi(); - k.setPointsDonnees(List.of( - KPITrendResponse.PointDonneeDTO.builder().date(LocalDateTime.now()).valeur(BigDecimal.ONE).anomalie(false).build(), - KPITrendResponse.PointDonneeDTO.builder().date(LocalDateTime.now()).valeur(BigDecimal.TEN).anomalie(true).build())); - assertThat(k.hasAnomalies()).isTrue(); - } - } -} +package dev.lions.unionflow.server.api.dto.analytics; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.math.BigDecimal; +import java.time.LocalDateTime; +import java.util.List; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; +import dev.lions.unionflow.server.api.enums.analytics.TypeMetrique; + +/** + * Tests unitaires pour KPITrendResponse. + * Couvre getLibelleMetrique, getUnite, getIcone, getCouleur, isTendancePositive/Negative/Stable, + * getVolatilite, isPredictionFiable, getNombrePointsDonnees, hasAnomalies. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests KPITrendResponse") +class KPITrendResponseTest { + + private static KPITrendResponse minimalKpi() { + return KPITrendResponse.builder() + .typeMetrique(TypeMetrique.NOMBRE_MEMBRES_ACTIFS) + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .pointsDonnees(List.of()) + .valeurActuelle(BigDecimal.ONE).build(); + } + + @Nested + @DisplayName("getLibelleMetrique, getUnite, getIcone, getCouleur") + class DelegationTypeMetrique { + + @Test + @DisplayName("délèguent à typeMetrique") + void testDelegation() { + KPITrendResponse k = minimalKpi(); + assertThat(k.getLibelleMetrique()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getLibelle()); + assertThat(k.getUnite()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getUnite()); + assertThat(k.getIcone()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getIcone()); + assertThat(k.getCouleur()).isEqualTo(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getCouleur()); + } + } + + @Nested + @DisplayName("isTendancePositive, isTendanceNegative, isTendanceStable") + class Tendance { + + @Test + @DisplayName("isTendancePositive true quand tendanceGenerale > 0") + void testPositive() { + KPITrendResponse k = minimalKpi(); + k.setTendanceGenerale(BigDecimal.ONE); + assertThat(k.isTendancePositive()).isTrue(); + assertThat(k.isTendanceNegative()).isFalse(); + assertThat(k.isTendanceStable()).isFalse(); + } + + @Test + @DisplayName("isTendanceNegative true quand tendanceGenerale < 0") + void testNegative() { + KPITrendResponse k = minimalKpi(); + k.setTendanceGenerale(BigDecimal.ONE.negate()); + assertThat(k.isTendanceNegative()).isTrue(); + assertThat(k.isTendancePositive()).isFalse(); + assertThat(k.isTendanceStable()).isFalse(); + } + + @Test + @DisplayName("isTendanceStable true quand tendanceGenerale == 0") + void testStable() { + KPITrendResponse k = minimalKpi(); + k.setTendanceGenerale(BigDecimal.ZERO); + assertThat(k.isTendanceStable()).isTrue(); + assertThat(k.isTendancePositive()).isFalse(); + assertThat(k.isTendanceNegative()).isFalse(); + } + + @Test + @DisplayName("toutes false quand tendanceGenerale null") + void testNull() { + KPITrendResponse k = minimalKpi(); + assertThat(k.isTendancePositive()).isFalse(); + assertThat(k.isTendanceNegative()).isFalse(); + assertThat(k.isTendanceStable()).isFalse(); + } + } + + @Nested + @DisplayName("getVolatilite") + class GetVolatilite { + + @Test + @DisplayName("retourne inconnue quand coefficientVariation null") + void testNull() { + KPITrendResponse k = minimalKpi(); + assertThat(k.getVolatilite()).isEqualTo("inconnue"); + } + + @Test + @DisplayName("retourne faible quand cv <= 0.1") + void testFaible() { + KPITrendResponse k = minimalKpi(); + k.setCoefficientVariation(new BigDecimal("0.05")); + assertThat(k.getVolatilite()).isEqualTo("faible"); + k.setCoefficientVariation(new BigDecimal("0.1")); + assertThat(k.getVolatilite()).isEqualTo("faible"); + } + + @Test + @DisplayName("retourne moyenne quand cv <= 0.3 et > 0.1") + void testMoyenne() { + KPITrendResponse k = minimalKpi(); + k.setCoefficientVariation(new BigDecimal("0.2")); + assertThat(k.getVolatilite()).isEqualTo("moyenne"); + k.setCoefficientVariation(new BigDecimal("0.3")); + assertThat(k.getVolatilite()).isEqualTo("moyenne"); + } + + @Test + @DisplayName("retourne élevée quand cv > 0.3") + void testElevee() { + KPITrendResponse k = minimalKpi(); + k.setCoefficientVariation(new BigDecimal("0.5")); + assertThat(k.getVolatilite()).isEqualTo("élevée"); + } + } + + @Nested + @DisplayName("isPredictionFiable") + class IsPredictionFiable { + + @Test + @DisplayName("retourne false quand coefficientCorrelation null ou < 0.7") + void testFalse() { + KPITrendResponse k = minimalKpi(); + assertThat(k.isPredictionFiable()).isFalse(); + k.setCoefficientCorrelation(new BigDecimal("0.5")); + assertThat(k.isPredictionFiable()).isFalse(); + } + + @Test + @DisplayName("retourne true quand coefficientCorrelation >= 0.7") + void testTrue() { + KPITrendResponse k = minimalKpi(); + k.setCoefficientCorrelation(new BigDecimal("0.7")); + assertThat(k.isPredictionFiable()).isTrue(); + k.setCoefficientCorrelation(new BigDecimal("0.95")); + assertThat(k.isPredictionFiable()).isTrue(); + } + } + + @Nested + @DisplayName("getNombrePointsDonnees") + class GetNombrePointsDonnees { + + @Test + @DisplayName("retourne 0 quand pointsDonnees null") + void testNull() { + KPITrendResponse k = KPITrendResponse.builder() + .typeMetrique(TypeMetrique.NOMBRE_MEMBRES_ACTIFS) + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .dateDebut(LocalDateTime.now()) + .dateFin(LocalDateTime.now()) + .valeurActuelle(BigDecimal.ONE) + .pointsDonnees(null).build(); + assertThat(k.getNombrePointsDonnees()).isEqualTo(0); + } + + @Test + @DisplayName("retourne la taille de pointsDonnees") + void testSize() { + KPITrendResponse k = minimalKpi(); + k.setPointsDonnees(List.of( + KPITrendResponse.PointDonneeDTO.builder().date(LocalDateTime.now()).valeur(BigDecimal.ONE).build(), + KPITrendResponse.PointDonneeDTO.builder().date(LocalDateTime.now()).valeur(BigDecimal.TEN).build())); + assertThat(k.getNombrePointsDonnees()).isEqualTo(2); + } + } + + @Nested + @DisplayName("hasAnomalies") + class HasAnomalies { + + @Test + @DisplayName("retourne false quand pointsDonnees null") + void testNull() { + KPITrendResponse k = minimalKpi(); + k.setPointsDonnees(null); + assertThat(k.hasAnomalies()).isFalse(); + } + + @Test + @DisplayName("retourne false quand aucun point anomalie") + void testFalse() { + KPITrendResponse k = minimalKpi(); + assertThat(k.hasAnomalies()).isFalse(); + k.setPointsDonnees(List.of( + KPITrendResponse.PointDonneeDTO.builder().date(LocalDateTime.now()).valeur(BigDecimal.ONE).anomalie(false).build())); + assertThat(k.hasAnomalies()).isFalse(); + } + + @Test + @DisplayName("retourne true quand au moins un point a anomalie true") + void testTrue() { + KPITrendResponse k = minimalKpi(); + k.setPointsDonnees(List.of( + KPITrendResponse.PointDonneeDTO.builder().date(LocalDateTime.now()).valeur(BigDecimal.ONE).anomalie(false).build(), + KPITrendResponse.PointDonneeDTO.builder().date(LocalDateTime.now()).valeur(BigDecimal.TEN).anomalie(true).build())); + assertThat(k.hasAnomalies()).isTrue(); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/analytics/ReportConfigDTOTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/analytics/ReportConfigDTOTest.java index 3441bc5..30cd639 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/analytics/ReportConfigDTOTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/analytics/ReportConfigDTOTest.java @@ -1,341 +1,341 @@ -package dev.lions.unionflow.server.api.dto.analytics; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalDateTime; -import java.util.List; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import dev.lions.unionflow.server.api.enums.analytics.FormatExport; -import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; - -/** - * Tests unitaires pour ReportConfigDTO. - * Couvre getNombreMetriques, getNombreSections, isPeriodePersonnalisee, isConfidentiel, - * necessiteGeneration, getFrequenceTexte (toutes branches). - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests ReportConfigDTO") -class ReportConfigDTOTest { - - @Nested - @DisplayName("getNombreMetriques") - class GetNombreMetriques { - - @Test - @DisplayName("retourne 0 quand metriques null") - void testNull() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(null) - .formatExport(FormatExport.PDF).build(); - assertThat(dto.getNombreMetriques()).isEqualTo(0); - } - - @Test - @DisplayName("retourne la taille de metriques") - void testSize() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of( - ReportConfigDTO.MetriqueConfigDTO.builder().typeMetrique(dev.lions.unionflow.server.api.enums.analytics.TypeMetrique.NOMBRE_MEMBRES_ACTIFS).build(), - ReportConfigDTO.MetriqueConfigDTO.builder().typeMetrique(dev.lions.unionflow.server.api.enums.analytics.TypeMetrique.TOTAL_COTISATIONS_COLLECTEES).build())) - .formatExport(FormatExport.PDF).build(); - assertThat(dto.getNombreMetriques()).isEqualTo(2); - } - } - - @Nested - @DisplayName("getNombreSections") - class GetNombreSections { - - @Test - @DisplayName("retourne 0 quand sections null") - void testNull() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .sections(null) - .formatExport(FormatExport.PDF).build(); - assertThat(dto.getNombreSections()).isEqualTo(0); - } - - @Test - @DisplayName("retourne la taille de sections") - void testSize() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .sections(List.of( - ReportConfigDTO.SectionRapportDTO.builder().nom("S1").typeSection("resume").build())) - .formatExport(FormatExport.PDF).build(); - assertThat(dto.getNombreSections()).isEqualTo(1); - } - } - - @Nested - @DisplayName("isPeriodePersonnalisee") - class IsPeriodePersonnalisee { - - @Test - @DisplayName("retourne true quand periodeAnalyse PERIODE_PERSONNALISEE") - void testTrue() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.PERIODE_PERSONNALISEE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF).build(); - assertThat(dto.isPeriodePersonnalisee()).isTrue(); - } - - @Test - @DisplayName("retourne false pour autre période") - void testFalse() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF).build(); - assertThat(dto.isPeriodePersonnalisee()).isFalse(); - } - } - - @Nested - @DisplayName("isConfidentiel") - class IsConfidentiel { - - @Test - @DisplayName("retourne false quand niveauConfidentialite null ou < 4") - void testFalse() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF).build(); - assertThat(dto.isConfidentiel()).isFalse(); - dto.setNiveauConfidentialite(3); - assertThat(dto.isConfidentiel()).isFalse(); - } - - @Test - @DisplayName("retourne false quand niveauConfidentialite explicitement null") - void testConfidentielNiveauNull() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF) - .niveauConfidentialite(5).build(); - dto.setNiveauConfidentialite(null); - assertThat(dto.isConfidentiel()).isFalse(); - } - - @Test - @DisplayName("retourne true quand niveauConfidentialite >= 4") - void testTrue() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF) - .niveauConfidentialite(4).build(); - assertThat(dto.isConfidentiel()).isTrue(); - dto.setNiveauConfidentialite(5); - assertThat(dto.isConfidentiel()).isTrue(); - } - - @Test - @DisplayName("retourne false quand niveauConfidentialite non null mais < 4") - void testNiveauNonNullInferieurA4() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF) - .niveauConfidentialite(3).build(); - assertThat(dto.isConfidentiel()).isFalse(); - } - } - - @Nested - @DisplayName("necessiteGeneration") - class NecessiteGeneration { - - @Test - @DisplayName("retourne false quand rapportAutomatique false") - void testNonAuto() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF) - .rapportAutomatique(false) - .prochaineGeneration(LocalDateTime.now().minusMinutes(1)).build(); - assertThat(dto.necessiteGeneration()).isFalse(); - } - - @Test - @DisplayName("retourne false quand prochaineGeneration null") - void testProchaineNull() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF) - .rapportAutomatique(true) - .prochaineGeneration(null).build(); - assertThat(dto.necessiteGeneration()).isFalse(); - } - - @Test - @DisplayName("retourne true quand automatique et prochaineGeneration dans le passé") - void testNecessite() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF) - .rapportAutomatique(true) - .prochaineGeneration(LocalDateTime.now().minusMinutes(10)).build(); - assertThat(dto.necessiteGeneration()).isTrue(); - } - - @Test - @DisplayName("retourne false quand prochaineGeneration dans le futur") - void testFutur() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF) - .rapportAutomatique(true) - .prochaineGeneration(LocalDateTime.now().plusHours(1)).build(); - assertThat(dto.necessiteGeneration()).isFalse(); - } - } - - @Nested - @DisplayName("getFrequenceTexte") - class GetFrequenceTexte { - - @Test - @DisplayName("retourne Manuelle quand frequenceGenerationHeures null") - void testNull() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF).build(); - assertThat(dto.getFrequenceTexte()).isEqualTo("Manuelle"); - } - - @Test - @DisplayName("retourne Toutes les heures pour 1") - void test1() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF) - .frequenceGenerationHeures(1).build(); - assertThat(dto.getFrequenceTexte()).isEqualTo("Toutes les heures"); - } - - @Test - @DisplayName("retourne Quotidienne pour 24") - void test24() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF) - .frequenceGenerationHeures(24).build(); - assertThat(dto.getFrequenceTexte()).isEqualTo("Quotidienne"); - } - - @Test - @DisplayName("retourne Hebdomadaire pour 168") - void test168() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF) - .frequenceGenerationHeures(168).build(); - assertThat(dto.getFrequenceTexte()).isEqualTo("Hebdomadaire"); - } - - @Test - @DisplayName("retourne Mensuelle pour 720") - void test720() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF) - .frequenceGenerationHeures(720).build(); - assertThat(dto.getFrequenceTexte()).isEqualTo("Mensuelle"); - } - - @Test - @DisplayName("retourne Toutes les X heures pour autre valeur") - void testDefault() { - ReportConfigDTO dto = ReportConfigDTO.builder() - .nom("Rapport") - .typeRapport("executif") - .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) - .utilisateurCreateurId(UUID.randomUUID()) - .metriques(List.of()) - .formatExport(FormatExport.PDF) - .frequenceGenerationHeures(12).build(); - assertThat(dto.getFrequenceTexte()).isEqualTo("Toutes les 12 heures"); - } - } -} +package dev.lions.unionflow.server.api.dto.analytics; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalDateTime; +import java.util.List; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import dev.lions.unionflow.server.api.enums.analytics.FormatExport; +import dev.lions.unionflow.server.api.enums.analytics.PeriodeAnalyse; + +/** + * Tests unitaires pour ReportConfigDTO. + * Couvre getNombreMetriques, getNombreSections, isPeriodePersonnalisee, isConfidentiel, + * necessiteGeneration, getFrequenceTexte (toutes branches). + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests ReportConfigDTO") +class ReportConfigDTOTest { + + @Nested + @DisplayName("getNombreMetriques") + class GetNombreMetriques { + + @Test + @DisplayName("retourne 0 quand metriques null") + void testNull() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(null) + .formatExport(FormatExport.PDF).build(); + assertThat(dto.getNombreMetriques()).isEqualTo(0); + } + + @Test + @DisplayName("retourne la taille de metriques") + void testSize() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of( + ReportConfigDTO.MetriqueConfigDTO.builder().typeMetrique(dev.lions.unionflow.server.api.enums.analytics.TypeMetrique.NOMBRE_MEMBRES_ACTIFS).build(), + ReportConfigDTO.MetriqueConfigDTO.builder().typeMetrique(dev.lions.unionflow.server.api.enums.analytics.TypeMetrique.TOTAL_COTISATIONS_COLLECTEES).build())) + .formatExport(FormatExport.PDF).build(); + assertThat(dto.getNombreMetriques()).isEqualTo(2); + } + } + + @Nested + @DisplayName("getNombreSections") + class GetNombreSections { + + @Test + @DisplayName("retourne 0 quand sections null") + void testNull() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .sections(null) + .formatExport(FormatExport.PDF).build(); + assertThat(dto.getNombreSections()).isEqualTo(0); + } + + @Test + @DisplayName("retourne la taille de sections") + void testSize() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .sections(List.of( + ReportConfigDTO.SectionRapportDTO.builder().nom("S1").typeSection("resume").build())) + .formatExport(FormatExport.PDF).build(); + assertThat(dto.getNombreSections()).isEqualTo(1); + } + } + + @Nested + @DisplayName("isPeriodePersonnalisee") + class IsPeriodePersonnalisee { + + @Test + @DisplayName("retourne true quand periodeAnalyse PERIODE_PERSONNALISEE") + void testTrue() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.PERIODE_PERSONNALISEE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF).build(); + assertThat(dto.isPeriodePersonnalisee()).isTrue(); + } + + @Test + @DisplayName("retourne false pour autre période") + void testFalse() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF).build(); + assertThat(dto.isPeriodePersonnalisee()).isFalse(); + } + } + + @Nested + @DisplayName("isConfidentiel") + class IsConfidentiel { + + @Test + @DisplayName("retourne false quand niveauConfidentialite null ou < 4") + void testFalse() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF).build(); + assertThat(dto.isConfidentiel()).isFalse(); + dto.setNiveauConfidentialite(3); + assertThat(dto.isConfidentiel()).isFalse(); + } + + @Test + @DisplayName("retourne false quand niveauConfidentialite explicitement null") + void testConfidentielNiveauNull() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF) + .niveauConfidentialite(5).build(); + dto.setNiveauConfidentialite(null); + assertThat(dto.isConfidentiel()).isFalse(); + } + + @Test + @DisplayName("retourne true quand niveauConfidentialite >= 4") + void testTrue() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF) + .niveauConfidentialite(4).build(); + assertThat(dto.isConfidentiel()).isTrue(); + dto.setNiveauConfidentialite(5); + assertThat(dto.isConfidentiel()).isTrue(); + } + + @Test + @DisplayName("retourne false quand niveauConfidentialite non null mais < 4") + void testNiveauNonNullInferieurA4() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF) + .niveauConfidentialite(3).build(); + assertThat(dto.isConfidentiel()).isFalse(); + } + } + + @Nested + @DisplayName("necessiteGeneration") + class NecessiteGeneration { + + @Test + @DisplayName("retourne false quand rapportAutomatique false") + void testNonAuto() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF) + .rapportAutomatique(false) + .prochaineGeneration(LocalDateTime.now().minusMinutes(1)).build(); + assertThat(dto.necessiteGeneration()).isFalse(); + } + + @Test + @DisplayName("retourne false quand prochaineGeneration null") + void testProchaineNull() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF) + .rapportAutomatique(true) + .prochaineGeneration(null).build(); + assertThat(dto.necessiteGeneration()).isFalse(); + } + + @Test + @DisplayName("retourne true quand automatique et prochaineGeneration dans le passé") + void testNecessite() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF) + .rapportAutomatique(true) + .prochaineGeneration(LocalDateTime.now().minusMinutes(10)).build(); + assertThat(dto.necessiteGeneration()).isTrue(); + } + + @Test + @DisplayName("retourne false quand prochaineGeneration dans le futur") + void testFutur() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF) + .rapportAutomatique(true) + .prochaineGeneration(LocalDateTime.now().plusHours(1)).build(); + assertThat(dto.necessiteGeneration()).isFalse(); + } + } + + @Nested + @DisplayName("getFrequenceTexte") + class GetFrequenceTexte { + + @Test + @DisplayName("retourne Manuelle quand frequenceGenerationHeures null") + void testNull() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF).build(); + assertThat(dto.getFrequenceTexte()).isEqualTo("Manuelle"); + } + + @Test + @DisplayName("retourne Toutes les heures pour 1") + void test1() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF) + .frequenceGenerationHeures(1).build(); + assertThat(dto.getFrequenceTexte()).isEqualTo("Toutes les heures"); + } + + @Test + @DisplayName("retourne Quotidienne pour 24") + void test24() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF) + .frequenceGenerationHeures(24).build(); + assertThat(dto.getFrequenceTexte()).isEqualTo("Quotidienne"); + } + + @Test + @DisplayName("retourne Hebdomadaire pour 168") + void test168() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF) + .frequenceGenerationHeures(168).build(); + assertThat(dto.getFrequenceTexte()).isEqualTo("Hebdomadaire"); + } + + @Test + @DisplayName("retourne Mensuelle pour 720") + void test720() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF) + .frequenceGenerationHeures(720).build(); + assertThat(dto.getFrequenceTexte()).isEqualTo("Mensuelle"); + } + + @Test + @DisplayName("retourne Toutes les X heures pour autre valeur") + void testDefault() { + ReportConfigDTO dto = ReportConfigDTO.builder() + .nom("Rapport") + .typeRapport("executif") + .periodeAnalyse(PeriodeAnalyse.CETTE_SEMAINE) + .utilisateurCreateurId(UUID.randomUUID()) + .metriques(List.of()) + .formatExport(FormatExport.PDF) + .frequenceGenerationHeures(12).build(); + assertThat(dto.getFrequenceTexte()).isEqualTo("Toutes les 12 heures"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/auth/request/LoginRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/auth/request/LoginRequestTest.java index 1f0d134..d5c7477 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/auth/request/LoginRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/auth/request/LoginRequestTest.java @@ -1,212 +1,212 @@ -package dev.lions.unionflow.server.api.dto.auth.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour LoginRequest (record). - * Couvre constructeur via builder, accesseurs, et tous les champs. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-01 - */ -@DisplayName("Tests LoginRequest") -class LoginRequestTest { - - @Nested - @DisplayName("Builder et construction") - class Builder { - - @Test - @DisplayName("builder avec tous les champs") - void testBuilderComplet() { - LoginRequest request = LoginRequest.builder() - .username("admin@test.com") - .password("secret123") - .typeCompte("ADMIN") - .rememberMe(true) - .build(); - - assertThat(request.username()).isEqualTo("admin@test.com"); - assertThat(request.password()).isEqualTo("secret123"); - assertThat(request.typeCompte()).isEqualTo("ADMIN"); - assertThat(request.rememberMe()).isTrue(); - } - - @Test - @DisplayName("builder avec champs minimum (rememberMe null)") - void testBuilderMinimum() { - LoginRequest request = LoginRequest.builder() - .username("user@test.com") - .password("pass123") - .typeCompte("MEMBRE") - .build(); - - assertThat(request.username()).isEqualTo("user@test.com"); - assertThat(request.password()).isEqualTo("pass123"); - assertThat(request.typeCompte()).isEqualTo("MEMBRE"); - assertThat(request.rememberMe()).isNull(); - } - - @Test - @DisplayName("builder avec rememberMe false") - void testBuilderRememberMeFalse() { - LoginRequest request = LoginRequest.builder() - .username("test@test.com") - .password("test123") - .typeCompte("ADMIN_ORGANISATION") - .rememberMe(false) - .build(); - - assertThat(request.rememberMe()).isFalse(); - } - } - - @Nested - @DisplayName("Accesseurs (record)") - class Accesseurs { - - @Test - @DisplayName("username() retourne la valeur") - void testUsername() { - LoginRequest request = LoginRequest.builder() - .username("john.doe@test.com") - .password("pass") - .typeCompte("MEMBRE") - .build(); - - assertThat(request.username()).isEqualTo("john.doe@test.com"); - } - - @Test - @DisplayName("password() retourne la valeur") - void testPassword() { - LoginRequest request = LoginRequest.builder() - .username("user") - .password("mySecretPass123!") - .typeCompte("MEMBRE") - .build(); - - assertThat(request.password()).isEqualTo("mySecretPass123!"); - } - - @Test - @DisplayName("typeCompte() retourne la valeur") - void testTypeCompte() { - LoginRequest request = LoginRequest.builder() - .username("super@test.com") - .password("pass") - .typeCompte("SUPER_ADMIN") - .build(); - - assertThat(request.typeCompte()).isEqualTo("SUPER_ADMIN"); - } - - @Test - @DisplayName("rememberMe() retourne la valeur") - void testRememberMe() { - LoginRequest request = LoginRequest.builder() - .username("user") - .password("pass") - .typeCompte("MEMBRE") - .rememberMe(true) - .build(); - - assertThat(request.rememberMe()).isTrue(); - } - } - - @Nested - @DisplayName("Equals et HashCode") - class EqualsHashCode { - - @Test - @DisplayName("equals retourne true pour même instance") - void testEqualsMemeInstance() { - LoginRequest request = LoginRequest.builder() - .username("user") - .password("pass") - .typeCompte("MEMBRE") - .build(); - - assertThat(request).isEqualTo(request); - } - - @Test - @DisplayName("equals retourne true pour mêmes valeurs") - void testEqualsMemeValeurs() { - LoginRequest r1 = LoginRequest.builder() - .username("user") - .password("pass") - .typeCompte("MEMBRE") - .rememberMe(true) - .build(); - - LoginRequest r2 = LoginRequest.builder() - .username("user") - .password("pass") - .typeCompte("MEMBRE") - .rememberMe(true) - .build(); - - assertThat(r1).isEqualTo(r2); - assertThat(r1.hashCode()).isEqualTo(r2.hashCode()); - } - - @Test - @DisplayName("equals retourne false pour valeurs différentes") - void testEqualsValeursDifferentes() { - LoginRequest r1 = LoginRequest.builder() - .username("user1") - .password("pass") - .typeCompte("MEMBRE") - .build(); - - LoginRequest r2 = LoginRequest.builder() - .username("user2") - .password("pass") - .typeCompte("MEMBRE") - .build(); - - assertThat(r1).isNotEqualTo(r2); - } - - @Test - @DisplayName("equals retourne false pour null") - void testEqualsNull() { - LoginRequest request = LoginRequest.builder() - .username("user") - .password("pass") - .typeCompte("MEMBRE") - .build(); - - assertThat(request).isNotEqualTo(null); - } - } - - @Nested - @DisplayName("ToString") - class ToString { - - @Test - @DisplayName("toString contient tous les champs") - void testToString() { - LoginRequest request = LoginRequest.builder() - .username("admin") - .password("secret") - .typeCompte("ADMIN") - .rememberMe(true) - .build(); - - String str = request.toString(); - assertThat(str).contains("username=admin"); - assertThat(str).contains("password=secret"); - assertThat(str).contains("typeCompte=ADMIN"); - assertThat(str).contains("rememberMe=true"); - } - } -} +package dev.lions.unionflow.server.api.dto.auth.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour LoginRequest (record). + * Couvre constructeur via builder, accesseurs, et tous les champs. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-01 + */ +@DisplayName("Tests LoginRequest") +class LoginRequestTest { + + @Nested + @DisplayName("Builder et construction") + class Builder { + + @Test + @DisplayName("builder avec tous les champs") + void testBuilderComplet() { + LoginRequest request = LoginRequest.builder() + .username("admin@test.com") + .password("secret123") + .typeCompte("ADMIN") + .rememberMe(true) + .build(); + + assertThat(request.username()).isEqualTo("admin@test.com"); + assertThat(request.password()).isEqualTo("secret123"); + assertThat(request.typeCompte()).isEqualTo("ADMIN"); + assertThat(request.rememberMe()).isTrue(); + } + + @Test + @DisplayName("builder avec champs minimum (rememberMe null)") + void testBuilderMinimum() { + LoginRequest request = LoginRequest.builder() + .username("user@test.com") + .password("pass123") + .typeCompte("MEMBRE") + .build(); + + assertThat(request.username()).isEqualTo("user@test.com"); + assertThat(request.password()).isEqualTo("pass123"); + assertThat(request.typeCompte()).isEqualTo("MEMBRE"); + assertThat(request.rememberMe()).isNull(); + } + + @Test + @DisplayName("builder avec rememberMe false") + void testBuilderRememberMeFalse() { + LoginRequest request = LoginRequest.builder() + .username("test@test.com") + .password("test123") + .typeCompte("ADMIN_ORGANISATION") + .rememberMe(false) + .build(); + + assertThat(request.rememberMe()).isFalse(); + } + } + + @Nested + @DisplayName("Accesseurs (record)") + class Accesseurs { + + @Test + @DisplayName("username() retourne la valeur") + void testUsername() { + LoginRequest request = LoginRequest.builder() + .username("john.doe@test.com") + .password("pass") + .typeCompte("MEMBRE") + .build(); + + assertThat(request.username()).isEqualTo("john.doe@test.com"); + } + + @Test + @DisplayName("password() retourne la valeur") + void testPassword() { + LoginRequest request = LoginRequest.builder() + .username("user") + .password("mySecretPass123!") + .typeCompte("MEMBRE") + .build(); + + assertThat(request.password()).isEqualTo("mySecretPass123!"); + } + + @Test + @DisplayName("typeCompte() retourne la valeur") + void testTypeCompte() { + LoginRequest request = LoginRequest.builder() + .username("super@test.com") + .password("pass") + .typeCompte("SUPER_ADMIN") + .build(); + + assertThat(request.typeCompte()).isEqualTo("SUPER_ADMIN"); + } + + @Test + @DisplayName("rememberMe() retourne la valeur") + void testRememberMe() { + LoginRequest request = LoginRequest.builder() + .username("user") + .password("pass") + .typeCompte("MEMBRE") + .rememberMe(true) + .build(); + + assertThat(request.rememberMe()).isTrue(); + } + } + + @Nested + @DisplayName("Equals et HashCode") + class EqualsHashCode { + + @Test + @DisplayName("equals retourne true pour même instance") + void testEqualsMemeInstance() { + LoginRequest request = LoginRequest.builder() + .username("user") + .password("pass") + .typeCompte("MEMBRE") + .build(); + + assertThat(request).isEqualTo(request); + } + + @Test + @DisplayName("equals retourne true pour mêmes valeurs") + void testEqualsMemeValeurs() { + LoginRequest r1 = LoginRequest.builder() + .username("user") + .password("pass") + .typeCompte("MEMBRE") + .rememberMe(true) + .build(); + + LoginRequest r2 = LoginRequest.builder() + .username("user") + .password("pass") + .typeCompte("MEMBRE") + .rememberMe(true) + .build(); + + assertThat(r1).isEqualTo(r2); + assertThat(r1.hashCode()).isEqualTo(r2.hashCode()); + } + + @Test + @DisplayName("equals retourne false pour valeurs différentes") + void testEqualsValeursDifferentes() { + LoginRequest r1 = LoginRequest.builder() + .username("user1") + .password("pass") + .typeCompte("MEMBRE") + .build(); + + LoginRequest r2 = LoginRequest.builder() + .username("user2") + .password("pass") + .typeCompte("MEMBRE") + .build(); + + assertThat(r1).isNotEqualTo(r2); + } + + @Test + @DisplayName("equals retourne false pour null") + void testEqualsNull() { + LoginRequest request = LoginRequest.builder() + .username("user") + .password("pass") + .typeCompte("MEMBRE") + .build(); + + assertThat(request).isNotEqualTo(null); + } + } + + @Nested + @DisplayName("ToString") + class ToString { + + @Test + @DisplayName("toString contient tous les champs") + void testToString() { + LoginRequest request = LoginRequest.builder() + .username("admin") + .password("secret") + .typeCompte("ADMIN") + .rememberMe(true) + .build(); + + String str = request.toString(); + assertThat(str).contains("username=admin"); + assertThat(str).contains("password=secret"); + assertThat(str).contains("typeCompte=ADMIN"); + assertThat(str).contains("rememberMe=true"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/auth/response/LoginResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/auth/response/LoginResponseTest.java index 236b3fd..7eddee0 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/auth/response/LoginResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/auth/response/LoginResponseTest.java @@ -1,403 +1,403 @@ -package dev.lions.unionflow.server.api.dto.auth.response; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalDateTime; -import java.util.Arrays; -import java.util.Collections; -import java.util.List; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour LoginResponse. - * Couvre builder, getters/setters, isExpired(), UserInfo, EntiteInfo. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-01 - */ -@DisplayName("Tests LoginResponse") -class LoginResponseTest { - - @Nested - @DisplayName("Builder et construction") - class Builder { - - @Test - @DisplayName("builder avec tous les champs") - void testBuilderComplet() { - LocalDateTime expiration = LocalDateTime.now().plusHours(1); - LoginResponse.UserInfo user = new LoginResponse.UserInfo(); - - LoginResponse response = LoginResponse.builder() - .accessToken("access_token_123") - .refreshToken("refresh_token_456") - .tokenType("Bearer") - .expiresIn(3600L) - .expirationDate(expiration) - .user(user) - .build(); - - assertThat(response.getAccessToken()).isEqualTo("access_token_123"); - assertThat(response.getRefreshToken()).isEqualTo("refresh_token_456"); - assertThat(response.getTokenType()).isEqualTo("Bearer"); - assertThat(response.getExpiresIn()).isEqualTo(3600L); - assertThat(response.getExpirationDate()).isEqualTo(expiration); - assertThat(response.getUser()).isEqualTo(user); - } - - @Test - @DisplayName("builder avec tokenType par défaut") - void testBuilderTokenTypeParDefaut() { - LoginResponse response = LoginResponse.builder() - .accessToken("token") - .refreshToken("refresh") - .expiresIn(3600L) - .build(); - - assertThat(response.getTokenType()).isEqualTo("Bearer"); - } - - @Test - @DisplayName("constructeur NoArgs") - void testConstructeurNoArgs() { - LoginResponse response = new LoginResponse(); - assertThat(response).isNotNull(); - assertThat(response.getAccessToken()).isNull(); - } - - @Test - @DisplayName("constructeur AllArgs") - void testConstructeurAllArgs() { - LocalDateTime expiration = LocalDateTime.now().plusHours(1); - LoginResponse.UserInfo user = new LoginResponse.UserInfo(); - - LoginResponse response = new LoginResponse( - "access", - "refresh", - "Bearer", - 3600L, - expiration, - user - ); - - assertThat(response.getAccessToken()).isEqualTo("access"); - assertThat(response.getRefreshToken()).isEqualTo("refresh"); - assertThat(response.getTokenType()).isEqualTo("Bearer"); - assertThat(response.getExpiresIn()).isEqualTo(3600L); - assertThat(response.getExpirationDate()).isEqualTo(expiration); - assertThat(response.getUser()).isEqualTo(user); - } - } - - @Nested - @DisplayName("Getters et Setters") - class GettersSetters { - - @Test - @DisplayName("setters et getters fonctionnent") - void testSettersGetters() { - LoginResponse response = new LoginResponse(); - LocalDateTime expiration = LocalDateTime.now().plusHours(2); - LoginResponse.UserInfo user = new LoginResponse.UserInfo(); - - response.setAccessToken("new_access"); - response.setRefreshToken("new_refresh"); - response.setTokenType("Custom"); - response.setExpiresIn(7200L); - response.setExpirationDate(expiration); - response.setUser(user); - - assertThat(response.getAccessToken()).isEqualTo("new_access"); - assertThat(response.getRefreshToken()).isEqualTo("new_refresh"); - assertThat(response.getTokenType()).isEqualTo("Custom"); - assertThat(response.getExpiresIn()).isEqualTo(7200L); - assertThat(response.getExpirationDate()).isEqualTo(expiration); - assertThat(response.getUser()).isEqualTo(user); - } - } - - @Nested - @DisplayName("isExpired") - class IsExpired { - - @Test - @DisplayName("retourne false quand expirationDate dans le futur") - void testNonExpire() { - LoginResponse response = LoginResponse.builder() - .accessToken("token") - .refreshToken("refresh") - .expirationDate(LocalDateTime.now().plusHours(1)) - .build(); - - assertThat(response.isExpired()).isFalse(); - } - - @Test - @DisplayName("retourne true quand expirationDate dans le passé") - void testExpire() { - LoginResponse response = LoginResponse.builder() - .accessToken("token") - .refreshToken("refresh") - .expirationDate(LocalDateTime.now().minusHours(1)) - .build(); - - assertThat(response.isExpired()).isTrue(); - } - - @Test - @DisplayName("retourne false quand expirationDate null") - void testExpirationNull() { - LoginResponse response = LoginResponse.builder() - .accessToken("token") - .refreshToken("refresh") - .expirationDate(null) - .build(); - - assertThat(response.isExpired()).isFalse(); - } - } - - @Nested - @DisplayName("UserInfo - Builder et construction") - class UserInfoBuilder { - - @Test - @DisplayName("builder UserInfo avec tous les champs") - void testBuilderComplet() { - UUID userId = UUID.randomUUID(); - LoginResponse.EntiteInfo entite = new LoginResponse.EntiteInfo(); - List roles = Arrays.asList("ADMIN", "MEMBRE"); - List permissions = Arrays.asList("READ", "WRITE"); - - LoginResponse.UserInfo user = LoginResponse.UserInfo.builder() - .id(userId) - .nom("Diallo") - .prenom("Amadou") - .email("amadou@test.com") - .username("adiallo") - .typeCompte("ADMIN") - .roles(roles) - .permissions(permissions) - .entite(entite) - .build(); - - assertThat(user.getId()).isEqualTo(userId); - assertThat(user.getNom()).isEqualTo("Diallo"); - assertThat(user.getPrenom()).isEqualTo("Amadou"); - assertThat(user.getEmail()).isEqualTo("amadou@test.com"); - assertThat(user.getUsername()).isEqualTo("adiallo"); - assertThat(user.getTypeCompte()).isEqualTo("ADMIN"); - assertThat(user.getRoles()).isEqualTo(roles); - assertThat(user.getPermissions()).isEqualTo(permissions); - assertThat(user.getEntite()).isEqualTo(entite); - } - - @Test - @DisplayName("constructeur NoArgs UserInfo") - void testConstructeurNoArgs() { - LoginResponse.UserInfo user = new LoginResponse.UserInfo(); - assertThat(user).isNotNull(); - assertThat(user.getId()).isNull(); - } - - @Test - @DisplayName("constructeur AllArgs UserInfo") - void testConstructeurAllArgs() { - UUID userId = UUID.randomUUID(); - LoginResponse.EntiteInfo entite = new LoginResponse.EntiteInfo(); - List roles = Collections.singletonList("MEMBRE"); - List permissions = Collections.singletonList("READ"); - - LoginResponse.UserInfo user = new LoginResponse.UserInfo( - userId, - "Traoré", - "Fatou", - "fatou@test.com", - "ftraore", - "MEMBRE", - roles, - permissions, - entite - ); - - assertThat(user.getId()).isEqualTo(userId); - assertThat(user.getNom()).isEqualTo("Traoré"); - assertThat(user.getPrenom()).isEqualTo("Fatou"); - assertThat(user.getEmail()).isEqualTo("fatou@test.com"); - assertThat(user.getUsername()).isEqualTo("ftraore"); - assertThat(user.getTypeCompte()).isEqualTo("MEMBRE"); - assertThat(user.getRoles()).isEqualTo(roles); - assertThat(user.getPermissions()).isEqualTo(permissions); - assertThat(user.getEntite()).isEqualTo(entite); - } - } - - @Nested - @DisplayName("UserInfo - Getters et Setters") - class UserInfoGettersSetters { - - @Test - @DisplayName("setters et getters fonctionnent") - void testSettersGetters() { - LoginResponse.UserInfo user = new LoginResponse.UserInfo(); - UUID userId = UUID.randomUUID(); - LoginResponse.EntiteInfo entite = new LoginResponse.EntiteInfo(); - List roles = Arrays.asList("ROLE1", "ROLE2"); - List permissions = Arrays.asList("PERM1", "PERM2"); - - user.setId(userId); - user.setNom("Ndiaye"); - user.setPrenom("Moussa"); - user.setEmail("moussa@test.com"); - user.setUsername("mndiaye"); - user.setTypeCompte("SUPER_ADMIN"); - user.setRoles(roles); - user.setPermissions(permissions); - user.setEntite(entite); - - assertThat(user.getId()).isEqualTo(userId); - assertThat(user.getNom()).isEqualTo("Ndiaye"); - assertThat(user.getPrenom()).isEqualTo("Moussa"); - assertThat(user.getEmail()).isEqualTo("moussa@test.com"); - assertThat(user.getUsername()).isEqualTo("mndiaye"); - assertThat(user.getTypeCompte()).isEqualTo("SUPER_ADMIN"); - assertThat(user.getRoles()).isEqualTo(roles); - assertThat(user.getPermissions()).isEqualTo(permissions); - assertThat(user.getEntite()).isEqualTo(entite); - } - } - - @Nested - @DisplayName("UserInfo - getNomComplet") - class UserInfoGetNomComplet { - - @Test - @DisplayName("retourne prenom + nom quand les deux sont présents") - void testPrenomEtNom() { - LoginResponse.UserInfo user = new LoginResponse.UserInfo(); - user.setPrenom("Amadou"); - user.setNom("Diallo"); - user.setUsername("adiallo"); - - assertThat(user.getNomComplet()).isEqualTo("Amadou Diallo"); - } - - @Test - @DisplayName("retourne nom quand prenom null") - void testNomSeul() { - LoginResponse.UserInfo user = new LoginResponse.UserInfo(); - user.setNom("Diallo"); - user.setUsername("adiallo"); - - assertThat(user.getNomComplet()).isEqualTo("Diallo"); - } - - @Test - @DisplayName("retourne username quand nom null") - void testUsernameSeul() { - LoginResponse.UserInfo user = new LoginResponse.UserInfo(); - user.setPrenom("Amadou"); - user.setUsername("adiallo"); - - assertThat(user.getNomComplet()).isEqualTo("adiallo"); - } - - @Test - @DisplayName("retourne username quand nom et prenom null") - void testUsernameParDefaut() { - LoginResponse.UserInfo user = new LoginResponse.UserInfo(); - user.setUsername("admin"); - - assertThat(user.getNomComplet()).isEqualTo("admin"); - } - - @Test - @DisplayName("retourne null quand tout est null") - void testToutNull() { - LoginResponse.UserInfo user = new LoginResponse.UserInfo(); - - assertThat(user.getNomComplet()).isNull(); - } - } - - @Nested - @DisplayName("EntiteInfo - Builder et construction") - class EntiteInfoBuilder { - - @Test - @DisplayName("builder EntiteInfo avec tous les champs") - void testBuilderComplet() { - UUID entiteId = UUID.randomUUID(); - - LoginResponse.EntiteInfo entite = LoginResponse.EntiteInfo.builder() - .id(entiteId) - .nom("Association ABC") - .type("Association") - .pays("Sénégal") - .ville("Dakar") - .build(); - - assertThat(entite.getId()).isEqualTo(entiteId); - assertThat(entite.getNom()).isEqualTo("Association ABC"); - assertThat(entite.getType()).isEqualTo("Association"); - assertThat(entite.getPays()).isEqualTo("Sénégal"); - assertThat(entite.getVille()).isEqualTo("Dakar"); - } - - @Test - @DisplayName("constructeur NoArgs EntiteInfo") - void testConstructeurNoArgs() { - LoginResponse.EntiteInfo entite = new LoginResponse.EntiteInfo(); - assertThat(entite).isNotNull(); - assertThat(entite.getId()).isNull(); - } - - @Test - @DisplayName("constructeur AllArgs EntiteInfo") - void testConstructeurAllArgs() { - UUID entiteId = UUID.randomUUID(); - - LoginResponse.EntiteInfo entite = new LoginResponse.EntiteInfo( - entiteId, - "Mutuelle XYZ", - "Mutuelle", - "Mali", - "Bamako" - ); - - assertThat(entite.getId()).isEqualTo(entiteId); - assertThat(entite.getNom()).isEqualTo("Mutuelle XYZ"); - assertThat(entite.getType()).isEqualTo("Mutuelle"); - assertThat(entite.getPays()).isEqualTo("Mali"); - assertThat(entite.getVille()).isEqualTo("Bamako"); - } - } - - @Nested - @DisplayName("EntiteInfo - Getters et Setters") - class EntiteInfoGettersSetters { - - @Test - @DisplayName("setters et getters fonctionnent") - void testSettersGetters() { - LoginResponse.EntiteInfo entite = new LoginResponse.EntiteInfo(); - UUID entiteId = UUID.randomUUID(); - - entite.setId(entiteId); - entite.setNom("Coopérative DEF"); - entite.setType("Coopérative"); - entite.setPays("Côte d'Ivoire"); - entite.setVille("Abidjan"); - - assertThat(entite.getId()).isEqualTo(entiteId); - assertThat(entite.getNom()).isEqualTo("Coopérative DEF"); - assertThat(entite.getType()).isEqualTo("Coopérative"); - assertThat(entite.getPays()).isEqualTo("Côte d'Ivoire"); - assertThat(entite.getVille()).isEqualTo("Abidjan"); - } - } -} +package dev.lions.unionflow.server.api.dto.auth.response; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalDateTime; +import java.util.Arrays; +import java.util.Collections; +import java.util.List; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour LoginResponse. + * Couvre builder, getters/setters, isExpired(), UserInfo, EntiteInfo. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-01 + */ +@DisplayName("Tests LoginResponse") +class LoginResponseTest { + + @Nested + @DisplayName("Builder et construction") + class Builder { + + @Test + @DisplayName("builder avec tous les champs") + void testBuilderComplet() { + LocalDateTime expiration = LocalDateTime.now().plusHours(1); + LoginResponse.UserInfo user = new LoginResponse.UserInfo(); + + LoginResponse response = LoginResponse.builder() + .accessToken("access_token_123") + .refreshToken("refresh_token_456") + .tokenType("Bearer") + .expiresIn(3600L) + .expirationDate(expiration) + .user(user) + .build(); + + assertThat(response.getAccessToken()).isEqualTo("access_token_123"); + assertThat(response.getRefreshToken()).isEqualTo("refresh_token_456"); + assertThat(response.getTokenType()).isEqualTo("Bearer"); + assertThat(response.getExpiresIn()).isEqualTo(3600L); + assertThat(response.getExpirationDate()).isEqualTo(expiration); + assertThat(response.getUser()).isEqualTo(user); + } + + @Test + @DisplayName("builder avec tokenType par défaut") + void testBuilderTokenTypeParDefaut() { + LoginResponse response = LoginResponse.builder() + .accessToken("token") + .refreshToken("refresh") + .expiresIn(3600L) + .build(); + + assertThat(response.getTokenType()).isEqualTo("Bearer"); + } + + @Test + @DisplayName("constructeur NoArgs") + void testConstructeurNoArgs() { + LoginResponse response = new LoginResponse(); + assertThat(response).isNotNull(); + assertThat(response.getAccessToken()).isNull(); + } + + @Test + @DisplayName("constructeur AllArgs") + void testConstructeurAllArgs() { + LocalDateTime expiration = LocalDateTime.now().plusHours(1); + LoginResponse.UserInfo user = new LoginResponse.UserInfo(); + + LoginResponse response = new LoginResponse( + "access", + "refresh", + "Bearer", + 3600L, + expiration, + user + ); + + assertThat(response.getAccessToken()).isEqualTo("access"); + assertThat(response.getRefreshToken()).isEqualTo("refresh"); + assertThat(response.getTokenType()).isEqualTo("Bearer"); + assertThat(response.getExpiresIn()).isEqualTo(3600L); + assertThat(response.getExpirationDate()).isEqualTo(expiration); + assertThat(response.getUser()).isEqualTo(user); + } + } + + @Nested + @DisplayName("Getters et Setters") + class GettersSetters { + + @Test + @DisplayName("setters et getters fonctionnent") + void testSettersGetters() { + LoginResponse response = new LoginResponse(); + LocalDateTime expiration = LocalDateTime.now().plusHours(2); + LoginResponse.UserInfo user = new LoginResponse.UserInfo(); + + response.setAccessToken("new_access"); + response.setRefreshToken("new_refresh"); + response.setTokenType("Custom"); + response.setExpiresIn(7200L); + response.setExpirationDate(expiration); + response.setUser(user); + + assertThat(response.getAccessToken()).isEqualTo("new_access"); + assertThat(response.getRefreshToken()).isEqualTo("new_refresh"); + assertThat(response.getTokenType()).isEqualTo("Custom"); + assertThat(response.getExpiresIn()).isEqualTo(7200L); + assertThat(response.getExpirationDate()).isEqualTo(expiration); + assertThat(response.getUser()).isEqualTo(user); + } + } + + @Nested + @DisplayName("isExpired") + class IsExpired { + + @Test + @DisplayName("retourne false quand expirationDate dans le futur") + void testNonExpire() { + LoginResponse response = LoginResponse.builder() + .accessToken("token") + .refreshToken("refresh") + .expirationDate(LocalDateTime.now().plusHours(1)) + .build(); + + assertThat(response.isExpired()).isFalse(); + } + + @Test + @DisplayName("retourne true quand expirationDate dans le passé") + void testExpire() { + LoginResponse response = LoginResponse.builder() + .accessToken("token") + .refreshToken("refresh") + .expirationDate(LocalDateTime.now().minusHours(1)) + .build(); + + assertThat(response.isExpired()).isTrue(); + } + + @Test + @DisplayName("retourne false quand expirationDate null") + void testExpirationNull() { + LoginResponse response = LoginResponse.builder() + .accessToken("token") + .refreshToken("refresh") + .expirationDate(null) + .build(); + + assertThat(response.isExpired()).isFalse(); + } + } + + @Nested + @DisplayName("UserInfo - Builder et construction") + class UserInfoBuilder { + + @Test + @DisplayName("builder UserInfo avec tous les champs") + void testBuilderComplet() { + UUID userId = UUID.randomUUID(); + LoginResponse.EntiteInfo entite = new LoginResponse.EntiteInfo(); + List roles = Arrays.asList("ADMIN", "MEMBRE"); + List permissions = Arrays.asList("READ", "WRITE"); + + LoginResponse.UserInfo user = LoginResponse.UserInfo.builder() + .id(userId) + .nom("Diallo") + .prenom("Amadou") + .email("amadou@test.com") + .username("adiallo") + .typeCompte("ADMIN") + .roles(roles) + .permissions(permissions) + .entite(entite) + .build(); + + assertThat(user.getId()).isEqualTo(userId); + assertThat(user.getNom()).isEqualTo("Diallo"); + assertThat(user.getPrenom()).isEqualTo("Amadou"); + assertThat(user.getEmail()).isEqualTo("amadou@test.com"); + assertThat(user.getUsername()).isEqualTo("adiallo"); + assertThat(user.getTypeCompte()).isEqualTo("ADMIN"); + assertThat(user.getRoles()).isEqualTo(roles); + assertThat(user.getPermissions()).isEqualTo(permissions); + assertThat(user.getEntite()).isEqualTo(entite); + } + + @Test + @DisplayName("constructeur NoArgs UserInfo") + void testConstructeurNoArgs() { + LoginResponse.UserInfo user = new LoginResponse.UserInfo(); + assertThat(user).isNotNull(); + assertThat(user.getId()).isNull(); + } + + @Test + @DisplayName("constructeur AllArgs UserInfo") + void testConstructeurAllArgs() { + UUID userId = UUID.randomUUID(); + LoginResponse.EntiteInfo entite = new LoginResponse.EntiteInfo(); + List roles = Collections.singletonList("MEMBRE"); + List permissions = Collections.singletonList("READ"); + + LoginResponse.UserInfo user = new LoginResponse.UserInfo( + userId, + "Traoré", + "Fatou", + "fatou@test.com", + "ftraore", + "MEMBRE", + roles, + permissions, + entite + ); + + assertThat(user.getId()).isEqualTo(userId); + assertThat(user.getNom()).isEqualTo("Traoré"); + assertThat(user.getPrenom()).isEqualTo("Fatou"); + assertThat(user.getEmail()).isEqualTo("fatou@test.com"); + assertThat(user.getUsername()).isEqualTo("ftraore"); + assertThat(user.getTypeCompte()).isEqualTo("MEMBRE"); + assertThat(user.getRoles()).isEqualTo(roles); + assertThat(user.getPermissions()).isEqualTo(permissions); + assertThat(user.getEntite()).isEqualTo(entite); + } + } + + @Nested + @DisplayName("UserInfo - Getters et Setters") + class UserInfoGettersSetters { + + @Test + @DisplayName("setters et getters fonctionnent") + void testSettersGetters() { + LoginResponse.UserInfo user = new LoginResponse.UserInfo(); + UUID userId = UUID.randomUUID(); + LoginResponse.EntiteInfo entite = new LoginResponse.EntiteInfo(); + List roles = Arrays.asList("ROLE1", "ROLE2"); + List permissions = Arrays.asList("PERM1", "PERM2"); + + user.setId(userId); + user.setNom("Ndiaye"); + user.setPrenom("Moussa"); + user.setEmail("moussa@test.com"); + user.setUsername("mndiaye"); + user.setTypeCompte("SUPER_ADMIN"); + user.setRoles(roles); + user.setPermissions(permissions); + user.setEntite(entite); + + assertThat(user.getId()).isEqualTo(userId); + assertThat(user.getNom()).isEqualTo("Ndiaye"); + assertThat(user.getPrenom()).isEqualTo("Moussa"); + assertThat(user.getEmail()).isEqualTo("moussa@test.com"); + assertThat(user.getUsername()).isEqualTo("mndiaye"); + assertThat(user.getTypeCompte()).isEqualTo("SUPER_ADMIN"); + assertThat(user.getRoles()).isEqualTo(roles); + assertThat(user.getPermissions()).isEqualTo(permissions); + assertThat(user.getEntite()).isEqualTo(entite); + } + } + + @Nested + @DisplayName("UserInfo - getNomComplet") + class UserInfoGetNomComplet { + + @Test + @DisplayName("retourne prenom + nom quand les deux sont présents") + void testPrenomEtNom() { + LoginResponse.UserInfo user = new LoginResponse.UserInfo(); + user.setPrenom("Amadou"); + user.setNom("Diallo"); + user.setUsername("adiallo"); + + assertThat(user.getNomComplet()).isEqualTo("Amadou Diallo"); + } + + @Test + @DisplayName("retourne nom quand prenom null") + void testNomSeul() { + LoginResponse.UserInfo user = new LoginResponse.UserInfo(); + user.setNom("Diallo"); + user.setUsername("adiallo"); + + assertThat(user.getNomComplet()).isEqualTo("Diallo"); + } + + @Test + @DisplayName("retourne username quand nom null") + void testUsernameSeul() { + LoginResponse.UserInfo user = new LoginResponse.UserInfo(); + user.setPrenom("Amadou"); + user.setUsername("adiallo"); + + assertThat(user.getNomComplet()).isEqualTo("adiallo"); + } + + @Test + @DisplayName("retourne username quand nom et prenom null") + void testUsernameParDefaut() { + LoginResponse.UserInfo user = new LoginResponse.UserInfo(); + user.setUsername("admin"); + + assertThat(user.getNomComplet()).isEqualTo("admin"); + } + + @Test + @DisplayName("retourne null quand tout est null") + void testToutNull() { + LoginResponse.UserInfo user = new LoginResponse.UserInfo(); + + assertThat(user.getNomComplet()).isNull(); + } + } + + @Nested + @DisplayName("EntiteInfo - Builder et construction") + class EntiteInfoBuilder { + + @Test + @DisplayName("builder EntiteInfo avec tous les champs") + void testBuilderComplet() { + UUID entiteId = UUID.randomUUID(); + + LoginResponse.EntiteInfo entite = LoginResponse.EntiteInfo.builder() + .id(entiteId) + .nom("Association ABC") + .type("Association") + .pays("Sénégal") + .ville("Dakar") + .build(); + + assertThat(entite.getId()).isEqualTo(entiteId); + assertThat(entite.getNom()).isEqualTo("Association ABC"); + assertThat(entite.getType()).isEqualTo("Association"); + assertThat(entite.getPays()).isEqualTo("Sénégal"); + assertThat(entite.getVille()).isEqualTo("Dakar"); + } + + @Test + @DisplayName("constructeur NoArgs EntiteInfo") + void testConstructeurNoArgs() { + LoginResponse.EntiteInfo entite = new LoginResponse.EntiteInfo(); + assertThat(entite).isNotNull(); + assertThat(entite.getId()).isNull(); + } + + @Test + @DisplayName("constructeur AllArgs EntiteInfo") + void testConstructeurAllArgs() { + UUID entiteId = UUID.randomUUID(); + + LoginResponse.EntiteInfo entite = new LoginResponse.EntiteInfo( + entiteId, + "Mutuelle XYZ", + "Mutuelle", + "Mali", + "Bamako" + ); + + assertThat(entite.getId()).isEqualTo(entiteId); + assertThat(entite.getNom()).isEqualTo("Mutuelle XYZ"); + assertThat(entite.getType()).isEqualTo("Mutuelle"); + assertThat(entite.getPays()).isEqualTo("Mali"); + assertThat(entite.getVille()).isEqualTo("Bamako"); + } + } + + @Nested + @DisplayName("EntiteInfo - Getters et Setters") + class EntiteInfoGettersSetters { + + @Test + @DisplayName("setters et getters fonctionnent") + void testSettersGetters() { + LoginResponse.EntiteInfo entite = new LoginResponse.EntiteInfo(); + UUID entiteId = UUID.randomUUID(); + + entite.setId(entiteId); + entite.setNom("Coopérative DEF"); + entite.setType("Coopérative"); + entite.setPays("Côte d'Ivoire"); + entite.setVille("Abidjan"); + + assertThat(entite.getId()).isEqualTo(entiteId); + assertThat(entite.getNom()).isEqualTo("Coopérative DEF"); + assertThat(entite.getType()).isEqualTo("Coopérative"); + assertThat(entite.getPays()).isEqualTo("Côte d'Ivoire"); + assertThat(entite.getVille()).isEqualTo("Abidjan"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/base/BaseDTOTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/base/BaseDTOTest.java index aa9a938..fcbd40d 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/base/BaseDTOTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/base/BaseDTOTest.java @@ -1,256 +1,256 @@ -package dev.lions.unionflow.server.api.dto.base; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour BaseDTO. - * Couvre constructeur, marquerCommeNouveau, marquerCommeModifie (version null et non null), - * desactiver, reactiver, isNouveau, isActif, equals, hashCode, toString. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests BaseDTO") -class BaseDTOTest { - - /** Sous-classe concrète pour tester BaseDTO (classe abstraite). */ - private static final class ConcreteBaseDTO extends BaseDTO { - // aucune propriété additionnelle - } - - @Nested - @DisplayName("Constructeur et état initial") - class Constructeur { - - @Test - @DisplayName("constructeur par défaut initialise dateCreation, actif et version") - void testConstructeurParDefaut() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - assertThat(dto.getDateCreation()).isNotNull(); - assertThat(dto.getActif()).isTrue(); - assertThat(dto.getVersion()).isEqualTo(0L); - assertThat(dto.getId()).isNull(); - } - } - - @Nested - @DisplayName("marquerCommeNouveau") - class MarquerCommeNouveau { - - @Test - @DisplayName("marquerCommeNouveau remplit dates, creePar, modifiePar, version et actif") - void testMarquerCommeNouveau() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - dto.setVersion(5L); - dto.setActif(false); - dto.marquerCommeNouveau("user@test.com"); - assertThat(dto.getDateCreation()).isNotNull(); - assertThat(dto.getDateModification()).isNotNull(); - assertThat(dto.getDateCreation()).isEqualTo(dto.getDateModification()); - assertThat(dto.getCreePar()).isEqualTo("user@test.com"); - assertThat(dto.getModifiePar()).isEqualTo("user@test.com"); - assertThat(dto.getVersion()).isEqualTo(0L); - assertThat(dto.getActif()).isTrue(); - } - } - - @Nested - @DisplayName("marquerCommeModifie") - class MarquerCommeModifie { - - @Test - @DisplayName("marquerCommeModifie quand version non null incrémente version") - void testMarquerCommeModifieVersionNonNull() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - dto.setVersion(3L); - dto.marquerCommeModifie("other@test.com"); - assertThat(dto.getModifiePar()).isEqualTo("other@test.com"); - assertThat(dto.getDateModification()).isNotNull(); - assertThat(dto.getVersion()).isEqualTo(4L); - } - - @Test - @DisplayName("marquerCommeModifie quand version null ne lance pas NPE") - void testMarquerCommeModifieVersionNull() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - dto.setVersion(null); - dto.marquerCommeModifie("other@test.com"); - assertThat(dto.getModifiePar()).isEqualTo("other@test.com"); - assertThat(dto.getVersion()).isNull(); - } - } - - @Nested - @DisplayName("desactiver et reactiver") - class DesactiverReactiver { - - @Test - @DisplayName("desactiver met actif à false et appelle marquerCommeModifie") - void testDesactiver() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - dto.desactiver("admin@test.com"); - assertThat(dto.getActif()).isFalse(); - assertThat(dto.getModifiePar()).isEqualTo("admin@test.com"); - } - - @Test - @DisplayName("reactiver met actif à true et appelle marquerCommeModifie") - void testReactiver() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - dto.setActif(false); - dto.reactiver("admin@test.com"); - assertThat(dto.getActif()).isTrue(); - assertThat(dto.getModifiePar()).isEqualTo("admin@test.com"); - } - } - - @Nested - @DisplayName("isNouveau") - class IsNouveau { - - @Test - @DisplayName("isNouveau retourne true quand id est null") - void testIsNouveauTrue() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - assertThat(dto.isNouveau()).isTrue(); - } - - @Test - @DisplayName("isNouveau retourne false quand id est non null") - void testIsNouveauFalse() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - dto.setId(UUID.randomUUID()); - assertThat(dto.isNouveau()).isFalse(); - } - } - - @Nested - @DisplayName("isActif") - class IsActif { - - @Test - @DisplayName("isActif retourne true quand actif est Boolean.TRUE") - void testIsActifTrue() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - dto.setActif(true); - assertThat(dto.isActif()).isTrue(); - } - - @Test - @DisplayName("isActif retourne false quand actif est false ou null") - void testIsActifFalse() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - dto.setActif(false); - assertThat(dto.isActif()).isFalse(); - dto.setActif(null); - assertThat(dto.isActif()).isFalse(); - } - } - - @Nested - @DisplayName("equals") - class Equals { - - @Test - @DisplayName("equals retourne true pour même instance") - void testEqualsMemeInstance() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - assertThat(dto.equals(dto)).isTrue(); - } - - @Test - @DisplayName("equals retourne false pour null") - void testEqualsNull() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - assertThat(dto.equals(null)).isFalse(); - } - - @Test - @DisplayName("equals retourne false pour classe différente") - void testEqualsClasseDifferent() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - assertThat(dto.equals("not a DTO")).isFalse(); - } - - @Test - @DisplayName("equals retourne true quand ids égaux (non null)") - void testEqualsIdsEgaux() { - UUID id = UUID.randomUUID(); - ConcreteBaseDTO a = new ConcreteBaseDTO(); - a.setId(id); - ConcreteBaseDTO b = new ConcreteBaseDTO(); - b.setId(id); - assertThat(a).isEqualTo(b); - } - - @Test - @DisplayName("equals retourne false quand id de this est null") - void testEqualsIdThisNull() { - ConcreteBaseDTO a = new ConcreteBaseDTO(); - a.setId(null); - ConcreteBaseDTO b = new ConcreteBaseDTO(); - b.setId(UUID.randomUUID()); - assertThat(a.equals(b)).isFalse(); - } - - @Test - @DisplayName("equals retourne false quand ids différents") - void testEqualsIdsDifferents() { - ConcreteBaseDTO a = new ConcreteBaseDTO(); - a.setId(UUID.randomUUID()); - ConcreteBaseDTO b = new ConcreteBaseDTO(); - b.setId(UUID.randomUUID()); - assertThat(a).isNotEqualTo(b); - } - } - - @Nested - @DisplayName("hashCode") - class HashCode { - - @Test - @DisplayName("hashCode retourne 0 quand id est null") - void testHashCodeIdNull() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - assertThat(dto.hashCode()).isEqualTo(0); - } - - @Test - @DisplayName("hashCode retourne id.hashCode() quand id non null") - void testHashCodeIdNonNull() { - UUID id = UUID.randomUUID(); - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - dto.setId(id); - assertThat(dto.hashCode()).isEqualTo(id.hashCode()); - } - } - - @Nested - @DisplayName("toString") - class ToString { - - @Test - @DisplayName("toString contient le nom de la classe et les champs") - void testToString() { - ConcreteBaseDTO dto = new ConcreteBaseDTO(); - UUID id = UUID.randomUUID(); - dto.setId(id); - dto.setCreePar("u1"); - dto.setModifiePar("u2"); - dto.setVersion(1L); - String s = dto.toString(); - assertThat(s).contains("ConcreteBaseDTO"); - assertThat(s).contains("id=" + id); - assertThat(s).contains("creePar='u1'"); - assertThat(s).contains("modifiePar='u2'"); - assertThat(s).contains("version=1"); - assertThat(s).contains("actif=true"); - } - } -} +package dev.lions.unionflow.server.api.dto.base; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour BaseDTO. + * Couvre constructeur, marquerCommeNouveau, marquerCommeModifie (version null et non null), + * desactiver, reactiver, isNouveau, isActif, equals, hashCode, toString. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests BaseDTO") +class BaseDTOTest { + + /** Sous-classe concrète pour tester BaseDTO (classe abstraite). */ + private static final class ConcreteBaseDTO extends BaseDTO { + // aucune propriété additionnelle + } + + @Nested + @DisplayName("Constructeur et état initial") + class Constructeur { + + @Test + @DisplayName("constructeur par défaut initialise dateCreation, actif et version") + void testConstructeurParDefaut() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + assertThat(dto.getDateCreation()).isNotNull(); + assertThat(dto.getActif()).isTrue(); + assertThat(dto.getVersion()).isEqualTo(0L); + assertThat(dto.getId()).isNull(); + } + } + + @Nested + @DisplayName("marquerCommeNouveau") + class MarquerCommeNouveau { + + @Test + @DisplayName("marquerCommeNouveau remplit dates, creePar, modifiePar, version et actif") + void testMarquerCommeNouveau() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + dto.setVersion(5L); + dto.setActif(false); + dto.marquerCommeNouveau("user@test.com"); + assertThat(dto.getDateCreation()).isNotNull(); + assertThat(dto.getDateModification()).isNotNull(); + assertThat(dto.getDateCreation()).isEqualTo(dto.getDateModification()); + assertThat(dto.getCreePar()).isEqualTo("user@test.com"); + assertThat(dto.getModifiePar()).isEqualTo("user@test.com"); + assertThat(dto.getVersion()).isEqualTo(0L); + assertThat(dto.getActif()).isTrue(); + } + } + + @Nested + @DisplayName("marquerCommeModifie") + class MarquerCommeModifie { + + @Test + @DisplayName("marquerCommeModifie quand version non null incrémente version") + void testMarquerCommeModifieVersionNonNull() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + dto.setVersion(3L); + dto.marquerCommeModifie("other@test.com"); + assertThat(dto.getModifiePar()).isEqualTo("other@test.com"); + assertThat(dto.getDateModification()).isNotNull(); + assertThat(dto.getVersion()).isEqualTo(4L); + } + + @Test + @DisplayName("marquerCommeModifie quand version null ne lance pas NPE") + void testMarquerCommeModifieVersionNull() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + dto.setVersion(null); + dto.marquerCommeModifie("other@test.com"); + assertThat(dto.getModifiePar()).isEqualTo("other@test.com"); + assertThat(dto.getVersion()).isNull(); + } + } + + @Nested + @DisplayName("desactiver et reactiver") + class DesactiverReactiver { + + @Test + @DisplayName("desactiver met actif à false et appelle marquerCommeModifie") + void testDesactiver() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + dto.desactiver("admin@test.com"); + assertThat(dto.getActif()).isFalse(); + assertThat(dto.getModifiePar()).isEqualTo("admin@test.com"); + } + + @Test + @DisplayName("reactiver met actif à true et appelle marquerCommeModifie") + void testReactiver() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + dto.setActif(false); + dto.reactiver("admin@test.com"); + assertThat(dto.getActif()).isTrue(); + assertThat(dto.getModifiePar()).isEqualTo("admin@test.com"); + } + } + + @Nested + @DisplayName("isNouveau") + class IsNouveau { + + @Test + @DisplayName("isNouveau retourne true quand id est null") + void testIsNouveauTrue() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + assertThat(dto.isNouveau()).isTrue(); + } + + @Test + @DisplayName("isNouveau retourne false quand id est non null") + void testIsNouveauFalse() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + dto.setId(UUID.randomUUID()); + assertThat(dto.isNouveau()).isFalse(); + } + } + + @Nested + @DisplayName("isActif") + class IsActif { + + @Test + @DisplayName("isActif retourne true quand actif est Boolean.TRUE") + void testIsActifTrue() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + dto.setActif(true); + assertThat(dto.isActif()).isTrue(); + } + + @Test + @DisplayName("isActif retourne false quand actif est false ou null") + void testIsActifFalse() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + dto.setActif(false); + assertThat(dto.isActif()).isFalse(); + dto.setActif(null); + assertThat(dto.isActif()).isFalse(); + } + } + + @Nested + @DisplayName("equals") + class Equals { + + @Test + @DisplayName("equals retourne true pour même instance") + void testEqualsMemeInstance() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + assertThat(dto.equals(dto)).isTrue(); + } + + @Test + @DisplayName("equals retourne false pour null") + void testEqualsNull() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + assertThat(dto.equals(null)).isFalse(); + } + + @Test + @DisplayName("equals retourne false pour classe différente") + void testEqualsClasseDifferent() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + assertThat(dto.equals("not a DTO")).isFalse(); + } + + @Test + @DisplayName("equals retourne true quand ids égaux (non null)") + void testEqualsIdsEgaux() { + UUID id = UUID.randomUUID(); + ConcreteBaseDTO a = new ConcreteBaseDTO(); + a.setId(id); + ConcreteBaseDTO b = new ConcreteBaseDTO(); + b.setId(id); + assertThat(a).isEqualTo(b); + } + + @Test + @DisplayName("equals retourne false quand id de this est null") + void testEqualsIdThisNull() { + ConcreteBaseDTO a = new ConcreteBaseDTO(); + a.setId(null); + ConcreteBaseDTO b = new ConcreteBaseDTO(); + b.setId(UUID.randomUUID()); + assertThat(a.equals(b)).isFalse(); + } + + @Test + @DisplayName("equals retourne false quand ids différents") + void testEqualsIdsDifferents() { + ConcreteBaseDTO a = new ConcreteBaseDTO(); + a.setId(UUID.randomUUID()); + ConcreteBaseDTO b = new ConcreteBaseDTO(); + b.setId(UUID.randomUUID()); + assertThat(a).isNotEqualTo(b); + } + } + + @Nested + @DisplayName("hashCode") + class HashCode { + + @Test + @DisplayName("hashCode retourne 0 quand id est null") + void testHashCodeIdNull() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + assertThat(dto.hashCode()).isEqualTo(0); + } + + @Test + @DisplayName("hashCode retourne id.hashCode() quand id non null") + void testHashCodeIdNonNull() { + UUID id = UUID.randomUUID(); + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + dto.setId(id); + assertThat(dto.hashCode()).isEqualTo(id.hashCode()); + } + } + + @Nested + @DisplayName("toString") + class ToString { + + @Test + @DisplayName("toString contient le nom de la classe et les champs") + void testToString() { + ConcreteBaseDTO dto = new ConcreteBaseDTO(); + UUID id = UUID.randomUUID(); + dto.setId(id); + dto.setCreePar("u1"); + dto.setModifiePar("u2"); + dto.setVersion(1L); + String s = dto.toString(); + assertThat(s).contains("ConcreteBaseDTO"); + assertThat(s).contains("id=" + id); + assertThat(s).contains("creePar='u1'"); + assertThat(s).contains("modifiePar='u2'"); + assertThat(s).contains("version=1"); + assertThat(s).contains("actif=true"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/base/BaseResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/base/BaseResponseTest.java index e73d693..075bad3 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/base/BaseResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/base/BaseResponseTest.java @@ -1,136 +1,136 @@ -package dev.lions.unionflow.server.api.dto.base; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour BaseResponse. - * Couvre equals() et hashCode() basés sur l'ID. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-01 - */ -@DisplayName("Tests BaseResponse") -class BaseResponseTest { - - /** Sous-classe concrète pour tester BaseResponse (classe abstraite). */ - private static final class ConcreteBaseResponse extends BaseResponse { - // aucune propriété additionnelle - } - - @Nested - @DisplayName("equals") - class Equals { - - @Test - @DisplayName("retourne true pour même instance") - void testEqualsMemeInstance() { - ConcreteBaseResponse response = new ConcreteBaseResponse(); - assertThat(response.equals(response)).isTrue(); - } - - @Test - @DisplayName("retourne false pour null") - void testEqualsNull() { - ConcreteBaseResponse response = new ConcreteBaseResponse(); - assertThat(response.equals(null)).isFalse(); - } - - @Test - @DisplayName("retourne false pour classe différente") - void testEqualsClasseDifferente() { - ConcreteBaseResponse response = new ConcreteBaseResponse(); - assertThat(response.equals("not a Response")).isFalse(); - } - - @Test - @DisplayName("retourne true quand ids égaux (non null)") - void testEqualsIdsEgaux() { - UUID id = UUID.randomUUID(); - ConcreteBaseResponse a = new ConcreteBaseResponse(); - a.setId(id); - ConcreteBaseResponse b = new ConcreteBaseResponse(); - b.setId(id); - assertThat(a).isEqualTo(b); - } - - @Test - @DisplayName("retourne false quand id de this est null") - void testEqualsIdThisNull() { - ConcreteBaseResponse a = new ConcreteBaseResponse(); - a.setId(null); - ConcreteBaseResponse b = new ConcreteBaseResponse(); - b.setId(UUID.randomUUID()); - assertThat(a.equals(b)).isFalse(); - } - - @Test - @DisplayName("retourne false quand id de that est null") - void testEqualsIdThatNull() { - ConcreteBaseResponse a = new ConcreteBaseResponse(); - a.setId(UUID.randomUUID()); - ConcreteBaseResponse b = new ConcreteBaseResponse(); - b.setId(null); - assertThat(a.equals(b)).isFalse(); - } - - @Test - @DisplayName("retourne false quand les deux ids sont null") - void testEqualsIdsDeuxNull() { - ConcreteBaseResponse a = new ConcreteBaseResponse(); - a.setId(null); - ConcreteBaseResponse b = new ConcreteBaseResponse(); - b.setId(null); - assertThat(a.equals(b)).isFalse(); - } - - @Test - @DisplayName("retourne false quand ids différents") - void testEqualsIdsDifferents() { - ConcreteBaseResponse a = new ConcreteBaseResponse(); - a.setId(UUID.randomUUID()); - ConcreteBaseResponse b = new ConcreteBaseResponse(); - b.setId(UUID.randomUUID()); - assertThat(a).isNotEqualTo(b); - } - } - - @Nested - @DisplayName("hashCode") - class HashCode { - - @Test - @DisplayName("retourne 0 quand id est null") - void testHashCodeIdNull() { - ConcreteBaseResponse response = new ConcreteBaseResponse(); - assertThat(response.hashCode()).isEqualTo(0); - } - - @Test - @DisplayName("retourne id.hashCode() quand id non null") - void testHashCodeIdNonNull() { - UUID id = UUID.randomUUID(); - ConcreteBaseResponse response = new ConcreteBaseResponse(); - response.setId(id); - assertThat(response.hashCode()).isEqualTo(id.hashCode()); - } - - @Test - @DisplayName("objets égaux ont même hashCode") - void testHashCodeConsistentAvecEquals() { - UUID id = UUID.randomUUID(); - ConcreteBaseResponse a = new ConcreteBaseResponse(); - a.setId(id); - ConcreteBaseResponse b = new ConcreteBaseResponse(); - b.setId(id); - - assertThat(a).isEqualTo(b); - assertThat(a.hashCode()).isEqualTo(b.hashCode()); - } - } -} +package dev.lions.unionflow.server.api.dto.base; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour BaseResponse. + * Couvre equals() et hashCode() basés sur l'ID. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-01 + */ +@DisplayName("Tests BaseResponse") +class BaseResponseTest { + + /** Sous-classe concrète pour tester BaseResponse (classe abstraite). */ + private static final class ConcreteBaseResponse extends BaseResponse { + // aucune propriété additionnelle + } + + @Nested + @DisplayName("equals") + class Equals { + + @Test + @DisplayName("retourne true pour même instance") + void testEqualsMemeInstance() { + ConcreteBaseResponse response = new ConcreteBaseResponse(); + assertThat(response.equals(response)).isTrue(); + } + + @Test + @DisplayName("retourne false pour null") + void testEqualsNull() { + ConcreteBaseResponse response = new ConcreteBaseResponse(); + assertThat(response.equals(null)).isFalse(); + } + + @Test + @DisplayName("retourne false pour classe différente") + void testEqualsClasseDifferente() { + ConcreteBaseResponse response = new ConcreteBaseResponse(); + assertThat(response.equals("not a Response")).isFalse(); + } + + @Test + @DisplayName("retourne true quand ids égaux (non null)") + void testEqualsIdsEgaux() { + UUID id = UUID.randomUUID(); + ConcreteBaseResponse a = new ConcreteBaseResponse(); + a.setId(id); + ConcreteBaseResponse b = new ConcreteBaseResponse(); + b.setId(id); + assertThat(a).isEqualTo(b); + } + + @Test + @DisplayName("retourne false quand id de this est null") + void testEqualsIdThisNull() { + ConcreteBaseResponse a = new ConcreteBaseResponse(); + a.setId(null); + ConcreteBaseResponse b = new ConcreteBaseResponse(); + b.setId(UUID.randomUUID()); + assertThat(a.equals(b)).isFalse(); + } + + @Test + @DisplayName("retourne false quand id de that est null") + void testEqualsIdThatNull() { + ConcreteBaseResponse a = new ConcreteBaseResponse(); + a.setId(UUID.randomUUID()); + ConcreteBaseResponse b = new ConcreteBaseResponse(); + b.setId(null); + assertThat(a.equals(b)).isFalse(); + } + + @Test + @DisplayName("retourne false quand les deux ids sont null") + void testEqualsIdsDeuxNull() { + ConcreteBaseResponse a = new ConcreteBaseResponse(); + a.setId(null); + ConcreteBaseResponse b = new ConcreteBaseResponse(); + b.setId(null); + assertThat(a.equals(b)).isFalse(); + } + + @Test + @DisplayName("retourne false quand ids différents") + void testEqualsIdsDifferents() { + ConcreteBaseResponse a = new ConcreteBaseResponse(); + a.setId(UUID.randomUUID()); + ConcreteBaseResponse b = new ConcreteBaseResponse(); + b.setId(UUID.randomUUID()); + assertThat(a).isNotEqualTo(b); + } + } + + @Nested + @DisplayName("hashCode") + class HashCode { + + @Test + @DisplayName("retourne 0 quand id est null") + void testHashCodeIdNull() { + ConcreteBaseResponse response = new ConcreteBaseResponse(); + assertThat(response.hashCode()).isEqualTo(0); + } + + @Test + @DisplayName("retourne id.hashCode() quand id non null") + void testHashCodeIdNonNull() { + UUID id = UUID.randomUUID(); + ConcreteBaseResponse response = new ConcreteBaseResponse(); + response.setId(id); + assertThat(response.hashCode()).isEqualTo(id.hashCode()); + } + + @Test + @DisplayName("objets égaux ont même hashCode") + void testHashCodeConsistentAvecEquals() { + UUID id = UUID.randomUUID(); + ConcreteBaseResponse a = new ConcreteBaseResponse(); + a.setId(id); + ConcreteBaseResponse b = new ConcreteBaseResponse(); + b.setId(id); + + assertThat(a).isEqualTo(b); + assertThat(a.hashCode()).isEqualTo(b.hashCode()); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/base/PageResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/base/PageResponseTest.java index cfa5e1a..d3d2b45 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/base/PageResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/base/PageResponseTest.java @@ -1,82 +1,82 @@ -package dev.lions.unionflow.server.api.dto.base; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.util.List; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour PageResponse. - * Couvre constructeur, getters, hasNext (true/false), hasPrevious (true/false). - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests PageResponse") -class PageResponseTest { - - @Nested - @DisplayName("Constructeur et getters") - class ConstructeurEtGetters { - - @Test - @DisplayName("constructeur initialise tous les champs") - void testConstructeur() { - List contenu = List.of("a", "b"); - PageResponse page = new PageResponse<>(contenu, 0, 10, 25L, 3); - assertThat(page.getContenu()).isSameAs(contenu); - assertThat(page.getPage()).isEqualTo(0); - assertThat(page.getTaille()).isEqualTo(10); - assertThat(page.getTotalElements()).isEqualTo(25L); - assertThat(page.getTotalPages()).isEqualTo(3); - } - } - - @Nested - @DisplayName("hasNext") - class HasNext { - - @Test - @DisplayName("hasNext retourne true quand page < totalPages - 1") - void testHasNextTrue() { - PageResponse page = new PageResponse<>(List.of("a"), 0, 10, 25L, 3); - assertThat(page.hasNext()).isTrue(); - } - - @Test - @DisplayName("hasNext retourne false quand page == totalPages - 1") - void testHasNextFalseDernierePage() { - PageResponse page = new PageResponse<>(List.of("a"), 2, 10, 25L, 3); - assertThat(page.hasNext()).isFalse(); - } - - @Test - @DisplayName("hasNext retourne false quand une seule page") - void testHasNextFalseUneSeulePage() { - PageResponse page = new PageResponse<>(List.of("a", "b"), 0, 10, 2L, 1); - assertThat(page.hasNext()).isFalse(); - } - } - - @Nested - @DisplayName("hasPrevious") - class HasPrevious { - - @Test - @DisplayName("hasPrevious retourne false sur la première page") - void testHasPreviousFalse() { - PageResponse page = new PageResponse<>(List.of("a"), 0, 10, 25L, 3); - assertThat(page.hasPrevious()).isFalse(); - } - - @Test - @DisplayName("hasPrevious retourne true quand page > 0") - void testHasPreviousTrue() { - PageResponse page = new PageResponse<>(List.of("a"), 1, 10, 25L, 3); - assertThat(page.hasPrevious()).isTrue(); - } - } -} +package dev.lions.unionflow.server.api.dto.base; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.List; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour PageResponse. + * Couvre constructeur, getters, hasNext (true/false), hasPrevious (true/false). + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests PageResponse") +class PageResponseTest { + + @Nested + @DisplayName("Constructeur et getters") + class ConstructeurEtGetters { + + @Test + @DisplayName("constructeur initialise tous les champs") + void testConstructeur() { + List contenu = List.of("a", "b"); + PageResponse page = new PageResponse<>(contenu, 0, 10, 25L, 3); + assertThat(page.getContenu()).isSameAs(contenu); + assertThat(page.getPage()).isEqualTo(0); + assertThat(page.getTaille()).isEqualTo(10); + assertThat(page.getTotalElements()).isEqualTo(25L); + assertThat(page.getTotalPages()).isEqualTo(3); + } + } + + @Nested + @DisplayName("hasNext") + class HasNext { + + @Test + @DisplayName("hasNext retourne true quand page < totalPages - 1") + void testHasNextTrue() { + PageResponse page = new PageResponse<>(List.of("a"), 0, 10, 25L, 3); + assertThat(page.hasNext()).isTrue(); + } + + @Test + @DisplayName("hasNext retourne false quand page == totalPages - 1") + void testHasNextFalseDernierePage() { + PageResponse page = new PageResponse<>(List.of("a"), 2, 10, 25L, 3); + assertThat(page.hasNext()).isFalse(); + } + + @Test + @DisplayName("hasNext retourne false quand une seule page") + void testHasNextFalseUneSeulePage() { + PageResponse page = new PageResponse<>(List.of("a", "b"), 0, 10, 2L, 1); + assertThat(page.hasNext()).isFalse(); + } + } + + @Nested + @DisplayName("hasPrevious") + class HasPrevious { + + @Test + @DisplayName("hasPrevious retourne false sur la première page") + void testHasPreviousFalse() { + PageResponse page = new PageResponse<>(List.of("a"), 0, 10, 25L, 3); + assertThat(page.hasPrevious()).isFalse(); + } + + @Test + @DisplayName("hasPrevious retourne true quand page > 0") + void testHasPreviousTrue() { + PageResponse page = new PageResponse<>(List.of("a"), 1, 10, 25L, 3); + assertThat(page.hasPrevious()).isTrue(); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/common/PagedResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/common/PagedResponseTest.java index 35fa79d..d6b9c86 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/common/PagedResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/common/PagedResponseTest.java @@ -1,225 +1,225 @@ -package dev.lions.unionflow.server.api.dto.common; - -import org.junit.jupiter.api.Test; -import java.util.Arrays; -import java.util.Collections; -import java.util.List; - -import static org.junit.jupiter.api.Assertions.*; - -/** - * Tests unitaires pour PagedResponse - */ -class PagedResponseTest { - - @Test - void testConstructeurVide() { - PagedResponse response = new PagedResponse<>(); - assertNull(response.getData()); - assertNull(response.getTotal()); - assertNull(response.getPage()); - assertNull(response.getSize()); - assertNull(response.getTotalPages()); - } - - @Test - void testConstructeurAvecParametres() { - List data = Arrays.asList("A", "B", "C"); - PagedResponse response = new PagedResponse<>(data, 100L, 2, 20); - - assertEquals(data, response.getData()); - assertEquals(100L, response.getTotal()); - assertEquals(2, response.getPage()); - assertEquals(20, response.getSize()); - assertEquals(5, response.getTotalPages()); // 100 / 20 = 5 - } - - @Test - void testConstructeurComplet() { - List data = Arrays.asList("A", "B"); - PagedResponse response = new PagedResponse<>(data, 50L, 1, 10, 5); - - assertEquals(data, response.getData()); - assertEquals(50L, response.getTotal()); - assertEquals(1, response.getPage()); - assertEquals(10, response.getSize()); - assertEquals(5, response.getTotalPages()); - } - - @Test - void testCalculTotalPages() { - // Cas normal : 100 éléments, 20 par page = 5 pages - PagedResponse response1 = new PagedResponse<>(Collections.emptyList(), 100L, 0, 20); - assertEquals(5, response1.getTotalPages()); - - // Cas avec reste : 101 éléments, 20 par page = 6 pages (arrondi supérieur) - PagedResponse response2 = new PagedResponse<>(Collections.emptyList(), 101L, 0, 20); - assertEquals(6, response2.getTotalPages()); - - // Cas avec 0 élément - PagedResponse response3 = new PagedResponse<>(Collections.emptyList(), 0L, 0, 20); - assertEquals(0, response3.getTotalPages()); - - // Cas avec size = 0 (éviter division par zéro) - PagedResponse response4 = new PagedResponse<>(Collections.emptyList(), 100L, 0, 0); - assertEquals(0, response4.getTotalPages()); - - // Cas avec total null - PagedResponse response5 = new PagedResponse<>(Collections.emptyList(), null, 0, 20); - assertEquals(0, response5.getTotalPages()); - } - - @Test - void testSetters() { - PagedResponse response = new PagedResponse<>(); - List data = Arrays.asList(1, 2, 3); - - response.setData(data); - response.setTotal(50L); - response.setPage(2); - response.setSize(10); - response.setTotalPages(5); - - assertEquals(data, response.getData()); - assertEquals(50L, response.getTotal()); - assertEquals(2, response.getPage()); - assertEquals(10, response.getSize()); - assertEquals(5, response.getTotalPages()); - } - - @Test - void testSetTotalRecalculeTotalPages() { - PagedResponse response = new PagedResponse<>(); - response.setSize(10); - response.setTotal(100L); - - // Doit recalculer totalPages automatiquement - assertEquals(10, response.getTotalPages()); - } - - @Test - void testSetSizeRecalculeTotalPages() { - PagedResponse response = new PagedResponse<>(); - response.setTotal(100L); - response.setSize(25); - - // Doit recalculer totalPages automatiquement - assertEquals(4, response.getTotalPages()); - } - - @Test - void testHasNext() { - // Page 0 sur 5 pages totales → hasNext = true - PagedResponse response1 = new PagedResponse<>(Collections.emptyList(), 100L, 0, 20); - assertTrue(response1.hasNext()); - - // Page 4 (dernière) sur 5 pages → hasNext = false - PagedResponse response2 = new PagedResponse<>(Collections.emptyList(), 100L, 4, 20); - assertFalse(response2.hasNext()); - - // Page null → hasNext = false - PagedResponse response3 = new PagedResponse<>(); - response3.setTotal(100L); - response3.setSize(20); - assertFalse(response3.hasNext()); - - // Page non-null mais totalPages null → hasNext = false - PagedResponse response4 = new PagedResponse<>(); - response4.setPage(2); - assertFalse(response4.hasNext()); - } - - @Test - void testHasPrevious() { - // Page 0 → hasPrevious = false - PagedResponse response1 = new PagedResponse<>(Collections.emptyList(), 100L, 0, 20); - assertFalse(response1.hasPrevious()); - - // Page 1 → hasPrevious = true - PagedResponse response2 = new PagedResponse<>(Collections.emptyList(), 100L, 1, 20); - assertTrue(response2.hasPrevious()); - - // Page null → hasPrevious = false - PagedResponse response3 = new PagedResponse<>(); - assertFalse(response3.hasPrevious()); - } - - @Test - void testIsEmpty() { - // Liste vide → isEmpty = true - PagedResponse response1 = new PagedResponse<>(Collections.emptyList(), 0L, 0, 20); - assertTrue(response1.isEmpty()); - - // Liste null → isEmpty = true - PagedResponse response2 = new PagedResponse<>(); - assertTrue(response2.isEmpty()); - - // Liste avec données → isEmpty = false - PagedResponse response3 = new PagedResponse<>(Arrays.asList("A", "B"), 2L, 0, 20); - assertFalse(response3.isEmpty()); - } - - @Test - void testToString() { - List data = Arrays.asList("A", "B", "C"); - PagedResponse response = new PagedResponse<>(data, 100L, 2, 20); - - String result = response.toString(); - - assertTrue(result.contains("total=100")); - assertTrue(result.contains("page=2")); - assertTrue(result.contains("size=20")); - assertTrue(result.contains("totalPages=5")); - assertTrue(result.contains("itemsCount=3")); - } - - @Test - void testToStringAvecDataNull() { - PagedResponse response = new PagedResponse<>(); - String result = response.toString(); - - assertTrue(result.contains("itemsCount=0")); - } - - @Test - void testCasBordure_TotalPagesAvecValeursPetites() { - // 1 élément, 10 par page = 1 page - PagedResponse response = new PagedResponse<>(Collections.emptyList(), 1L, 0, 10); - assertEquals(1, response.getTotalPages()); - } - - @Test - void testCasBordure_TotalPagesAvecValeursGrandes() { - // 999999 éléments, 100 par page = 10000 pages - PagedResponse response = new PagedResponse<>(Collections.emptyList(), 999999L, 0, 100); - assertEquals(10000, response.getTotalPages()); - } - - @Test - void testGenerique() { - // Test avec différents types génériques - PagedResponse intResponse = new PagedResponse<>(Arrays.asList(1, 2, 3), 3L, 0, 10); - assertEquals(3, intResponse.getData().size()); - - PagedResponse doubleResponse = new PagedResponse<>(Arrays.asList(1.5, 2.5), 2L, 0, 10); - assertEquals(2, doubleResponse.getData().size()); - - PagedResponse customResponse = new PagedResponse<>( - Arrays.asList(new CustomDTO("test")), 1L, 0, 10 - ); - assertEquals(1, customResponse.getData().size()); - } - - // Classe DTO personnalisée pour tester le générique - private static class CustomDTO { - private final String value; - - public CustomDTO(String value) { - this.value = value; - } - - public String getValue() { - return value; - } - } -} +package dev.lions.unionflow.server.api.dto.common; + +import org.junit.jupiter.api.Test; +import java.util.Arrays; +import java.util.Collections; +import java.util.List; + +import static org.junit.jupiter.api.Assertions.*; + +/** + * Tests unitaires pour PagedResponse + */ +class PagedResponseTest { + + @Test + void testConstructeurVide() { + PagedResponse response = new PagedResponse<>(); + assertNull(response.getData()); + assertNull(response.getTotal()); + assertNull(response.getPage()); + assertNull(response.getSize()); + assertNull(response.getTotalPages()); + } + + @Test + void testConstructeurAvecParametres() { + List data = Arrays.asList("A", "B", "C"); + PagedResponse response = new PagedResponse<>(data, 100L, 2, 20); + + assertEquals(data, response.getData()); + assertEquals(100L, response.getTotal()); + assertEquals(2, response.getPage()); + assertEquals(20, response.getSize()); + assertEquals(5, response.getTotalPages()); // 100 / 20 = 5 + } + + @Test + void testConstructeurComplet() { + List data = Arrays.asList("A", "B"); + PagedResponse response = new PagedResponse<>(data, 50L, 1, 10, 5); + + assertEquals(data, response.getData()); + assertEquals(50L, response.getTotal()); + assertEquals(1, response.getPage()); + assertEquals(10, response.getSize()); + assertEquals(5, response.getTotalPages()); + } + + @Test + void testCalculTotalPages() { + // Cas normal : 100 éléments, 20 par page = 5 pages + PagedResponse response1 = new PagedResponse<>(Collections.emptyList(), 100L, 0, 20); + assertEquals(5, response1.getTotalPages()); + + // Cas avec reste : 101 éléments, 20 par page = 6 pages (arrondi supérieur) + PagedResponse response2 = new PagedResponse<>(Collections.emptyList(), 101L, 0, 20); + assertEquals(6, response2.getTotalPages()); + + // Cas avec 0 élément + PagedResponse response3 = new PagedResponse<>(Collections.emptyList(), 0L, 0, 20); + assertEquals(0, response3.getTotalPages()); + + // Cas avec size = 0 (éviter division par zéro) + PagedResponse response4 = new PagedResponse<>(Collections.emptyList(), 100L, 0, 0); + assertEquals(0, response4.getTotalPages()); + + // Cas avec total null + PagedResponse response5 = new PagedResponse<>(Collections.emptyList(), null, 0, 20); + assertEquals(0, response5.getTotalPages()); + } + + @Test + void testSetters() { + PagedResponse response = new PagedResponse<>(); + List data = Arrays.asList(1, 2, 3); + + response.setData(data); + response.setTotal(50L); + response.setPage(2); + response.setSize(10); + response.setTotalPages(5); + + assertEquals(data, response.getData()); + assertEquals(50L, response.getTotal()); + assertEquals(2, response.getPage()); + assertEquals(10, response.getSize()); + assertEquals(5, response.getTotalPages()); + } + + @Test + void testSetTotalRecalculeTotalPages() { + PagedResponse response = new PagedResponse<>(); + response.setSize(10); + response.setTotal(100L); + + // Doit recalculer totalPages automatiquement + assertEquals(10, response.getTotalPages()); + } + + @Test + void testSetSizeRecalculeTotalPages() { + PagedResponse response = new PagedResponse<>(); + response.setTotal(100L); + response.setSize(25); + + // Doit recalculer totalPages automatiquement + assertEquals(4, response.getTotalPages()); + } + + @Test + void testHasNext() { + // Page 0 sur 5 pages totales → hasNext = true + PagedResponse response1 = new PagedResponse<>(Collections.emptyList(), 100L, 0, 20); + assertTrue(response1.hasNext()); + + // Page 4 (dernière) sur 5 pages → hasNext = false + PagedResponse response2 = new PagedResponse<>(Collections.emptyList(), 100L, 4, 20); + assertFalse(response2.hasNext()); + + // Page null → hasNext = false + PagedResponse response3 = new PagedResponse<>(); + response3.setTotal(100L); + response3.setSize(20); + assertFalse(response3.hasNext()); + + // Page non-null mais totalPages null → hasNext = false + PagedResponse response4 = new PagedResponse<>(); + response4.setPage(2); + assertFalse(response4.hasNext()); + } + + @Test + void testHasPrevious() { + // Page 0 → hasPrevious = false + PagedResponse response1 = new PagedResponse<>(Collections.emptyList(), 100L, 0, 20); + assertFalse(response1.hasPrevious()); + + // Page 1 → hasPrevious = true + PagedResponse response2 = new PagedResponse<>(Collections.emptyList(), 100L, 1, 20); + assertTrue(response2.hasPrevious()); + + // Page null → hasPrevious = false + PagedResponse response3 = new PagedResponse<>(); + assertFalse(response3.hasPrevious()); + } + + @Test + void testIsEmpty() { + // Liste vide → isEmpty = true + PagedResponse response1 = new PagedResponse<>(Collections.emptyList(), 0L, 0, 20); + assertTrue(response1.isEmpty()); + + // Liste null → isEmpty = true + PagedResponse response2 = new PagedResponse<>(); + assertTrue(response2.isEmpty()); + + // Liste avec données → isEmpty = false + PagedResponse response3 = new PagedResponse<>(Arrays.asList("A", "B"), 2L, 0, 20); + assertFalse(response3.isEmpty()); + } + + @Test + void testToString() { + List data = Arrays.asList("A", "B", "C"); + PagedResponse response = new PagedResponse<>(data, 100L, 2, 20); + + String result = response.toString(); + + assertTrue(result.contains("total=100")); + assertTrue(result.contains("page=2")); + assertTrue(result.contains("size=20")); + assertTrue(result.contains("totalPages=5")); + assertTrue(result.contains("itemsCount=3")); + } + + @Test + void testToStringAvecDataNull() { + PagedResponse response = new PagedResponse<>(); + String result = response.toString(); + + assertTrue(result.contains("itemsCount=0")); + } + + @Test + void testCasBordure_TotalPagesAvecValeursPetites() { + // 1 élément, 10 par page = 1 page + PagedResponse response = new PagedResponse<>(Collections.emptyList(), 1L, 0, 10); + assertEquals(1, response.getTotalPages()); + } + + @Test + void testCasBordure_TotalPagesAvecValeursGrandes() { + // 999999 éléments, 100 par page = 10000 pages + PagedResponse response = new PagedResponse<>(Collections.emptyList(), 999999L, 0, 100); + assertEquals(10000, response.getTotalPages()); + } + + @Test + void testGenerique() { + // Test avec différents types génériques + PagedResponse intResponse = new PagedResponse<>(Arrays.asList(1, 2, 3), 3L, 0, 10); + assertEquals(3, intResponse.getData().size()); + + PagedResponse doubleResponse = new PagedResponse<>(Arrays.asList(1.5, 2.5), 2L, 0, 10); + assertEquals(2, doubleResponse.getData().size()); + + PagedResponse customResponse = new PagedResponse<>( + Arrays.asList(new CustomDTO("test")), 1L, 0, 10 + ); + assertEquals(1, customResponse.getData().size()); + } + + // Classe DTO personnalisée pour tester le générique + private static class CustomDTO { + private final String value; + + public CustomDTO(String value) { + this.value = value; + } + + public String getValue() { + return value; + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/communication/request/CreateConversationRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/communication/request/CreateConversationRequestTest.java index f894e29..037b7f8 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/communication/request/CreateConversationRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/communication/request/CreateConversationRequestTest.java @@ -1,186 +1,186 @@ -package dev.lions.unionflow.server.api.dto.communication.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.communication.ConversationType; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.List; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeAll; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour CreateConversationRequest. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@DisplayName("Tests CreateConversationRequest") -class CreateConversationRequestTest { - - private static Validator validator; - - @BeforeAll - static void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - @DisplayName("Le builder doit créer un CreateConversationRequest valide") - void testBuilderValid() { - UUID participant1 = UUID.randomUUID(); - UUID participant2 = UUID.randomUUID(); - UUID orgId = UUID.randomUUID(); - - CreateConversationRequest request = - CreateConversationRequest.builder() - .name("Test Conversation") - .description("Test description") - .type(ConversationType.GROUP) - .participantIds(List.of(participant1, participant2)) - .organisationId(orgId) - .build(); - - assertThat(request.name()).isEqualTo("Test Conversation"); - assertThat(request.description()).isEqualTo("Test description"); - assertThat(request.type()).isEqualTo(ConversationType.GROUP); - assertThat(request.participantIds()).containsExactly(participant1, participant2); - assertThat(request.organisationId()).isEqualTo(orgId); - - Set> violations = validator.validate(request); - assertThat(violations).isEmpty(); - } - - @Test - @DisplayName("La validation doit échouer si le nom est null") - void testValidationNameNull() { - CreateConversationRequest request = - CreateConversationRequest.builder() - .type(ConversationType.INDIVIDUAL) - .participantIds(List.of(UUID.randomUUID())) - .build(); - - Set> violations = validator.validate(request); - assertThat(violations).hasSize(1); - assertThat(violations.iterator().next().getMessage()).contains("vide"); - } - - @Test - @DisplayName("La validation doit échouer si le nom est vide") - void testValidationNameBlank() { - CreateConversationRequest request = - CreateConversationRequest.builder() - .name(" ") - .type(ConversationType.INDIVIDUAL) - .participantIds(List.of(UUID.randomUUID())) - .build(); - - Set> violations = validator.validate(request); - assertThat(violations).hasSize(1); - } - - @Test - @DisplayName("La validation doit échouer si le nom dépasse 255 caractères") - void testValidationNameTooLong() { - String longName = "a".repeat(256); - CreateConversationRequest request = - CreateConversationRequest.builder() - .name(longName) - .type(ConversationType.INDIVIDUAL) - .participantIds(List.of(UUID.randomUUID())) - .build(); - - Set> violations = validator.validate(request); - assertThat(violations).hasSize(1); - assertThat(violations.iterator().next().getMessage()).contains("taille"); - } - - @Test - @DisplayName("La validation doit échouer si la description dépasse 1000 caractères") - void testValidationDescriptionTooLong() { - String longDesc = "a".repeat(1001); - CreateConversationRequest request = - CreateConversationRequest.builder() - .name("Test") - .description(longDesc) - .type(ConversationType.INDIVIDUAL) - .participantIds(List.of(UUID.randomUUID())) - .build(); - - Set> violations = validator.validate(request); - assertThat(violations).hasSize(1); - assertThat(violations.iterator().next().getMessage()).contains("taille"); - } - - @Test - @DisplayName("La validation doit échouer si le type est null") - void testValidationTypeNull() { - CreateConversationRequest request = - CreateConversationRequest.builder() - .name("Test") - .participantIds(List.of(UUID.randomUUID())) - .build(); - - Set> violations = validator.validate(request); - assertThat(violations).hasSize(1); - assertThat(violations.iterator().next().getMessage()).contains("nul"); - } - - @Test - @DisplayName("La validation doit échouer si participantIds est vide") - void testValidationParticipantsEmpty() { - CreateConversationRequest request = - CreateConversationRequest.builder() - .name("Test") - .type(ConversationType.INDIVIDUAL) - .participantIds(List.of()) - .build(); - - Set> violations = validator.validate(request); - assertThat(violations).hasSize(1); - assertThat(violations.iterator().next().getMessage()).contains("vide"); - } - - @Test - @DisplayName("La validation doit échouer si participantIds est null") - void testValidationParticipantsNull() { - CreateConversationRequest request = - CreateConversationRequest.builder() - .name("Test") - .type(ConversationType.INDIVIDUAL) - .build(); - - Set> violations = validator.validate(request); - assertThat(violations).hasSize(1); - } - - @Test - @DisplayName("Deux instances avec les mêmes valeurs doivent être égales") - void testEquality() { - UUID participant = UUID.randomUUID(); - - CreateConversationRequest request1 = - CreateConversationRequest.builder() - .name("Test") - .type(ConversationType.INDIVIDUAL) - .participantIds(List.of(participant)) - .build(); - - CreateConversationRequest request2 = - CreateConversationRequest.builder() - .name("Test") - .type(ConversationType.INDIVIDUAL) - .participantIds(List.of(participant)) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } -} +package dev.lions.unionflow.server.api.dto.communication.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.communication.ConversationType; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.List; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeAll; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour CreateConversationRequest. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@DisplayName("Tests CreateConversationRequest") +class CreateConversationRequestTest { + + private static Validator validator; + + @BeforeAll + static void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + @DisplayName("Le builder doit créer un CreateConversationRequest valide") + void testBuilderValid() { + UUID participant1 = UUID.randomUUID(); + UUID participant2 = UUID.randomUUID(); + UUID orgId = UUID.randomUUID(); + + CreateConversationRequest request = + CreateConversationRequest.builder() + .name("Test Conversation") + .description("Test description") + .type(ConversationType.GROUP) + .participantIds(List.of(participant1, participant2)) + .organisationId(orgId) + .build(); + + assertThat(request.name()).isEqualTo("Test Conversation"); + assertThat(request.description()).isEqualTo("Test description"); + assertThat(request.type()).isEqualTo(ConversationType.GROUP); + assertThat(request.participantIds()).containsExactly(participant1, participant2); + assertThat(request.organisationId()).isEqualTo(orgId); + + Set> violations = validator.validate(request); + assertThat(violations).isEmpty(); + } + + @Test + @DisplayName("La validation doit échouer si le nom est null") + void testValidationNameNull() { + CreateConversationRequest request = + CreateConversationRequest.builder() + .type(ConversationType.INDIVIDUAL) + .participantIds(List.of(UUID.randomUUID())) + .build(); + + Set> violations = validator.validate(request); + assertThat(violations).hasSize(1); + assertThat(violations.iterator().next().getMessage()).contains("vide"); + } + + @Test + @DisplayName("La validation doit échouer si le nom est vide") + void testValidationNameBlank() { + CreateConversationRequest request = + CreateConversationRequest.builder() + .name(" ") + .type(ConversationType.INDIVIDUAL) + .participantIds(List.of(UUID.randomUUID())) + .build(); + + Set> violations = validator.validate(request); + assertThat(violations).hasSize(1); + } + + @Test + @DisplayName("La validation doit échouer si le nom dépasse 255 caractères") + void testValidationNameTooLong() { + String longName = "a".repeat(256); + CreateConversationRequest request = + CreateConversationRequest.builder() + .name(longName) + .type(ConversationType.INDIVIDUAL) + .participantIds(List.of(UUID.randomUUID())) + .build(); + + Set> violations = validator.validate(request); + assertThat(violations).hasSize(1); + assertThat(violations.iterator().next().getMessage()).contains("taille"); + } + + @Test + @DisplayName("La validation doit échouer si la description dépasse 1000 caractères") + void testValidationDescriptionTooLong() { + String longDesc = "a".repeat(1001); + CreateConversationRequest request = + CreateConversationRequest.builder() + .name("Test") + .description(longDesc) + .type(ConversationType.INDIVIDUAL) + .participantIds(List.of(UUID.randomUUID())) + .build(); + + Set> violations = validator.validate(request); + assertThat(violations).hasSize(1); + assertThat(violations.iterator().next().getMessage()).contains("taille"); + } + + @Test + @DisplayName("La validation doit échouer si le type est null") + void testValidationTypeNull() { + CreateConversationRequest request = + CreateConversationRequest.builder() + .name("Test") + .participantIds(List.of(UUID.randomUUID())) + .build(); + + Set> violations = validator.validate(request); + assertThat(violations).hasSize(1); + assertThat(violations.iterator().next().getMessage()).contains("nul"); + } + + @Test + @DisplayName("La validation doit échouer si participantIds est vide") + void testValidationParticipantsEmpty() { + CreateConversationRequest request = + CreateConversationRequest.builder() + .name("Test") + .type(ConversationType.INDIVIDUAL) + .participantIds(List.of()) + .build(); + + Set> violations = validator.validate(request); + assertThat(violations).hasSize(1); + assertThat(violations.iterator().next().getMessage()).contains("vide"); + } + + @Test + @DisplayName("La validation doit échouer si participantIds est null") + void testValidationParticipantsNull() { + CreateConversationRequest request = + CreateConversationRequest.builder() + .name("Test") + .type(ConversationType.INDIVIDUAL) + .build(); + + Set> violations = validator.validate(request); + assertThat(violations).hasSize(1); + } + + @Test + @DisplayName("Deux instances avec les mêmes valeurs doivent être égales") + void testEquality() { + UUID participant = UUID.randomUUID(); + + CreateConversationRequest request1 = + CreateConversationRequest.builder() + .name("Test") + .type(ConversationType.INDIVIDUAL) + .participantIds(List.of(participant)) + .build(); + + CreateConversationRequest request2 = + CreateConversationRequest.builder() + .name("Test") + .type(ConversationType.INDIVIDUAL) + .participantIds(List.of(participant)) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/communication/request/SendMessageRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/communication/request/SendMessageRequestTest.java index df90bf4..64bf0be 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/communication/request/SendMessageRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/communication/request/SendMessageRequestTest.java @@ -1,171 +1,171 @@ -package dev.lions.unionflow.server.api.dto.communication.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.communication.MessagePriority; -import dev.lions.unionflow.server.api.enums.communication.MessageType; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.List; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeAll; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour SendMessageRequest. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@DisplayName("Tests SendMessageRequest") -class SendMessageRequestTest { - - private static Validator validator; - - @BeforeAll - static void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - @DisplayName("Le builder doit créer un SendMessageRequest valide") - void testBuilderValid() { - UUID conversationId = UUID.randomUUID(); - UUID recipient1 = UUID.randomUUID(); - UUID recipient2 = UUID.randomUUID(); - - SendMessageRequest request = - SendMessageRequest.builder() - .conversationId(conversationId) - .content("Test message content") - .type(MessageType.INDIVIDUAL) - .priority(MessagePriority.NORMAL) - .recipientIds(List.of(recipient1, recipient2)) - .recipientRoles(List.of("ADMIN", "USER")) - .attachments(List.of("file1.pdf", "file2.png")) - .build(); - - assertThat(request.conversationId()).isEqualTo(conversationId); - assertThat(request.content()).isEqualTo("Test message content"); - assertThat(request.type()).isEqualTo(MessageType.INDIVIDUAL); - assertThat(request.priority()).isEqualTo(MessagePriority.NORMAL); - assertThat(request.recipientIds()).containsExactly(recipient1, recipient2); - assertThat(request.recipientRoles()).containsExactly("ADMIN", "USER"); - assertThat(request.attachments()).containsExactly("file1.pdf", "file2.png"); - - Set> violations = validator.validate(request); - assertThat(violations).isEmpty(); - } - - @Test - @DisplayName("La validation doit échouer si conversationId est null") - void testValidationConversationIdNull() { - SendMessageRequest request = - SendMessageRequest.builder().content("Test message").build(); - - Set> violations = validator.validate(request); - assertThat(violations).hasSize(1); - assertThat(violations.iterator().next().getMessage()).contains("nul"); - } - - @Test - @DisplayName("La validation doit échouer si le content est null") - void testValidationContentNull() { - SendMessageRequest request = - SendMessageRequest.builder().conversationId(UUID.randomUUID()).build(); - - Set> violations = validator.validate(request); - assertThat(violations).hasSize(1); - assertThat(violations.iterator().next().getMessage()).contains("vide"); - } - - @Test - @DisplayName("La validation doit échouer si le content est vide") - void testValidationContentBlank() { - SendMessageRequest request = - SendMessageRequest.builder() - .conversationId(UUID.randomUUID()) - .content(" ") - .build(); - - Set> violations = validator.validate(request); - assertThat(violations).hasSize(1); - } - - @Test - @DisplayName("La validation doit échouer si le content dépasse 10000 caractères") - void testValidationContentTooLong() { - String longContent = "a".repeat(10001); - SendMessageRequest request = - SendMessageRequest.builder() - .conversationId(UUID.randomUUID()) - .content(longContent) - .build(); - - Set> violations = validator.validate(request); - assertThat(violations).hasSize(1); - assertThat(violations.iterator().next().getMessage()).contains("taille"); - } - - @Test - @DisplayName("Le type et priority peuvent être null (champs optionnels)") - void testOptionalFields() { - SendMessageRequest request = - SendMessageRequest.builder() - .conversationId(UUID.randomUUID()) - .content("Test message") - .build(); - - Set> violations = validator.validate(request); - assertThat(violations).isEmpty(); - } - - @Test - @DisplayName("Les listes peuvent être nulles (champs optionnels)") - void testOptionalLists() { - SendMessageRequest request = - SendMessageRequest.builder() - .conversationId(UUID.randomUUID()) - .content("Test message") - .recipientIds(null) - .recipientRoles(null) - .attachments(null) - .build(); - - assertThat(request.recipientIds()).isNull(); - assertThat(request.recipientRoles()).isNull(); - assertThat(request.attachments()).isNull(); - - Set> violations = validator.validate(request); - assertThat(violations).isEmpty(); - } - - @Test - @DisplayName("Deux instances avec les mêmes valeurs doivent être égales") - void testEquality() { - UUID conversationId = UUID.randomUUID(); - - SendMessageRequest request1 = - SendMessageRequest.builder() - .conversationId(conversationId) - .content("Test message") - .type(MessageType.SYSTEM) - .build(); - - SendMessageRequest request2 = - SendMessageRequest.builder() - .conversationId(conversationId) - .content("Test message") - .type(MessageType.SYSTEM) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } -} +package dev.lions.unionflow.server.api.dto.communication.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.communication.MessagePriority; +import dev.lions.unionflow.server.api.enums.communication.MessageType; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.List; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeAll; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour SendMessageRequest. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@DisplayName("Tests SendMessageRequest") +class SendMessageRequestTest { + + private static Validator validator; + + @BeforeAll + static void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + @DisplayName("Le builder doit créer un SendMessageRequest valide") + void testBuilderValid() { + UUID conversationId = UUID.randomUUID(); + UUID recipient1 = UUID.randomUUID(); + UUID recipient2 = UUID.randomUUID(); + + SendMessageRequest request = + SendMessageRequest.builder() + .conversationId(conversationId) + .content("Test message content") + .type(MessageType.INDIVIDUAL) + .priority(MessagePriority.NORMAL) + .recipientIds(List.of(recipient1, recipient2)) + .recipientRoles(List.of("ADMIN", "USER")) + .attachments(List.of("file1.pdf", "file2.png")) + .build(); + + assertThat(request.conversationId()).isEqualTo(conversationId); + assertThat(request.content()).isEqualTo("Test message content"); + assertThat(request.type()).isEqualTo(MessageType.INDIVIDUAL); + assertThat(request.priority()).isEqualTo(MessagePriority.NORMAL); + assertThat(request.recipientIds()).containsExactly(recipient1, recipient2); + assertThat(request.recipientRoles()).containsExactly("ADMIN", "USER"); + assertThat(request.attachments()).containsExactly("file1.pdf", "file2.png"); + + Set> violations = validator.validate(request); + assertThat(violations).isEmpty(); + } + + @Test + @DisplayName("La validation doit échouer si conversationId est null") + void testValidationConversationIdNull() { + SendMessageRequest request = + SendMessageRequest.builder().content("Test message").build(); + + Set> violations = validator.validate(request); + assertThat(violations).hasSize(1); + assertThat(violations.iterator().next().getMessage()).contains("nul"); + } + + @Test + @DisplayName("La validation doit échouer si le content est null") + void testValidationContentNull() { + SendMessageRequest request = + SendMessageRequest.builder().conversationId(UUID.randomUUID()).build(); + + Set> violations = validator.validate(request); + assertThat(violations).hasSize(1); + assertThat(violations.iterator().next().getMessage()).contains("vide"); + } + + @Test + @DisplayName("La validation doit échouer si le content est vide") + void testValidationContentBlank() { + SendMessageRequest request = + SendMessageRequest.builder() + .conversationId(UUID.randomUUID()) + .content(" ") + .build(); + + Set> violations = validator.validate(request); + assertThat(violations).hasSize(1); + } + + @Test + @DisplayName("La validation doit échouer si le content dépasse 10000 caractères") + void testValidationContentTooLong() { + String longContent = "a".repeat(10001); + SendMessageRequest request = + SendMessageRequest.builder() + .conversationId(UUID.randomUUID()) + .content(longContent) + .build(); + + Set> violations = validator.validate(request); + assertThat(violations).hasSize(1); + assertThat(violations.iterator().next().getMessage()).contains("taille"); + } + + @Test + @DisplayName("Le type et priority peuvent être null (champs optionnels)") + void testOptionalFields() { + SendMessageRequest request = + SendMessageRequest.builder() + .conversationId(UUID.randomUUID()) + .content("Test message") + .build(); + + Set> violations = validator.validate(request); + assertThat(violations).isEmpty(); + } + + @Test + @DisplayName("Les listes peuvent être nulles (champs optionnels)") + void testOptionalLists() { + SendMessageRequest request = + SendMessageRequest.builder() + .conversationId(UUID.randomUUID()) + .content("Test message") + .recipientIds(null) + .recipientRoles(null) + .attachments(null) + .build(); + + assertThat(request.recipientIds()).isNull(); + assertThat(request.recipientRoles()).isNull(); + assertThat(request.attachments()).isNull(); + + Set> violations = validator.validate(request); + assertThat(violations).isEmpty(); + } + + @Test + @DisplayName("Deux instances avec les mêmes valeurs doivent être égales") + void testEquality() { + UUID conversationId = UUID.randomUUID(); + + SendMessageRequest request1 = + SendMessageRequest.builder() + .conversationId(conversationId) + .content("Test message") + .type(MessageType.SYSTEM) + .build(); + + SendMessageRequest request2 = + SendMessageRequest.builder() + .conversationId(conversationId) + .content("Test message") + .type(MessageType.SYSTEM) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateCompteComptableRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateCompteComptableRequestTest.java index 414ded6..6f30fbd 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateCompteComptableRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateCompteComptableRequestTest.java @@ -1,159 +1,159 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.comptabilite.TypeCompteComptable; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateCompteComptableRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - CreateCompteComptableRequest request = CreateCompteComptableRequest.builder() - .numeroCompte("401000") - .libelle("Fournisseurs") - .typeCompte(TypeCompteComptable.PASSIF) - .classeComptable(4) - .soldeInitial(BigDecimal.valueOf(1000.00)) - .soldeActuel(BigDecimal.valueOf(1500.00)) - .compteCollectif(true) - .compteAnalytique(false) - .description("Compte fournisseurs principal") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroCompte()).isEqualTo("401000"); - assertThat(request.libelle()).isEqualTo("Fournisseurs"); - assertThat(request.typeCompte()).isEqualTo(TypeCompteComptable.PASSIF); - assertThat(request.classeComptable()).isEqualTo(4); - assertThat(request.soldeInitial()).isEqualByComparingTo(BigDecimal.valueOf(1000.00)); - assertThat(request.soldeActuel()).isEqualByComparingTo(BigDecimal.valueOf(1500.00)); - assertThat(request.compteCollectif()).isTrue(); - assertThat(request.compteAnalytique()).isFalse(); - assertThat(request.description()).isEqualTo("Compte fournisseurs principal"); - } - - @Test - void testBuilder_MinimalFields() { - CreateCompteComptableRequest request = CreateCompteComptableRequest.builder() - .numeroCompte("512000") - .libelle("Banque") - .typeCompte(TypeCompteComptable.TRESORERIE) - .classeComptable(5) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroCompte()).isEqualTo("512000"); - assertThat(request.libelle()).isEqualTo("Banque"); - assertThat(request.typeCompte()).isEqualTo(TypeCompteComptable.TRESORERIE); - assertThat(request.classeComptable()).isEqualTo(5); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateCompteComptableRequest request = CreateCompteComptableRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroCompte")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeCompte")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("classeComptable")); - } - - @Test - void testValidation_ClasseComptableTooSmall() { - CreateCompteComptableRequest request = CreateCompteComptableRequest.builder() - .numeroCompte("001000") - .libelle("Test") - .typeCompte(TypeCompteComptable.ACTIF) - .classeComptable(0) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("classeComptable")); - } - - @Test - void testValidation_ClasseComptableTooLarge() { - CreateCompteComptableRequest request = CreateCompteComptableRequest.builder() - .numeroCompte("801000") - .libelle("Test") - .typeCompte(TypeCompteComptable.AUTRE) - .classeComptable(8) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("classeComptable")); - } - - @Test - void testValidation_ValidFields() { - CreateCompteComptableRequest request = CreateCompteComptableRequest.builder() - .numeroCompte("601000") - .libelle("Achats de marchandises") - .typeCompte(TypeCompteComptable.CHARGES) - .classeComptable(6) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - CreateCompteComptableRequest request1 = CreateCompteComptableRequest.builder() - .numeroCompte("411000") - .libelle("Clients") - .typeCompte(TypeCompteComptable.ACTIF) - .classeComptable(4) - .build(); - - CreateCompteComptableRequest request2 = CreateCompteComptableRequest.builder() - .numeroCompte("411000") - .libelle("Clients") - .typeCompte(TypeCompteComptable.ACTIF) - .classeComptable(4) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateCompteComptableRequest request = CreateCompteComptableRequest.builder() - .numeroCompte("701000") - .libelle("Ventes de produits") - .typeCompte(TypeCompteComptable.PRODUITS) - .classeComptable(7) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateCompteComptableRequest"); - assertThat(toString).contains("701000"); - } -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.comptabilite.TypeCompteComptable; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateCompteComptableRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + CreateCompteComptableRequest request = CreateCompteComptableRequest.builder() + .numeroCompte("401000") + .libelle("Fournisseurs") + .typeCompte(TypeCompteComptable.PASSIF) + .classeComptable(4) + .soldeInitial(BigDecimal.valueOf(1000.00)) + .soldeActuel(BigDecimal.valueOf(1500.00)) + .compteCollectif(true) + .compteAnalytique(false) + .description("Compte fournisseurs principal") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroCompte()).isEqualTo("401000"); + assertThat(request.libelle()).isEqualTo("Fournisseurs"); + assertThat(request.typeCompte()).isEqualTo(TypeCompteComptable.PASSIF); + assertThat(request.classeComptable()).isEqualTo(4); + assertThat(request.soldeInitial()).isEqualByComparingTo(BigDecimal.valueOf(1000.00)); + assertThat(request.soldeActuel()).isEqualByComparingTo(BigDecimal.valueOf(1500.00)); + assertThat(request.compteCollectif()).isTrue(); + assertThat(request.compteAnalytique()).isFalse(); + assertThat(request.description()).isEqualTo("Compte fournisseurs principal"); + } + + @Test + void testBuilder_MinimalFields() { + CreateCompteComptableRequest request = CreateCompteComptableRequest.builder() + .numeroCompte("512000") + .libelle("Banque") + .typeCompte(TypeCompteComptable.TRESORERIE) + .classeComptable(5) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroCompte()).isEqualTo("512000"); + assertThat(request.libelle()).isEqualTo("Banque"); + assertThat(request.typeCompte()).isEqualTo(TypeCompteComptable.TRESORERIE); + assertThat(request.classeComptable()).isEqualTo(5); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateCompteComptableRequest request = CreateCompteComptableRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroCompte")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeCompte")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("classeComptable")); + } + + @Test + void testValidation_ClasseComptableTooSmall() { + CreateCompteComptableRequest request = CreateCompteComptableRequest.builder() + .numeroCompte("001000") + .libelle("Test") + .typeCompte(TypeCompteComptable.ACTIF) + .classeComptable(0) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("classeComptable")); + } + + @Test + void testValidation_ClasseComptableTooLarge() { + CreateCompteComptableRequest request = CreateCompteComptableRequest.builder() + .numeroCompte("801000") + .libelle("Test") + .typeCompte(TypeCompteComptable.AUTRE) + .classeComptable(8) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("classeComptable")); + } + + @Test + void testValidation_ValidFields() { + CreateCompteComptableRequest request = CreateCompteComptableRequest.builder() + .numeroCompte("601000") + .libelle("Achats de marchandises") + .typeCompte(TypeCompteComptable.CHARGES) + .classeComptable(6) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + CreateCompteComptableRequest request1 = CreateCompteComptableRequest.builder() + .numeroCompte("411000") + .libelle("Clients") + .typeCompte(TypeCompteComptable.ACTIF) + .classeComptable(4) + .build(); + + CreateCompteComptableRequest request2 = CreateCompteComptableRequest.builder() + .numeroCompte("411000") + .libelle("Clients") + .typeCompte(TypeCompteComptable.ACTIF) + .classeComptable(4) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateCompteComptableRequest request = CreateCompteComptableRequest.builder() + .numeroCompte("701000") + .libelle("Ventes de produits") + .typeCompte(TypeCompteComptable.PRODUITS) + .classeComptable(7) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateCompteComptableRequest"); + assertThat(toString).contains("701000"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateEcritureComptableRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateEcritureComptableRequestTest.java index 594a85a..a11d659 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateEcritureComptableRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateEcritureComptableRequestTest.java @@ -1,193 +1,193 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.List; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateEcritureComptableRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID journalId = UUID.randomUUID(); - UUID organisationId = UUID.randomUUID(); - UUID paiementId = UUID.randomUUID(); - LocalDate dateEcriture = LocalDate.of(2025, 3, 15); - - CreateLigneEcritureRequest ligne = CreateLigneEcritureRequest.builder() - .numeroLigne(1) - .montantDebit(BigDecimal.valueOf(1000.00)) - .montantCredit(BigDecimal.ZERO) - .libelle("Ligne 1") - .ecritureId(UUID.randomUUID()) - .compteComptableId(UUID.randomUUID()) - .build(); - - CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder() - .numeroPiece("EC-2025-001") - .dateEcriture(dateEcriture) - .libelle("Écriture de test") - .reference("REF-001") - .lettrage("A") - .pointe(true) - .montantDebit(BigDecimal.valueOf(1000.00)) - .montantCredit(BigDecimal.valueOf(1000.00)) - .commentaire("Commentaire test") - .journalId(journalId) - .organisationId(organisationId) - .paiementId(paiementId) - .lignes(List.of(ligne)) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroPiece()).isEqualTo("EC-2025-001"); - assertThat(request.dateEcriture()).isEqualTo(dateEcriture); - assertThat(request.libelle()).isEqualTo("Écriture de test"); - assertThat(request.reference()).isEqualTo("REF-001"); - assertThat(request.lettrage()).isEqualTo("A"); - assertThat(request.pointe()).isTrue(); - assertThat(request.montantDebit()).isEqualByComparingTo(BigDecimal.valueOf(1000.00)); - assertThat(request.montantCredit()).isEqualByComparingTo(BigDecimal.valueOf(1000.00)); - assertThat(request.commentaire()).isEqualTo("Commentaire test"); - assertThat(request.journalId()).isEqualTo(journalId); - assertThat(request.organisationId()).isEqualTo(organisationId); - assertThat(request.paiementId()).isEqualTo(paiementId); - assertThat(request.lignes()).hasSize(1); - } - - @Test - void testBuilder_MinimalFields() { - UUID journalId = UUID.randomUUID(); - LocalDate dateEcriture = LocalDate.of(2025, 3, 15); - - CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder() - .numeroPiece("EC-2025-002") - .dateEcriture(dateEcriture) - .libelle("Écriture minimale") - .journalId(journalId) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroPiece()).isEqualTo("EC-2025-002"); - assertThat(request.dateEcriture()).isEqualTo(dateEcriture); - assertThat(request.libelle()).isEqualTo("Écriture minimale"); - assertThat(request.journalId()).isEqualTo(journalId); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroPiece")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateEcriture")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("journalId")); - } - - @Test - void testValidation_NegativeMontantDebit() { - CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder() - .numeroPiece("EC-2025-003") - .dateEcriture(LocalDate.now()) - .libelle("Écriture test") - .journalId(UUID.randomUUID()) - .montantDebit(BigDecimal.valueOf(-100.00)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDebit")); - } - - @Test - void testValidation_NegativeMontantCredit() { - CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder() - .numeroPiece("EC-2025-004") - .dateEcriture(LocalDate.now()) - .libelle("Écriture test") - .journalId(UUID.randomUUID()) - .montantCredit(BigDecimal.valueOf(-100.00)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantCredit")); - } - - @Test - void testValidation_ValidFields() { - CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder() - .numeroPiece("EC-2025-005") - .dateEcriture(LocalDate.of(2025, 3, 15)) - .libelle("Écriture valide") - .journalId(UUID.randomUUID()) - .montantDebit(BigDecimal.valueOf(1000.00)) - .montantCredit(BigDecimal.valueOf(1000.00)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID journalId = UUID.randomUUID(); - LocalDate dateEcriture = LocalDate.of(2025, 3, 15); - - CreateEcritureComptableRequest request1 = CreateEcritureComptableRequest.builder() - .numeroPiece("EC-2025-006") - .dateEcriture(dateEcriture) - .libelle("Écriture test") - .journalId(journalId) - .build(); - - CreateEcritureComptableRequest request2 = CreateEcritureComptableRequest.builder() - .numeroPiece("EC-2025-006") - .dateEcriture(dateEcriture) - .libelle("Écriture test") - .journalId(journalId) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder() - .numeroPiece("EC-2025-007") - .dateEcriture(LocalDate.of(2025, 3, 15)) - .libelle("Écriture toString") - .journalId(UUID.randomUUID()) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateEcritureComptableRequest"); - assertThat(toString).contains("EC-2025-007"); - } -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.List; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateEcritureComptableRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID journalId = UUID.randomUUID(); + UUID organisationId = UUID.randomUUID(); + UUID paiementId = UUID.randomUUID(); + LocalDate dateEcriture = LocalDate.of(2025, 3, 15); + + CreateLigneEcritureRequest ligne = CreateLigneEcritureRequest.builder() + .numeroLigne(1) + .montantDebit(BigDecimal.valueOf(1000.00)) + .montantCredit(BigDecimal.ZERO) + .libelle("Ligne 1") + .ecritureId(UUID.randomUUID()) + .compteComptableId(UUID.randomUUID()) + .build(); + + CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder() + .numeroPiece("EC-2025-001") + .dateEcriture(dateEcriture) + .libelle("Écriture de test") + .reference("REF-001") + .lettrage("A") + .pointe(true) + .montantDebit(BigDecimal.valueOf(1000.00)) + .montantCredit(BigDecimal.valueOf(1000.00)) + .commentaire("Commentaire test") + .journalId(journalId) + .organisationId(organisationId) + .paiementId(paiementId) + .lignes(List.of(ligne)) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroPiece()).isEqualTo("EC-2025-001"); + assertThat(request.dateEcriture()).isEqualTo(dateEcriture); + assertThat(request.libelle()).isEqualTo("Écriture de test"); + assertThat(request.reference()).isEqualTo("REF-001"); + assertThat(request.lettrage()).isEqualTo("A"); + assertThat(request.pointe()).isTrue(); + assertThat(request.montantDebit()).isEqualByComparingTo(BigDecimal.valueOf(1000.00)); + assertThat(request.montantCredit()).isEqualByComparingTo(BigDecimal.valueOf(1000.00)); + assertThat(request.commentaire()).isEqualTo("Commentaire test"); + assertThat(request.journalId()).isEqualTo(journalId); + assertThat(request.organisationId()).isEqualTo(organisationId); + assertThat(request.paiementId()).isEqualTo(paiementId); + assertThat(request.lignes()).hasSize(1); + } + + @Test + void testBuilder_MinimalFields() { + UUID journalId = UUID.randomUUID(); + LocalDate dateEcriture = LocalDate.of(2025, 3, 15); + + CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder() + .numeroPiece("EC-2025-002") + .dateEcriture(dateEcriture) + .libelle("Écriture minimale") + .journalId(journalId) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroPiece()).isEqualTo("EC-2025-002"); + assertThat(request.dateEcriture()).isEqualTo(dateEcriture); + assertThat(request.libelle()).isEqualTo("Écriture minimale"); + assertThat(request.journalId()).isEqualTo(journalId); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroPiece")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateEcriture")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("journalId")); + } + + @Test + void testValidation_NegativeMontantDebit() { + CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder() + .numeroPiece("EC-2025-003") + .dateEcriture(LocalDate.now()) + .libelle("Écriture test") + .journalId(UUID.randomUUID()) + .montantDebit(BigDecimal.valueOf(-100.00)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDebit")); + } + + @Test + void testValidation_NegativeMontantCredit() { + CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder() + .numeroPiece("EC-2025-004") + .dateEcriture(LocalDate.now()) + .libelle("Écriture test") + .journalId(UUID.randomUUID()) + .montantCredit(BigDecimal.valueOf(-100.00)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantCredit")); + } + + @Test + void testValidation_ValidFields() { + CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder() + .numeroPiece("EC-2025-005") + .dateEcriture(LocalDate.of(2025, 3, 15)) + .libelle("Écriture valide") + .journalId(UUID.randomUUID()) + .montantDebit(BigDecimal.valueOf(1000.00)) + .montantCredit(BigDecimal.valueOf(1000.00)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID journalId = UUID.randomUUID(); + LocalDate dateEcriture = LocalDate.of(2025, 3, 15); + + CreateEcritureComptableRequest request1 = CreateEcritureComptableRequest.builder() + .numeroPiece("EC-2025-006") + .dateEcriture(dateEcriture) + .libelle("Écriture test") + .journalId(journalId) + .build(); + + CreateEcritureComptableRequest request2 = CreateEcritureComptableRequest.builder() + .numeroPiece("EC-2025-006") + .dateEcriture(dateEcriture) + .libelle("Écriture test") + .journalId(journalId) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateEcritureComptableRequest request = CreateEcritureComptableRequest.builder() + .numeroPiece("EC-2025-007") + .dateEcriture(LocalDate.of(2025, 3, 15)) + .libelle("Écriture toString") + .journalId(UUID.randomUUID()) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateEcritureComptableRequest"); + assertThat(toString).contains("EC-2025-007"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateJournalComptableRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateJournalComptableRequestTest.java index 3ff3928..494cf04 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateJournalComptableRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateJournalComptableRequestTest.java @@ -1,136 +1,136 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.comptabilite.TypeJournalComptable; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.time.LocalDate; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateJournalComptableRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDate dateDebut = LocalDate.of(2025, 1, 1); - LocalDate dateFin = LocalDate.of(2025, 12, 31); - - CreateJournalComptableRequest request = CreateJournalComptableRequest.builder() - .code("ACH") - .libelle("Journal des achats") - .typeJournal(TypeJournalComptable.ACHATS) - .dateDebut(dateDebut) - .dateFin(dateFin) - .statut("ACTIF") - .description("Journal pour les achats de marchandises") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.code()).isEqualTo("ACH"); - assertThat(request.libelle()).isEqualTo("Journal des achats"); - assertThat(request.typeJournal()).isEqualTo(TypeJournalComptable.ACHATS); - assertThat(request.dateDebut()).isEqualTo(dateDebut); - assertThat(request.dateFin()).isEqualTo(dateFin); - assertThat(request.statut()).isEqualTo("ACTIF"); - assertThat(request.description()).isEqualTo("Journal pour les achats de marchandises"); - } - - @Test - void testBuilder_MinimalFields() { - CreateJournalComptableRequest request = CreateJournalComptableRequest.builder() - .code("BNQ") - .libelle("Journal banque") - .typeJournal(TypeJournalComptable.BANQUE) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.code()).isEqualTo("BNQ"); - assertThat(request.libelle()).isEqualTo("Journal banque"); - assertThat(request.typeJournal()).isEqualTo(TypeJournalComptable.BANQUE); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateJournalComptableRequest request = CreateJournalComptableRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeJournal")); - } - - @Test - void testValidation_ValidFields() { - CreateJournalComptableRequest request = CreateJournalComptableRequest.builder() - .code("VNTE") - .libelle("Journal des ventes") - .typeJournal(TypeJournalComptable.VENTES) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testValidation_AllJournalTypes() { - for (TypeJournalComptable type : TypeJournalComptable.values()) { - CreateJournalComptableRequest request = CreateJournalComptableRequest.builder() - .code(type.name()) - .libelle("Journal " + type.getLibelle()) - .typeJournal(type) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - } - - @Test - void testEquals() { - CreateJournalComptableRequest request1 = CreateJournalComptableRequest.builder() - .code("CAI") - .libelle("Journal caisse") - .typeJournal(TypeJournalComptable.CAISSE) - .build(); - - CreateJournalComptableRequest request2 = CreateJournalComptableRequest.builder() - .code("CAI") - .libelle("Journal caisse") - .typeJournal(TypeJournalComptable.CAISSE) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateJournalComptableRequest request = CreateJournalComptableRequest.builder() - .code("OD") - .libelle("Opérations diverses") - .typeJournal(TypeJournalComptable.OD) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateJournalComptableRequest"); - assertThat(toString).contains("OD"); - } -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.comptabilite.TypeJournalComptable; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.time.LocalDate; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateJournalComptableRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDate dateDebut = LocalDate.of(2025, 1, 1); + LocalDate dateFin = LocalDate.of(2025, 12, 31); + + CreateJournalComptableRequest request = CreateJournalComptableRequest.builder() + .code("ACH") + .libelle("Journal des achats") + .typeJournal(TypeJournalComptable.ACHATS) + .dateDebut(dateDebut) + .dateFin(dateFin) + .statut("ACTIF") + .description("Journal pour les achats de marchandises") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.code()).isEqualTo("ACH"); + assertThat(request.libelle()).isEqualTo("Journal des achats"); + assertThat(request.typeJournal()).isEqualTo(TypeJournalComptable.ACHATS); + assertThat(request.dateDebut()).isEqualTo(dateDebut); + assertThat(request.dateFin()).isEqualTo(dateFin); + assertThat(request.statut()).isEqualTo("ACTIF"); + assertThat(request.description()).isEqualTo("Journal pour les achats de marchandises"); + } + + @Test + void testBuilder_MinimalFields() { + CreateJournalComptableRequest request = CreateJournalComptableRequest.builder() + .code("BNQ") + .libelle("Journal banque") + .typeJournal(TypeJournalComptable.BANQUE) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.code()).isEqualTo("BNQ"); + assertThat(request.libelle()).isEqualTo("Journal banque"); + assertThat(request.typeJournal()).isEqualTo(TypeJournalComptable.BANQUE); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateJournalComptableRequest request = CreateJournalComptableRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeJournal")); + } + + @Test + void testValidation_ValidFields() { + CreateJournalComptableRequest request = CreateJournalComptableRequest.builder() + .code("VNTE") + .libelle("Journal des ventes") + .typeJournal(TypeJournalComptable.VENTES) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testValidation_AllJournalTypes() { + for (TypeJournalComptable type : TypeJournalComptable.values()) { + CreateJournalComptableRequest request = CreateJournalComptableRequest.builder() + .code(type.name()) + .libelle("Journal " + type.getLibelle()) + .typeJournal(type) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + } + + @Test + void testEquals() { + CreateJournalComptableRequest request1 = CreateJournalComptableRequest.builder() + .code("CAI") + .libelle("Journal caisse") + .typeJournal(TypeJournalComptable.CAISSE) + .build(); + + CreateJournalComptableRequest request2 = CreateJournalComptableRequest.builder() + .code("CAI") + .libelle("Journal caisse") + .typeJournal(TypeJournalComptable.CAISSE) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateJournalComptableRequest request = CreateJournalComptableRequest.builder() + .code("OD") + .libelle("Opérations diverses") + .typeJournal(TypeJournalComptable.OD) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateJournalComptableRequest"); + assertThat(toString).contains("OD"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateLigneEcritureRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateLigneEcritureRequestTest.java index 6f36cb4..50f10b5 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateLigneEcritureRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/CreateLigneEcritureRequestTest.java @@ -1,190 +1,190 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateLigneEcritureRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID ecritureId = UUID.randomUUID(); - UUID compteComptableId = UUID.randomUUID(); - - CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() - .numeroLigne(1) - .montantDebit(BigDecimal.valueOf(1000.00)) - .montantCredit(BigDecimal.ZERO) - .libelle("Ligne d'écriture test") - .reference("REF-LIGNE-001") - .ecritureId(ecritureId) - .compteComptableId(compteComptableId) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroLigne()).isEqualTo(1); - assertThat(request.montantDebit()).isEqualByComparingTo(BigDecimal.valueOf(1000.00)); - assertThat(request.montantCredit()).isEqualByComparingTo(BigDecimal.ZERO); - assertThat(request.libelle()).isEqualTo("Ligne d'écriture test"); - assertThat(request.reference()).isEqualTo("REF-LIGNE-001"); - assertThat(request.ecritureId()).isEqualTo(ecritureId); - assertThat(request.compteComptableId()).isEqualTo(compteComptableId); - } - - @Test - void testBuilder_MinimalFields() { - UUID ecritureId = UUID.randomUUID(); - UUID compteComptableId = UUID.randomUUID(); - - CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() - .numeroLigne(1) - .ecritureId(ecritureId) - .compteComptableId(compteComptableId) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroLigne()).isEqualTo(1); - assertThat(request.ecritureId()).isEqualTo(ecritureId); - assertThat(request.compteComptableId()).isEqualTo(compteComptableId); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroLigne")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ecritureId")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("compteComptableId")); - } - - @Test - void testValidation_NumeroLigneZero() { - CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() - .numeroLigne(0) - .ecritureId(UUID.randomUUID()) - .compteComptableId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroLigne")); - } - - @Test - void testValidation_NumeroLigneNegative() { - CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() - .numeroLigne(-1) - .ecritureId(UUID.randomUUID()) - .compteComptableId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroLigne")); - } - - @Test - void testValidation_NegativeMontantDebit() { - CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() - .numeroLigne(1) - .montantDebit(BigDecimal.valueOf(-100.00)) - .ecritureId(UUID.randomUUID()) - .compteComptableId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDebit")); - } - - @Test - void testValidation_NegativeMontantCredit() { - CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() - .numeroLigne(1) - .montantCredit(BigDecimal.valueOf(-100.00)) - .ecritureId(UUID.randomUUID()) - .compteComptableId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantCredit")); - } - - @Test - void testValidation_ValidFields() { - CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() - .numeroLigne(1) - .montantDebit(BigDecimal.valueOf(500.00)) - .montantCredit(BigDecimal.ZERO) - .ecritureId(UUID.randomUUID()) - .compteComptableId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID ecritureId = UUID.randomUUID(); - UUID compteComptableId = UUID.randomUUID(); - - CreateLigneEcritureRequest request1 = CreateLigneEcritureRequest.builder() - .numeroLigne(1) - .montantDebit(BigDecimal.valueOf(1000.00)) - .ecritureId(ecritureId) - .compteComptableId(compteComptableId) - .build(); - - CreateLigneEcritureRequest request2 = CreateLigneEcritureRequest.builder() - .numeroLigne(1) - .montantDebit(BigDecimal.valueOf(1000.00)) - .ecritureId(ecritureId) - .compteComptableId(compteComptableId) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() - .numeroLigne(1) - .libelle("Test ligne") - .ecritureId(UUID.randomUUID()) - .compteComptableId(UUID.randomUUID()) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateLigneEcritureRequest"); - assertThat(toString).contains("Test ligne"); - } -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateLigneEcritureRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID ecritureId = UUID.randomUUID(); + UUID compteComptableId = UUID.randomUUID(); + + CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() + .numeroLigne(1) + .montantDebit(BigDecimal.valueOf(1000.00)) + .montantCredit(BigDecimal.ZERO) + .libelle("Ligne d'écriture test") + .reference("REF-LIGNE-001") + .ecritureId(ecritureId) + .compteComptableId(compteComptableId) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroLigne()).isEqualTo(1); + assertThat(request.montantDebit()).isEqualByComparingTo(BigDecimal.valueOf(1000.00)); + assertThat(request.montantCredit()).isEqualByComparingTo(BigDecimal.ZERO); + assertThat(request.libelle()).isEqualTo("Ligne d'écriture test"); + assertThat(request.reference()).isEqualTo("REF-LIGNE-001"); + assertThat(request.ecritureId()).isEqualTo(ecritureId); + assertThat(request.compteComptableId()).isEqualTo(compteComptableId); + } + + @Test + void testBuilder_MinimalFields() { + UUID ecritureId = UUID.randomUUID(); + UUID compteComptableId = UUID.randomUUID(); + + CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() + .numeroLigne(1) + .ecritureId(ecritureId) + .compteComptableId(compteComptableId) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroLigne()).isEqualTo(1); + assertThat(request.ecritureId()).isEqualTo(ecritureId); + assertThat(request.compteComptableId()).isEqualTo(compteComptableId); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroLigne")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ecritureId")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("compteComptableId")); + } + + @Test + void testValidation_NumeroLigneZero() { + CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() + .numeroLigne(0) + .ecritureId(UUID.randomUUID()) + .compteComptableId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroLigne")); + } + + @Test + void testValidation_NumeroLigneNegative() { + CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() + .numeroLigne(-1) + .ecritureId(UUID.randomUUID()) + .compteComptableId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroLigne")); + } + + @Test + void testValidation_NegativeMontantDebit() { + CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() + .numeroLigne(1) + .montantDebit(BigDecimal.valueOf(-100.00)) + .ecritureId(UUID.randomUUID()) + .compteComptableId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDebit")); + } + + @Test + void testValidation_NegativeMontantCredit() { + CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() + .numeroLigne(1) + .montantCredit(BigDecimal.valueOf(-100.00)) + .ecritureId(UUID.randomUUID()) + .compteComptableId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantCredit")); + } + + @Test + void testValidation_ValidFields() { + CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() + .numeroLigne(1) + .montantDebit(BigDecimal.valueOf(500.00)) + .montantCredit(BigDecimal.ZERO) + .ecritureId(UUID.randomUUID()) + .compteComptableId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID ecritureId = UUID.randomUUID(); + UUID compteComptableId = UUID.randomUUID(); + + CreateLigneEcritureRequest request1 = CreateLigneEcritureRequest.builder() + .numeroLigne(1) + .montantDebit(BigDecimal.valueOf(1000.00)) + .ecritureId(ecritureId) + .compteComptableId(compteComptableId) + .build(); + + CreateLigneEcritureRequest request2 = CreateLigneEcritureRequest.builder() + .numeroLigne(1) + .montantDebit(BigDecimal.valueOf(1000.00)) + .ecritureId(ecritureId) + .compteComptableId(compteComptableId) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateLigneEcritureRequest request = CreateLigneEcritureRequest.builder() + .numeroLigne(1) + .libelle("Test ligne") + .ecritureId(UUID.randomUUID()) + .compteComptableId(UUID.randomUUID()) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateLigneEcritureRequest"); + assertThat(toString).contains("Test ligne"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateCompteComptableRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateCompteComptableRequestTest.java index 3b891f3..9006b9e 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateCompteComptableRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateCompteComptableRequestTest.java @@ -1,143 +1,143 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.comptabilite.TypeCompteComptable; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateCompteComptableRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder() - .numeroCompte("401000") - .libelle("Fournisseurs mis à jour") - .typeCompte(TypeCompteComptable.PASSIF) - .classeComptable(4) - .soldeInitial(BigDecimal.valueOf(2000.00)) - .soldeActuel(BigDecimal.valueOf(2500.00)) - .compteCollectif(false) - .compteAnalytique(true) - .description("Compte fournisseurs modifié") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroCompte()).isEqualTo("401000"); - assertThat(request.libelle()).isEqualTo("Fournisseurs mis à jour"); - assertThat(request.typeCompte()).isEqualTo(TypeCompteComptable.PASSIF); - assertThat(request.classeComptable()).isEqualTo(4); - assertThat(request.soldeInitial()).isEqualByComparingTo(BigDecimal.valueOf(2000.00)); - assertThat(request.soldeActuel()).isEqualByComparingTo(BigDecimal.valueOf(2500.00)); - assertThat(request.compteCollectif()).isFalse(); - assertThat(request.compteAnalytique()).isTrue(); - assertThat(request.description()).isEqualTo("Compte fournisseurs modifié"); - } - - @Test - void testBuilder_MinimalFields() { - UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder() - .libelle("Banque modifiée") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.libelle()).isEqualTo("Banque modifiée"); - } - - @Test - void testValidation_ClasseComptableTooSmall() { - UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder() - .classeComptable(0) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("classeComptable")); - } - - @Test - void testValidation_ClasseComptableTooLarge() { - UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder() - .classeComptable(8) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("classeComptable")); - } - - @Test - void testValidation_ValidFields() { - UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder() - .numeroCompte("512000") - .libelle("Banque mise à jour") - .typeCompte(TypeCompteComptable.TRESORERIE) - .classeComptable(5) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testValidation_EmptyRequest() { - UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UpdateCompteComptableRequest request1 = UpdateCompteComptableRequest.builder() - .numeroCompte("411000") - .libelle("Clients modifiés") - .typeCompte(TypeCompteComptable.ACTIF) - .classeComptable(4) - .build(); - - UpdateCompteComptableRequest request2 = UpdateCompteComptableRequest.builder() - .numeroCompte("411000") - .libelle("Clients modifiés") - .typeCompte(TypeCompteComptable.ACTIF) - .classeComptable(4) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder() - .numeroCompte("701000") - .libelle("Ventes modifiées") - .typeCompte(TypeCompteComptable.PRODUITS) - .classeComptable(7) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateCompteComptableRequest"); - assertThat(toString).contains("701000"); - } -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.comptabilite.TypeCompteComptable; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateCompteComptableRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder() + .numeroCompte("401000") + .libelle("Fournisseurs mis à jour") + .typeCompte(TypeCompteComptable.PASSIF) + .classeComptable(4) + .soldeInitial(BigDecimal.valueOf(2000.00)) + .soldeActuel(BigDecimal.valueOf(2500.00)) + .compteCollectif(false) + .compteAnalytique(true) + .description("Compte fournisseurs modifié") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroCompte()).isEqualTo("401000"); + assertThat(request.libelle()).isEqualTo("Fournisseurs mis à jour"); + assertThat(request.typeCompte()).isEqualTo(TypeCompteComptable.PASSIF); + assertThat(request.classeComptable()).isEqualTo(4); + assertThat(request.soldeInitial()).isEqualByComparingTo(BigDecimal.valueOf(2000.00)); + assertThat(request.soldeActuel()).isEqualByComparingTo(BigDecimal.valueOf(2500.00)); + assertThat(request.compteCollectif()).isFalse(); + assertThat(request.compteAnalytique()).isTrue(); + assertThat(request.description()).isEqualTo("Compte fournisseurs modifié"); + } + + @Test + void testBuilder_MinimalFields() { + UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder() + .libelle("Banque modifiée") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.libelle()).isEqualTo("Banque modifiée"); + } + + @Test + void testValidation_ClasseComptableTooSmall() { + UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder() + .classeComptable(0) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("classeComptable")); + } + + @Test + void testValidation_ClasseComptableTooLarge() { + UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder() + .classeComptable(8) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("classeComptable")); + } + + @Test + void testValidation_ValidFields() { + UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder() + .numeroCompte("512000") + .libelle("Banque mise à jour") + .typeCompte(TypeCompteComptable.TRESORERIE) + .classeComptable(5) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testValidation_EmptyRequest() { + UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UpdateCompteComptableRequest request1 = UpdateCompteComptableRequest.builder() + .numeroCompte("411000") + .libelle("Clients modifiés") + .typeCompte(TypeCompteComptable.ACTIF) + .classeComptable(4) + .build(); + + UpdateCompteComptableRequest request2 = UpdateCompteComptableRequest.builder() + .numeroCompte("411000") + .libelle("Clients modifiés") + .typeCompte(TypeCompteComptable.ACTIF) + .classeComptable(4) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateCompteComptableRequest request = UpdateCompteComptableRequest.builder() + .numeroCompte("701000") + .libelle("Ventes modifiées") + .typeCompte(TypeCompteComptable.PRODUITS) + .classeComptable(7) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateCompteComptableRequest"); + assertThat(toString).contains("701000"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateEcritureComptableRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateEcritureComptableRequestTest.java index bab3a48..9a0b2a9 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateEcritureComptableRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateEcritureComptableRequestTest.java @@ -1,166 +1,166 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.List; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateEcritureComptableRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID journalId = UUID.randomUUID(); - UUID paiementId = UUID.randomUUID(); - LocalDate dateEcriture = LocalDate.of(2025, 3, 16); - - UpdateLigneEcritureRequest ligne = UpdateLigneEcritureRequest.builder() - .numeroLigne(1) - .montantDebit(BigDecimal.valueOf(2000.00)) - .montantCredit(BigDecimal.ZERO) - .libelle("Ligne modifiée") - .compteComptableId(UUID.randomUUID()) - .build(); - - UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder() - .numeroPiece("EC-2025-008") - .dateEcriture(dateEcriture) - .libelle("Écriture modifiée") - .reference("REF-002") - .lettrage("B") - .pointe(false) - .montantDebit(BigDecimal.valueOf(2000.00)) - .montantCredit(BigDecimal.valueOf(2000.00)) - .commentaire("Commentaire modifié") - .journalId(journalId) - .paiementId(paiementId) - .lignes(List.of(ligne)) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroPiece()).isEqualTo("EC-2025-008"); - assertThat(request.dateEcriture()).isEqualTo(dateEcriture); - assertThat(request.libelle()).isEqualTo("Écriture modifiée"); - assertThat(request.reference()).isEqualTo("REF-002"); - assertThat(request.lettrage()).isEqualTo("B"); - assertThat(request.pointe()).isFalse(); - assertThat(request.montantDebit()).isEqualByComparingTo(BigDecimal.valueOf(2000.00)); - assertThat(request.montantCredit()).isEqualByComparingTo(BigDecimal.valueOf(2000.00)); - assertThat(request.commentaire()).isEqualTo("Commentaire modifié"); - assertThat(request.journalId()).isEqualTo(journalId); - assertThat(request.paiementId()).isEqualTo(paiementId); - assertThat(request.lignes()).hasSize(1); - } - - @Test - void testBuilder_MinimalFields() { - UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder() - .libelle("Libellé modifié") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.libelle()).isEqualTo("Libellé modifié"); - } - - @Test - void testValidation_NegativeMontantDebit() { - UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder() - .montantDebit(BigDecimal.valueOf(-100.00)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDebit")); - } - - @Test - void testValidation_NegativeMontantCredit() { - UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder() - .montantCredit(BigDecimal.valueOf(-100.00)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantCredit")); - } - - @Test - void testValidation_ValidFields() { - UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder() - .numeroPiece("EC-2025-009") - .dateEcriture(LocalDate.of(2025, 3, 16)) - .libelle("Écriture valide") - .montantDebit(BigDecimal.valueOf(1500.00)) - .montantCredit(BigDecimal.valueOf(1500.00)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testValidation_EmptyRequest() { - UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID journalId = UUID.randomUUID(); - LocalDate dateEcriture = LocalDate.of(2025, 3, 16); - - UpdateEcritureComptableRequest request1 = UpdateEcritureComptableRequest.builder() - .numeroPiece("EC-2025-010") - .dateEcriture(dateEcriture) - .libelle("Écriture test") - .journalId(journalId) - .build(); - - UpdateEcritureComptableRequest request2 = UpdateEcritureComptableRequest.builder() - .numeroPiece("EC-2025-010") - .dateEcriture(dateEcriture) - .libelle("Écriture test") - .journalId(journalId) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder() - .numeroPiece("EC-2025-011") - .dateEcriture(LocalDate.of(2025, 3, 16)) - .libelle("Écriture toString") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateEcritureComptableRequest"); - assertThat(toString).contains("EC-2025-011"); - } -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.List; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateEcritureComptableRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID journalId = UUID.randomUUID(); + UUID paiementId = UUID.randomUUID(); + LocalDate dateEcriture = LocalDate.of(2025, 3, 16); + + UpdateLigneEcritureRequest ligne = UpdateLigneEcritureRequest.builder() + .numeroLigne(1) + .montantDebit(BigDecimal.valueOf(2000.00)) + .montantCredit(BigDecimal.ZERO) + .libelle("Ligne modifiée") + .compteComptableId(UUID.randomUUID()) + .build(); + + UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder() + .numeroPiece("EC-2025-008") + .dateEcriture(dateEcriture) + .libelle("Écriture modifiée") + .reference("REF-002") + .lettrage("B") + .pointe(false) + .montantDebit(BigDecimal.valueOf(2000.00)) + .montantCredit(BigDecimal.valueOf(2000.00)) + .commentaire("Commentaire modifié") + .journalId(journalId) + .paiementId(paiementId) + .lignes(List.of(ligne)) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroPiece()).isEqualTo("EC-2025-008"); + assertThat(request.dateEcriture()).isEqualTo(dateEcriture); + assertThat(request.libelle()).isEqualTo("Écriture modifiée"); + assertThat(request.reference()).isEqualTo("REF-002"); + assertThat(request.lettrage()).isEqualTo("B"); + assertThat(request.pointe()).isFalse(); + assertThat(request.montantDebit()).isEqualByComparingTo(BigDecimal.valueOf(2000.00)); + assertThat(request.montantCredit()).isEqualByComparingTo(BigDecimal.valueOf(2000.00)); + assertThat(request.commentaire()).isEqualTo("Commentaire modifié"); + assertThat(request.journalId()).isEqualTo(journalId); + assertThat(request.paiementId()).isEqualTo(paiementId); + assertThat(request.lignes()).hasSize(1); + } + + @Test + void testBuilder_MinimalFields() { + UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder() + .libelle("Libellé modifié") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.libelle()).isEqualTo("Libellé modifié"); + } + + @Test + void testValidation_NegativeMontantDebit() { + UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder() + .montantDebit(BigDecimal.valueOf(-100.00)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDebit")); + } + + @Test + void testValidation_NegativeMontantCredit() { + UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder() + .montantCredit(BigDecimal.valueOf(-100.00)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantCredit")); + } + + @Test + void testValidation_ValidFields() { + UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder() + .numeroPiece("EC-2025-009") + .dateEcriture(LocalDate.of(2025, 3, 16)) + .libelle("Écriture valide") + .montantDebit(BigDecimal.valueOf(1500.00)) + .montantCredit(BigDecimal.valueOf(1500.00)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testValidation_EmptyRequest() { + UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID journalId = UUID.randomUUID(); + LocalDate dateEcriture = LocalDate.of(2025, 3, 16); + + UpdateEcritureComptableRequest request1 = UpdateEcritureComptableRequest.builder() + .numeroPiece("EC-2025-010") + .dateEcriture(dateEcriture) + .libelle("Écriture test") + .journalId(journalId) + .build(); + + UpdateEcritureComptableRequest request2 = UpdateEcritureComptableRequest.builder() + .numeroPiece("EC-2025-010") + .dateEcriture(dateEcriture) + .libelle("Écriture test") + .journalId(journalId) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateEcritureComptableRequest request = UpdateEcritureComptableRequest.builder() + .numeroPiece("EC-2025-011") + .dateEcriture(LocalDate.of(2025, 3, 16)) + .libelle("Écriture toString") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateEcritureComptableRequest"); + assertThat(toString).contains("EC-2025-011"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateJournalComptableRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateJournalComptableRequestTest.java index b35931c..7f82234 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateJournalComptableRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateJournalComptableRequestTest.java @@ -1,125 +1,125 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.comptabilite.TypeJournalComptable; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.time.LocalDate; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateJournalComptableRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDate dateDebut = LocalDate.of(2025, 1, 1); - LocalDate dateFin = LocalDate.of(2025, 12, 31); - - UpdateJournalComptableRequest request = UpdateJournalComptableRequest.builder() - .libelle("Journal des achats modifié") - .typeJournal(TypeJournalComptable.ACHATS) - .dateDebut(dateDebut) - .dateFin(dateFin) - .statut("INACTIF") - .description("Description modifiée") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.libelle()).isEqualTo("Journal des achats modifié"); - assertThat(request.typeJournal()).isEqualTo(TypeJournalComptable.ACHATS); - assertThat(request.dateDebut()).isEqualTo(dateDebut); - assertThat(request.dateFin()).isEqualTo(dateFin); - assertThat(request.statut()).isEqualTo("INACTIF"); - assertThat(request.description()).isEqualTo("Description modifiée"); - } - - @Test - void testBuilder_MinimalFields() { - UpdateJournalComptableRequest request = UpdateJournalComptableRequest.builder() - .libelle("Libellé modifié") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.libelle()).isEqualTo("Libellé modifié"); - } - - @Test - void testValidation_EmptyRequest() { - UpdateJournalComptableRequest request = UpdateJournalComptableRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testValidation_ValidFields() { - UpdateJournalComptableRequest request = UpdateJournalComptableRequest.builder() - .libelle("Journal des ventes modifié") - .typeJournal(TypeJournalComptable.VENTES) - .statut("ACTIF") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testValidation_AllJournalTypes() { - for (TypeJournalComptable type : TypeJournalComptable.values()) { - UpdateJournalComptableRequest request = UpdateJournalComptableRequest.builder() - .libelle("Journal " + type.getLibelle() + " modifié") - .typeJournal(type) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - } - - @Test - void testEquals() { - UpdateJournalComptableRequest request1 = UpdateJournalComptableRequest.builder() - .libelle("Journal caisse modifié") - .typeJournal(TypeJournalComptable.CAISSE) - .statut("ACTIF") - .build(); - - UpdateJournalComptableRequest request2 = UpdateJournalComptableRequest.builder() - .libelle("Journal caisse modifié") - .typeJournal(TypeJournalComptable.CAISSE) - .statut("ACTIF") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateJournalComptableRequest request = UpdateJournalComptableRequest.builder() - .libelle("Opérations diverses modifié") - .typeJournal(TypeJournalComptable.OD) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateJournalComptableRequest"); - assertThat(toString).contains("Opérations diverses modifié"); - } -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.comptabilite.TypeJournalComptable; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.time.LocalDate; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateJournalComptableRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDate dateDebut = LocalDate.of(2025, 1, 1); + LocalDate dateFin = LocalDate.of(2025, 12, 31); + + UpdateJournalComptableRequest request = UpdateJournalComptableRequest.builder() + .libelle("Journal des achats modifié") + .typeJournal(TypeJournalComptable.ACHATS) + .dateDebut(dateDebut) + .dateFin(dateFin) + .statut("INACTIF") + .description("Description modifiée") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.libelle()).isEqualTo("Journal des achats modifié"); + assertThat(request.typeJournal()).isEqualTo(TypeJournalComptable.ACHATS); + assertThat(request.dateDebut()).isEqualTo(dateDebut); + assertThat(request.dateFin()).isEqualTo(dateFin); + assertThat(request.statut()).isEqualTo("INACTIF"); + assertThat(request.description()).isEqualTo("Description modifiée"); + } + + @Test + void testBuilder_MinimalFields() { + UpdateJournalComptableRequest request = UpdateJournalComptableRequest.builder() + .libelle("Libellé modifié") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.libelle()).isEqualTo("Libellé modifié"); + } + + @Test + void testValidation_EmptyRequest() { + UpdateJournalComptableRequest request = UpdateJournalComptableRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testValidation_ValidFields() { + UpdateJournalComptableRequest request = UpdateJournalComptableRequest.builder() + .libelle("Journal des ventes modifié") + .typeJournal(TypeJournalComptable.VENTES) + .statut("ACTIF") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testValidation_AllJournalTypes() { + for (TypeJournalComptable type : TypeJournalComptable.values()) { + UpdateJournalComptableRequest request = UpdateJournalComptableRequest.builder() + .libelle("Journal " + type.getLibelle() + " modifié") + .typeJournal(type) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + } + + @Test + void testEquals() { + UpdateJournalComptableRequest request1 = UpdateJournalComptableRequest.builder() + .libelle("Journal caisse modifié") + .typeJournal(TypeJournalComptable.CAISSE) + .statut("ACTIF") + .build(); + + UpdateJournalComptableRequest request2 = UpdateJournalComptableRequest.builder() + .libelle("Journal caisse modifié") + .typeJournal(TypeJournalComptable.CAISSE) + .statut("ACTIF") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateJournalComptableRequest request = UpdateJournalComptableRequest.builder() + .libelle("Opérations diverses modifié") + .typeJournal(TypeJournalComptable.OD) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateJournalComptableRequest"); + assertThat(toString).contains("Opérations diverses modifié"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateLigneEcritureRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateLigneEcritureRequestTest.java index 8f2014c..2e5090b 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateLigneEcritureRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/comptabilite/request/UpdateLigneEcritureRequestTest.java @@ -1,162 +1,162 @@ -package dev.lions.unionflow.server.api.dto.comptabilite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateLigneEcritureRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID compteComptableId = UUID.randomUUID(); - - UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() - .numeroLigne(2) - .montantDebit(BigDecimal.valueOf(2000.00)) - .montantCredit(BigDecimal.ZERO) - .libelle("Ligne d'écriture modifiée") - .reference("REF-LIGNE-002") - .compteComptableId(compteComptableId) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroLigne()).isEqualTo(2); - assertThat(request.montantDebit()).isEqualByComparingTo(BigDecimal.valueOf(2000.00)); - assertThat(request.montantCredit()).isEqualByComparingTo(BigDecimal.ZERO); - assertThat(request.libelle()).isEqualTo("Ligne d'écriture modifiée"); - assertThat(request.reference()).isEqualTo("REF-LIGNE-002"); - assertThat(request.compteComptableId()).isEqualTo(compteComptableId); - } - - @Test - void testBuilder_MinimalFields() { - UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() - .libelle("Libellé modifié") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.libelle()).isEqualTo("Libellé modifié"); - } - - @Test - void testValidation_NumeroLigneZero() { - UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() - .numeroLigne(0) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroLigne")); - } - - @Test - void testValidation_NumeroLigneNegative() { - UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() - .numeroLigne(-1) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroLigne")); - } - - @Test - void testValidation_NegativeMontantDebit() { - UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() - .montantDebit(BigDecimal.valueOf(-100.00)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDebit")); - } - - @Test - void testValidation_NegativeMontantCredit() { - UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() - .montantCredit(BigDecimal.valueOf(-100.00)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantCredit")); - } - - @Test - void testValidation_ValidFields() { - UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() - .numeroLigne(3) - .montantDebit(BigDecimal.valueOf(500.00)) - .montantCredit(BigDecimal.ZERO) - .compteComptableId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testValidation_EmptyRequest() { - UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID compteComptableId = UUID.randomUUID(); - - UpdateLigneEcritureRequest request1 = UpdateLigneEcritureRequest.builder() - .numeroLigne(1) - .montantDebit(BigDecimal.valueOf(1000.00)) - .compteComptableId(compteComptableId) - .build(); - - UpdateLigneEcritureRequest request2 = UpdateLigneEcritureRequest.builder() - .numeroLigne(1) - .montantDebit(BigDecimal.valueOf(1000.00)) - .compteComptableId(compteComptableId) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() - .numeroLigne(1) - .libelle("Test ligne modifiée") - .compteComptableId(UUID.randomUUID()) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateLigneEcritureRequest"); - assertThat(toString).contains("Test ligne modifiée"); - } -} +package dev.lions.unionflow.server.api.dto.comptabilite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateLigneEcritureRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID compteComptableId = UUID.randomUUID(); + + UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() + .numeroLigne(2) + .montantDebit(BigDecimal.valueOf(2000.00)) + .montantCredit(BigDecimal.ZERO) + .libelle("Ligne d'écriture modifiée") + .reference("REF-LIGNE-002") + .compteComptableId(compteComptableId) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroLigne()).isEqualTo(2); + assertThat(request.montantDebit()).isEqualByComparingTo(BigDecimal.valueOf(2000.00)); + assertThat(request.montantCredit()).isEqualByComparingTo(BigDecimal.ZERO); + assertThat(request.libelle()).isEqualTo("Ligne d'écriture modifiée"); + assertThat(request.reference()).isEqualTo("REF-LIGNE-002"); + assertThat(request.compteComptableId()).isEqualTo(compteComptableId); + } + + @Test + void testBuilder_MinimalFields() { + UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() + .libelle("Libellé modifié") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.libelle()).isEqualTo("Libellé modifié"); + } + + @Test + void testValidation_NumeroLigneZero() { + UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() + .numeroLigne(0) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroLigne")); + } + + @Test + void testValidation_NumeroLigneNegative() { + UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() + .numeroLigne(-1) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroLigne")); + } + + @Test + void testValidation_NegativeMontantDebit() { + UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() + .montantDebit(BigDecimal.valueOf(-100.00)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDebit")); + } + + @Test + void testValidation_NegativeMontantCredit() { + UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() + .montantCredit(BigDecimal.valueOf(-100.00)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantCredit")); + } + + @Test + void testValidation_ValidFields() { + UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() + .numeroLigne(3) + .montantDebit(BigDecimal.valueOf(500.00)) + .montantCredit(BigDecimal.ZERO) + .compteComptableId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testValidation_EmptyRequest() { + UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID compteComptableId = UUID.randomUUID(); + + UpdateLigneEcritureRequest request1 = UpdateLigneEcritureRequest.builder() + .numeroLigne(1) + .montantDebit(BigDecimal.valueOf(1000.00)) + .compteComptableId(compteComptableId) + .build(); + + UpdateLigneEcritureRequest request2 = UpdateLigneEcritureRequest.builder() + .numeroLigne(1) + .montantDebit(BigDecimal.valueOf(1000.00)) + .compteComptableId(compteComptableId) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateLigneEcritureRequest request = UpdateLigneEcritureRequest.builder() + .numeroLigne(1) + .libelle("Test ligne modifiée") + .compteComptableId(UUID.randomUUID()) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateLigneEcritureRequest"); + assertThat(toString).contains("Test ligne modifiée"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/config/request/CreateConfigurationRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/config/request/CreateConfigurationRequestTest.java index 4aa119b..ebd8c1d 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/config/request/CreateConfigurationRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/config/request/CreateConfigurationRequestTest.java @@ -1,109 +1,109 @@ -package dev.lions.unionflow.server.api.dto.config.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Map; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateConfigurationRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - Map metadonnees = Map.of("unit", "XOF", "min", 1000, "max", 1000000); - - CreateConfigurationRequest request = CreateConfigurationRequest.builder() - .cle("seuil.transaction.max") - .valeur("1000000") - .type("NUMERIC") - .categorie("LCB_FT") - .description("Seuil maximum pour les transactions") - .modifiable(true) - .visible(true) - .metadonnees(metadonnees) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.cle()).isEqualTo("seuil.transaction.max"); - assertThat(request.valeur()).isEqualTo("1000000"); - assertThat(request.type()).isEqualTo("NUMERIC"); - assertThat(request.categorie()).isEqualTo("LCB_FT"); - assertThat(request.description()).isEqualTo("Seuil maximum pour les transactions"); - assertThat(request.modifiable()).isTrue(); - assertThat(request.visible()).isTrue(); - assertThat(request.metadonnees()).isEqualTo(metadonnees); - } - - @Test - void testBuilder_MinimalFields() { - CreateConfigurationRequest request = CreateConfigurationRequest.builder() - .cle("simple.config") - .valeur("value") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.cle()).isEqualTo("simple.config"); - assertThat(request.valeur()).isEqualTo("value"); - } - - @Test - void testValidation_ValidFields() { - CreateConfigurationRequest request = CreateConfigurationRequest.builder() - .cle("test.config") - .valeur("test_value") - .type("STRING") - .categorie("GENERAL") - .modifiable(true) - .visible(true) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - CreateConfigurationRequest request1 = CreateConfigurationRequest.builder() - .cle("config.key") - .valeur("value") - .type("STRING") - .build(); - - CreateConfigurationRequest request2 = CreateConfigurationRequest.builder() - .cle("config.key") - .valeur("value") - .type("STRING") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateConfigurationRequest request = CreateConfigurationRequest.builder() - .cle("test.key") - .valeur("test_value") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateConfigurationRequest"); - assertThat(toString).contains("test.key"); - } -} +package dev.lions.unionflow.server.api.dto.config.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Map; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateConfigurationRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + Map metadonnees = Map.of("unit", "XOF", "min", 1000, "max", 1000000); + + CreateConfigurationRequest request = CreateConfigurationRequest.builder() + .cle("seuil.transaction.max") + .valeur("1000000") + .type("NUMERIC") + .categorie("LCB_FT") + .description("Seuil maximum pour les transactions") + .modifiable(true) + .visible(true) + .metadonnees(metadonnees) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.cle()).isEqualTo("seuil.transaction.max"); + assertThat(request.valeur()).isEqualTo("1000000"); + assertThat(request.type()).isEqualTo("NUMERIC"); + assertThat(request.categorie()).isEqualTo("LCB_FT"); + assertThat(request.description()).isEqualTo("Seuil maximum pour les transactions"); + assertThat(request.modifiable()).isTrue(); + assertThat(request.visible()).isTrue(); + assertThat(request.metadonnees()).isEqualTo(metadonnees); + } + + @Test + void testBuilder_MinimalFields() { + CreateConfigurationRequest request = CreateConfigurationRequest.builder() + .cle("simple.config") + .valeur("value") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.cle()).isEqualTo("simple.config"); + assertThat(request.valeur()).isEqualTo("value"); + } + + @Test + void testValidation_ValidFields() { + CreateConfigurationRequest request = CreateConfigurationRequest.builder() + .cle("test.config") + .valeur("test_value") + .type("STRING") + .categorie("GENERAL") + .modifiable(true) + .visible(true) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + CreateConfigurationRequest request1 = CreateConfigurationRequest.builder() + .cle("config.key") + .valeur("value") + .type("STRING") + .build(); + + CreateConfigurationRequest request2 = CreateConfigurationRequest.builder() + .cle("config.key") + .valeur("value") + .type("STRING") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateConfigurationRequest request = CreateConfigurationRequest.builder() + .cle("test.key") + .valeur("test_value") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateConfigurationRequest"); + assertThat(toString).contains("test.key"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/config/request/UpdateConfigurationRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/config/request/UpdateConfigurationRequestTest.java index e69ff86..1c0b435 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/config/request/UpdateConfigurationRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/config/request/UpdateConfigurationRequestTest.java @@ -1,102 +1,102 @@ -package dev.lions.unionflow.server.api.dto.config.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Map; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateConfigurationRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - Map metadonnees = Map.of("lastUpdated", "2026-03-15"); - - UpdateConfigurationRequest request = UpdateConfigurationRequest.builder() - .cle("updated.key") - .valeur("updated_value") - .type("STRING") - .categorie("SYSTEM") - .description("Updated description") - .modifiable(false) - .visible(false) - .metadonnees(metadonnees) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.cle()).isEqualTo("updated.key"); - assertThat(request.valeur()).isEqualTo("updated_value"); - assertThat(request.type()).isEqualTo("STRING"); - assertThat(request.categorie()).isEqualTo("SYSTEM"); - assertThat(request.description()).isEqualTo("Updated description"); - assertThat(request.modifiable()).isFalse(); - assertThat(request.visible()).isFalse(); - assertThat(request.metadonnees()).isEqualTo(metadonnees); - } - - @Test - void testBuilder_MinimalFields() { - UpdateConfigurationRequest request = UpdateConfigurationRequest.builder() - .valeur("new_value") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.valeur()).isEqualTo("new_value"); - } - - @Test - void testValidation_ValidFields() { - UpdateConfigurationRequest request = UpdateConfigurationRequest.builder() - .cle("test.key") - .valeur("test_value") - .modifiable(true) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UpdateConfigurationRequest request1 = UpdateConfigurationRequest.builder() - .cle("key") - .valeur("value") - .build(); - - UpdateConfigurationRequest request2 = UpdateConfigurationRequest.builder() - .cle("key") - .valeur("value") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateConfigurationRequest request = UpdateConfigurationRequest.builder() - .cle("test.key") - .valeur("test_value") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateConfigurationRequest"); - assertThat(toString).contains("test.key"); - } -} +package dev.lions.unionflow.server.api.dto.config.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Map; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateConfigurationRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + Map metadonnees = Map.of("lastUpdated", "2026-03-15"); + + UpdateConfigurationRequest request = UpdateConfigurationRequest.builder() + .cle("updated.key") + .valeur("updated_value") + .type("STRING") + .categorie("SYSTEM") + .description("Updated description") + .modifiable(false) + .visible(false) + .metadonnees(metadonnees) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.cle()).isEqualTo("updated.key"); + assertThat(request.valeur()).isEqualTo("updated_value"); + assertThat(request.type()).isEqualTo("STRING"); + assertThat(request.categorie()).isEqualTo("SYSTEM"); + assertThat(request.description()).isEqualTo("Updated description"); + assertThat(request.modifiable()).isFalse(); + assertThat(request.visible()).isFalse(); + assertThat(request.metadonnees()).isEqualTo(metadonnees); + } + + @Test + void testBuilder_MinimalFields() { + UpdateConfigurationRequest request = UpdateConfigurationRequest.builder() + .valeur("new_value") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.valeur()).isEqualTo("new_value"); + } + + @Test + void testValidation_ValidFields() { + UpdateConfigurationRequest request = UpdateConfigurationRequest.builder() + .cle("test.key") + .valeur("test_value") + .modifiable(true) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UpdateConfigurationRequest request1 = UpdateConfigurationRequest.builder() + .cle("key") + .valeur("value") + .build(); + + UpdateConfigurationRequest request2 = UpdateConfigurationRequest.builder() + .cle("key") + .valeur("value") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateConfigurationRequest request = UpdateConfigurationRequest.builder() + .cle("test.key") + .valeur("test_value") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateConfigurationRequest"); + assertThat(toString).contains("test.key"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/cotisation/request/CreateCotisationRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/cotisation/request/CreateCotisationRequestTest.java index affd94e..e5efa57 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/cotisation/request/CreateCotisationRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/cotisation/request/CreateCotisationRequestTest.java @@ -1,339 +1,339 @@ -package dev.lions.unionflow.server.api.dto.cotisation.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateCotisationRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID membreId = UUID.randomUUID(); - UUID organisationId = UUID.randomUUID(); - LocalDate dateEcheance = LocalDate.now().plusDays(30); - - CreateCotisationRequest request = CreateCotisationRequest.builder() - .membreId(membreId) - .organisationId(organisationId) - .typeCotisation("MENSUELLE") - .libelle("Cotisation Janvier 2025") - .description("Cotisation mensuelle pour le mois de janvier") - .montantDu(new BigDecimal("25000.00")) - .codeDevise("XOF") - .dateEcheance(dateEcheance) - .periode("Janvier 2025") - .annee(2025) - .mois(1) - .recurrente(true) - .observations("Paiement à effectuer avant la fin du mois") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.membreId()).isEqualTo(membreId); - assertThat(request.organisationId()).isEqualTo(organisationId); - assertThat(request.typeCotisation()).isEqualTo("MENSUELLE"); - assertThat(request.libelle()).isEqualTo("Cotisation Janvier 2025"); - assertThat(request.description()).contains("janvier"); - assertThat(request.montantDu()).isEqualByComparingTo(new BigDecimal("25000.00")); - assertThat(request.codeDevise()).isEqualTo("XOF"); - assertThat(request.dateEcheance()).isEqualTo(dateEcheance); - assertThat(request.periode()).isEqualTo("Janvier 2025"); - assertThat(request.annee()).isEqualTo(2025); - assertThat(request.mois()).isEqualTo(1); - assertThat(request.recurrente()).isTrue(); - assertThat(request.observations()).contains("Paiement"); - } - - @Test - void testBuilder_MinimalFields() { - UUID membreId = UUID.randomUUID(); - UUID organisationId = UUID.randomUUID(); - LocalDate dateEcheance = LocalDate.now().plusMonths(1); - - CreateCotisationRequest request = CreateCotisationRequest.builder() - .membreId(membreId) - .organisationId(organisationId) - .typeCotisation("ANNUELLE") - .libelle("Cotisation Simple") - .montantDu(new BigDecimal("50000.00")) - .dateEcheance(dateEcheance) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.membreId()).isEqualTo(membreId); - assertThat(request.organisationId()).isEqualTo(organisationId); - assertThat(request.typeCotisation()).isEqualTo("ANNUELLE"); - assertThat(request.libelle()).isEqualTo("Cotisation Simple"); - assertThat(request.montantDu()).isEqualByComparingTo(new BigDecimal("50000.00")); - assertThat(request.dateEcheance()).isEqualTo(dateEcheance); - assertThat(request.description()).isNull(); - assertThat(request.codeDevise()).isNull(); - assertThat(request.periode()).isNull(); - assertThat(request.annee()).isNull(); - assertThat(request.mois()).isNull(); - assertThat(request.recurrente()).isNull(); - assertThat(request.observations()).isNull(); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateCotisationRequest request = CreateCotisationRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("membreId")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("organisationId")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeCotisation")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDu")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateEcheance")); - } - - @Test - void testValidation_EmptyTypeCotisation() { - CreateCotisationRequest request = CreateCotisationRequest.builder() - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .typeCotisation("") - .libelle("Test") - .montantDu(new BigDecimal("10000.00")) - .dateEcheance(LocalDate.now().plusDays(10)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeCotisation")); - } - - @Test - void testValidation_EmptyLibelle() { - CreateCotisationRequest request = CreateCotisationRequest.builder() - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .typeCotisation("MENSUELLE") - .libelle("") - .montantDu(new BigDecimal("10000.00")) - .dateEcheance(LocalDate.now().plusDays(10)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); - } - - @Test - void testValidation_MontantZero() { - CreateCotisationRequest request = CreateCotisationRequest.builder() - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .typeCotisation("MENSUELLE") - .libelle("Test") - .montantDu(BigDecimal.ZERO) - .dateEcheance(LocalDate.now().plusDays(10)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDu")); - } - - @Test - void testValidation_MontantNegatif() { - CreateCotisationRequest request = CreateCotisationRequest.builder() - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .typeCotisation("MENSUELLE") - .libelle("Test") - .montantDu(new BigDecimal("-1000.00")) - .dateEcheance(LocalDate.now().plusDays(10)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDu")); - } - - @Test - void testValidation_CodeDeviseTooLong() { - CreateCotisationRequest request = CreateCotisationRequest.builder() - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .typeCotisation("MENSUELLE") - .libelle("Test") - .montantDu(new BigDecimal("10000.00")) - .codeDevise("XOFF") - .dateEcheance(LocalDate.now().plusDays(10)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codeDevise")); - } - - @Test - void testValidation_CodeDeviseTooShort() { - CreateCotisationRequest request = CreateCotisationRequest.builder() - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .typeCotisation("MENSUELLE") - .libelle("Test") - .montantDu(new BigDecimal("10000.00")) - .codeDevise("XO") - .dateEcheance(LocalDate.now().plusDays(10)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codeDevise")); - } - - @Test - void testValidation_AnneeTooOld() { - CreateCotisationRequest request = CreateCotisationRequest.builder() - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .typeCotisation("MENSUELLE") - .libelle("Test") - .montantDu(new BigDecimal("10000.00")) - .dateEcheance(LocalDate.now().plusDays(10)) - .annee(2019) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("annee")); - } - - @Test - void testValidation_AnneeTooFuture() { - CreateCotisationRequest request = CreateCotisationRequest.builder() - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .typeCotisation("MENSUELLE") - .libelle("Test") - .montantDu(new BigDecimal("10000.00")) - .dateEcheance(LocalDate.now().plusDays(10)) - .annee(2101) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("annee")); - } - - @Test - void testValidation_MoisInvalide() { - CreateCotisationRequest request = CreateCotisationRequest.builder() - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .typeCotisation("MENSUELLE") - .libelle("Test") - .montantDu(new BigDecimal("10000.00")) - .dateEcheance(LocalDate.now().plusDays(10)) - .mois(13) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("mois")); - } - - @Test - void testValidation_ValidFields() { - CreateCotisationRequest request = CreateCotisationRequest.builder() - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .typeCotisation("TRIMESTRIELLE") - .libelle("Cotisation Valide") - .description("Description valide") - .montantDu(new BigDecimal("75000.00")) - .codeDevise("XOF") - .dateEcheance(LocalDate.now().plusMonths(3)) - .periode("T1 2025") - .annee(2025) - .mois(3) - .recurrente(false) - .observations("Aucune observation") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID membreId = UUID.randomUUID(); - UUID organisationId = UUID.randomUUID(); - LocalDate dateEcheance = LocalDate.now().plusDays(15); - - CreateCotisationRequest request1 = CreateCotisationRequest.builder() - .membreId(membreId) - .organisationId(organisationId) - .typeCotisation("MENSUELLE") - .libelle("Même Cotisation") - .montantDu(new BigDecimal("20000.00")) - .dateEcheance(dateEcheance) - .build(); - - CreateCotisationRequest request2 = CreateCotisationRequest.builder() - .membreId(membreId) - .organisationId(organisationId) - .typeCotisation("MENSUELLE") - .libelle("Même Cotisation") - .montantDu(new BigDecimal("20000.00")) - .dateEcheance(dateEcheance) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateCotisationRequest request = CreateCotisationRequest.builder() - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .typeCotisation("ANNUELLE") - .libelle("ToString Test Cotisation") - .montantDu(new BigDecimal("100000.00")) - .dateEcheance(LocalDate.now().plusYears(1)) - .annee(2026) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateCotisationRequest"); - assertThat(toString).contains("ToString Test Cotisation"); - assertThat(toString).contains("ANNUELLE"); - assertThat(toString).contains("100000.00"); - } -} +package dev.lions.unionflow.server.api.dto.cotisation.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateCotisationRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID membreId = UUID.randomUUID(); + UUID organisationId = UUID.randomUUID(); + LocalDate dateEcheance = LocalDate.now().plusDays(30); + + CreateCotisationRequest request = CreateCotisationRequest.builder() + .membreId(membreId) + .organisationId(organisationId) + .typeCotisation("MENSUELLE") + .libelle("Cotisation Janvier 2025") + .description("Cotisation mensuelle pour le mois de janvier") + .montantDu(new BigDecimal("25000.00")) + .codeDevise("XOF") + .dateEcheance(dateEcheance) + .periode("Janvier 2025") + .annee(2025) + .mois(1) + .recurrente(true) + .observations("Paiement à effectuer avant la fin du mois") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.membreId()).isEqualTo(membreId); + assertThat(request.organisationId()).isEqualTo(organisationId); + assertThat(request.typeCotisation()).isEqualTo("MENSUELLE"); + assertThat(request.libelle()).isEqualTo("Cotisation Janvier 2025"); + assertThat(request.description()).contains("janvier"); + assertThat(request.montantDu()).isEqualByComparingTo(new BigDecimal("25000.00")); + assertThat(request.codeDevise()).isEqualTo("XOF"); + assertThat(request.dateEcheance()).isEqualTo(dateEcheance); + assertThat(request.periode()).isEqualTo("Janvier 2025"); + assertThat(request.annee()).isEqualTo(2025); + assertThat(request.mois()).isEqualTo(1); + assertThat(request.recurrente()).isTrue(); + assertThat(request.observations()).contains("Paiement"); + } + + @Test + void testBuilder_MinimalFields() { + UUID membreId = UUID.randomUUID(); + UUID organisationId = UUID.randomUUID(); + LocalDate dateEcheance = LocalDate.now().plusMonths(1); + + CreateCotisationRequest request = CreateCotisationRequest.builder() + .membreId(membreId) + .organisationId(organisationId) + .typeCotisation("ANNUELLE") + .libelle("Cotisation Simple") + .montantDu(new BigDecimal("50000.00")) + .dateEcheance(dateEcheance) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.membreId()).isEqualTo(membreId); + assertThat(request.organisationId()).isEqualTo(organisationId); + assertThat(request.typeCotisation()).isEqualTo("ANNUELLE"); + assertThat(request.libelle()).isEqualTo("Cotisation Simple"); + assertThat(request.montantDu()).isEqualByComparingTo(new BigDecimal("50000.00")); + assertThat(request.dateEcheance()).isEqualTo(dateEcheance); + assertThat(request.description()).isNull(); + assertThat(request.codeDevise()).isNull(); + assertThat(request.periode()).isNull(); + assertThat(request.annee()).isNull(); + assertThat(request.mois()).isNull(); + assertThat(request.recurrente()).isNull(); + assertThat(request.observations()).isNull(); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateCotisationRequest request = CreateCotisationRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("membreId")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("organisationId")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeCotisation")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDu")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateEcheance")); + } + + @Test + void testValidation_EmptyTypeCotisation() { + CreateCotisationRequest request = CreateCotisationRequest.builder() + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .typeCotisation("") + .libelle("Test") + .montantDu(new BigDecimal("10000.00")) + .dateEcheance(LocalDate.now().plusDays(10)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeCotisation")); + } + + @Test + void testValidation_EmptyLibelle() { + CreateCotisationRequest request = CreateCotisationRequest.builder() + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .typeCotisation("MENSUELLE") + .libelle("") + .montantDu(new BigDecimal("10000.00")) + .dateEcheance(LocalDate.now().plusDays(10)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); + } + + @Test + void testValidation_MontantZero() { + CreateCotisationRequest request = CreateCotisationRequest.builder() + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .typeCotisation("MENSUELLE") + .libelle("Test") + .montantDu(BigDecimal.ZERO) + .dateEcheance(LocalDate.now().plusDays(10)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDu")); + } + + @Test + void testValidation_MontantNegatif() { + CreateCotisationRequest request = CreateCotisationRequest.builder() + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .typeCotisation("MENSUELLE") + .libelle("Test") + .montantDu(new BigDecimal("-1000.00")) + .dateEcheance(LocalDate.now().plusDays(10)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDu")); + } + + @Test + void testValidation_CodeDeviseTooLong() { + CreateCotisationRequest request = CreateCotisationRequest.builder() + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .typeCotisation("MENSUELLE") + .libelle("Test") + .montantDu(new BigDecimal("10000.00")) + .codeDevise("XOFF") + .dateEcheance(LocalDate.now().plusDays(10)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codeDevise")); + } + + @Test + void testValidation_CodeDeviseTooShort() { + CreateCotisationRequest request = CreateCotisationRequest.builder() + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .typeCotisation("MENSUELLE") + .libelle("Test") + .montantDu(new BigDecimal("10000.00")) + .codeDevise("XO") + .dateEcheance(LocalDate.now().plusDays(10)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codeDevise")); + } + + @Test + void testValidation_AnneeTooOld() { + CreateCotisationRequest request = CreateCotisationRequest.builder() + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .typeCotisation("MENSUELLE") + .libelle("Test") + .montantDu(new BigDecimal("10000.00")) + .dateEcheance(LocalDate.now().plusDays(10)) + .annee(2019) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("annee")); + } + + @Test + void testValidation_AnneeTooFuture() { + CreateCotisationRequest request = CreateCotisationRequest.builder() + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .typeCotisation("MENSUELLE") + .libelle("Test") + .montantDu(new BigDecimal("10000.00")) + .dateEcheance(LocalDate.now().plusDays(10)) + .annee(2101) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("annee")); + } + + @Test + void testValidation_MoisInvalide() { + CreateCotisationRequest request = CreateCotisationRequest.builder() + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .typeCotisation("MENSUELLE") + .libelle("Test") + .montantDu(new BigDecimal("10000.00")) + .dateEcheance(LocalDate.now().plusDays(10)) + .mois(13) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("mois")); + } + + @Test + void testValidation_ValidFields() { + CreateCotisationRequest request = CreateCotisationRequest.builder() + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .typeCotisation("TRIMESTRIELLE") + .libelle("Cotisation Valide") + .description("Description valide") + .montantDu(new BigDecimal("75000.00")) + .codeDevise("XOF") + .dateEcheance(LocalDate.now().plusMonths(3)) + .periode("T1 2025") + .annee(2025) + .mois(3) + .recurrente(false) + .observations("Aucune observation") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID membreId = UUID.randomUUID(); + UUID organisationId = UUID.randomUUID(); + LocalDate dateEcheance = LocalDate.now().plusDays(15); + + CreateCotisationRequest request1 = CreateCotisationRequest.builder() + .membreId(membreId) + .organisationId(organisationId) + .typeCotisation("MENSUELLE") + .libelle("Même Cotisation") + .montantDu(new BigDecimal("20000.00")) + .dateEcheance(dateEcheance) + .build(); + + CreateCotisationRequest request2 = CreateCotisationRequest.builder() + .membreId(membreId) + .organisationId(organisationId) + .typeCotisation("MENSUELLE") + .libelle("Même Cotisation") + .montantDu(new BigDecimal("20000.00")) + .dateEcheance(dateEcheance) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateCotisationRequest request = CreateCotisationRequest.builder() + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .typeCotisation("ANNUELLE") + .libelle("ToString Test Cotisation") + .montantDu(new BigDecimal("100000.00")) + .dateEcheance(LocalDate.now().plusYears(1)) + .annee(2026) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateCotisationRequest"); + assertThat(toString).contains("ToString Test Cotisation"); + assertThat(toString).contains("ANNUELLE"); + assertThat(toString).contains("100000.00"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/cotisation/request/UpdateCotisationRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/cotisation/request/UpdateCotisationRequestTest.java index 4157f8f..a53074b 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/cotisation/request/UpdateCotisationRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/cotisation/request/UpdateCotisationRequestTest.java @@ -1,231 +1,231 @@ -package dev.lions.unionflow.server.api.dto.cotisation.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateCotisationRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDate dateEcheance = LocalDate.now().plusDays(45); - - UpdateCotisationRequest request = UpdateCotisationRequest.builder() - .libelle("Cotisation Mise à Jour") - .description("Description mise à jour de la cotisation") - .montantDu(new BigDecimal("30000.00")) - .dateEcheance(dateEcheance) - .observations("Observations modifiées") - .statut("EN_ATTENTE") - .annee(2026) - .mois(6) - .recurrente(false) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.libelle()).isEqualTo("Cotisation Mise à Jour"); - assertThat(request.description()).contains("mise à jour"); - assertThat(request.montantDu()).isEqualByComparingTo(new BigDecimal("30000.00")); - assertThat(request.dateEcheance()).isEqualTo(dateEcheance); - assertThat(request.observations()).contains("modifiées"); - assertThat(request.statut()).isEqualTo("EN_ATTENTE"); - assertThat(request.annee()).isEqualTo(2026); - assertThat(request.mois()).isEqualTo(6); - assertThat(request.recurrente()).isFalse(); - } - - @Test - void testBuilder_MinimalFields() { - UpdateCotisationRequest request = UpdateCotisationRequest.builder().build(); - - assertThat(request).isNotNull(); - assertThat(request.libelle()).isNull(); - assertThat(request.description()).isNull(); - assertThat(request.montantDu()).isNull(); - assertThat(request.dateEcheance()).isNull(); - assertThat(request.observations()).isNull(); - assertThat(request.statut()).isNull(); - assertThat(request.annee()).isNull(); - assertThat(request.mois()).isNull(); - assertThat(request.recurrente()).isNull(); - } - - @Test - void testValidation_LibelleTooLong() { - String longLibelle = "A".repeat(101); - UpdateCotisationRequest request = UpdateCotisationRequest.builder() - .libelle(longLibelle) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); - } - - @Test - void testValidation_DescriptionTooLong() { - String longDescription = "B".repeat(501); - UpdateCotisationRequest request = UpdateCotisationRequest.builder() - .description(longDescription) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); - } - - @Test - void testValidation_MontantZero() { - UpdateCotisationRequest request = UpdateCotisationRequest.builder() - .montantDu(BigDecimal.ZERO) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDu")); - } - - @Test - void testValidation_MontantNegatif() { - UpdateCotisationRequest request = UpdateCotisationRequest.builder() - .montantDu(new BigDecimal("-500.00")) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDu")); - } - - @Test - void testValidation_ObservationsTooLong() { - String longObservations = "C".repeat(1001); - UpdateCotisationRequest request = UpdateCotisationRequest.builder() - .observations(longObservations) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("observations")); - } - - @Test - void testValidation_AnneeTooOld() { - UpdateCotisationRequest request = UpdateCotisationRequest.builder().annee(2018).build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("annee")); - } - - @Test - void testValidation_AnneeTooFuture() { - UpdateCotisationRequest request = UpdateCotisationRequest.builder().annee(2105).build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("annee")); - } - - @Test - void testValidation_MoisZero() { - UpdateCotisationRequest request = UpdateCotisationRequest.builder().mois(0).build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("mois")); - } - - @Test - void testValidation_MoisTooHigh() { - UpdateCotisationRequest request = UpdateCotisationRequest.builder().mois(15).build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("mois")); - } - - @Test - void testValidation_ValidFields() { - UpdateCotisationRequest request = UpdateCotisationRequest.builder() - .libelle("Libellé Valide") - .description("Description valide et complète") - .montantDu(new BigDecimal("45000.00")) - .dateEcheance(LocalDate.now().plusMonths(2)) - .observations("Observations valides") - .statut("PAYE") - .annee(2025) - .mois(8) - .recurrente(true) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - LocalDate dateEcheance = LocalDate.now().plusDays(20); - - UpdateCotisationRequest request1 = UpdateCotisationRequest.builder() - .libelle("Même Libellé") - .montantDu(new BigDecimal("15000.00")) - .dateEcheance(dateEcheance) - .statut("EN_COURS") - .build(); - - UpdateCotisationRequest request2 = UpdateCotisationRequest.builder() - .libelle("Même Libellé") - .montantDu(new BigDecimal("15000.00")) - .dateEcheance(dateEcheance) - .statut("EN_COURS") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateCotisationRequest request = UpdateCotisationRequest.builder() - .libelle("ToString Cotisation") - .montantDu(new BigDecimal("55000.00")) - .statut("VALIDE") - .annee(2027) - .mois(12) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateCotisationRequest"); - assertThat(toString).contains("ToString Cotisation"); - assertThat(toString).contains("55000.00"); - assertThat(toString).contains("VALIDE"); - } -} +package dev.lions.unionflow.server.api.dto.cotisation.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateCotisationRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDate dateEcheance = LocalDate.now().plusDays(45); + + UpdateCotisationRequest request = UpdateCotisationRequest.builder() + .libelle("Cotisation Mise à Jour") + .description("Description mise à jour de la cotisation") + .montantDu(new BigDecimal("30000.00")) + .dateEcheance(dateEcheance) + .observations("Observations modifiées") + .statut("EN_ATTENTE") + .annee(2026) + .mois(6) + .recurrente(false) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.libelle()).isEqualTo("Cotisation Mise à Jour"); + assertThat(request.description()).contains("mise à jour"); + assertThat(request.montantDu()).isEqualByComparingTo(new BigDecimal("30000.00")); + assertThat(request.dateEcheance()).isEqualTo(dateEcheance); + assertThat(request.observations()).contains("modifiées"); + assertThat(request.statut()).isEqualTo("EN_ATTENTE"); + assertThat(request.annee()).isEqualTo(2026); + assertThat(request.mois()).isEqualTo(6); + assertThat(request.recurrente()).isFalse(); + } + + @Test + void testBuilder_MinimalFields() { + UpdateCotisationRequest request = UpdateCotisationRequest.builder().build(); + + assertThat(request).isNotNull(); + assertThat(request.libelle()).isNull(); + assertThat(request.description()).isNull(); + assertThat(request.montantDu()).isNull(); + assertThat(request.dateEcheance()).isNull(); + assertThat(request.observations()).isNull(); + assertThat(request.statut()).isNull(); + assertThat(request.annee()).isNull(); + assertThat(request.mois()).isNull(); + assertThat(request.recurrente()).isNull(); + } + + @Test + void testValidation_LibelleTooLong() { + String longLibelle = "A".repeat(101); + UpdateCotisationRequest request = UpdateCotisationRequest.builder() + .libelle(longLibelle) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); + } + + @Test + void testValidation_DescriptionTooLong() { + String longDescription = "B".repeat(501); + UpdateCotisationRequest request = UpdateCotisationRequest.builder() + .description(longDescription) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); + } + + @Test + void testValidation_MontantZero() { + UpdateCotisationRequest request = UpdateCotisationRequest.builder() + .montantDu(BigDecimal.ZERO) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDu")); + } + + @Test + void testValidation_MontantNegatif() { + UpdateCotisationRequest request = UpdateCotisationRequest.builder() + .montantDu(new BigDecimal("-500.00")) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDu")); + } + + @Test + void testValidation_ObservationsTooLong() { + String longObservations = "C".repeat(1001); + UpdateCotisationRequest request = UpdateCotisationRequest.builder() + .observations(longObservations) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("observations")); + } + + @Test + void testValidation_AnneeTooOld() { + UpdateCotisationRequest request = UpdateCotisationRequest.builder().annee(2018).build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("annee")); + } + + @Test + void testValidation_AnneeTooFuture() { + UpdateCotisationRequest request = UpdateCotisationRequest.builder().annee(2105).build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("annee")); + } + + @Test + void testValidation_MoisZero() { + UpdateCotisationRequest request = UpdateCotisationRequest.builder().mois(0).build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("mois")); + } + + @Test + void testValidation_MoisTooHigh() { + UpdateCotisationRequest request = UpdateCotisationRequest.builder().mois(15).build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("mois")); + } + + @Test + void testValidation_ValidFields() { + UpdateCotisationRequest request = UpdateCotisationRequest.builder() + .libelle("Libellé Valide") + .description("Description valide et complète") + .montantDu(new BigDecimal("45000.00")) + .dateEcheance(LocalDate.now().plusMonths(2)) + .observations("Observations valides") + .statut("PAYE") + .annee(2025) + .mois(8) + .recurrente(true) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + LocalDate dateEcheance = LocalDate.now().plusDays(20); + + UpdateCotisationRequest request1 = UpdateCotisationRequest.builder() + .libelle("Même Libellé") + .montantDu(new BigDecimal("15000.00")) + .dateEcheance(dateEcheance) + .statut("EN_COURS") + .build(); + + UpdateCotisationRequest request2 = UpdateCotisationRequest.builder() + .libelle("Même Libellé") + .montantDu(new BigDecimal("15000.00")) + .dateEcheance(dateEcheance) + .statut("EN_COURS") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateCotisationRequest request = UpdateCotisationRequest.builder() + .libelle("ToString Cotisation") + .montantDu(new BigDecimal("55000.00")) + .statut("VALIDE") + .annee(2027) + .mois(12) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateCotisationRequest"); + assertThat(toString).contains("ToString Cotisation"); + assertThat(toString).contains("55000.00"); + assertThat(toString).contains("VALIDE"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/cotisation/response/CotisationResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/cotisation/response/CotisationResponseTest.java index aa0e8d4..4025a5b 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/cotisation/response/CotisationResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/cotisation/response/CotisationResponseTest.java @@ -1,307 +1,307 @@ -package dev.lions.unionflow.server.api.dto.cotisation.response; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalDateTime; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour CotisationResponse. - * Couvre les propriétés d'affichage membre/organisation (nomCompletMembre, - * initialesMembre, typeMembre, regionOrganisation, iconeOrganisation). - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-04 - */ -@DisplayName("Tests CotisationResponse") -class CotisationResponseTest { - - @Nested - @DisplayName("Builder et getters – propriétés membre/organisation") - class BuilderEtGetters { - - @Test - @DisplayName("builder remplit nomCompletMembre, initialesMembre, typeMembre") - void builder_remplitProprietesMembre() { - CotisationResponse r = CotisationResponse.builder() - .nomCompletMembre("Jean Dupont") - .initialesMembre("JD") - .typeMembre("Actif") - .nomMembre("Jean Dupont") - .numeroMembre("M-001") - .build(); - - assertThat(r.getNomCompletMembre()).isEqualTo("Jean Dupont"); - assertThat(r.getInitialesMembre()).isEqualTo("JD"); - assertThat(r.getTypeMembre()).isEqualTo("Actif"); - } - - @Test - @DisplayName("builder remplit regionOrganisation et iconeOrganisation") - void builder_remplitProprietesOrganisation() { - CotisationResponse r = CotisationResponse.builder() - .nomOrganisation("Club Lions Abidjan") - .regionOrganisation("Abidjan") - .iconeOrganisation("pi-users") - .build(); - - assertThat(r.getRegionOrganisation()).isEqualTo("Abidjan"); - assertThat(r.getIconeOrganisation()).isEqualTo("pi-users"); - } - - @Test - @DisplayName("propriétés null acceptées") - void builder_accepteNull() { - CotisationResponse r = CotisationResponse.builder() - .numeroReference("REF-1") - .build(); - - assertThat(r.getNomCompletMembre()).isNull(); - assertThat(r.getInitialesMembre()).isNull(); - assertThat(r.getTypeMembre()).isNull(); - assertThat(r.getRegionOrganisation()).isNull(); - assertThat(r.getIconeOrganisation()).isNull(); - } - - @Test - @DisplayName("setters mettent à jour les propriétés") - void setters_mettentAJour() { - CotisationResponse r = new CotisationResponse(); - r.setNomCompletMembre("Marie Martin"); - r.setInitialesMembre("MM"); - r.setTypeMembre("En attente"); - r.setRegionOrganisation("Dakar"); - r.setIconeOrganisation("pi-building"); - - assertThat(r.getNomCompletMembre()).isEqualTo("Marie Martin"); - assertThat(r.getInitialesMembre()).isEqualTo("MM"); - assertThat(r.getTypeMembre()).isEqualTo("En attente"); - assertThat(r.getRegionOrganisation()).isEqualTo("Dakar"); - assertThat(r.getIconeOrganisation()).isEqualTo("pi-building"); - } - - @Test - @DisplayName("builder remplit typeLibelle, typeSeverity, typeIcon, statutSeverity, statutIcon") - void builder_remplitTypeEtStatutTag() { - CotisationResponse r = CotisationResponse.builder() - .type("ANNUELLE") - .typeLibelle("Annuelle") - .typeSeverity("success") - .typeIcon("pi-star") - .statut("PAYEE") - .statutSeverity("success") - .statutIcon("pi-check") - .build(); - - assertThat(r.getType()).isEqualTo("ANNUELLE"); - assertThat(r.getTypeLibelle()).isEqualTo("Annuelle"); - assertThat(r.getTypeSeverity()).isEqualTo("success"); - assertThat(r.getTypeIcon()).isEqualTo("pi-star"); - assertThat(r.getStatutSeverity()).isEqualTo("success"); - assertThat(r.getStatutIcon()).isEqualTo("pi-check"); - } - - @Test - @DisplayName("builder remplit montant, montantFormatte, dates formatées, retard, mode paiement") - void builder_remplitAffichage() { - CotisationResponse r = CotisationResponse.builder() - .montant(BigDecimal.valueOf(10000)) - .montantFormatte("10 000") - .dateEcheanceFormattee("15/03/2026") - .retardCouleur("text-green-600") - .retardTexte("À jour") - .datePaiementFormattee("01/03/2026 14:30") - .modePaiementIcon("pi-wallet") - .modePaiementLibelle("Espèces") - .build(); - - assertThat(r.getMontant()).isEqualByComparingTo(BigDecimal.valueOf(10000)); - assertThat(r.getMontantFormatte()).isEqualTo("10 000"); - assertThat(r.getDateEcheanceFormattee()).isEqualTo("15/03/2026"); - assertThat(r.getRetardCouleur()).isEqualTo("text-green-600"); - assertThat(r.getRetardTexte()).isEqualTo("À jour"); - assertThat(r.getDatePaiementFormattee()).isEqualTo("01/03/2026 14:30"); - assertThat(r.getModePaiementIcon()).isEqualTo("pi-wallet"); - assertThat(r.getModePaiementLibelle()).isEqualTo("Espèces"); - } - } - - @Nested - @DisplayName("Méthodes de formatage des montants") - class MethodesFormatageMontants { - - @Test - @DisplayName("getMontantDuFormatte retourne 0 FCFA quand montantDu null") - void testMontantDuNull() { - CotisationResponse r = CotisationResponse.builder().build(); - assertThat(r.getMontantDuFormatte()).isEqualTo("0 FCFA"); - } - - @Test - @DisplayName("getMontantDuFormatte formate avec devise par défaut FCFA") - void testMontantDuSansDevise() { - CotisationResponse r = CotisationResponse.builder().montantDu(BigDecimal.valueOf(5000)).build(); - assertThat(r.getMontantDuFormatte()).isEqualTo("5,000 FCFA"); - } - - @Test - @DisplayName("getMontantDuFormatte formate avec codeDevise fourni") - void testMontantDuAvecDevise() { - CotisationResponse r = CotisationResponse.builder().montantDu(BigDecimal.valueOf(5000)).codeDevise("XOF").build(); - assertThat(r.getMontantDuFormatte()).isEqualTo("5,000 XOF"); - } - - @Test - @DisplayName("getMontantPayeFormatte retourne 0 FCFA quand montantPaye null") - void testMontantPayeNull() { - CotisationResponse r = CotisationResponse.builder().build(); - assertThat(r.getMontantPayeFormatte()).isEqualTo("0 FCFA"); - } - - @Test - @DisplayName("getMontantPayeFormatte formate avec devise par défaut FCFA") - void testMontantPayeSansDevise() { - CotisationResponse r = CotisationResponse.builder().montantPaye(BigDecimal.valueOf(2000)).build(); - assertThat(r.getMontantPayeFormatte()).isEqualTo("2,000 FCFA"); - } - - @Test - @DisplayName("getMontantPayeFormatte formate avec codeDevise fourni") - void testMontantPayeAvecDevise() { - CotisationResponse r = CotisationResponse.builder().montantPaye(BigDecimal.valueOf(2000)).codeDevise("EUR").build(); - assertThat(r.getMontantPayeFormatte()).isEqualTo("2,000 EUR"); - } - - @Test - @DisplayName("getMontantRestantFormatte retourne 0 FCFA quand montantRestant null") - void testMontantRestantNull() { - CotisationResponse r = CotisationResponse.builder().build(); - assertThat(r.getMontantRestantFormatte()).isEqualTo("0 FCFA"); - } - - @Test - @DisplayName("getMontantRestantFormatte formate avec devise par défaut FCFA") - void testMontantRestantSansDevise() { - CotisationResponse r = CotisationResponse.builder().montantRestant(BigDecimal.valueOf(3000)).build(); - assertThat(r.getMontantRestantFormatte()).isEqualTo("3,000 FCFA"); - } - - @Test - @DisplayName("getMontantRestantFormatte formate avec codeDevise fourni") - void testMontantRestantAvecDevise() { - CotisationResponse r = CotisationResponse.builder().montantRestant(BigDecimal.valueOf(3000)).codeDevise("XOF").build(); - assertThat(r.getMontantRestantFormatte()).isEqualTo("3,000 XOF"); - } - - @Test - @DisplayName("isMontantRestantPositif retourne false quand montantRestant null") - void testMontantRestantPositifNull() { - CotisationResponse r = CotisationResponse.builder().build(); - assertThat(r.isMontantRestantPositif()).isFalse(); - } - - @Test - @DisplayName("isMontantRestantPositif retourne false quand montantRestant = 0") - void testMontantRestantPositifZero() { - CotisationResponse r = CotisationResponse.builder().montantRestant(BigDecimal.ZERO).build(); - assertThat(r.isMontantRestantPositif()).isFalse(); - } - - @Test - @DisplayName("isMontantRestantPositif retourne false quand montantRestant négatif") - void testMontantRestantPositifNegatif() { - CotisationResponse r = CotisationResponse.builder().montantRestant(BigDecimal.valueOf(-100)).build(); - assertThat(r.isMontantRestantPositif()).isFalse(); - } - - @Test - @DisplayName("isMontantRestantPositif retourne true quand montantRestant > 0") - void testMontantRestantPositifVrai() { - CotisationResponse r = CotisationResponse.builder().montantRestant(BigDecimal.valueOf(500)).build(); - assertThat(r.isMontantRestantPositif()).isTrue(); - } - } - - @Nested - @DisplayName("Alias getMethodePaiementLibelle") - class AliasMethodePaiement { - - @Test - @DisplayName("getMethodePaiementLibelle retourne modePaiementLibelle") - void getMethodePaiementLibelle_retourneModePaiementLibelle() { - CotisationResponse r = CotisationResponse.builder() - .modePaiementLibelle("Wave Money") - .build(); - - assertThat(r.getMethodePaiementLibelle()).isEqualTo("Wave Money"); - } - - @Test - @DisplayName("getMethodePaiementLibelle retourne null si non renseigné") - void getMethodePaiementLibelle_null() { - CotisationResponse r = CotisationResponse.builder().build(); - assertThat(r.getMethodePaiementLibelle()).isNull(); - } - } - - @Nested - @DisplayName("Builder complet") - class BuilderComplet { - - @Test - @DisplayName("builder avec toutes les propriétés principales") - void builder_complet() { - UUID id = UUID.randomUUID(); - UUID membreId = UUID.randomUUID(); - UUID orgId = UUID.randomUUID(); - LocalDate dateEcheance = LocalDate.now().plusMonths(1); - LocalDateTime datePaiement = LocalDateTime.now(); - - CotisationResponse r = CotisationResponse.builder() - .numeroReference("COT-2026-001") - .membreId(membreId) - .nomMembre("Jean Dupont") - .nomCompletMembre("Jean Dupont") - .initialesMembre("JD") - .typeMembre("Actif") - .numeroMembre("M-001") - .organisationId(orgId) - .nomOrganisation("Club Test") - .regionOrganisation("Abidjan") - .iconeOrganisation("pi-star") - .typeCotisation("MENSUELLE") - .libelle("Cotisation mars") - .montantDu(BigDecimal.valueOf(5000)) - .montantPaye(BigDecimal.ZERO) - .montantRestant(BigDecimal.valueOf(5000)) - .codeDevise("XOF") - .statut("EN_ATTENTE") - .dateEcheance(dateEcheance) - .datePaiement(datePaiement) - .annee(2026) - .mois(3) - .build(); - r.setId(id); - - assertThat(r.getId()).isEqualTo(id); - assertThat(r.getNumeroReference()).isEqualTo("COT-2026-001"); - assertThat(r.getMembreId()).isEqualTo(membreId); - assertThat(r.getNomCompletMembre()).isEqualTo("Jean Dupont"); - assertThat(r.getInitialesMembre()).isEqualTo("JD"); - assertThat(r.getTypeMembre()).isEqualTo("Actif"); - assertThat(r.getOrganisationId()).isEqualTo(orgId); - assertThat(r.getNomOrganisation()).isEqualTo("Club Test"); - assertThat(r.getRegionOrganisation()).isEqualTo("Abidjan"); - assertThat(r.getIconeOrganisation()).isEqualTo("pi-star"); - assertThat(r.getMontantDu()).isEqualByComparingTo(BigDecimal.valueOf(5000)); - assertThat(r.getStatut()).isEqualTo("EN_ATTENTE"); - assertThat(r.getDateEcheance()).isEqualTo(dateEcheance); - } - } -} +package dev.lions.unionflow.server.api.dto.cotisation.response; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour CotisationResponse. + * Couvre les propriétés d'affichage membre/organisation (nomCompletMembre, + * initialesMembre, typeMembre, regionOrganisation, iconeOrganisation). + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-04 + */ +@DisplayName("Tests CotisationResponse") +class CotisationResponseTest { + + @Nested + @DisplayName("Builder et getters – propriétés membre/organisation") + class BuilderEtGetters { + + @Test + @DisplayName("builder remplit nomCompletMembre, initialesMembre, typeMembre") + void builder_remplitProprietesMembre() { + CotisationResponse r = CotisationResponse.builder() + .nomCompletMembre("Jean Dupont") + .initialesMembre("JD") + .typeMembre("Actif") + .nomMembre("Jean Dupont") + .numeroMembre("M-001") + .build(); + + assertThat(r.getNomCompletMembre()).isEqualTo("Jean Dupont"); + assertThat(r.getInitialesMembre()).isEqualTo("JD"); + assertThat(r.getTypeMembre()).isEqualTo("Actif"); + } + + @Test + @DisplayName("builder remplit regionOrganisation et iconeOrganisation") + void builder_remplitProprietesOrganisation() { + CotisationResponse r = CotisationResponse.builder() + .nomOrganisation("Club Lions Abidjan") + .regionOrganisation("Abidjan") + .iconeOrganisation("pi-users") + .build(); + + assertThat(r.getRegionOrganisation()).isEqualTo("Abidjan"); + assertThat(r.getIconeOrganisation()).isEqualTo("pi-users"); + } + + @Test + @DisplayName("propriétés null acceptées") + void builder_accepteNull() { + CotisationResponse r = CotisationResponse.builder() + .numeroReference("REF-1") + .build(); + + assertThat(r.getNomCompletMembre()).isNull(); + assertThat(r.getInitialesMembre()).isNull(); + assertThat(r.getTypeMembre()).isNull(); + assertThat(r.getRegionOrganisation()).isNull(); + assertThat(r.getIconeOrganisation()).isNull(); + } + + @Test + @DisplayName("setters mettent à jour les propriétés") + void setters_mettentAJour() { + CotisationResponse r = new CotisationResponse(); + r.setNomCompletMembre("Marie Martin"); + r.setInitialesMembre("MM"); + r.setTypeMembre("En attente"); + r.setRegionOrganisation("Dakar"); + r.setIconeOrganisation("pi-building"); + + assertThat(r.getNomCompletMembre()).isEqualTo("Marie Martin"); + assertThat(r.getInitialesMembre()).isEqualTo("MM"); + assertThat(r.getTypeMembre()).isEqualTo("En attente"); + assertThat(r.getRegionOrganisation()).isEqualTo("Dakar"); + assertThat(r.getIconeOrganisation()).isEqualTo("pi-building"); + } + + @Test + @DisplayName("builder remplit typeLibelle, typeSeverity, typeIcon, statutSeverity, statutIcon") + void builder_remplitTypeEtStatutTag() { + CotisationResponse r = CotisationResponse.builder() + .type("ANNUELLE") + .typeLibelle("Annuelle") + .typeSeverity("success") + .typeIcon("pi-star") + .statut("PAYEE") + .statutSeverity("success") + .statutIcon("pi-check") + .build(); + + assertThat(r.getType()).isEqualTo("ANNUELLE"); + assertThat(r.getTypeLibelle()).isEqualTo("Annuelle"); + assertThat(r.getTypeSeverity()).isEqualTo("success"); + assertThat(r.getTypeIcon()).isEqualTo("pi-star"); + assertThat(r.getStatutSeverity()).isEqualTo("success"); + assertThat(r.getStatutIcon()).isEqualTo("pi-check"); + } + + @Test + @DisplayName("builder remplit montant, montantFormatte, dates formatées, retard, mode paiement") + void builder_remplitAffichage() { + CotisationResponse r = CotisationResponse.builder() + .montant(BigDecimal.valueOf(10000)) + .montantFormatte("10 000") + .dateEcheanceFormattee("15/03/2026") + .retardCouleur("text-green-600") + .retardTexte("À jour") + .datePaiementFormattee("01/03/2026 14:30") + .modePaiementIcon("pi-wallet") + .modePaiementLibelle("Espèces") + .build(); + + assertThat(r.getMontant()).isEqualByComparingTo(BigDecimal.valueOf(10000)); + assertThat(r.getMontantFormatte()).isEqualTo("10 000"); + assertThat(r.getDateEcheanceFormattee()).isEqualTo("15/03/2026"); + assertThat(r.getRetardCouleur()).isEqualTo("text-green-600"); + assertThat(r.getRetardTexte()).isEqualTo("À jour"); + assertThat(r.getDatePaiementFormattee()).isEqualTo("01/03/2026 14:30"); + assertThat(r.getModePaiementIcon()).isEqualTo("pi-wallet"); + assertThat(r.getModePaiementLibelle()).isEqualTo("Espèces"); + } + } + + @Nested + @DisplayName("Méthodes de formatage des montants") + class MethodesFormatageMontants { + + @Test + @DisplayName("getMontantDuFormatte retourne 0 FCFA quand montantDu null") + void testMontantDuNull() { + CotisationResponse r = CotisationResponse.builder().build(); + assertThat(r.getMontantDuFormatte()).isEqualTo("0 FCFA"); + } + + @Test + @DisplayName("getMontantDuFormatte formate avec devise par défaut FCFA") + void testMontantDuSansDevise() { + CotisationResponse r = CotisationResponse.builder().montantDu(BigDecimal.valueOf(5000)).build(); + assertThat(r.getMontantDuFormatte()).isEqualTo("5,000 FCFA"); + } + + @Test + @DisplayName("getMontantDuFormatte formate avec codeDevise fourni") + void testMontantDuAvecDevise() { + CotisationResponse r = CotisationResponse.builder().montantDu(BigDecimal.valueOf(5000)).codeDevise("XOF").build(); + assertThat(r.getMontantDuFormatte()).isEqualTo("5,000 XOF"); + } + + @Test + @DisplayName("getMontantPayeFormatte retourne 0 FCFA quand montantPaye null") + void testMontantPayeNull() { + CotisationResponse r = CotisationResponse.builder().build(); + assertThat(r.getMontantPayeFormatte()).isEqualTo("0 FCFA"); + } + + @Test + @DisplayName("getMontantPayeFormatte formate avec devise par défaut FCFA") + void testMontantPayeSansDevise() { + CotisationResponse r = CotisationResponse.builder().montantPaye(BigDecimal.valueOf(2000)).build(); + assertThat(r.getMontantPayeFormatte()).isEqualTo("2,000 FCFA"); + } + + @Test + @DisplayName("getMontantPayeFormatte formate avec codeDevise fourni") + void testMontantPayeAvecDevise() { + CotisationResponse r = CotisationResponse.builder().montantPaye(BigDecimal.valueOf(2000)).codeDevise("EUR").build(); + assertThat(r.getMontantPayeFormatte()).isEqualTo("2,000 EUR"); + } + + @Test + @DisplayName("getMontantRestantFormatte retourne 0 FCFA quand montantRestant null") + void testMontantRestantNull() { + CotisationResponse r = CotisationResponse.builder().build(); + assertThat(r.getMontantRestantFormatte()).isEqualTo("0 FCFA"); + } + + @Test + @DisplayName("getMontantRestantFormatte formate avec devise par défaut FCFA") + void testMontantRestantSansDevise() { + CotisationResponse r = CotisationResponse.builder().montantRestant(BigDecimal.valueOf(3000)).build(); + assertThat(r.getMontantRestantFormatte()).isEqualTo("3,000 FCFA"); + } + + @Test + @DisplayName("getMontantRestantFormatte formate avec codeDevise fourni") + void testMontantRestantAvecDevise() { + CotisationResponse r = CotisationResponse.builder().montantRestant(BigDecimal.valueOf(3000)).codeDevise("XOF").build(); + assertThat(r.getMontantRestantFormatte()).isEqualTo("3,000 XOF"); + } + + @Test + @DisplayName("isMontantRestantPositif retourne false quand montantRestant null") + void testMontantRestantPositifNull() { + CotisationResponse r = CotisationResponse.builder().build(); + assertThat(r.isMontantRestantPositif()).isFalse(); + } + + @Test + @DisplayName("isMontantRestantPositif retourne false quand montantRestant = 0") + void testMontantRestantPositifZero() { + CotisationResponse r = CotisationResponse.builder().montantRestant(BigDecimal.ZERO).build(); + assertThat(r.isMontantRestantPositif()).isFalse(); + } + + @Test + @DisplayName("isMontantRestantPositif retourne false quand montantRestant négatif") + void testMontantRestantPositifNegatif() { + CotisationResponse r = CotisationResponse.builder().montantRestant(BigDecimal.valueOf(-100)).build(); + assertThat(r.isMontantRestantPositif()).isFalse(); + } + + @Test + @DisplayName("isMontantRestantPositif retourne true quand montantRestant > 0") + void testMontantRestantPositifVrai() { + CotisationResponse r = CotisationResponse.builder().montantRestant(BigDecimal.valueOf(500)).build(); + assertThat(r.isMontantRestantPositif()).isTrue(); + } + } + + @Nested + @DisplayName("Alias getMethodePaiementLibelle") + class AliasMethodePaiement { + + @Test + @DisplayName("getMethodePaiementLibelle retourne modePaiementLibelle") + void getMethodePaiementLibelle_retourneModePaiementLibelle() { + CotisationResponse r = CotisationResponse.builder() + .modePaiementLibelle("Wave Money") + .build(); + + assertThat(r.getMethodePaiementLibelle()).isEqualTo("Wave Money"); + } + + @Test + @DisplayName("getMethodePaiementLibelle retourne null si non renseigné") + void getMethodePaiementLibelle_null() { + CotisationResponse r = CotisationResponse.builder().build(); + assertThat(r.getMethodePaiementLibelle()).isNull(); + } + } + + @Nested + @DisplayName("Builder complet") + class BuilderComplet { + + @Test + @DisplayName("builder avec toutes les propriétés principales") + void builder_complet() { + UUID id = UUID.randomUUID(); + UUID membreId = UUID.randomUUID(); + UUID orgId = UUID.randomUUID(); + LocalDate dateEcheance = LocalDate.now().plusMonths(1); + LocalDateTime datePaiement = LocalDateTime.now(); + + CotisationResponse r = CotisationResponse.builder() + .numeroReference("COT-2026-001") + .membreId(membreId) + .nomMembre("Jean Dupont") + .nomCompletMembre("Jean Dupont") + .initialesMembre("JD") + .typeMembre("Actif") + .numeroMembre("M-001") + .organisationId(orgId) + .nomOrganisation("Club Test") + .regionOrganisation("Abidjan") + .iconeOrganisation("pi-star") + .typeCotisation("MENSUELLE") + .libelle("Cotisation mars") + .montantDu(BigDecimal.valueOf(5000)) + .montantPaye(BigDecimal.ZERO) + .montantRestant(BigDecimal.valueOf(5000)) + .codeDevise("XOF") + .statut("EN_ATTENTE") + .dateEcheance(dateEcheance) + .datePaiement(datePaiement) + .annee(2026) + .mois(3) + .build(); + r.setId(id); + + assertThat(r.getId()).isEqualTo(id); + assertThat(r.getNumeroReference()).isEqualTo("COT-2026-001"); + assertThat(r.getMembreId()).isEqualTo(membreId); + assertThat(r.getNomCompletMembre()).isEqualTo("Jean Dupont"); + assertThat(r.getInitialesMembre()).isEqualTo("JD"); + assertThat(r.getTypeMembre()).isEqualTo("Actif"); + assertThat(r.getOrganisationId()).isEqualTo(orgId); + assertThat(r.getNomOrganisation()).isEqualTo("Club Test"); + assertThat(r.getRegionOrganisation()).isEqualTo("Abidjan"); + assertThat(r.getIconeOrganisation()).isEqualTo("pi-star"); + assertThat(r.getMontantDu()).isEqualByComparingTo(BigDecimal.valueOf(5000)); + assertThat(r.getStatut()).isEqualTo("EN_ATTENTE"); + assertThat(r.getDateEcheance()).isEqualTo(dateEcheance); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardDataResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardDataResponseTest.java index cf9197f..e78aeb4 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardDataResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardDataResponseTest.java @@ -1,444 +1,444 @@ -package dev.lions.unionflow.server.api.dto.dashboard; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalDateTime; -import java.util.List; -import java.util.Map; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour DashboardDataResponse. - * Couvre tous les getters et méthodes utilitaires (toutes branches). - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests DashboardDataResponse") -class DashboardDataResponseTest { - - /** Sous-classe pour couvrir la branche getIsToday() == null dans le filtre. */ - private static final class EventWithNullIsToday extends UpcomingEventResponse { - @Override - public Boolean getIsToday() { return null; } - } - - /** Sous-classe pour couvrir la branche getIsTomorrow() == null dans le filtre. */ - private static final class EventWithNullIsTomorrow extends UpcomingEventResponse { - @Override - public Boolean getIsTomorrow() { return null; } - } - - /** Sous-classe pour couvrir la branche getIsRecent() == null dans le filtre. */ - private static final class ActivityWithNullIsRecent extends RecentActivityResponse { - @Override - public Boolean getIsRecent() { return null; } - } - - /** Sous-classe pour couvrir la branche getIsToday() == null (activité) dans le filtre. */ - private static final class ActivityWithNullIsToday extends RecentActivityResponse { - @Override - public Boolean getIsToday() { return null; } - } - - @Nested - @DisplayName("Constructeur et getters/setters") - class ConstructeurEtGetters { - - @Test - @DisplayName("builder et getters fonctionnent") - void testBuilderEtGetters() { - DashboardStatsResponse stats = new DashboardStatsResponse(); - List activities = List.of(); - List events = List.of(); - Map prefs = Map.of("theme", "dark"); - DashboardDataResponse dto = DashboardDataResponse.builder() - .stats(stats) - .recentActivities(activities) - .upcomingEvents(events) - .userPreferences(prefs) - .organizationId("org1") - .userId("user1") - .build(); - assertThat(dto.getStats()).isSameAs(stats); - assertThat(dto.getRecentActivities()).isSameAs(activities); - assertThat(dto.getUpcomingEvents()).isSameAs(events); - assertThat(dto.getUserPreferences()).isEqualTo(prefs); - assertThat(dto.getOrganizationId()).isEqualTo("org1"); - assertThat(dto.getUserId()).isEqualTo("user1"); - } - - @Test - @DisplayName("no-args et setters") - void testNoArgsEtSetters() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setStats(new DashboardStatsResponse()); - dto.setOrganizationId("o2"); - assertThat(dto.getOrganizationId()).isEqualTo("o2"); - } - } - - @Nested - @DisplayName("getTodayEventsCount") - class GetTodayEventsCount { - - @Test - @DisplayName("retourne 0 quand upcomingEvents est null") - void testNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUpcomingEvents(null); - assertThat(dto.getTodayEventsCount()).isEqualTo(0); - } - - @Test - @DisplayName("compte les événements avec isToday true") - void testCompteToday() { - LocalDateTime now = LocalDateTime.now(); - UpcomingEventResponse today = UpcomingEventResponse.builder().startDate(now).build(); - UpcomingEventResponse other = UpcomingEventResponse.builder().startDate(now.plusDays(2)).build(); - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUpcomingEvents(List.of(today, other)); - assertThat(dto.getTodayEventsCount()).isEqualTo(1); - } - - @Test - @DisplayName("exclut les événements dont getIsToday() est null") - void testFiltreIsTodayNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUpcomingEvents(List.of(new EventWithNullIsToday())); - assertThat(dto.getTodayEventsCount()).isEqualTo(0); - } - - @Test - @DisplayName("une liste mixte (null, true, false) compte uniquement les isToday true") - void testFiltreMixteToday() { - LocalDateTime now = LocalDateTime.now(); - UpcomingEventResponse today = UpcomingEventResponse.builder().startDate(now).build(); - UpcomingEventResponse other = UpcomingEventResponse.builder().startDate(now.plusDays(2)).build(); - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUpcomingEvents(List.of(new EventWithNullIsToday(), today, other)); - assertThat(dto.getTodayEventsCount()).isEqualTo(1); - } - } - - @Nested - @DisplayName("getTomorrowEventsCount") - class GetTomorrowEventsCount { - - @Test - @DisplayName("retourne 0 quand upcomingEvents est null") - void testNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUpcomingEvents(null); - assertThat(dto.getTomorrowEventsCount()).isEqualTo(0); - } - - @Test - @DisplayName("compte les événements avec isTomorrow true") - void testCompteTomorrow() { - UpcomingEventResponse tomorrow = UpcomingEventResponse.builder() - .startDate(LocalDateTime.now().plusDays(1)).build(); - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUpcomingEvents(List.of(tomorrow)); - assertThat(dto.getTomorrowEventsCount()).isEqualTo(1); - } - - @Test - @DisplayName("exclut les événements dont getIsTomorrow() est null") - void testFiltreIsTomorrowNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUpcomingEvents(List.of(new EventWithNullIsTomorrow())); - assertThat(dto.getTomorrowEventsCount()).isEqualTo(0); - } - - @Test - @DisplayName("une liste mixte pour demain compte uniquement les isTomorrow true") - void testFiltreMixteTomorrow() { - UpcomingEventResponse tomorrow = UpcomingEventResponse.builder().startDate(LocalDateTime.now().plusDays(1)).build(); - UpcomingEventResponse other = UpcomingEventResponse.builder().startDate(LocalDateTime.now().plusDays(3)).build(); - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUpcomingEvents(List.of(new EventWithNullIsTomorrow(), tomorrow, other)); - assertThat(dto.getTomorrowEventsCount()).isEqualTo(1); - } - } - - @Nested - @DisplayName("getRecentActivitiesCount") - class GetRecentActivitiesCount { - - @Test - @DisplayName("retourne 0 quand recentActivities est null") - void testNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setRecentActivities(null); - assertThat(dto.getRecentActivitiesCount()).isEqualTo(0); - } - - @Test - @DisplayName("compte les activités avec isRecent true") - void testCompteRecent() { - RecentActivityResponse recent = RecentActivityResponse.builder() - .timestamp(LocalDateTime.now().minusHours(1)).build(); - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setRecentActivities(List.of(recent)); - assertThat(dto.getRecentActivitiesCount()).isEqualTo(1); - } - - @Test - @DisplayName("exclut les activités dont getIsRecent() est null") - void testFiltreIsRecentNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setRecentActivities(List.of(new ActivityWithNullIsRecent())); - assertThat(dto.getRecentActivitiesCount()).isEqualTo(0); - } - - @Test - @DisplayName("une liste mixte pour isRecent compte uniquement les isRecent true") - void testFiltreMixteRecent() { - RecentActivityResponse recent = RecentActivityResponse.builder().timestamp(LocalDateTime.now().minusHours(1)).build(); - RecentActivityResponse old = RecentActivityResponse.builder().timestamp(LocalDateTime.now().minusDays(2)).build(); - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setRecentActivities(List.of(new ActivityWithNullIsRecent(), recent, old)); - assertThat(dto.getRecentActivitiesCount()).isEqualTo(1); - } - } - - @Nested - @DisplayName("getTodayActivitiesCount") - class GetTodayActivitiesCount { - - @Test - @DisplayName("retourne 0 quand recentActivities est null") - void testNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setRecentActivities(null); - assertThat(dto.getTodayActivitiesCount()).isEqualTo(0); - } - - @Test - @DisplayName("compte les activités avec isToday true") - void testCompteToday() { - RecentActivityResponse today = RecentActivityResponse.builder() - .timestamp(LocalDateTime.now()).build(); - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setRecentActivities(List.of(today)); - assertThat(dto.getTodayActivitiesCount()).isEqualTo(1); - } - - @Test - @DisplayName("exclut les activités dont getIsToday() est null") - void testFiltreIsTodayNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setRecentActivities(List.of(new ActivityWithNullIsToday())); - assertThat(dto.getTodayActivitiesCount()).isEqualTo(0); - } - - @Test - @DisplayName("une liste mixte pour isToday activité compte uniquement les isToday true") - void testFiltreMixteTodayActivity() { - RecentActivityResponse today = RecentActivityResponse.builder().timestamp(LocalDateTime.now()).build(); - RecentActivityResponse other = RecentActivityResponse.builder().timestamp(LocalDateTime.now().minusDays(1)).build(); - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setRecentActivities(List.of(new ActivityWithNullIsToday(), today, other)); - assertThat(dto.getTodayActivitiesCount()).isEqualTo(1); - } - } - - @Nested - @DisplayName("getHasUpcomingEvents") - class GetHasUpcomingEvents { - - @Test - @DisplayName("retourne false quand upcomingEvents est null") - void testNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUpcomingEvents(null); - assertThat(dto.getHasUpcomingEvents()).isFalse(); - } - - @Test - @DisplayName("retourne false quand upcomingEvents est vide") - void testVide() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUpcomingEvents(List.of()); - assertThat(dto.getHasUpcomingEvents()).isFalse(); - } - - @Test - @DisplayName("retourne true quand upcomingEvents non vide") - void testNonVide() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUpcomingEvents(List.of(UpcomingEventResponse.builder().build())); - assertThat(dto.getHasUpcomingEvents()).isTrue(); - } - } - - @Nested - @DisplayName("getHasRecentActivities") - class GetHasRecentActivities { - - @Test - @DisplayName("retourne false quand recentActivities est null") - void testNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setRecentActivities(null); - assertThat(dto.getHasRecentActivities()).isFalse(); - } - - @Test - @DisplayName("retourne false quand recentActivities est vide") - void testVide() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setRecentActivities(List.of()); - assertThat(dto.getHasRecentActivities()).isFalse(); - } - - @Test - @DisplayName("retourne true quand recentActivities non vide") - void testNonVide() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setRecentActivities(List.of(RecentActivityResponse.builder().build())); - assertThat(dto.getHasRecentActivities()).isTrue(); - } - } - - @Nested - @DisplayName("getThemePreference") - class GetThemePreference { - - @Test - @DisplayName("retourne royal_teal quand userPreferences est null") - void testNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(null); - assertThat(dto.getThemePreference()).isEqualTo("royal_teal"); - } - - @Test - @DisplayName("retourne la valeur theme si présente") - void testAvecTheme() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(Map.of("theme", "dark")); - assertThat(dto.getThemePreference()).isEqualTo("dark"); - } - - @Test - @DisplayName("retourne royal_teal par défaut si theme absent") - void testDefaut() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(Map.of("other", "x")); - assertThat(dto.getThemePreference()).isEqualTo("royal_teal"); - } - } - - @Nested - @DisplayName("getLanguagePreference") - class GetLanguagePreference { - - @Test - @DisplayName("retourne fr quand userPreferences est null") - void testNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(null); - assertThat(dto.getLanguagePreference()).isEqualTo("fr"); - } - - @Test - @DisplayName("retourne la valeur language si présente") - void testAvecLanguage() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(Map.of("language", "en")); - assertThat(dto.getLanguagePreference()).isEqualTo("en"); - } - - @Test - @DisplayName("retourne fr par défaut si language absent") - void testDefaut() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(Map.of()); - assertThat(dto.getLanguagePreference()).isEqualTo("fr"); - } - } - - @Nested - @DisplayName("getNotificationsEnabled") - class GetNotificationsEnabled { - - @Test - @DisplayName("retourne true quand userPreferences est null") - void testNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(null); - assertThat(dto.getNotificationsEnabled()).isTrue(); - } - - @Test - @DisplayName("retourne la valeur notifications si présente") - void testAvecValeur() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(Map.of("notifications", false)); - assertThat(dto.getNotificationsEnabled()).isFalse(); - } - - @Test - @DisplayName("retourne true par défaut si notifications absent") - void testDefaut() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(Map.of()); - assertThat(dto.getNotificationsEnabled()).isTrue(); - } - } - - @Nested - @DisplayName("getAutoRefreshEnabled") - class GetAutoRefreshEnabled { - - @Test - @DisplayName("retourne true quand userPreferences est null") - void testNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(null); - assertThat(dto.getAutoRefreshEnabled()).isTrue(); - } - - @Test - @DisplayName("retourne la valeur autoRefresh si présente") - void testAvecValeur() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(Map.of("autoRefresh", false)); - assertThat(dto.getAutoRefreshEnabled()).isFalse(); - } - } - - @Nested - @DisplayName("getRefreshInterval") - class GetRefreshInterval { - - @Test - @DisplayName("retourne 300 quand userPreferences est null") - void testNull() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(null); - assertThat(dto.getRefreshInterval()).isEqualTo(300); - } - - @Test - @DisplayName("retourne la valeur refreshInterval si présente") - void testAvecValeur() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(Map.of("refreshInterval", 60)); - assertThat(dto.getRefreshInterval()).isEqualTo(60); - } - - @Test - @DisplayName("retourne 300 par défaut si refreshInterval absent") - void testDefaut() { - DashboardDataResponse dto = new DashboardDataResponse(); - dto.setUserPreferences(Map.of()); - assertThat(dto.getRefreshInterval()).isEqualTo(300); - } - } -} +package dev.lions.unionflow.server.api.dto.dashboard; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalDateTime; +import java.util.List; +import java.util.Map; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour DashboardDataResponse. + * Couvre tous les getters et méthodes utilitaires (toutes branches). + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests DashboardDataResponse") +class DashboardDataResponseTest { + + /** Sous-classe pour couvrir la branche getIsToday() == null dans le filtre. */ + private static final class EventWithNullIsToday extends UpcomingEventResponse { + @Override + public Boolean getIsToday() { return null; } + } + + /** Sous-classe pour couvrir la branche getIsTomorrow() == null dans le filtre. */ + private static final class EventWithNullIsTomorrow extends UpcomingEventResponse { + @Override + public Boolean getIsTomorrow() { return null; } + } + + /** Sous-classe pour couvrir la branche getIsRecent() == null dans le filtre. */ + private static final class ActivityWithNullIsRecent extends RecentActivityResponse { + @Override + public Boolean getIsRecent() { return null; } + } + + /** Sous-classe pour couvrir la branche getIsToday() == null (activité) dans le filtre. */ + private static final class ActivityWithNullIsToday extends RecentActivityResponse { + @Override + public Boolean getIsToday() { return null; } + } + + @Nested + @DisplayName("Constructeur et getters/setters") + class ConstructeurEtGetters { + + @Test + @DisplayName("builder et getters fonctionnent") + void testBuilderEtGetters() { + DashboardStatsResponse stats = new DashboardStatsResponse(); + List activities = List.of(); + List events = List.of(); + Map prefs = Map.of("theme", "dark"); + DashboardDataResponse dto = DashboardDataResponse.builder() + .stats(stats) + .recentActivities(activities) + .upcomingEvents(events) + .userPreferences(prefs) + .organizationId("org1") + .userId("user1") + .build(); + assertThat(dto.getStats()).isSameAs(stats); + assertThat(dto.getRecentActivities()).isSameAs(activities); + assertThat(dto.getUpcomingEvents()).isSameAs(events); + assertThat(dto.getUserPreferences()).isEqualTo(prefs); + assertThat(dto.getOrganizationId()).isEqualTo("org1"); + assertThat(dto.getUserId()).isEqualTo("user1"); + } + + @Test + @DisplayName("no-args et setters") + void testNoArgsEtSetters() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setStats(new DashboardStatsResponse()); + dto.setOrganizationId("o2"); + assertThat(dto.getOrganizationId()).isEqualTo("o2"); + } + } + + @Nested + @DisplayName("getTodayEventsCount") + class GetTodayEventsCount { + + @Test + @DisplayName("retourne 0 quand upcomingEvents est null") + void testNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUpcomingEvents(null); + assertThat(dto.getTodayEventsCount()).isEqualTo(0); + } + + @Test + @DisplayName("compte les événements avec isToday true") + void testCompteToday() { + LocalDateTime now = LocalDateTime.now(); + UpcomingEventResponse today = UpcomingEventResponse.builder().startDate(now).build(); + UpcomingEventResponse other = UpcomingEventResponse.builder().startDate(now.plusDays(2)).build(); + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUpcomingEvents(List.of(today, other)); + assertThat(dto.getTodayEventsCount()).isEqualTo(1); + } + + @Test + @DisplayName("exclut les événements dont getIsToday() est null") + void testFiltreIsTodayNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUpcomingEvents(List.of(new EventWithNullIsToday())); + assertThat(dto.getTodayEventsCount()).isEqualTo(0); + } + + @Test + @DisplayName("une liste mixte (null, true, false) compte uniquement les isToday true") + void testFiltreMixteToday() { + LocalDateTime now = LocalDateTime.now(); + UpcomingEventResponse today = UpcomingEventResponse.builder().startDate(now).build(); + UpcomingEventResponse other = UpcomingEventResponse.builder().startDate(now.plusDays(2)).build(); + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUpcomingEvents(List.of(new EventWithNullIsToday(), today, other)); + assertThat(dto.getTodayEventsCount()).isEqualTo(1); + } + } + + @Nested + @DisplayName("getTomorrowEventsCount") + class GetTomorrowEventsCount { + + @Test + @DisplayName("retourne 0 quand upcomingEvents est null") + void testNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUpcomingEvents(null); + assertThat(dto.getTomorrowEventsCount()).isEqualTo(0); + } + + @Test + @DisplayName("compte les événements avec isTomorrow true") + void testCompteTomorrow() { + UpcomingEventResponse tomorrow = UpcomingEventResponse.builder() + .startDate(LocalDateTime.now().plusDays(1)).build(); + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUpcomingEvents(List.of(tomorrow)); + assertThat(dto.getTomorrowEventsCount()).isEqualTo(1); + } + + @Test + @DisplayName("exclut les événements dont getIsTomorrow() est null") + void testFiltreIsTomorrowNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUpcomingEvents(List.of(new EventWithNullIsTomorrow())); + assertThat(dto.getTomorrowEventsCount()).isEqualTo(0); + } + + @Test + @DisplayName("une liste mixte pour demain compte uniquement les isTomorrow true") + void testFiltreMixteTomorrow() { + UpcomingEventResponse tomorrow = UpcomingEventResponse.builder().startDate(LocalDateTime.now().plusDays(1)).build(); + UpcomingEventResponse other = UpcomingEventResponse.builder().startDate(LocalDateTime.now().plusDays(3)).build(); + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUpcomingEvents(List.of(new EventWithNullIsTomorrow(), tomorrow, other)); + assertThat(dto.getTomorrowEventsCount()).isEqualTo(1); + } + } + + @Nested + @DisplayName("getRecentActivitiesCount") + class GetRecentActivitiesCount { + + @Test + @DisplayName("retourne 0 quand recentActivities est null") + void testNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setRecentActivities(null); + assertThat(dto.getRecentActivitiesCount()).isEqualTo(0); + } + + @Test + @DisplayName("compte les activités avec isRecent true") + void testCompteRecent() { + RecentActivityResponse recent = RecentActivityResponse.builder() + .timestamp(LocalDateTime.now().minusHours(1)).build(); + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setRecentActivities(List.of(recent)); + assertThat(dto.getRecentActivitiesCount()).isEqualTo(1); + } + + @Test + @DisplayName("exclut les activités dont getIsRecent() est null") + void testFiltreIsRecentNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setRecentActivities(List.of(new ActivityWithNullIsRecent())); + assertThat(dto.getRecentActivitiesCount()).isEqualTo(0); + } + + @Test + @DisplayName("une liste mixte pour isRecent compte uniquement les isRecent true") + void testFiltreMixteRecent() { + RecentActivityResponse recent = RecentActivityResponse.builder().timestamp(LocalDateTime.now().minusHours(1)).build(); + RecentActivityResponse old = RecentActivityResponse.builder().timestamp(LocalDateTime.now().minusDays(2)).build(); + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setRecentActivities(List.of(new ActivityWithNullIsRecent(), recent, old)); + assertThat(dto.getRecentActivitiesCount()).isEqualTo(1); + } + } + + @Nested + @DisplayName("getTodayActivitiesCount") + class GetTodayActivitiesCount { + + @Test + @DisplayName("retourne 0 quand recentActivities est null") + void testNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setRecentActivities(null); + assertThat(dto.getTodayActivitiesCount()).isEqualTo(0); + } + + @Test + @DisplayName("compte les activités avec isToday true") + void testCompteToday() { + RecentActivityResponse today = RecentActivityResponse.builder() + .timestamp(LocalDateTime.now()).build(); + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setRecentActivities(List.of(today)); + assertThat(dto.getTodayActivitiesCount()).isEqualTo(1); + } + + @Test + @DisplayName("exclut les activités dont getIsToday() est null") + void testFiltreIsTodayNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setRecentActivities(List.of(new ActivityWithNullIsToday())); + assertThat(dto.getTodayActivitiesCount()).isEqualTo(0); + } + + @Test + @DisplayName("une liste mixte pour isToday activité compte uniquement les isToday true") + void testFiltreMixteTodayActivity() { + RecentActivityResponse today = RecentActivityResponse.builder().timestamp(LocalDateTime.now()).build(); + RecentActivityResponse other = RecentActivityResponse.builder().timestamp(LocalDateTime.now().minusDays(1)).build(); + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setRecentActivities(List.of(new ActivityWithNullIsToday(), today, other)); + assertThat(dto.getTodayActivitiesCount()).isEqualTo(1); + } + } + + @Nested + @DisplayName("getHasUpcomingEvents") + class GetHasUpcomingEvents { + + @Test + @DisplayName("retourne false quand upcomingEvents est null") + void testNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUpcomingEvents(null); + assertThat(dto.getHasUpcomingEvents()).isFalse(); + } + + @Test + @DisplayName("retourne false quand upcomingEvents est vide") + void testVide() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUpcomingEvents(List.of()); + assertThat(dto.getHasUpcomingEvents()).isFalse(); + } + + @Test + @DisplayName("retourne true quand upcomingEvents non vide") + void testNonVide() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUpcomingEvents(List.of(UpcomingEventResponse.builder().build())); + assertThat(dto.getHasUpcomingEvents()).isTrue(); + } + } + + @Nested + @DisplayName("getHasRecentActivities") + class GetHasRecentActivities { + + @Test + @DisplayName("retourne false quand recentActivities est null") + void testNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setRecentActivities(null); + assertThat(dto.getHasRecentActivities()).isFalse(); + } + + @Test + @DisplayName("retourne false quand recentActivities est vide") + void testVide() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setRecentActivities(List.of()); + assertThat(dto.getHasRecentActivities()).isFalse(); + } + + @Test + @DisplayName("retourne true quand recentActivities non vide") + void testNonVide() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setRecentActivities(List.of(RecentActivityResponse.builder().build())); + assertThat(dto.getHasRecentActivities()).isTrue(); + } + } + + @Nested + @DisplayName("getThemePreference") + class GetThemePreference { + + @Test + @DisplayName("retourne royal_teal quand userPreferences est null") + void testNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(null); + assertThat(dto.getThemePreference()).isEqualTo("royal_teal"); + } + + @Test + @DisplayName("retourne la valeur theme si présente") + void testAvecTheme() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(Map.of("theme", "dark")); + assertThat(dto.getThemePreference()).isEqualTo("dark"); + } + + @Test + @DisplayName("retourne royal_teal par défaut si theme absent") + void testDefaut() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(Map.of("other", "x")); + assertThat(dto.getThemePreference()).isEqualTo("royal_teal"); + } + } + + @Nested + @DisplayName("getLanguagePreference") + class GetLanguagePreference { + + @Test + @DisplayName("retourne fr quand userPreferences est null") + void testNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(null); + assertThat(dto.getLanguagePreference()).isEqualTo("fr"); + } + + @Test + @DisplayName("retourne la valeur language si présente") + void testAvecLanguage() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(Map.of("language", "en")); + assertThat(dto.getLanguagePreference()).isEqualTo("en"); + } + + @Test + @DisplayName("retourne fr par défaut si language absent") + void testDefaut() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(Map.of()); + assertThat(dto.getLanguagePreference()).isEqualTo("fr"); + } + } + + @Nested + @DisplayName("getNotificationsEnabled") + class GetNotificationsEnabled { + + @Test + @DisplayName("retourne true quand userPreferences est null") + void testNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(null); + assertThat(dto.getNotificationsEnabled()).isTrue(); + } + + @Test + @DisplayName("retourne la valeur notifications si présente") + void testAvecValeur() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(Map.of("notifications", false)); + assertThat(dto.getNotificationsEnabled()).isFalse(); + } + + @Test + @DisplayName("retourne true par défaut si notifications absent") + void testDefaut() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(Map.of()); + assertThat(dto.getNotificationsEnabled()).isTrue(); + } + } + + @Nested + @DisplayName("getAutoRefreshEnabled") + class GetAutoRefreshEnabled { + + @Test + @DisplayName("retourne true quand userPreferences est null") + void testNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(null); + assertThat(dto.getAutoRefreshEnabled()).isTrue(); + } + + @Test + @DisplayName("retourne la valeur autoRefresh si présente") + void testAvecValeur() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(Map.of("autoRefresh", false)); + assertThat(dto.getAutoRefreshEnabled()).isFalse(); + } + } + + @Nested + @DisplayName("getRefreshInterval") + class GetRefreshInterval { + + @Test + @DisplayName("retourne 300 quand userPreferences est null") + void testNull() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(null); + assertThat(dto.getRefreshInterval()).isEqualTo(300); + } + + @Test + @DisplayName("retourne la valeur refreshInterval si présente") + void testAvecValeur() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(Map.of("refreshInterval", 60)); + assertThat(dto.getRefreshInterval()).isEqualTo(60); + } + + @Test + @DisplayName("retourne 300 par défaut si refreshInterval absent") + void testDefaut() { + DashboardDataResponse dto = new DashboardDataResponse(); + dto.setUserPreferences(Map.of()); + assertThat(dto.getRefreshInterval()).isEqualTo(300); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardStatsResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardStatsResponseTest.java index 1a99c3e..40fdd03 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardStatsResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/DashboardStatsResponseTest.java @@ -1,223 +1,223 @@ -package dev.lions.unionflow.server.api.dto.dashboard; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalDateTime; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour DashboardStatsResponse. - * Couvre getFormattedContributionAmount (null, >= 1M, >= 1K, else), - * getHasGrowth, getIsHighEngagement, getInactiveMembers, getActiveMemberPercentage, - * getEngagementPercentage. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests DashboardStatsResponse") -class DashboardStatsResponseTest { - - @Nested - @DisplayName("Constructeur et getters/setters") - class ConstructeurEtGetters { - - @Test - @DisplayName("builder et getters") - void testBuilder() { - DashboardStatsResponse dto = DashboardStatsResponse.builder() - .totalMembers(100) - .activeMembers(80) - .totalEvents(10) - .lastUpdated(LocalDateTime.now()) - .build(); - assertThat(dto.getTotalMembers()).isEqualTo(100); - assertThat(dto.getActiveMembers()).isEqualTo(80); - assertThat(dto.getTotalEvents()).isEqualTo(10); - } - } - - @Nested - @DisplayName("getFormattedContributionAmount") - class GetFormattedContributionAmount { - - @Test - @DisplayName("retourne 0 quand totalContributionAmount est null") - void testNull() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setTotalContributionAmount(null); - assertThat(dto.getFormattedContributionAmount()).isEqualTo("0"); - } - - @Test - @DisplayName("retourne format M quand >= 1_000_000") - void testMillions() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setTotalContributionAmount(2_500_000.0); - String formatted = dto.getFormattedContributionAmount(); - assertThat(formatted).matches("2[.,]5M"); - } - - @Test - @DisplayName("retourne format K quand >= 1_000 et < 1_000_000") - void testMilliers() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setTotalContributionAmount(5_000.0); - assertThat(dto.getFormattedContributionAmount()).isEqualTo("5K"); - } - - @Test - @DisplayName("retourne format entier quand < 1_000") - void testPetitMontant() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setTotalContributionAmount(99.0); - assertThat(dto.getFormattedContributionAmount()).isEqualTo("99"); - } - } - - @Nested - @DisplayName("getHasGrowth") - class GetHasGrowth { - - @Test - @DisplayName("retourne false quand monthlyGrowth est null") - void testNull() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setMonthlyGrowth(null); - assertThat(dto.getHasGrowth()).isFalse(); - } - - @Test - @DisplayName("retourne false quand monthlyGrowth <= 0") - void testZeroOuNegatif() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setMonthlyGrowth(0.0); - assertThat(dto.getHasGrowth()).isFalse(); - dto.setMonthlyGrowth(-1.0); - assertThat(dto.getHasGrowth()).isFalse(); - } - - @Test - @DisplayName("retourne true quand monthlyGrowth > 0") - void testPositif() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setMonthlyGrowth(0.5); - assertThat(dto.getHasGrowth()).isTrue(); - } - } - - @Nested - @DisplayName("getIsHighEngagement") - class GetIsHighEngagement { - - @Test - @DisplayName("retourne false quand engagementRate est null") - void testNull() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setEngagementRate(null); - assertThat(dto.getIsHighEngagement()).isFalse(); - } - - @Test - @DisplayName("retourne false quand engagementRate <= 0.7") - void testFaible() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setEngagementRate(0.5); - assertThat(dto.getIsHighEngagement()).isFalse(); - dto.setEngagementRate(0.7); - assertThat(dto.getIsHighEngagement()).isFalse(); - } - - @Test - @DisplayName("retourne true quand engagementRate > 0.7") - void testEleve() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setEngagementRate(0.85); - assertThat(dto.getIsHighEngagement()).isTrue(); - } - } - - @Nested - @DisplayName("getInactiveMembers") - class GetInactiveMembers { - - @Test - @DisplayName("retourne 0 quand totalMembers ou activeMembers est null") - void testNull() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setTotalMembers(null); - dto.setActiveMembers(10); - assertThat(dto.getInactiveMembers()).isEqualTo(0.0); - dto.setTotalMembers(100); - dto.setActiveMembers(null); - assertThat(dto.getInactiveMembers()).isEqualTo(0.0); - } - - @Test - @DisplayName("retourne totalMembers - activeMembers") - void testCalcul() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setTotalMembers(100); - dto.setActiveMembers(30); - assertThat(dto.getInactiveMembers()).isEqualTo(70.0); - } - } - - @Nested - @DisplayName("getActiveMemberPercentage") - class GetActiveMemberPercentage { - - @Test - @DisplayName("retourne 0 quand totalMembers ou activeMembers est null") - void testNull() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setTotalMembers(null); - dto.setActiveMembers(50); - assertThat(dto.getActiveMemberPercentage()).isEqualTo(0.0); - dto.setTotalMembers(100); - dto.setActiveMembers(null); - assertThat(dto.getActiveMemberPercentage()).isEqualTo(0.0); - } - - @Test - @DisplayName("retourne 0 quand totalMembers est 0") - void testTotalZero() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setTotalMembers(0); - dto.setActiveMembers(0); - assertThat(dto.getActiveMemberPercentage()).isEqualTo(0.0); - } - - @Test - @DisplayName("retourne le pourcentage actif") - void testPourcentage() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setTotalMembers(100); - dto.setActiveMembers(25); - assertThat(dto.getActiveMemberPercentage()).isEqualTo(25.0); - } - } - - @Nested - @DisplayName("getEngagementPercentage") - class GetEngagementPercentage { - - @Test - @DisplayName("retourne 0 quand engagementRate est null") - void testNull() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setEngagementRate(null); - assertThat(dto.getEngagementPercentage()).isEqualTo(0.0); - } - - @Test - @DisplayName("retourne engagementRate * 100") - void testCalcul() { - DashboardStatsResponse dto = new DashboardStatsResponse(); - dto.setEngagementRate(0.75); - assertThat(dto.getEngagementPercentage()).isEqualTo(75.0); - } - } -} +package dev.lions.unionflow.server.api.dto.dashboard; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalDateTime; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour DashboardStatsResponse. + * Couvre getFormattedContributionAmount (null, >= 1M, >= 1K, else), + * getHasGrowth, getIsHighEngagement, getInactiveMembers, getActiveMemberPercentage, + * getEngagementPercentage. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests DashboardStatsResponse") +class DashboardStatsResponseTest { + + @Nested + @DisplayName("Constructeur et getters/setters") + class ConstructeurEtGetters { + + @Test + @DisplayName("builder et getters") + void testBuilder() { + DashboardStatsResponse dto = DashboardStatsResponse.builder() + .totalMembers(100) + .activeMembers(80) + .totalEvents(10) + .lastUpdated(LocalDateTime.now()) + .build(); + assertThat(dto.getTotalMembers()).isEqualTo(100); + assertThat(dto.getActiveMembers()).isEqualTo(80); + assertThat(dto.getTotalEvents()).isEqualTo(10); + } + } + + @Nested + @DisplayName("getFormattedContributionAmount") + class GetFormattedContributionAmount { + + @Test + @DisplayName("retourne 0 quand totalContributionAmount est null") + void testNull() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setTotalContributionAmount(null); + assertThat(dto.getFormattedContributionAmount()).isEqualTo("0"); + } + + @Test + @DisplayName("retourne format M quand >= 1_000_000") + void testMillions() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setTotalContributionAmount(2_500_000.0); + String formatted = dto.getFormattedContributionAmount(); + assertThat(formatted).matches("2[.,]5M"); + } + + @Test + @DisplayName("retourne format K quand >= 1_000 et < 1_000_000") + void testMilliers() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setTotalContributionAmount(5_000.0); + assertThat(dto.getFormattedContributionAmount()).isEqualTo("5K"); + } + + @Test + @DisplayName("retourne format entier quand < 1_000") + void testPetitMontant() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setTotalContributionAmount(99.0); + assertThat(dto.getFormattedContributionAmount()).isEqualTo("99"); + } + } + + @Nested + @DisplayName("getHasGrowth") + class GetHasGrowth { + + @Test + @DisplayName("retourne false quand monthlyGrowth est null") + void testNull() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setMonthlyGrowth(null); + assertThat(dto.getHasGrowth()).isFalse(); + } + + @Test + @DisplayName("retourne false quand monthlyGrowth <= 0") + void testZeroOuNegatif() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setMonthlyGrowth(0.0); + assertThat(dto.getHasGrowth()).isFalse(); + dto.setMonthlyGrowth(-1.0); + assertThat(dto.getHasGrowth()).isFalse(); + } + + @Test + @DisplayName("retourne true quand monthlyGrowth > 0") + void testPositif() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setMonthlyGrowth(0.5); + assertThat(dto.getHasGrowth()).isTrue(); + } + } + + @Nested + @DisplayName("getIsHighEngagement") + class GetIsHighEngagement { + + @Test + @DisplayName("retourne false quand engagementRate est null") + void testNull() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setEngagementRate(null); + assertThat(dto.getIsHighEngagement()).isFalse(); + } + + @Test + @DisplayName("retourne false quand engagementRate <= 0.7") + void testFaible() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setEngagementRate(0.5); + assertThat(dto.getIsHighEngagement()).isFalse(); + dto.setEngagementRate(0.7); + assertThat(dto.getIsHighEngagement()).isFalse(); + } + + @Test + @DisplayName("retourne true quand engagementRate > 0.7") + void testEleve() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setEngagementRate(0.85); + assertThat(dto.getIsHighEngagement()).isTrue(); + } + } + + @Nested + @DisplayName("getInactiveMembers") + class GetInactiveMembers { + + @Test + @DisplayName("retourne 0 quand totalMembers ou activeMembers est null") + void testNull() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setTotalMembers(null); + dto.setActiveMembers(10); + assertThat(dto.getInactiveMembers()).isEqualTo(0.0); + dto.setTotalMembers(100); + dto.setActiveMembers(null); + assertThat(dto.getInactiveMembers()).isEqualTo(0.0); + } + + @Test + @DisplayName("retourne totalMembers - activeMembers") + void testCalcul() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setTotalMembers(100); + dto.setActiveMembers(30); + assertThat(dto.getInactiveMembers()).isEqualTo(70.0); + } + } + + @Nested + @DisplayName("getActiveMemberPercentage") + class GetActiveMemberPercentage { + + @Test + @DisplayName("retourne 0 quand totalMembers ou activeMembers est null") + void testNull() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setTotalMembers(null); + dto.setActiveMembers(50); + assertThat(dto.getActiveMemberPercentage()).isEqualTo(0.0); + dto.setTotalMembers(100); + dto.setActiveMembers(null); + assertThat(dto.getActiveMemberPercentage()).isEqualTo(0.0); + } + + @Test + @DisplayName("retourne 0 quand totalMembers est 0") + void testTotalZero() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setTotalMembers(0); + dto.setActiveMembers(0); + assertThat(dto.getActiveMemberPercentage()).isEqualTo(0.0); + } + + @Test + @DisplayName("retourne le pourcentage actif") + void testPourcentage() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setTotalMembers(100); + dto.setActiveMembers(25); + assertThat(dto.getActiveMemberPercentage()).isEqualTo(25.0); + } + } + + @Nested + @DisplayName("getEngagementPercentage") + class GetEngagementPercentage { + + @Test + @DisplayName("retourne 0 quand engagementRate est null") + void testNull() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setEngagementRate(null); + assertThat(dto.getEngagementPercentage()).isEqualTo(0.0); + } + + @Test + @DisplayName("retourne engagementRate * 100") + void testCalcul() { + DashboardStatsResponse dto = new DashboardStatsResponse(); + dto.setEngagementRate(0.75); + assertThat(dto.getEngagementPercentage()).isEqualTo(75.0); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/RecentActivityResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/RecentActivityResponseTest.java index cd68b28..4790753 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/RecentActivityResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/RecentActivityResponseTest.java @@ -1,213 +1,213 @@ -package dev.lions.unionflow.server.api.dto.dashboard; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalDateTime; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour RecentActivityResponse. - * Couvre getTimeAgo (toutes branches), getActivityIcon, getActivityColor, getIsRecent, getIsToday. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests RecentActivityResponse") -class RecentActivityResponseTest { - - @Nested - @DisplayName("getTimeAgo") - class GetTimeAgo { - - @Test - @DisplayName("retourne chaîne vide quand timestamp null") - void testNull() { - RecentActivityResponse dto = RecentActivityResponse.builder().build(); - assertThat(dto.getTimeAgo()).isEmpty(); - } - - @Test - @DisplayName("retourne Xmin quand moins de 60 minutes") - void testMinutes() { - RecentActivityResponse dto = RecentActivityResponse.builder() - .timestamp(LocalDateTime.now().minusMinutes(30)).build(); - assertThat(dto.getTimeAgo()).isEqualTo("30min"); - } - - @Test - @DisplayName("retourne Xh quand moins de 24h") - void testHeures() { - RecentActivityResponse dto = RecentActivityResponse.builder() - .timestamp(LocalDateTime.now().minusHours(5)).build(); - assertThat(dto.getTimeAgo()).isEqualTo("5h"); - } - - @Test - @DisplayName("retourne Xj quand moins de 7 jours") - void testJours() { - RecentActivityResponse dto = RecentActivityResponse.builder() - .timestamp(LocalDateTime.now().minusDays(3)).build(); - assertThat(dto.getTimeAgo()).isEqualTo("3j"); - } - - @Test - @DisplayName("retourne Xsem quand 7 jours ou plus") - void testSemaines() { - RecentActivityResponse dto = RecentActivityResponse.builder() - .timestamp(LocalDateTime.now().minusDays(14)).build(); - assertThat(dto.getTimeAgo()).isEqualTo("2sem"); - } - } - - @Nested - @DisplayName("getActivityIcon") - class GetActivityIcon { - - @Test - @DisplayName("retourne help_outline quand type null") - void testNull() { - RecentActivityResponse dto = RecentActivityResponse.builder().build(); - assertThat(dto.getActivityIcon()).isEqualTo("help_outline"); - } - - @Test - @DisplayName("retourne icône selon type member, event, contribution, organization, system") - void testIcons() { - assertThat(RecentActivityResponse.builder().type("member").build().getActivityIcon()).isEqualTo("person"); - assertThat(RecentActivityResponse.builder().type("event").build().getActivityIcon()).isEqualTo("event"); - assertThat(RecentActivityResponse.builder().type("contribution").build().getActivityIcon()).isEqualTo("payment"); - assertThat(RecentActivityResponse.builder().type("organization").build().getActivityIcon()).isEqualTo("business"); - assertThat(RecentActivityResponse.builder().type("system").build().getActivityIcon()).isEqualTo("settings"); - } - - @Test - @DisplayName("retourne info pour type inconnu") - void testDefault() { - RecentActivityResponse dto = RecentActivityResponse.builder().type("other").build(); - assertThat(dto.getActivityIcon()).isEqualTo("info"); - } - - @Test - @DisplayName("type insensible à la casse") - void testCaseInsensitive() { - assertThat(RecentActivityResponse.builder().type("MEMBER").build().getActivityIcon()).isEqualTo("person"); - } - } - - @Nested - @DisplayName("getActivityColor") - class GetActivityColor { - - @Test - @DisplayName("retourne grey quand type null") - void testNull() { - RecentActivityResponse dto = RecentActivityResponse.builder().build(); - assertThat(dto.getActivityColor()).isEqualTo("#6B7280"); - } - - @Test - @DisplayName("retourne couleur selon type") - void testCouleurs() { - assertThat(RecentActivityResponse.builder().type("member").build().getActivityColor()).isEqualTo("#10B981"); - assertThat(RecentActivityResponse.builder().type("event").build().getActivityColor()).isEqualTo("#3B82F6"); - assertThat(RecentActivityResponse.builder().type("contribution").build().getActivityColor()).isEqualTo("#008B8B"); - assertThat(RecentActivityResponse.builder().type("organization").build().getActivityColor()).isEqualTo("#4169E1"); - assertThat(RecentActivityResponse.builder().type("system").build().getActivityColor()).isEqualTo("#6B7280"); - } - - @Test - @DisplayName("retourne grey pour type inconnu") - void testDefault() { - RecentActivityResponse dto = RecentActivityResponse.builder().type("other").build(); - assertThat(dto.getActivityColor()).isEqualTo("#6B7280"); - } - } - - @Nested - @DisplayName("getIsRecent") - class GetIsRecent { - - @Test - @DisplayName("retourne false quand timestamp null") - void testNull() { - RecentActivityResponse dto = RecentActivityResponse.builder().build(); - assertThat(dto.getIsRecent()).isFalse(); - } - - @Test - @DisplayName("retourne true quand moins de 24h") - void testRecent() { - RecentActivityResponse dto = RecentActivityResponse.builder() - .timestamp(LocalDateTime.now().minusHours(2)).build(); - assertThat(dto.getIsRecent()).isTrue(); - } - - @Test - @DisplayName("retourne false quand plus de 24h") - void testNotRecent() { - RecentActivityResponse dto = RecentActivityResponse.builder() - .timestamp(LocalDateTime.now().minusHours(25)).build(); - assertThat(dto.getIsRecent()).isFalse(); - } - } - - @Nested - @DisplayName("getIsToday") - class GetIsToday { - - @Test - @DisplayName("retourne false quand timestamp null") - void testNull() { - RecentActivityResponse dto = RecentActivityResponse.builder().build(); - assertThat(dto.getIsToday()).isFalse(); - } - - @Test - @DisplayName("retourne true quand timestamp aujourd'hui") - void testToday() { - RecentActivityResponse dto = RecentActivityResponse.builder() - .timestamp(LocalDateTime.now()).build(); - assertThat(dto.getIsToday()).isTrue(); - } - - @Test - @DisplayName("retourne false quand timestamp autre jour") - void testOtherDay() { - RecentActivityResponse dto = RecentActivityResponse.builder() - .timestamp(LocalDateTime.now().minusDays(1)).build(); - assertThat(dto.getIsToday()).isFalse(); - } - } - - @Nested - @DisplayName("Getters standards") - class GettersStandards { - - @Test - @DisplayName("tous les champs builder sont accessibles") - void testBuilderGetters() { - LocalDateTime ts = LocalDateTime.now(); - RecentActivityResponse dto = RecentActivityResponse.builder() - .id("act1") - .type("event") - .title("Titre") - .description("Desc") - .userName("User") - .timestamp(ts) - .userAvatar("http://avatar") - .actionUrl("http://action") - .build(); - assertThat(dto.getId()).isEqualTo("act1"); - assertThat(dto.getType()).isEqualTo("event"); - assertThat(dto.getTitle()).isEqualTo("Titre"); - assertThat(dto.getDescription()).isEqualTo("Desc"); - assertThat(dto.getUserName()).isEqualTo("User"); - assertThat(dto.getTimestamp()).isEqualTo(ts); - assertThat(dto.getUserAvatar()).isEqualTo("http://avatar"); - assertThat(dto.getActionUrl()).isEqualTo("http://action"); - } - } -} +package dev.lions.unionflow.server.api.dto.dashboard; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalDateTime; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour RecentActivityResponse. + * Couvre getTimeAgo (toutes branches), getActivityIcon, getActivityColor, getIsRecent, getIsToday. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests RecentActivityResponse") +class RecentActivityResponseTest { + + @Nested + @DisplayName("getTimeAgo") + class GetTimeAgo { + + @Test + @DisplayName("retourne chaîne vide quand timestamp null") + void testNull() { + RecentActivityResponse dto = RecentActivityResponse.builder().build(); + assertThat(dto.getTimeAgo()).isEmpty(); + } + + @Test + @DisplayName("retourne Xmin quand moins de 60 minutes") + void testMinutes() { + RecentActivityResponse dto = RecentActivityResponse.builder() + .timestamp(LocalDateTime.now().minusMinutes(30)).build(); + assertThat(dto.getTimeAgo()).isEqualTo("30min"); + } + + @Test + @DisplayName("retourne Xh quand moins de 24h") + void testHeures() { + RecentActivityResponse dto = RecentActivityResponse.builder() + .timestamp(LocalDateTime.now().minusHours(5)).build(); + assertThat(dto.getTimeAgo()).isEqualTo("5h"); + } + + @Test + @DisplayName("retourne Xj quand moins de 7 jours") + void testJours() { + RecentActivityResponse dto = RecentActivityResponse.builder() + .timestamp(LocalDateTime.now().minusDays(3)).build(); + assertThat(dto.getTimeAgo()).isEqualTo("3j"); + } + + @Test + @DisplayName("retourne Xsem quand 7 jours ou plus") + void testSemaines() { + RecentActivityResponse dto = RecentActivityResponse.builder() + .timestamp(LocalDateTime.now().minusDays(14)).build(); + assertThat(dto.getTimeAgo()).isEqualTo("2sem"); + } + } + + @Nested + @DisplayName("getActivityIcon") + class GetActivityIcon { + + @Test + @DisplayName("retourne help_outline quand type null") + void testNull() { + RecentActivityResponse dto = RecentActivityResponse.builder().build(); + assertThat(dto.getActivityIcon()).isEqualTo("help_outline"); + } + + @Test + @DisplayName("retourne icône selon type member, event, contribution, organization, system") + void testIcons() { + assertThat(RecentActivityResponse.builder().type("member").build().getActivityIcon()).isEqualTo("person"); + assertThat(RecentActivityResponse.builder().type("event").build().getActivityIcon()).isEqualTo("event"); + assertThat(RecentActivityResponse.builder().type("contribution").build().getActivityIcon()).isEqualTo("payment"); + assertThat(RecentActivityResponse.builder().type("organization").build().getActivityIcon()).isEqualTo("business"); + assertThat(RecentActivityResponse.builder().type("system").build().getActivityIcon()).isEqualTo("settings"); + } + + @Test + @DisplayName("retourne info pour type inconnu") + void testDefault() { + RecentActivityResponse dto = RecentActivityResponse.builder().type("other").build(); + assertThat(dto.getActivityIcon()).isEqualTo("info"); + } + + @Test + @DisplayName("type insensible à la casse") + void testCaseInsensitive() { + assertThat(RecentActivityResponse.builder().type("MEMBER").build().getActivityIcon()).isEqualTo("person"); + } + } + + @Nested + @DisplayName("getActivityColor") + class GetActivityColor { + + @Test + @DisplayName("retourne grey quand type null") + void testNull() { + RecentActivityResponse dto = RecentActivityResponse.builder().build(); + assertThat(dto.getActivityColor()).isEqualTo("#6B7280"); + } + + @Test + @DisplayName("retourne couleur selon type") + void testCouleurs() { + assertThat(RecentActivityResponse.builder().type("member").build().getActivityColor()).isEqualTo("#10B981"); + assertThat(RecentActivityResponse.builder().type("event").build().getActivityColor()).isEqualTo("#3B82F6"); + assertThat(RecentActivityResponse.builder().type("contribution").build().getActivityColor()).isEqualTo("#008B8B"); + assertThat(RecentActivityResponse.builder().type("organization").build().getActivityColor()).isEqualTo("#4169E1"); + assertThat(RecentActivityResponse.builder().type("system").build().getActivityColor()).isEqualTo("#6B7280"); + } + + @Test + @DisplayName("retourne grey pour type inconnu") + void testDefault() { + RecentActivityResponse dto = RecentActivityResponse.builder().type("other").build(); + assertThat(dto.getActivityColor()).isEqualTo("#6B7280"); + } + } + + @Nested + @DisplayName("getIsRecent") + class GetIsRecent { + + @Test + @DisplayName("retourne false quand timestamp null") + void testNull() { + RecentActivityResponse dto = RecentActivityResponse.builder().build(); + assertThat(dto.getIsRecent()).isFalse(); + } + + @Test + @DisplayName("retourne true quand moins de 24h") + void testRecent() { + RecentActivityResponse dto = RecentActivityResponse.builder() + .timestamp(LocalDateTime.now().minusHours(2)).build(); + assertThat(dto.getIsRecent()).isTrue(); + } + + @Test + @DisplayName("retourne false quand plus de 24h") + void testNotRecent() { + RecentActivityResponse dto = RecentActivityResponse.builder() + .timestamp(LocalDateTime.now().minusHours(25)).build(); + assertThat(dto.getIsRecent()).isFalse(); + } + } + + @Nested + @DisplayName("getIsToday") + class GetIsToday { + + @Test + @DisplayName("retourne false quand timestamp null") + void testNull() { + RecentActivityResponse dto = RecentActivityResponse.builder().build(); + assertThat(dto.getIsToday()).isFalse(); + } + + @Test + @DisplayName("retourne true quand timestamp aujourd'hui") + void testToday() { + RecentActivityResponse dto = RecentActivityResponse.builder() + .timestamp(LocalDateTime.now()).build(); + assertThat(dto.getIsToday()).isTrue(); + } + + @Test + @DisplayName("retourne false quand timestamp autre jour") + void testOtherDay() { + RecentActivityResponse dto = RecentActivityResponse.builder() + .timestamp(LocalDateTime.now().minusDays(1)).build(); + assertThat(dto.getIsToday()).isFalse(); + } + } + + @Nested + @DisplayName("Getters standards") + class GettersStandards { + + @Test + @DisplayName("tous les champs builder sont accessibles") + void testBuilderGetters() { + LocalDateTime ts = LocalDateTime.now(); + RecentActivityResponse dto = RecentActivityResponse.builder() + .id("act1") + .type("event") + .title("Titre") + .description("Desc") + .userName("User") + .timestamp(ts) + .userAvatar("http://avatar") + .actionUrl("http://action") + .build(); + assertThat(dto.getId()).isEqualTo("act1"); + assertThat(dto.getType()).isEqualTo("event"); + assertThat(dto.getTitle()).isEqualTo("Titre"); + assertThat(dto.getDescription()).isEqualTo("Desc"); + assertThat(dto.getUserName()).isEqualTo("User"); + assertThat(dto.getTimestamp()).isEqualTo(ts); + assertThat(dto.getUserAvatar()).isEqualTo("http://avatar"); + assertThat(dto.getActionUrl()).isEqualTo("http://action"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/UpcomingEventResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/UpcomingEventResponseTest.java index d7f5a64..788b119 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/UpcomingEventResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/dashboard/UpcomingEventResponseTest.java @@ -1,443 +1,443 @@ -package dev.lions.unionflow.server.api.dto.dashboard; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalDate; -import java.time.LocalDateTime; -import java.util.List; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour UpcomingEventResponse. - * Couvre getDaysUntilEvent (toutes branches), getFillPercentage, getIsFull, getIsAlmostFull, - * getIsToday, getIsTomorrow, getStatusColor, getStatusLabel, getAvailableSpots, getParticipationSummary. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests UpcomingEventResponse") -class UpcomingEventResponseTest { - - @Nested - @DisplayName("getDaysUntilEvent") - class GetDaysUntilEvent { - - @Test - @DisplayName("retourne chaîne vide quand startDate est null") - void testStartDateNull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); - assertThat(dto.getDaysUntilEvent()).isEmpty(); - } - - @Test - @DisplayName("retourne En cours quand événement aujourd'hui déjà commencé (now fixe pour éviter passage à minuit)") - void testEnCours() { - LocalDateTime now = LocalDateTime.of(2025, 6, 10, 14, 0); - LocalDateTime startDate = now.minusHours(1); // même jour, commencé il y a 1 h - UpcomingEventResponse dto = UpcomingEventResponse.builder().startDate(startDate).build(); - assertThat(dto.getDaysUntilEvent(now)).isEqualTo("En cours"); - } - - @Test - @DisplayName("retourne En cours quand startDate est la veille (days < 0)") - void testEnCoursStartDateHier() { - LocalDateTime now = LocalDateTime.of(2025, 6, 10, 0, 30); - LocalDateTime startDate = LocalDateTime.of(2025, 6, 9, 23, 0); // veille 23h - UpcomingEventResponse dto = UpcomingEventResponse.builder().startDate(startDate).build(); - assertThat(dto.getDaysUntilEvent(now)).isEqualTo("En cours"); - } - - @Test - @DisplayName("retourne Bientôt quand aujourd'hui dans moins de 2h (now fixe pour éviter passage à minuit)") - void testBientot() { - LocalDateTime now = LocalDateTime.of(2025, 6, 10, 14, 0); - LocalDateTime startDate = now.plusMinutes(30); - UpcomingEventResponse dto = UpcomingEventResponse.builder().startDate(startDate).build(); - assertThat(dto.getDaysUntilEvent(now)).isEqualTo("Bientôt"); - } - - @Test - @DisplayName("retourne Aujourd'hui quand aujourd'hui dans plus de 2h") - void testAujourdhui() { - // Date fixe « aujourd'hui » à 15h pour éviter la dépendance à l'heure d'exécution - // (now().plusHours(5) peut tomber le lendemain après 19h et renvoyer « Demain ») - LocalDateTime now = LocalDateTime.now(); - LocalDateTime startDate = LocalDate.now().atTime(15, 0); - UpcomingEventResponse dto = UpcomingEventResponse.builder().startDate(startDate).build(); - // Utiliser le même 'now' capturé pour éviter les décalages temporels - String result = dto.getDaysUntilEvent(now); - // Selon l'heure d'exécution : >= 2h dans le futur → Aujourd'hui, < 2h → Bientôt, passé → En cours - boolean atLeast2hFromNow = !startDate.isBefore(now.plusHours(2)); - boolean inFuture = startDate.isAfter(now); - if (atLeast2hFromNow) { - assertThat(result).isEqualTo("Aujourd'hui"); - } else if (inFuture) { - assertThat(result).isEqualTo("Bientôt"); - } else { - assertThat(result).isEqualTo("En cours"); - } - } - - @Test - @DisplayName("retourne Aujourd'hui quand même jour et plus de 2h dans le futur (appel avec now fixe pour couverture Jacoco)") - void testAujourdhuiAvecNowFixe() { - LocalDateTime now = LocalDateTime.of(2025, 6, 10, 10, 0); - LocalDateTime startDate = LocalDateTime.of(2025, 6, 10, 15, 0); - UpcomingEventResponse dto = UpcomingEventResponse.builder().startDate(startDate).build(); - assertThat(dto.getDaysUntilEvent(now)).isEqualTo("Aujourd'hui"); - } - - @Test - @DisplayName("retourne Demain quand startDate est demain") - void testDemain() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .startDate(LocalDateTime.now().plusDays(1)).build(); - assertThat(dto.getDaysUntilEvent()).isEqualTo("Demain"); - } - - @Test - @DisplayName("retourne Dans X jours quand moins de 7 jours") - void testDansJours() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .startDate(LocalDateTime.now().plusDays(3)).build(); - assertThat(dto.getDaysUntilEvent()).isEqualTo("Dans 3 jours"); - } - - @Test - @DisplayName("retourne Dans 1 semaine quand 7 jours ou plus (jours < 7 false)") - void testUneSemaine() { - LocalDateTime now = LocalDateTime.now(); - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .startDate(now.plusDays(8)).build(); - String result = dto.getDaysUntilEvent(); - assertThat(result).isEqualTo("Dans 1 semaine"); - } - - @Test - @DisplayName("retourne Dans X semaines quand au moins 14 jours") - void testSemaines() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .startDate(LocalDateTime.now().plusDays(15)).build(); - assertThat(dto.getDaysUntilEvent()).isEqualTo("Dans 2 semaines"); - } - } - - @Nested - @DisplayName("getFillPercentage") - class GetFillPercentage { - - @Test - @DisplayName("retourne 0 quand maxParticipants ou currentParticipants est null") - void testNull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().maxParticipants(10).build(); - assertThat(dto.getFillPercentage()).isEqualTo(0.0); - dto.setCurrentParticipants(5); - dto.setMaxParticipants(null); - assertThat(dto.getFillPercentage()).isEqualTo(0.0); - } - - @Test - @DisplayName("retourne 0 quand maxParticipants est 0") - void testMaxZero() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .maxParticipants(0).currentParticipants(0).build(); - assertThat(dto.getFillPercentage()).isEqualTo(0.0); - } - - @Test - @DisplayName("retourne le pourcentage de remplissage") - void testPourcentage() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .maxParticipants(10).currentParticipants(4).build(); - assertThat(dto.getFillPercentage()).isEqualTo(40.0); - } - } - - @Nested - @DisplayName("getIsFull") - class GetIsFull { - - @Test - @DisplayName("retourne false quand max ou current null") - void testNull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); - assertThat(dto.getIsFull()).isFalse(); - } - - @Test - @DisplayName("retourne false quand maxParticipants défini mais currentParticipants null") - void testMaxDefinitCurrentNull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .maxParticipants(10) - .build(); - assertThat(dto.getIsFull()).isFalse(); - } - - @Test - @DisplayName("retourne true quand current >= max") - void testFull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .maxParticipants(5).currentParticipants(5).build(); - assertThat(dto.getIsFull()).isTrue(); - } - - @Test - @DisplayName("retourne false quand current < max") - void testNotFull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .maxParticipants(5).currentParticipants(3).build(); - assertThat(dto.getIsFull()).isFalse(); - } - } - - @Nested - @DisplayName("getIsAlmostFull") - class GetIsAlmostFull { - - @Test - @DisplayName("retourne true quand fillPercentage entre 80 et 100") - void testAlmostFull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .maxParticipants(10).currentParticipants(9).build(); - assertThat(dto.getIsAlmostFull()).isTrue(); - } - - @Test - @DisplayName("retourne false quand fillPercentage < 80") - void testNotAlmostFull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .maxParticipants(10).currentParticipants(5).build(); - assertThat(dto.getIsAlmostFull()).isFalse(); - } - - @Test - @DisplayName("retourne false quand fillPercentage 100") - void testFullNotAlmostFull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .maxParticipants(10).currentParticipants(10).build(); - assertThat(dto.getIsAlmostFull()).isFalse(); - } - } - - @Nested - @DisplayName("getIsToday et getIsTomorrow") - class GetIsTodayTomorrow { - - @Test - @DisplayName("getIsToday retourne false quand startDate null") - void testIsTodayNull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); - assertThat(dto.getIsToday()).isFalse(); - } - - @Test - @DisplayName("getIsToday retourne true quand startDate aujourd'hui") - void testIsTodayTrue() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .startDate(LocalDateTime.now()).build(); - assertThat(dto.getIsToday()).isTrue(); - } - - @Test - @DisplayName("getIsTomorrow retourne false quand startDate null") - void testIsTomorrowNull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); - assertThat(dto.getIsTomorrow()).isFalse(); - } - - @Test - @DisplayName("getIsTomorrow retourne true quand startDate demain") - void testIsTomorrowTrue() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .startDate(LocalDateTime.now().plusDays(1)).build(); - assertThat(dto.getIsTomorrow()).isTrue(); - } - } - - @Nested - @DisplayName("getStatusColor") - class GetStatusColor { - - @Test - @DisplayName("retourne grey quand status null") - void testNull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); - assertThat(dto.getStatusColor()).isEqualTo("#6B7280"); - } - - @Test - @DisplayName("retourne couleur selon status confirmed") - void testConfirmed() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().status("confirmed").build(); - assertThat(dto.getStatusColor()).isEqualTo("#10B981"); - } - - @Test - @DisplayName("retourne couleur selon status open") - void testOpen() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().status("open").build(); - assertThat(dto.getStatusColor()).isEqualTo("#3B82F6"); - } - - @Test - @DisplayName("retourne couleur selon status cancelled") - void testCancelled() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().status("cancelled").build(); - assertThat(dto.getStatusColor()).isEqualTo("#EF4444"); - } - - @Test - @DisplayName("retourne couleur selon status postponed") - void testPostponed() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().status("postponed").build(); - assertThat(dto.getStatusColor()).isEqualTo("#F59E0B"); - } - - @Test - @DisplayName("retourne grey pour status inconnu") - void testDefault() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().status("unknown").build(); - assertThat(dto.getStatusColor()).isEqualTo("#6B7280"); - } - - @Test - @DisplayName("status insensible à la casse") - void testCaseInsensitive() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().status("CONFIRMED").build(); - assertThat(dto.getStatusColor()).isEqualTo("#10B981"); - } - } - - @Nested - @DisplayName("getStatusLabel") - class GetStatusLabel { - - @Test - @DisplayName("retourne Inconnu quand status null") - void testNull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); - assertThat(dto.getStatusLabel()).isEqualTo("Inconnu"); - } - - @Test - @DisplayName("retourne libellé pour confirmed, open, cancelled, postponed") - void testLabels() { - assertThat(UpcomingEventResponse.builder().status("confirmed").build().getStatusLabel()).isEqualTo("Confirmé"); - assertThat(UpcomingEventResponse.builder().status("open").build().getStatusLabel()).isEqualTo("Ouvert"); - assertThat(UpcomingEventResponse.builder().status("cancelled").build().getStatusLabel()).isEqualTo("Annulé"); - assertThat(UpcomingEventResponse.builder().status("postponed").build().getStatusLabel()).isEqualTo("Reporté"); - } - - @Test - @DisplayName("retourne status tel quel pour valeur inconnue") - void testDefault() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().status("custom").build(); - assertThat(dto.getStatusLabel()).isEqualTo("custom"); - } - } - - @Nested - @DisplayName("getAvailableSpots") - class GetAvailableSpots { - - @Test - @DisplayName("retourne 0 quand max ou current null") - void testNull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); - assertThat(dto.getAvailableSpots()).isEqualTo(0); - } - - @Test - @DisplayName("retourne 0 quand maxParticipants défini mais currentParticipants null") - void testMaxDefinitCurrentNull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .maxParticipants(10) - .build(); - assertThat(dto.getAvailableSpots()).isEqualTo(0); - } - - @Test - @DisplayName("retourne max - current") - void testCalcul() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .maxParticipants(10).currentParticipants(7).build(); - assertThat(dto.getAvailableSpots()).isEqualTo(3); - } - - @Test - @DisplayName("retourne 0 quand current > max (Math.max)") - void testNegatif() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .maxParticipants(5).currentParticipants(10).build(); - assertThat(dto.getAvailableSpots()).isEqualTo(0); - } - } - - @Nested - @DisplayName("getParticipationSummary") - class GetParticipationSummary { - - @Test - @DisplayName("retourne 0/0 quand max ou current null") - void testNull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); - assertThat(dto.getParticipationSummary()).isEqualTo("0/0 participants"); - } - - @Test - @DisplayName("retourne 0/0 quand maxParticipants défini mais currentParticipants null") - void testMaxDefinitCurrentNull() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .maxParticipants(20) - .build(); - assertThat(dto.getParticipationSummary()).isEqualTo("0/0 participants"); - } - - @Test - @DisplayName("retourne current/max participants") - void testSummary() { - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .maxParticipants(20).currentParticipants(12).build(); - assertThat(dto.getParticipationSummary()).isEqualTo("12/20 participants"); - } - } - - @Nested - @DisplayName("Getters standards") - class GettersStandards { - - @Test - @DisplayName("tous les champs builder sont accessibles") - void testBuilderGetters() { - LocalDateTime start = LocalDateTime.now(); - LocalDateTime end = start.plusHours(2); - UpcomingEventResponse dto = UpcomingEventResponse.builder() - .id("ev1") - .title("Titre") - .description("Desc") - .startDate(start) - .endDate(end) - .location("Paris") - .maxParticipants(50) - .currentParticipants(10) - .status("open") - .imageUrl("http://img") - .tags(List.of("a", "b")) - .build(); - assertThat(dto.getId()).isEqualTo("ev1"); - assertThat(dto.getTitle()).isEqualTo("Titre"); - assertThat(dto.getDescription()).isEqualTo("Desc"); - assertThat(dto.getStartDate()).isEqualTo(start); - assertThat(dto.getEndDate()).isEqualTo(end); - assertThat(dto.getLocation()).isEqualTo("Paris"); - assertThat(dto.getMaxParticipants()).isEqualTo(50); - assertThat(dto.getCurrentParticipants()).isEqualTo(10); - assertThat(dto.getStatus()).isEqualTo("open"); - assertThat(dto.getImageUrl()).isEqualTo("http://img"); - assertThat(dto.getTags()).containsExactly("a", "b"); - } - } -} +package dev.lions.unionflow.server.api.dto.dashboard; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.util.List; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour UpcomingEventResponse. + * Couvre getDaysUntilEvent (toutes branches), getFillPercentage, getIsFull, getIsAlmostFull, + * getIsToday, getIsTomorrow, getStatusColor, getStatusLabel, getAvailableSpots, getParticipationSummary. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests UpcomingEventResponse") +class UpcomingEventResponseTest { + + @Nested + @DisplayName("getDaysUntilEvent") + class GetDaysUntilEvent { + + @Test + @DisplayName("retourne chaîne vide quand startDate est null") + void testStartDateNull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); + assertThat(dto.getDaysUntilEvent()).isEmpty(); + } + + @Test + @DisplayName("retourne En cours quand événement aujourd'hui déjà commencé (now fixe pour éviter passage à minuit)") + void testEnCours() { + LocalDateTime now = LocalDateTime.of(2025, 6, 10, 14, 0); + LocalDateTime startDate = now.minusHours(1); // même jour, commencé il y a 1 h + UpcomingEventResponse dto = UpcomingEventResponse.builder().startDate(startDate).build(); + assertThat(dto.getDaysUntilEvent(now)).isEqualTo("En cours"); + } + + @Test + @DisplayName("retourne En cours quand startDate est la veille (days < 0)") + void testEnCoursStartDateHier() { + LocalDateTime now = LocalDateTime.of(2025, 6, 10, 0, 30); + LocalDateTime startDate = LocalDateTime.of(2025, 6, 9, 23, 0); // veille 23h + UpcomingEventResponse dto = UpcomingEventResponse.builder().startDate(startDate).build(); + assertThat(dto.getDaysUntilEvent(now)).isEqualTo("En cours"); + } + + @Test + @DisplayName("retourne Bientôt quand aujourd'hui dans moins de 2h (now fixe pour éviter passage à minuit)") + void testBientot() { + LocalDateTime now = LocalDateTime.of(2025, 6, 10, 14, 0); + LocalDateTime startDate = now.plusMinutes(30); + UpcomingEventResponse dto = UpcomingEventResponse.builder().startDate(startDate).build(); + assertThat(dto.getDaysUntilEvent(now)).isEqualTo("Bientôt"); + } + + @Test + @DisplayName("retourne Aujourd'hui quand aujourd'hui dans plus de 2h") + void testAujourdhui() { + // Date fixe « aujourd'hui » à 15h pour éviter la dépendance à l'heure d'exécution + // (now().plusHours(5) peut tomber le lendemain après 19h et renvoyer « Demain ») + LocalDateTime now = LocalDateTime.now(); + LocalDateTime startDate = LocalDate.now().atTime(15, 0); + UpcomingEventResponse dto = UpcomingEventResponse.builder().startDate(startDate).build(); + // Utiliser le même 'now' capturé pour éviter les décalages temporels + String result = dto.getDaysUntilEvent(now); + // Selon l'heure d'exécution : >= 2h dans le futur → Aujourd'hui, < 2h → Bientôt, passé → En cours + boolean atLeast2hFromNow = !startDate.isBefore(now.plusHours(2)); + boolean inFuture = startDate.isAfter(now); + if (atLeast2hFromNow) { + assertThat(result).isEqualTo("Aujourd'hui"); + } else if (inFuture) { + assertThat(result).isEqualTo("Bientôt"); + } else { + assertThat(result).isEqualTo("En cours"); + } + } + + @Test + @DisplayName("retourne Aujourd'hui quand même jour et plus de 2h dans le futur (appel avec now fixe pour couverture Jacoco)") + void testAujourdhuiAvecNowFixe() { + LocalDateTime now = LocalDateTime.of(2025, 6, 10, 10, 0); + LocalDateTime startDate = LocalDateTime.of(2025, 6, 10, 15, 0); + UpcomingEventResponse dto = UpcomingEventResponse.builder().startDate(startDate).build(); + assertThat(dto.getDaysUntilEvent(now)).isEqualTo("Aujourd'hui"); + } + + @Test + @DisplayName("retourne Demain quand startDate est demain") + void testDemain() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .startDate(LocalDateTime.now().plusDays(1)).build(); + assertThat(dto.getDaysUntilEvent()).isEqualTo("Demain"); + } + + @Test + @DisplayName("retourne Dans X jours quand moins de 7 jours") + void testDansJours() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .startDate(LocalDateTime.now().plusDays(3)).build(); + assertThat(dto.getDaysUntilEvent()).isEqualTo("Dans 3 jours"); + } + + @Test + @DisplayName("retourne Dans 1 semaine quand 7 jours ou plus (jours < 7 false)") + void testUneSemaine() { + LocalDateTime now = LocalDateTime.now(); + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .startDate(now.plusDays(8)).build(); + String result = dto.getDaysUntilEvent(); + assertThat(result).isEqualTo("Dans 1 semaine"); + } + + @Test + @DisplayName("retourne Dans X semaines quand au moins 14 jours") + void testSemaines() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .startDate(LocalDateTime.now().plusDays(15)).build(); + assertThat(dto.getDaysUntilEvent()).isEqualTo("Dans 2 semaines"); + } + } + + @Nested + @DisplayName("getFillPercentage") + class GetFillPercentage { + + @Test + @DisplayName("retourne 0 quand maxParticipants ou currentParticipants est null") + void testNull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().maxParticipants(10).build(); + assertThat(dto.getFillPercentage()).isEqualTo(0.0); + dto.setCurrentParticipants(5); + dto.setMaxParticipants(null); + assertThat(dto.getFillPercentage()).isEqualTo(0.0); + } + + @Test + @DisplayName("retourne 0 quand maxParticipants est 0") + void testMaxZero() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .maxParticipants(0).currentParticipants(0).build(); + assertThat(dto.getFillPercentage()).isEqualTo(0.0); + } + + @Test + @DisplayName("retourne le pourcentage de remplissage") + void testPourcentage() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .maxParticipants(10).currentParticipants(4).build(); + assertThat(dto.getFillPercentage()).isEqualTo(40.0); + } + } + + @Nested + @DisplayName("getIsFull") + class GetIsFull { + + @Test + @DisplayName("retourne false quand max ou current null") + void testNull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); + assertThat(dto.getIsFull()).isFalse(); + } + + @Test + @DisplayName("retourne false quand maxParticipants défini mais currentParticipants null") + void testMaxDefinitCurrentNull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .maxParticipants(10) + .build(); + assertThat(dto.getIsFull()).isFalse(); + } + + @Test + @DisplayName("retourne true quand current >= max") + void testFull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .maxParticipants(5).currentParticipants(5).build(); + assertThat(dto.getIsFull()).isTrue(); + } + + @Test + @DisplayName("retourne false quand current < max") + void testNotFull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .maxParticipants(5).currentParticipants(3).build(); + assertThat(dto.getIsFull()).isFalse(); + } + } + + @Nested + @DisplayName("getIsAlmostFull") + class GetIsAlmostFull { + + @Test + @DisplayName("retourne true quand fillPercentage entre 80 et 100") + void testAlmostFull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .maxParticipants(10).currentParticipants(9).build(); + assertThat(dto.getIsAlmostFull()).isTrue(); + } + + @Test + @DisplayName("retourne false quand fillPercentage < 80") + void testNotAlmostFull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .maxParticipants(10).currentParticipants(5).build(); + assertThat(dto.getIsAlmostFull()).isFalse(); + } + + @Test + @DisplayName("retourne false quand fillPercentage 100") + void testFullNotAlmostFull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .maxParticipants(10).currentParticipants(10).build(); + assertThat(dto.getIsAlmostFull()).isFalse(); + } + } + + @Nested + @DisplayName("getIsToday et getIsTomorrow") + class GetIsTodayTomorrow { + + @Test + @DisplayName("getIsToday retourne false quand startDate null") + void testIsTodayNull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); + assertThat(dto.getIsToday()).isFalse(); + } + + @Test + @DisplayName("getIsToday retourne true quand startDate aujourd'hui") + void testIsTodayTrue() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .startDate(LocalDateTime.now()).build(); + assertThat(dto.getIsToday()).isTrue(); + } + + @Test + @DisplayName("getIsTomorrow retourne false quand startDate null") + void testIsTomorrowNull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); + assertThat(dto.getIsTomorrow()).isFalse(); + } + + @Test + @DisplayName("getIsTomorrow retourne true quand startDate demain") + void testIsTomorrowTrue() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .startDate(LocalDateTime.now().plusDays(1)).build(); + assertThat(dto.getIsTomorrow()).isTrue(); + } + } + + @Nested + @DisplayName("getStatusColor") + class GetStatusColor { + + @Test + @DisplayName("retourne grey quand status null") + void testNull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); + assertThat(dto.getStatusColor()).isEqualTo("#6B7280"); + } + + @Test + @DisplayName("retourne couleur selon status confirmed") + void testConfirmed() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().status("confirmed").build(); + assertThat(dto.getStatusColor()).isEqualTo("#10B981"); + } + + @Test + @DisplayName("retourne couleur selon status open") + void testOpen() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().status("open").build(); + assertThat(dto.getStatusColor()).isEqualTo("#3B82F6"); + } + + @Test + @DisplayName("retourne couleur selon status cancelled") + void testCancelled() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().status("cancelled").build(); + assertThat(dto.getStatusColor()).isEqualTo("#EF4444"); + } + + @Test + @DisplayName("retourne couleur selon status postponed") + void testPostponed() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().status("postponed").build(); + assertThat(dto.getStatusColor()).isEqualTo("#F59E0B"); + } + + @Test + @DisplayName("retourne grey pour status inconnu") + void testDefault() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().status("unknown").build(); + assertThat(dto.getStatusColor()).isEqualTo("#6B7280"); + } + + @Test + @DisplayName("status insensible à la casse") + void testCaseInsensitive() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().status("CONFIRMED").build(); + assertThat(dto.getStatusColor()).isEqualTo("#10B981"); + } + } + + @Nested + @DisplayName("getStatusLabel") + class GetStatusLabel { + + @Test + @DisplayName("retourne Inconnu quand status null") + void testNull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); + assertThat(dto.getStatusLabel()).isEqualTo("Inconnu"); + } + + @Test + @DisplayName("retourne libellé pour confirmed, open, cancelled, postponed") + void testLabels() { + assertThat(UpcomingEventResponse.builder().status("confirmed").build().getStatusLabel()).isEqualTo("Confirmé"); + assertThat(UpcomingEventResponse.builder().status("open").build().getStatusLabel()).isEqualTo("Ouvert"); + assertThat(UpcomingEventResponse.builder().status("cancelled").build().getStatusLabel()).isEqualTo("Annulé"); + assertThat(UpcomingEventResponse.builder().status("postponed").build().getStatusLabel()).isEqualTo("Reporté"); + } + + @Test + @DisplayName("retourne status tel quel pour valeur inconnue") + void testDefault() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().status("custom").build(); + assertThat(dto.getStatusLabel()).isEqualTo("custom"); + } + } + + @Nested + @DisplayName("getAvailableSpots") + class GetAvailableSpots { + + @Test + @DisplayName("retourne 0 quand max ou current null") + void testNull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); + assertThat(dto.getAvailableSpots()).isEqualTo(0); + } + + @Test + @DisplayName("retourne 0 quand maxParticipants défini mais currentParticipants null") + void testMaxDefinitCurrentNull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .maxParticipants(10) + .build(); + assertThat(dto.getAvailableSpots()).isEqualTo(0); + } + + @Test + @DisplayName("retourne max - current") + void testCalcul() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .maxParticipants(10).currentParticipants(7).build(); + assertThat(dto.getAvailableSpots()).isEqualTo(3); + } + + @Test + @DisplayName("retourne 0 quand current > max (Math.max)") + void testNegatif() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .maxParticipants(5).currentParticipants(10).build(); + assertThat(dto.getAvailableSpots()).isEqualTo(0); + } + } + + @Nested + @DisplayName("getParticipationSummary") + class GetParticipationSummary { + + @Test + @DisplayName("retourne 0/0 quand max ou current null") + void testNull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder().build(); + assertThat(dto.getParticipationSummary()).isEqualTo("0/0 participants"); + } + + @Test + @DisplayName("retourne 0/0 quand maxParticipants défini mais currentParticipants null") + void testMaxDefinitCurrentNull() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .maxParticipants(20) + .build(); + assertThat(dto.getParticipationSummary()).isEqualTo("0/0 participants"); + } + + @Test + @DisplayName("retourne current/max participants") + void testSummary() { + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .maxParticipants(20).currentParticipants(12).build(); + assertThat(dto.getParticipationSummary()).isEqualTo("12/20 participants"); + } + } + + @Nested + @DisplayName("Getters standards") + class GettersStandards { + + @Test + @DisplayName("tous les champs builder sont accessibles") + void testBuilderGetters() { + LocalDateTime start = LocalDateTime.now(); + LocalDateTime end = start.plusHours(2); + UpcomingEventResponse dto = UpcomingEventResponse.builder() + .id("ev1") + .title("Titre") + .description("Desc") + .startDate(start) + .endDate(end) + .location("Paris") + .maxParticipants(50) + .currentParticipants(10) + .status("open") + .imageUrl("http://img") + .tags(List.of("a", "b")) + .build(); + assertThat(dto.getId()).isEqualTo("ev1"); + assertThat(dto.getTitle()).isEqualTo("Titre"); + assertThat(dto.getDescription()).isEqualTo("Desc"); + assertThat(dto.getStartDate()).isEqualTo(start); + assertThat(dto.getEndDate()).isEqualTo(end); + assertThat(dto.getLocation()).isEqualTo("Paris"); + assertThat(dto.getMaxParticipants()).isEqualTo(50); + assertThat(dto.getCurrentParticipants()).isEqualTo(10); + assertThat(dto.getStatus()).isEqualTo("open"); + assertThat(dto.getImageUrl()).isEqualTo("http://img"); + assertThat(dto.getTags()).containsExactly("a", "b"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/document/request/CreateDocumentRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/document/request/CreateDocumentRequestTest.java index fb55d3c..5d5c4a9 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/document/request/CreateDocumentRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/document/request/CreateDocumentRequestTest.java @@ -1,173 +1,173 @@ -package dev.lions.unionflow.server.api.dto.document.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.document.TypeDocument; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateDocumentRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - CreateDocumentRequest request = CreateDocumentRequest.builder() - .nomFichier("document_2025.pdf") - .nomOriginal("Document Original.pdf") - .cheminStockage("/storage/documents/2025/") - .typeMime("application/pdf") - .tailleOctets(1024000L) - .typeDocument(TypeDocument.CONTRAT) - .hashMd5("5d41402abc4b2a76b9719d911017c592") - .hashSha256("e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855") - .description("Contrat de prestation") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.nomFichier()).isEqualTo("document_2025.pdf"); - assertThat(request.nomOriginal()).isEqualTo("Document Original.pdf"); - assertThat(request.cheminStockage()).isEqualTo("/storage/documents/2025/"); - assertThat(request.typeMime()).isEqualTo("application/pdf"); - assertThat(request.tailleOctets()).isEqualTo(1024000L); - assertThat(request.typeDocument()).isEqualTo(TypeDocument.CONTRAT); - assertThat(request.hashMd5()).isEqualTo("5d41402abc4b2a76b9719d911017c592"); - assertThat(request.hashSha256()) - .isEqualTo("e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"); - assertThat(request.description()).isEqualTo("Contrat de prestation"); - } - - @Test - void testBuilder_MinimalFields() { - CreateDocumentRequest request = CreateDocumentRequest.builder() - .nomFichier("simple.pdf") - .cheminStockage("/storage/") - .tailleOctets(1024L) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.nomFichier()).isEqualTo("simple.pdf"); - assertThat(request.cheminStockage()).isEqualTo("/storage/"); - assertThat(request.tailleOctets()).isEqualTo(1024L); - assertThat(request.nomOriginal()).isNull(); - assertThat(request.typeMime()).isNull(); - assertThat(request.typeDocument()).isNull(); - assertThat(request.hashMd5()).isNull(); - assertThat(request.hashSha256()).isNull(); - assertThat(request.description()).isNull(); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateDocumentRequest request = CreateDocumentRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nomFichier")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("cheminStockage")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("tailleOctets")); - } - - @Test - void testValidation_EmptyNomFichier() { - CreateDocumentRequest request = CreateDocumentRequest.builder() - .nomFichier("") - .cheminStockage("/storage/") - .tailleOctets(1024L) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nomFichier")); - } - - @Test - void testValidation_EmptyCheminStockage() { - CreateDocumentRequest request = CreateDocumentRequest.builder() - .nomFichier("file.pdf") - .cheminStockage("") - .tailleOctets(1024L) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("cheminStockage")); - } - - @Test - void testValidation_NegativeTaille() { - CreateDocumentRequest request = CreateDocumentRequest.builder() - .nomFichier("file.pdf") - .cheminStockage("/storage/") - .tailleOctets(-100L) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("tailleOctets")); - } - - @Test - void testValidation_ValidFields() { - CreateDocumentRequest request = CreateDocumentRequest.builder() - .nomFichier("valid.pdf") - .cheminStockage("/storage/docs/") - .tailleOctets(2048L) - .typeDocument(TypeDocument.FACTURE) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - CreateDocumentRequest request1 = CreateDocumentRequest.builder() - .nomFichier("doc.pdf") - .cheminStockage("/storage/") - .tailleOctets(1024L) - .build(); - - CreateDocumentRequest request2 = CreateDocumentRequest.builder() - .nomFichier("doc.pdf") - .cheminStockage("/storage/") - .tailleOctets(1024L) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateDocumentRequest request = CreateDocumentRequest.builder() - .nomFichier("test.pdf") - .cheminStockage("/storage/test/") - .tailleOctets(512L) - .typeDocument(TypeDocument.RAPPORT) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateDocumentRequest"); - assertThat(toString).contains("test.pdf"); - assertThat(toString).contains("RAPPORT"); - } -} +package dev.lions.unionflow.server.api.dto.document.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.document.TypeDocument; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateDocumentRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + CreateDocumentRequest request = CreateDocumentRequest.builder() + .nomFichier("document_2025.pdf") + .nomOriginal("Document Original.pdf") + .cheminStockage("/storage/documents/2025/") + .typeMime("application/pdf") + .tailleOctets(1024000L) + .typeDocument(TypeDocument.CONTRAT) + .hashMd5("5d41402abc4b2a76b9719d911017c592") + .hashSha256("e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855") + .description("Contrat de prestation") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.nomFichier()).isEqualTo("document_2025.pdf"); + assertThat(request.nomOriginal()).isEqualTo("Document Original.pdf"); + assertThat(request.cheminStockage()).isEqualTo("/storage/documents/2025/"); + assertThat(request.typeMime()).isEqualTo("application/pdf"); + assertThat(request.tailleOctets()).isEqualTo(1024000L); + assertThat(request.typeDocument()).isEqualTo(TypeDocument.CONTRAT); + assertThat(request.hashMd5()).isEqualTo("5d41402abc4b2a76b9719d911017c592"); + assertThat(request.hashSha256()) + .isEqualTo("e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"); + assertThat(request.description()).isEqualTo("Contrat de prestation"); + } + + @Test + void testBuilder_MinimalFields() { + CreateDocumentRequest request = CreateDocumentRequest.builder() + .nomFichier("simple.pdf") + .cheminStockage("/storage/") + .tailleOctets(1024L) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.nomFichier()).isEqualTo("simple.pdf"); + assertThat(request.cheminStockage()).isEqualTo("/storage/"); + assertThat(request.tailleOctets()).isEqualTo(1024L); + assertThat(request.nomOriginal()).isNull(); + assertThat(request.typeMime()).isNull(); + assertThat(request.typeDocument()).isNull(); + assertThat(request.hashMd5()).isNull(); + assertThat(request.hashSha256()).isNull(); + assertThat(request.description()).isNull(); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateDocumentRequest request = CreateDocumentRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nomFichier")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("cheminStockage")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("tailleOctets")); + } + + @Test + void testValidation_EmptyNomFichier() { + CreateDocumentRequest request = CreateDocumentRequest.builder() + .nomFichier("") + .cheminStockage("/storage/") + .tailleOctets(1024L) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nomFichier")); + } + + @Test + void testValidation_EmptyCheminStockage() { + CreateDocumentRequest request = CreateDocumentRequest.builder() + .nomFichier("file.pdf") + .cheminStockage("") + .tailleOctets(1024L) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("cheminStockage")); + } + + @Test + void testValidation_NegativeTaille() { + CreateDocumentRequest request = CreateDocumentRequest.builder() + .nomFichier("file.pdf") + .cheminStockage("/storage/") + .tailleOctets(-100L) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("tailleOctets")); + } + + @Test + void testValidation_ValidFields() { + CreateDocumentRequest request = CreateDocumentRequest.builder() + .nomFichier("valid.pdf") + .cheminStockage("/storage/docs/") + .tailleOctets(2048L) + .typeDocument(TypeDocument.FACTURE) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + CreateDocumentRequest request1 = CreateDocumentRequest.builder() + .nomFichier("doc.pdf") + .cheminStockage("/storage/") + .tailleOctets(1024L) + .build(); + + CreateDocumentRequest request2 = CreateDocumentRequest.builder() + .nomFichier("doc.pdf") + .cheminStockage("/storage/") + .tailleOctets(1024L) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateDocumentRequest request = CreateDocumentRequest.builder() + .nomFichier("test.pdf") + .cheminStockage("/storage/test/") + .tailleOctets(512L) + .typeDocument(TypeDocument.RAPPORT) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateDocumentRequest"); + assertThat(toString).contains("test.pdf"); + assertThat(toString).contains("RAPPORT"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/document/request/CreatePieceJointeRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/document/request/CreatePieceJointeRequestTest.java index 39560fc..e486f3f 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/document/request/CreatePieceJointeRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/document/request/CreatePieceJointeRequestTest.java @@ -1,168 +1,168 @@ -package dev.lions.unionflow.server.api.dto.document.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreatePieceJointeRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID documentId = UUID.randomUUID(); - UUID entiteId = UUID.randomUUID(); - - CreatePieceJointeRequest request = CreatePieceJointeRequest.builder() - .ordre(1) - .libelle("Pièce principale") - .commentaire("Document requis pour validation") - .documentId(documentId) - .typeEntiteRattachee("MEMBRE") - .entiteRattacheeId(entiteId) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.ordre()).isEqualTo(1); - assertThat(request.libelle()).isEqualTo("Pièce principale"); - assertThat(request.commentaire()).isEqualTo("Document requis pour validation"); - assertThat(request.documentId()).isEqualTo(documentId); - assertThat(request.typeEntiteRattachee()).isEqualTo("MEMBRE"); - assertThat(request.entiteRattacheeId()).isEqualTo(entiteId); - } - - @Test - void testBuilder_MinimalFields() { - UUID documentId = UUID.randomUUID(); - UUID entiteId = UUID.randomUUID(); - - CreatePieceJointeRequest request = CreatePieceJointeRequest.builder() - .ordre(1) - .documentId(documentId) - .typeEntiteRattachee("ORGANISATION") - .entiteRattacheeId(entiteId) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.ordre()).isEqualTo(1); - assertThat(request.documentId()).isEqualTo(documentId); - assertThat(request.typeEntiteRattachee()).isEqualTo("ORGANISATION"); - assertThat(request.entiteRattacheeId()).isEqualTo(entiteId); - assertThat(request.libelle()).isNull(); - assertThat(request.commentaire()).isNull(); - } - - @Test - void testValidation_MissingRequiredFields() { - CreatePieceJointeRequest request = CreatePieceJointeRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ordre")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("documentId")); - assertThat(violations) - .anyMatch(v -> v.getPropertyPath().toString().equals("typeEntiteRattachee")); - assertThat(violations) - .anyMatch(v -> v.getPropertyPath().toString().equals("entiteRattacheeId")); - } - - @Test - void testValidation_OrdreZero() { - CreatePieceJointeRequest request = CreatePieceJointeRequest.builder() - .ordre(0) - .documentId(UUID.randomUUID()) - .typeEntiteRattachee("MEMBRE") - .entiteRattacheeId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ordre")); - } - - @Test - void testValidation_OrdreNegatif() { - CreatePieceJointeRequest request = CreatePieceJointeRequest.builder() - .ordre(-5) - .documentId(UUID.randomUUID()) - .typeEntiteRattachee("MEMBRE") - .entiteRattacheeId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ordre")); - } - - @Test - void testValidation_ValidFields() { - CreatePieceJointeRequest request = CreatePieceJointeRequest.builder() - .ordre(2) - .libelle("Pièce valide") - .documentId(UUID.randomUUID()) - .typeEntiteRattachee("EVENEMENT") - .entiteRattacheeId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID documentId = UUID.randomUUID(); - UUID entiteId = UUID.randomUUID(); - - CreatePieceJointeRequest request1 = CreatePieceJointeRequest.builder() - .ordre(1) - .documentId(documentId) - .typeEntiteRattachee("MEMBRE") - .entiteRattacheeId(entiteId) - .build(); - - CreatePieceJointeRequest request2 = CreatePieceJointeRequest.builder() - .ordre(1) - .documentId(documentId) - .typeEntiteRattachee("MEMBRE") - .entiteRattacheeId(entiteId) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreatePieceJointeRequest request = CreatePieceJointeRequest.builder() - .ordre(3) - .libelle("Test Pièce") - .documentId(UUID.randomUUID()) - .typeEntiteRattachee("CONTRAT") - .entiteRattacheeId(UUID.randomUUID()) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreatePieceJointeRequest"); - assertThat(toString).contains("Test Pièce"); - assertThat(toString).contains("CONTRAT"); - } -} +package dev.lions.unionflow.server.api.dto.document.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreatePieceJointeRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID documentId = UUID.randomUUID(); + UUID entiteId = UUID.randomUUID(); + + CreatePieceJointeRequest request = CreatePieceJointeRequest.builder() + .ordre(1) + .libelle("Pièce principale") + .commentaire("Document requis pour validation") + .documentId(documentId) + .typeEntiteRattachee("MEMBRE") + .entiteRattacheeId(entiteId) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.ordre()).isEqualTo(1); + assertThat(request.libelle()).isEqualTo("Pièce principale"); + assertThat(request.commentaire()).isEqualTo("Document requis pour validation"); + assertThat(request.documentId()).isEqualTo(documentId); + assertThat(request.typeEntiteRattachee()).isEqualTo("MEMBRE"); + assertThat(request.entiteRattacheeId()).isEqualTo(entiteId); + } + + @Test + void testBuilder_MinimalFields() { + UUID documentId = UUID.randomUUID(); + UUID entiteId = UUID.randomUUID(); + + CreatePieceJointeRequest request = CreatePieceJointeRequest.builder() + .ordre(1) + .documentId(documentId) + .typeEntiteRattachee("ORGANISATION") + .entiteRattacheeId(entiteId) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.ordre()).isEqualTo(1); + assertThat(request.documentId()).isEqualTo(documentId); + assertThat(request.typeEntiteRattachee()).isEqualTo("ORGANISATION"); + assertThat(request.entiteRattacheeId()).isEqualTo(entiteId); + assertThat(request.libelle()).isNull(); + assertThat(request.commentaire()).isNull(); + } + + @Test + void testValidation_MissingRequiredFields() { + CreatePieceJointeRequest request = CreatePieceJointeRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ordre")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("documentId")); + assertThat(violations) + .anyMatch(v -> v.getPropertyPath().toString().equals("typeEntiteRattachee")); + assertThat(violations) + .anyMatch(v -> v.getPropertyPath().toString().equals("entiteRattacheeId")); + } + + @Test + void testValidation_OrdreZero() { + CreatePieceJointeRequest request = CreatePieceJointeRequest.builder() + .ordre(0) + .documentId(UUID.randomUUID()) + .typeEntiteRattachee("MEMBRE") + .entiteRattacheeId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ordre")); + } + + @Test + void testValidation_OrdreNegatif() { + CreatePieceJointeRequest request = CreatePieceJointeRequest.builder() + .ordre(-5) + .documentId(UUID.randomUUID()) + .typeEntiteRattachee("MEMBRE") + .entiteRattacheeId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ordre")); + } + + @Test + void testValidation_ValidFields() { + CreatePieceJointeRequest request = CreatePieceJointeRequest.builder() + .ordre(2) + .libelle("Pièce valide") + .documentId(UUID.randomUUID()) + .typeEntiteRattachee("EVENEMENT") + .entiteRattacheeId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID documentId = UUID.randomUUID(); + UUID entiteId = UUID.randomUUID(); + + CreatePieceJointeRequest request1 = CreatePieceJointeRequest.builder() + .ordre(1) + .documentId(documentId) + .typeEntiteRattachee("MEMBRE") + .entiteRattacheeId(entiteId) + .build(); + + CreatePieceJointeRequest request2 = CreatePieceJointeRequest.builder() + .ordre(1) + .documentId(documentId) + .typeEntiteRattachee("MEMBRE") + .entiteRattacheeId(entiteId) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreatePieceJointeRequest request = CreatePieceJointeRequest.builder() + .ordre(3) + .libelle("Test Pièce") + .documentId(UUID.randomUUID()) + .typeEntiteRattachee("CONTRAT") + .entiteRattacheeId(UUID.randomUUID()) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreatePieceJointeRequest"); + assertThat(toString).contains("Test Pièce"); + assertThat(toString).contains("CONTRAT"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/document/request/UpdateDocumentRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/document/request/UpdateDocumentRequestTest.java index 5204319..9ed7598 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/document/request/UpdateDocumentRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/document/request/UpdateDocumentRequestTest.java @@ -1,95 +1,95 @@ -package dev.lions.unionflow.server.api.dto.document.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.document.TypeDocument; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateDocumentRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UpdateDocumentRequest request = UpdateDocumentRequest.builder() - .nomFichier("updated_document.pdf") - .nomOriginal("Updated Original.pdf") - .typeDocument(TypeDocument.RECU) - .description("Description mise à jour") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.nomFichier()).isEqualTo("updated_document.pdf"); - assertThat(request.nomOriginal()).isEqualTo("Updated Original.pdf"); - assertThat(request.typeDocument()).isEqualTo(TypeDocument.RECU); - assertThat(request.description()).isEqualTo("Description mise à jour"); - } - - @Test - void testBuilder_MinimalFields() { - UpdateDocumentRequest request = UpdateDocumentRequest.builder().build(); - - assertThat(request).isNotNull(); - assertThat(request.nomFichier()).isNull(); - assertThat(request.nomOriginal()).isNull(); - assertThat(request.typeDocument()).isNull(); - assertThat(request.description()).isNull(); - } - - @Test - void testValidation_ValidFields() { - UpdateDocumentRequest request = UpdateDocumentRequest.builder() - .nomFichier("valid_update.pdf") - .typeDocument(TypeDocument.AUTRE) - .description("Valid description") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UpdateDocumentRequest request1 = UpdateDocumentRequest.builder() - .nomFichier("same.pdf") - .typeDocument(TypeDocument.PHOTO) - .build(); - - UpdateDocumentRequest request2 = UpdateDocumentRequest.builder() - .nomFichier("same.pdf") - .typeDocument(TypeDocument.PHOTO) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateDocumentRequest request = UpdateDocumentRequest.builder() - .nomFichier("toString_test.pdf") - .typeDocument(TypeDocument.IDENTITE) - .description("Test toString") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateDocumentRequest"); - assertThat(toString).contains("toString_test.pdf"); - assertThat(toString).contains("IDENTITE"); - } -} +package dev.lions.unionflow.server.api.dto.document.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.document.TypeDocument; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateDocumentRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UpdateDocumentRequest request = UpdateDocumentRequest.builder() + .nomFichier("updated_document.pdf") + .nomOriginal("Updated Original.pdf") + .typeDocument(TypeDocument.RECU) + .description("Description mise à jour") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.nomFichier()).isEqualTo("updated_document.pdf"); + assertThat(request.nomOriginal()).isEqualTo("Updated Original.pdf"); + assertThat(request.typeDocument()).isEqualTo(TypeDocument.RECU); + assertThat(request.description()).isEqualTo("Description mise à jour"); + } + + @Test + void testBuilder_MinimalFields() { + UpdateDocumentRequest request = UpdateDocumentRequest.builder().build(); + + assertThat(request).isNotNull(); + assertThat(request.nomFichier()).isNull(); + assertThat(request.nomOriginal()).isNull(); + assertThat(request.typeDocument()).isNull(); + assertThat(request.description()).isNull(); + } + + @Test + void testValidation_ValidFields() { + UpdateDocumentRequest request = UpdateDocumentRequest.builder() + .nomFichier("valid_update.pdf") + .typeDocument(TypeDocument.AUTRE) + .description("Valid description") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UpdateDocumentRequest request1 = UpdateDocumentRequest.builder() + .nomFichier("same.pdf") + .typeDocument(TypeDocument.PHOTO) + .build(); + + UpdateDocumentRequest request2 = UpdateDocumentRequest.builder() + .nomFichier("same.pdf") + .typeDocument(TypeDocument.PHOTO) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateDocumentRequest request = UpdateDocumentRequest.builder() + .nomFichier("toString_test.pdf") + .typeDocument(TypeDocument.IDENTITE) + .description("Test toString") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateDocumentRequest"); + assertThat(toString).contains("toString_test.pdf"); + assertThat(toString).contains("IDENTITE"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/document/request/UpdatePieceJointeRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/document/request/UpdatePieceJointeRequestTest.java index f97e225..c7661f7 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/document/request/UpdatePieceJointeRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/document/request/UpdatePieceJointeRequestTest.java @@ -1,110 +1,110 @@ -package dev.lions.unionflow.server.api.dto.document.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdatePieceJointeRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UpdatePieceJointeRequest request = UpdatePieceJointeRequest.builder() - .ordre(5) - .libelle("Libellé mis à jour") - .commentaire("Nouveau commentaire") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.ordre()).isEqualTo(5); - assertThat(request.libelle()).isEqualTo("Libellé mis à jour"); - assertThat(request.commentaire()).isEqualTo("Nouveau commentaire"); - } - - @Test - void testBuilder_MinimalFields() { - UpdatePieceJointeRequest request = UpdatePieceJointeRequest.builder().build(); - - assertThat(request).isNotNull(); - assertThat(request.ordre()).isNull(); - assertThat(request.libelle()).isNull(); - assertThat(request.commentaire()).isNull(); - } - - @Test - void testValidation_OrdreZero() { - UpdatePieceJointeRequest request = UpdatePieceJointeRequest.builder().ordre(0).build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ordre")); - } - - @Test - void testValidation_OrdreNegatif() { - UpdatePieceJointeRequest request = UpdatePieceJointeRequest.builder().ordre(-10).build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ordre")); - } - - @Test - void testValidation_ValidFields() { - UpdatePieceJointeRequest request = UpdatePieceJointeRequest.builder() - .ordre(3) - .libelle("Valid label") - .commentaire("Valid comment") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UpdatePieceJointeRequest request1 = UpdatePieceJointeRequest.builder() - .ordre(2) - .libelle("Same label") - .build(); - - UpdatePieceJointeRequest request2 = UpdatePieceJointeRequest.builder() - .ordre(2) - .libelle("Same label") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdatePieceJointeRequest request = UpdatePieceJointeRequest.builder() - .ordre(7) - .libelle("Test toString") - .commentaire("Comment test") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdatePieceJointeRequest"); - assertThat(toString).contains("Test toString"); - } -} +package dev.lions.unionflow.server.api.dto.document.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdatePieceJointeRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UpdatePieceJointeRequest request = UpdatePieceJointeRequest.builder() + .ordre(5) + .libelle("Libellé mis à jour") + .commentaire("Nouveau commentaire") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.ordre()).isEqualTo(5); + assertThat(request.libelle()).isEqualTo("Libellé mis à jour"); + assertThat(request.commentaire()).isEqualTo("Nouveau commentaire"); + } + + @Test + void testBuilder_MinimalFields() { + UpdatePieceJointeRequest request = UpdatePieceJointeRequest.builder().build(); + + assertThat(request).isNotNull(); + assertThat(request.ordre()).isNull(); + assertThat(request.libelle()).isNull(); + assertThat(request.commentaire()).isNull(); + } + + @Test + void testValidation_OrdreZero() { + UpdatePieceJointeRequest request = UpdatePieceJointeRequest.builder().ordre(0).build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ordre")); + } + + @Test + void testValidation_OrdreNegatif() { + UpdatePieceJointeRequest request = UpdatePieceJointeRequest.builder().ordre(-10).build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ordre")); + } + + @Test + void testValidation_ValidFields() { + UpdatePieceJointeRequest request = UpdatePieceJointeRequest.builder() + .ordre(3) + .libelle("Valid label") + .commentaire("Valid comment") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UpdatePieceJointeRequest request1 = UpdatePieceJointeRequest.builder() + .ordre(2) + .libelle("Same label") + .build(); + + UpdatePieceJointeRequest request2 = UpdatePieceJointeRequest.builder() + .ordre(2) + .libelle("Same label") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdatePieceJointeRequest request = UpdatePieceJointeRequest.builder() + .ordre(7) + .libelle("Test toString") + .commentaire("Comment test") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdatePieceJointeRequest"); + assertThat(toString).contains("Test toString"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/evenement/request/CreateEvenementRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/evenement/request/CreateEvenementRequestTest.java index 6c127f6..be5b8bb 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/evenement/request/CreateEvenementRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/evenement/request/CreateEvenementRequestTest.java @@ -1,282 +1,282 @@ -package dev.lions.unionflow.server.api.dto.evenement.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; -import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; -import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalTime; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateEvenementRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID associationId = UUID.randomUUID(); - LocalDate dateDebut = LocalDate.now().plusDays(10); - LocalDate dateFin = LocalDate.now().plusDays(12); - LocalDate dateLimite = LocalDate.now().plusDays(5); - - CreateEvenementRequest request = CreateEvenementRequest.builder() - .titre("Assemblée Générale 2025") - .description("Réunion annuelle de tous les membres") - .typeEvenement(TypeEvenementMetier.ASSEMBLEE_GENERALE) - .statut(StatutEvenement.PLANIFIE) - .priorite(PrioriteEvenement.HAUTE) - .dateDebut(dateDebut) - .dateFin(dateFin) - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(17, 0)) - .lieu("Salle des Congrès") - .adresse("123 Avenue de la République") - .ville("Dakar") - .region("Dakar") - .latitude(new BigDecimal("14.6937")) - .longitude(new BigDecimal("-17.4441")) - .associationId(associationId) - .organisateur("Comité d'Organisation") - .emailOrganisateur("contact@unionflow.org") - .telephoneOrganisateur("+221 33 123 45 67") - .capaciteMax(500) - .budget(new BigDecimal("5000000.00")) - .coutReel(new BigDecimal("4500000.00")) - .codeDevise("XOF") - .inscriptionObligatoire(true) - .dateLimiteInscription(dateLimite) - .evenementPublic(false) - .recurrent(false) - .frequenceRecurrence(null) - .instructions("Apporter votre carte de membre") - .materielNecessaire("Aucun") - .conditionsMeteo("Intérieur") - .imageUrl("https://example.com/image.jpg") - .couleurTheme("#FF5733") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.titre()).isEqualTo("Assemblée Générale 2025"); - assertThat(request.description()).contains("Réunion annuelle"); - assertThat(request.typeEvenement()).isEqualTo(TypeEvenementMetier.ASSEMBLEE_GENERALE); - assertThat(request.statut()).isEqualTo(StatutEvenement.PLANIFIE); - assertThat(request.priorite()).isEqualTo(PrioriteEvenement.HAUTE); - assertThat(request.dateDebut()).isEqualTo(dateDebut); - assertThat(request.dateFin()).isEqualTo(dateFin); - assertThat(request.heureDebut()).isEqualTo(LocalTime.of(9, 0)); - assertThat(request.heureFin()).isEqualTo(LocalTime.of(17, 0)); - assertThat(request.lieu()).isEqualTo("Salle des Congrès"); - assertThat(request.ville()).isEqualTo("Dakar"); - assertThat(request.capaciteMax()).isEqualTo(500); - assertThat(request.budget()).isEqualByComparingTo(new BigDecimal("5000000.00")); - assertThat(request.codeDevise()).isEqualTo("XOF"); - assertThat(request.inscriptionObligatoire()).isTrue(); - assertThat(request.couleurTheme()).isEqualTo("#FF5733"); - } - - @Test - void testBuilder_MinimalFields() { - UUID associationId = UUID.randomUUID(); - LocalDate dateDebut = LocalDate.now().plusDays(1); - - CreateEvenementRequest request = CreateEvenementRequest.builder() - .titre("Événement Simple") - .typeEvenement(TypeEvenementMetier.FORMATION) - .statut(StatutEvenement.CONFIRME) - .dateDebut(dateDebut) - .lieu("Salle A") - .associationId(associationId) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.titre()).isEqualTo("Événement Simple"); - assertThat(request.typeEvenement()).isEqualTo(TypeEvenementMetier.FORMATION); - assertThat(request.statut()).isEqualTo(StatutEvenement.CONFIRME); - assertThat(request.dateDebut()).isEqualTo(dateDebut); - assertThat(request.lieu()).isEqualTo("Salle A"); - assertThat(request.associationId()).isEqualTo(associationId); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateEvenementRequest request = CreateEvenementRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("titre")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeEvenement")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("statut")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateDebut")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("lieu")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("associationId")); - } - - @Test - void testValidation_TitreTooShort() { - CreateEvenementRequest request = CreateEvenementRequest.builder() - .titre("AB") - .typeEvenement(TypeEvenementMetier.CONFERENCE) - .statut(StatutEvenement.PLANIFIE) - .dateDebut(LocalDate.now().plusDays(1)) - .lieu("Lieu") - .associationId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("titre")); - } - - @Test - void testValidation_EmailInvalide() { - CreateEvenementRequest request = CreateEvenementRequest.builder() - .titre("Événement Test") - .typeEvenement(TypeEvenementMetier.ATELIER) - .statut(StatutEvenement.PLANIFIE) - .dateDebut(LocalDate.now().plusDays(1)) - .lieu("Lieu") - .associationId(UUID.randomUUID()) - .emailOrganisateur("invalid-email") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("emailOrganisateur")); - } - - @Test - void testValidation_LatitudeInvalide() { - CreateEvenementRequest request = CreateEvenementRequest.builder() - .titre("Événement Test") - .typeEvenement(TypeEvenementMetier.CEREMONIE) - .statut(StatutEvenement.PLANIFIE) - .dateDebut(LocalDate.now().plusDays(1)) - .lieu("Lieu") - .associationId(UUID.randomUUID()) - .latitude(new BigDecimal("95.0")) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("latitude")); - } - - @Test - void testValidation_LongitudeInvalide() { - CreateEvenementRequest request = CreateEvenementRequest.builder() - .titre("Événement Test") - .typeEvenement(TypeEvenementMetier.ACTION_CARITATIVE) - .statut(StatutEvenement.PLANIFIE) - .dateDebut(LocalDate.now().plusDays(1)) - .lieu("Lieu") - .associationId(UUID.randomUUID()) - .longitude(new BigDecimal("-185.0")) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("longitude")); - } - - @Test - void testValidation_CouleurThemeInvalide() { - CreateEvenementRequest request = CreateEvenementRequest.builder() - .titre("Événement Test") - .typeEvenement(TypeEvenementMetier.AUTRE) - .statut(StatutEvenement.PLANIFIE) - .dateDebut(LocalDate.now().plusDays(1)) - .lieu("Lieu") - .associationId(UUID.randomUUID()) - .couleurTheme("invalid") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("couleurTheme")); - } - - @Test - void testValidation_ValidFields() { - CreateEvenementRequest request = CreateEvenementRequest.builder() - .titre("Événement Valide") - .typeEvenement(TypeEvenementMetier.REUNION_BUREAU) - .statut(StatutEvenement.CONFIRME) - .dateDebut(LocalDate.now().plusDays(5)) - .lieu("Bureau Central") - .associationId(UUID.randomUUID()) - .emailOrganisateur("valid@example.com") - .telephoneOrganisateur("+221 77 123 45 67") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID associationId = UUID.randomUUID(); - LocalDate dateDebut = LocalDate.now().plusDays(1); - - CreateEvenementRequest request1 = CreateEvenementRequest.builder() - .titre("Même Événement") - .typeEvenement(TypeEvenementMetier.FORMATION) - .statut(StatutEvenement.PLANIFIE) - .dateDebut(dateDebut) - .lieu("Lieu") - .associationId(associationId) - .build(); - - CreateEvenementRequest request2 = CreateEvenementRequest.builder() - .titre("Même Événement") - .typeEvenement(TypeEvenementMetier.FORMATION) - .statut(StatutEvenement.PLANIFIE) - .dateDebut(dateDebut) - .lieu("Lieu") - .associationId(associationId) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateEvenementRequest request = CreateEvenementRequest.builder() - .titre("Test ToString") - .typeEvenement(TypeEvenementMetier.ACTIVITE_SOCIALE) - .statut(StatutEvenement.PLANIFIE) - .dateDebut(LocalDate.now().plusDays(1)) - .lieu("Test Lieu") - .associationId(UUID.randomUUID()) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateEvenementRequest"); - assertThat(toString).contains("Test ToString"); - assertThat(toString).contains("ACTIVITE_SOCIALE"); - } -} +package dev.lions.unionflow.server.api.dto.evenement.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; +import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; +import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalTime; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateEvenementRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID associationId = UUID.randomUUID(); + LocalDate dateDebut = LocalDate.now().plusDays(10); + LocalDate dateFin = LocalDate.now().plusDays(12); + LocalDate dateLimite = LocalDate.now().plusDays(5); + + CreateEvenementRequest request = CreateEvenementRequest.builder() + .titre("Assemblée Générale 2025") + .description("Réunion annuelle de tous les membres") + .typeEvenement(TypeEvenementMetier.ASSEMBLEE_GENERALE) + .statut(StatutEvenement.PLANIFIE) + .priorite(PrioriteEvenement.HAUTE) + .dateDebut(dateDebut) + .dateFin(dateFin) + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(17, 0)) + .lieu("Salle des Congrès") + .adresse("123 Avenue de la République") + .ville("Dakar") + .region("Dakar") + .latitude(new BigDecimal("14.6937")) + .longitude(new BigDecimal("-17.4441")) + .associationId(associationId) + .organisateur("Comité d'Organisation") + .emailOrganisateur("contact@unionflow.org") + .telephoneOrganisateur("+221 33 123 45 67") + .capaciteMax(500) + .budget(new BigDecimal("5000000.00")) + .coutReel(new BigDecimal("4500000.00")) + .codeDevise("XOF") + .inscriptionObligatoire(true) + .dateLimiteInscription(dateLimite) + .evenementPublic(false) + .recurrent(false) + .frequenceRecurrence(null) + .instructions("Apporter votre carte de membre") + .materielNecessaire("Aucun") + .conditionsMeteo("Intérieur") + .imageUrl("https://example.com/image.jpg") + .couleurTheme("#FF5733") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.titre()).isEqualTo("Assemblée Générale 2025"); + assertThat(request.description()).contains("Réunion annuelle"); + assertThat(request.typeEvenement()).isEqualTo(TypeEvenementMetier.ASSEMBLEE_GENERALE); + assertThat(request.statut()).isEqualTo(StatutEvenement.PLANIFIE); + assertThat(request.priorite()).isEqualTo(PrioriteEvenement.HAUTE); + assertThat(request.dateDebut()).isEqualTo(dateDebut); + assertThat(request.dateFin()).isEqualTo(dateFin); + assertThat(request.heureDebut()).isEqualTo(LocalTime.of(9, 0)); + assertThat(request.heureFin()).isEqualTo(LocalTime.of(17, 0)); + assertThat(request.lieu()).isEqualTo("Salle des Congrès"); + assertThat(request.ville()).isEqualTo("Dakar"); + assertThat(request.capaciteMax()).isEqualTo(500); + assertThat(request.budget()).isEqualByComparingTo(new BigDecimal("5000000.00")); + assertThat(request.codeDevise()).isEqualTo("XOF"); + assertThat(request.inscriptionObligatoire()).isTrue(); + assertThat(request.couleurTheme()).isEqualTo("#FF5733"); + } + + @Test + void testBuilder_MinimalFields() { + UUID associationId = UUID.randomUUID(); + LocalDate dateDebut = LocalDate.now().plusDays(1); + + CreateEvenementRequest request = CreateEvenementRequest.builder() + .titre("Événement Simple") + .typeEvenement(TypeEvenementMetier.FORMATION) + .statut(StatutEvenement.CONFIRME) + .dateDebut(dateDebut) + .lieu("Salle A") + .associationId(associationId) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.titre()).isEqualTo("Événement Simple"); + assertThat(request.typeEvenement()).isEqualTo(TypeEvenementMetier.FORMATION); + assertThat(request.statut()).isEqualTo(StatutEvenement.CONFIRME); + assertThat(request.dateDebut()).isEqualTo(dateDebut); + assertThat(request.lieu()).isEqualTo("Salle A"); + assertThat(request.associationId()).isEqualTo(associationId); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateEvenementRequest request = CreateEvenementRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("titre")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeEvenement")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("statut")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateDebut")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("lieu")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("associationId")); + } + + @Test + void testValidation_TitreTooShort() { + CreateEvenementRequest request = CreateEvenementRequest.builder() + .titre("AB") + .typeEvenement(TypeEvenementMetier.CONFERENCE) + .statut(StatutEvenement.PLANIFIE) + .dateDebut(LocalDate.now().plusDays(1)) + .lieu("Lieu") + .associationId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("titre")); + } + + @Test + void testValidation_EmailInvalide() { + CreateEvenementRequest request = CreateEvenementRequest.builder() + .titre("Événement Test") + .typeEvenement(TypeEvenementMetier.ATELIER) + .statut(StatutEvenement.PLANIFIE) + .dateDebut(LocalDate.now().plusDays(1)) + .lieu("Lieu") + .associationId(UUID.randomUUID()) + .emailOrganisateur("invalid-email") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("emailOrganisateur")); + } + + @Test + void testValidation_LatitudeInvalide() { + CreateEvenementRequest request = CreateEvenementRequest.builder() + .titre("Événement Test") + .typeEvenement(TypeEvenementMetier.CEREMONIE) + .statut(StatutEvenement.PLANIFIE) + .dateDebut(LocalDate.now().plusDays(1)) + .lieu("Lieu") + .associationId(UUID.randomUUID()) + .latitude(new BigDecimal("95.0")) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("latitude")); + } + + @Test + void testValidation_LongitudeInvalide() { + CreateEvenementRequest request = CreateEvenementRequest.builder() + .titre("Événement Test") + .typeEvenement(TypeEvenementMetier.ACTION_CARITATIVE) + .statut(StatutEvenement.PLANIFIE) + .dateDebut(LocalDate.now().plusDays(1)) + .lieu("Lieu") + .associationId(UUID.randomUUID()) + .longitude(new BigDecimal("-185.0")) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("longitude")); + } + + @Test + void testValidation_CouleurThemeInvalide() { + CreateEvenementRequest request = CreateEvenementRequest.builder() + .titre("Événement Test") + .typeEvenement(TypeEvenementMetier.AUTRE) + .statut(StatutEvenement.PLANIFIE) + .dateDebut(LocalDate.now().plusDays(1)) + .lieu("Lieu") + .associationId(UUID.randomUUID()) + .couleurTheme("invalid") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("couleurTheme")); + } + + @Test + void testValidation_ValidFields() { + CreateEvenementRequest request = CreateEvenementRequest.builder() + .titre("Événement Valide") + .typeEvenement(TypeEvenementMetier.REUNION_BUREAU) + .statut(StatutEvenement.CONFIRME) + .dateDebut(LocalDate.now().plusDays(5)) + .lieu("Bureau Central") + .associationId(UUID.randomUUID()) + .emailOrganisateur("valid@example.com") + .telephoneOrganisateur("+221 77 123 45 67") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID associationId = UUID.randomUUID(); + LocalDate dateDebut = LocalDate.now().plusDays(1); + + CreateEvenementRequest request1 = CreateEvenementRequest.builder() + .titre("Même Événement") + .typeEvenement(TypeEvenementMetier.FORMATION) + .statut(StatutEvenement.PLANIFIE) + .dateDebut(dateDebut) + .lieu("Lieu") + .associationId(associationId) + .build(); + + CreateEvenementRequest request2 = CreateEvenementRequest.builder() + .titre("Même Événement") + .typeEvenement(TypeEvenementMetier.FORMATION) + .statut(StatutEvenement.PLANIFIE) + .dateDebut(dateDebut) + .lieu("Lieu") + .associationId(associationId) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateEvenementRequest request = CreateEvenementRequest.builder() + .titre("Test ToString") + .typeEvenement(TypeEvenementMetier.ACTIVITE_SOCIALE) + .statut(StatutEvenement.PLANIFIE) + .dateDebut(LocalDate.now().plusDays(1)) + .lieu("Test Lieu") + .associationId(UUID.randomUUID()) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateEvenementRequest"); + assertThat(toString).contains("Test ToString"); + assertThat(toString).contains("ACTIVITE_SOCIALE"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/evenement/request/UpdateEvenementRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/evenement/request/UpdateEvenementRequestTest.java index 16a52d4..4720854 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/evenement/request/UpdateEvenementRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/evenement/request/UpdateEvenementRequestTest.java @@ -1,205 +1,205 @@ -package dev.lions.unionflow.server.api.dto.evenement.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; -import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; -import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalTime; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateEvenementRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDate dateDebut = LocalDate.now().plusDays(15); - LocalDate dateFin = LocalDate.now().plusDays(17); - LocalDate dateLimite = LocalDate.now().plusDays(10); - - UpdateEvenementRequest request = UpdateEvenementRequest.builder() - .titre("Événement Mis à Jour") - .description("Description modifiée") - .typeEvenement(TypeEvenementMetier.CONFERENCE) - .statut(StatutEvenement.CONFIRME) - .priorite(PrioriteEvenement.NORMALE) - .dateDebut(dateDebut) - .dateFin(dateFin) - .heureDebut(LocalTime.of(10, 0)) - .heureFin(LocalTime.of(18, 0)) - .lieu("Nouveau Lieu") - .adresse("Nouvelle Adresse") - .ville("Saint-Louis") - .region("Saint-Louis") - .latitude(new BigDecimal("16.0333")) - .longitude(new BigDecimal("-16.5000")) - .organisateur("Nouveau Organisateur") - .emailOrganisateur("nouveau@example.com") - .telephoneOrganisateur("+221 77 987 65 43") - .capaciteMax(800) - .budget(new BigDecimal("8000000.00")) - .coutReel(new BigDecimal("7500000.00")) - .codeDevise("XOF") - .inscriptionObligatoire(false) - .dateLimiteInscription(dateLimite) - .evenementPublic(true) - .recurrent(true) - .frequenceRecurrence("MENSUEL") - .instructions("Nouvelles instructions") - .materielNecessaire("Ordinateur portable") - .conditionsMeteo("Extérieur") - .imageUrl("https://example.com/new-image.jpg") - .couleurTheme("#3498DB") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.titre()).isEqualTo("Événement Mis à Jour"); - assertThat(request.description()).isEqualTo("Description modifiée"); - assertThat(request.typeEvenement()).isEqualTo(TypeEvenementMetier.CONFERENCE); - assertThat(request.statut()).isEqualTo(StatutEvenement.CONFIRME); - assertThat(request.priorite()).isEqualTo(PrioriteEvenement.NORMALE); - assertThat(request.dateDebut()).isEqualTo(dateDebut); - assertThat(request.dateFin()).isEqualTo(dateFin); - assertThat(request.lieu()).isEqualTo("Nouveau Lieu"); - assertThat(request.ville()).isEqualTo("Saint-Louis"); - assertThat(request.capaciteMax()).isEqualTo(800); - assertThat(request.budget()).isEqualByComparingTo(new BigDecimal("8000000.00")); - assertThat(request.evenementPublic()).isTrue(); - assertThat(request.recurrent()).isTrue(); - assertThat(request.couleurTheme()).isEqualTo("#3498DB"); - } - - @Test - void testBuilder_MinimalFields() { - UpdateEvenementRequest request = UpdateEvenementRequest.builder() - .titre("Titre Simple") - .lieu("Lieu Simple") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.titre()).isEqualTo("Titre Simple"); - assertThat(request.lieu()).isEqualTo("Lieu Simple"); - assertThat(request.description()).isNull(); - assertThat(request.typeEvenement()).isNull(); - assertThat(request.statut()).isNull(); - } - - @Test - void testValidation_EmptyLieu() { - UpdateEvenementRequest request = UpdateEvenementRequest.builder().lieu("").build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("lieu")); - } - - @Test - void testValidation_EmailInvalide() { - UpdateEvenementRequest request = UpdateEvenementRequest.builder() - .lieu("Lieu Test") - .emailOrganisateur("not-an-email") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("emailOrganisateur")); - } - - @Test - void testValidation_LatitudeInvalide() { - UpdateEvenementRequest request = UpdateEvenementRequest.builder() - .lieu("Lieu Test") - .latitude(new BigDecimal("100.0")) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("latitude")); - } - - @Test - void testValidation_CouleurThemeInvalide() { - UpdateEvenementRequest request = UpdateEvenementRequest.builder() - .lieu("Lieu Test") - .couleurTheme("NotAColor") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("couleurTheme")); - } - - @Test - void testValidation_ValidFields() { - UpdateEvenementRequest request = UpdateEvenementRequest.builder() - .titre("Événement Valide") - .lieu("Lieu Valide") - .typeEvenement(TypeEvenementMetier.ATELIER) - .statut(StatutEvenement.EN_COURS) - .emailOrganisateur("valide@test.com") - .telephoneOrganisateur("+221 33 111 22 33") - .latitude(new BigDecimal("14.5")) - .longitude(new BigDecimal("-17.5")) - .couleurTheme("#AABBCC") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UpdateEvenementRequest request1 = UpdateEvenementRequest.builder() - .titre("Même Titre") - .lieu("Même Lieu") - .statut(StatutEvenement.REPORTE) - .build(); - - UpdateEvenementRequest request2 = UpdateEvenementRequest.builder() - .titre("Même Titre") - .lieu("Même Lieu") - .statut(StatutEvenement.REPORTE) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateEvenementRequest request = UpdateEvenementRequest.builder() - .titre("ToString Test") - .lieu("Test Lieu") - .typeEvenement(TypeEvenementMetier.CEREMONIE) - .statut(StatutEvenement.TERMINE) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateEvenementRequest"); - assertThat(toString).contains("ToString Test"); - assertThat(toString).contains("CEREMONIE"); - assertThat(toString).contains("TERMINE"); - } -} +package dev.lions.unionflow.server.api.dto.evenement.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; +import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; +import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalTime; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateEvenementRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDate dateDebut = LocalDate.now().plusDays(15); + LocalDate dateFin = LocalDate.now().plusDays(17); + LocalDate dateLimite = LocalDate.now().plusDays(10); + + UpdateEvenementRequest request = UpdateEvenementRequest.builder() + .titre("Événement Mis à Jour") + .description("Description modifiée") + .typeEvenement(TypeEvenementMetier.CONFERENCE) + .statut(StatutEvenement.CONFIRME) + .priorite(PrioriteEvenement.NORMALE) + .dateDebut(dateDebut) + .dateFin(dateFin) + .heureDebut(LocalTime.of(10, 0)) + .heureFin(LocalTime.of(18, 0)) + .lieu("Nouveau Lieu") + .adresse("Nouvelle Adresse") + .ville("Saint-Louis") + .region("Saint-Louis") + .latitude(new BigDecimal("16.0333")) + .longitude(new BigDecimal("-16.5000")) + .organisateur("Nouveau Organisateur") + .emailOrganisateur("nouveau@example.com") + .telephoneOrganisateur("+221 77 987 65 43") + .capaciteMax(800) + .budget(new BigDecimal("8000000.00")) + .coutReel(new BigDecimal("7500000.00")) + .codeDevise("XOF") + .inscriptionObligatoire(false) + .dateLimiteInscription(dateLimite) + .evenementPublic(true) + .recurrent(true) + .frequenceRecurrence("MENSUEL") + .instructions("Nouvelles instructions") + .materielNecessaire("Ordinateur portable") + .conditionsMeteo("Extérieur") + .imageUrl("https://example.com/new-image.jpg") + .couleurTheme("#3498DB") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.titre()).isEqualTo("Événement Mis à Jour"); + assertThat(request.description()).isEqualTo("Description modifiée"); + assertThat(request.typeEvenement()).isEqualTo(TypeEvenementMetier.CONFERENCE); + assertThat(request.statut()).isEqualTo(StatutEvenement.CONFIRME); + assertThat(request.priorite()).isEqualTo(PrioriteEvenement.NORMALE); + assertThat(request.dateDebut()).isEqualTo(dateDebut); + assertThat(request.dateFin()).isEqualTo(dateFin); + assertThat(request.lieu()).isEqualTo("Nouveau Lieu"); + assertThat(request.ville()).isEqualTo("Saint-Louis"); + assertThat(request.capaciteMax()).isEqualTo(800); + assertThat(request.budget()).isEqualByComparingTo(new BigDecimal("8000000.00")); + assertThat(request.evenementPublic()).isTrue(); + assertThat(request.recurrent()).isTrue(); + assertThat(request.couleurTheme()).isEqualTo("#3498DB"); + } + + @Test + void testBuilder_MinimalFields() { + UpdateEvenementRequest request = UpdateEvenementRequest.builder() + .titre("Titre Simple") + .lieu("Lieu Simple") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.titre()).isEqualTo("Titre Simple"); + assertThat(request.lieu()).isEqualTo("Lieu Simple"); + assertThat(request.description()).isNull(); + assertThat(request.typeEvenement()).isNull(); + assertThat(request.statut()).isNull(); + } + + @Test + void testValidation_EmptyLieu() { + UpdateEvenementRequest request = UpdateEvenementRequest.builder().lieu("").build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("lieu")); + } + + @Test + void testValidation_EmailInvalide() { + UpdateEvenementRequest request = UpdateEvenementRequest.builder() + .lieu("Lieu Test") + .emailOrganisateur("not-an-email") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("emailOrganisateur")); + } + + @Test + void testValidation_LatitudeInvalide() { + UpdateEvenementRequest request = UpdateEvenementRequest.builder() + .lieu("Lieu Test") + .latitude(new BigDecimal("100.0")) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("latitude")); + } + + @Test + void testValidation_CouleurThemeInvalide() { + UpdateEvenementRequest request = UpdateEvenementRequest.builder() + .lieu("Lieu Test") + .couleurTheme("NotAColor") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("couleurTheme")); + } + + @Test + void testValidation_ValidFields() { + UpdateEvenementRequest request = UpdateEvenementRequest.builder() + .titre("Événement Valide") + .lieu("Lieu Valide") + .typeEvenement(TypeEvenementMetier.ATELIER) + .statut(StatutEvenement.EN_COURS) + .emailOrganisateur("valide@test.com") + .telephoneOrganisateur("+221 33 111 22 33") + .latitude(new BigDecimal("14.5")) + .longitude(new BigDecimal("-17.5")) + .couleurTheme("#AABBCC") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UpdateEvenementRequest request1 = UpdateEvenementRequest.builder() + .titre("Même Titre") + .lieu("Même Lieu") + .statut(StatutEvenement.REPORTE) + .build(); + + UpdateEvenementRequest request2 = UpdateEvenementRequest.builder() + .titre("Même Titre") + .lieu("Même Lieu") + .statut(StatutEvenement.REPORTE) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateEvenementRequest request = UpdateEvenementRequest.builder() + .titre("ToString Test") + .lieu("Test Lieu") + .typeEvenement(TypeEvenementMetier.CEREMONIE) + .statut(StatutEvenement.TERMINE) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateEvenementRequest"); + assertThat(toString).contains("ToString Test"); + assertThat(toString).contains("CEREMONIE"); + assertThat(toString).contains("TERMINE"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/evenement/response/EvenementResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/evenement/response/EvenementResponseTest.java index 9264da4..41e46a8 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/evenement/response/EvenementResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/evenement/response/EvenementResponseTest.java @@ -1,750 +1,750 @@ -package dev.lions.unionflow.server.api.dto.evenement.response; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalDateTime; -import java.time.LocalTime; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; -import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; -import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; - -/** - * Tests unitaires pour EvenementResponse. - * Couvre getAdresseComplete (toutes branches avec séparateur), getTauxPresence, - * sontInscriptionsOuvertes, estBudgetDepasse, getEcartBudgetaire, et autres méthodes. - */ -@DisplayName("Tests EvenementResponse") -class EvenementResponseTest { - - private static EvenementResponse base() { - return EvenementResponse.builder() - .titre("Event") - .typeEvenement(TypeEvenementMetier.CONFERENCE) - .statut(StatutEvenement.PLANIFIE) - .priorite(PrioriteEvenement.NORMALE) - .dateDebut(LocalDate.now().plusDays(1)) - .dateFin(LocalDate.now().plusDays(1)) - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(18, 0)) - .capaciteMax(100) - .participantsInscrits(10) - .build(); - } - - @Nested - @DisplayName("getAdresseComplete") - class GetAdresseComplete { - - @Test - @DisplayName("retourne chaîne vide quand tout null") - void testVide() { - EvenementResponse r = EvenementResponse.builder().build(); - assertThat(r.getAdresseComplete()).isEmpty(); - } - - @Test - @DisplayName("concatène lieu, adresse, ville, region avec séparateur") - void testAvecSeparateur() { - EvenementResponse r = EvenementResponse.builder() - .lieu("Salle A") - .adresse("1 rue Test") - .ville("Paris") - .region("Île-de-France") - .build(); - assertThat(r.getAdresseComplete()) - .isEqualTo("Salle A, 1 rue Test, Paris, Île-de-France"); - } - - @Test - @DisplayName("lieu seul sans virgule") - void testLieuSeul() { - EvenementResponse r = EvenementResponse.builder().lieu("Salle A").build(); - assertThat(r.getAdresseComplete()).isEqualTo("Salle A"); - } - - @Test - @DisplayName("adresse après lieu avec virgule") - void testLieuEtAdresse() { - EvenementResponse r = EvenementResponse.builder() - .lieu("Salle A") - .adresse("1 rue Test") - .build(); - assertThat(r.getAdresseComplete()).isEqualTo("Salle A, 1 rue Test"); - } - - @Test - @DisplayName("ville après adresse avec virgule") - void testAvecVille() { - EvenementResponse r = EvenementResponse.builder() - .lieu("Salle A") - .ville("Lyon") - .build(); - assertThat(r.getAdresseComplete()).isEqualTo("Salle A, Lyon"); - } - - @Test - @DisplayName("ignore champs vides ou blancs") - void testChampsVides() { - EvenementResponse r = EvenementResponse.builder() - .lieu(" ") - .adresse("") - .ville("Lyon") - .build(); - assertThat(r.getAdresseComplete()).isEqualTo("Lyon"); - } - - @Test - @DisplayName("adresse seule sans virgule (premier champ)") - void testAdresseSeule() { - EvenementResponse r = EvenementResponse.builder() - .adresse("1 rue Test") - .build(); - assertThat(r.getAdresseComplete()).isEqualTo("1 rue Test"); - } - - @Test - @DisplayName("ville avec espaces uniquement est ignorée") - void testVilleEspaces() { - EvenementResponse r = EvenementResponse.builder() - .lieu("Salle") - .ville(" ") - .build(); - assertThat(r.getAdresseComplete()).isEqualTo("Salle"); - } - - @Test - @DisplayName("region avec espaces uniquement est ignorée") - void testRegionEspaces() { - EvenementResponse r = EvenementResponse.builder() - .lieu("Salle") - .region(" ") - .build(); - assertThat(r.getAdresseComplete()).isEqualTo("Salle"); - } - - @Test - @DisplayName("region seule sans virgule (premier champ)") - void testRegionSeule() { - EvenementResponse r = EvenementResponse.builder() - .region("Île-de-France") - .build(); - assertThat(r.getAdresseComplete()).isEqualTo("Île-de-France"); - } - } - - @Nested - @DisplayName("getTauxPresence") - class GetTauxPresence { - - @Test - @DisplayName("retourne 0 quand participantsInscrits null") - void testInscritsNull() { - EvenementResponse r = base(); - r.setParticipantsInscrits(null); - r.setParticipantsPresents(5); - assertThat(r.getTauxPresence()).isEqualTo(0); - } - - @Test - @DisplayName("retourne 0 quand participantsInscrits 0") - void testInscritsZero() { - EvenementResponse r = base(); - r.setParticipantsInscrits(0); - r.setParticipantsPresents(0); - assertThat(r.getTauxPresence()).isEqualTo(0); - } - - @Test - @DisplayName("retourne 0 quand participantsPresents null") - void testPresentsNull() { - EvenementResponse r = base(); - r.setParticipantsInscrits(10); - r.setParticipantsPresents(null); - assertThat(r.getTauxPresence()).isEqualTo(0); - } - - @Test - @DisplayName("calcule pourcentage présence") - void testCalcul() { - EvenementResponse r = base(); - r.setParticipantsInscrits(100); - r.setParticipantsPresents(75); - assertThat(r.getTauxPresence()).isEqualTo(75); - } - } - - @Nested - @DisplayName("sontInscriptionsOuvertes") - class SontInscriptionsOuvertes { - - @Test - @DisplayName("false quand événement annulé") - void testAnnule() { - EvenementResponse r = base(); - r.setStatut(StatutEvenement.ANNULE); - assertThat(r.sontInscriptionsOuvertes()).isFalse(); - } - - @Test - @DisplayName("false quand événement terminé") - void testTermine() { - EvenementResponse r = base(); - r.setStatut(StatutEvenement.TERMINE); - assertThat(r.sontInscriptionsOuvertes()).isFalse(); - } - - @Test - @DisplayName("false quand dateLimiteInscription dépassée") - void testDateLimitePassee() { - EvenementResponse r = base(); - r.setDateLimiteInscription(LocalDate.now().minusDays(1)); - assertThat(r.sontInscriptionsOuvertes()).isFalse(); - } - - @Test - @DisplayName("false quand événement complet") - void testComplet() { - EvenementResponse r = base(); - r.setCapaciteMax(10); - r.setParticipantsInscrits(10); - assertThat(r.sontInscriptionsOuvertes()).isFalse(); - } - - @Test - @DisplayName("true quand inscriptions ouvertes") - void testOuvertes() { - EvenementResponse r = base(); - r.setDateLimiteInscription(LocalDate.now().plusDays(5)); - r.setCapaciteMax(100); - r.setParticipantsInscrits(50); - assertThat(r.sontInscriptionsOuvertes()).isTrue(); - } - } - - @Nested - @DisplayName("getDureeEnHeures, estEvenementMultiJours, getTypeEvenementLibelle, getStatutLibelle, getPrioriteLibelle") - class AutresMethodes { - - @Test - @DisplayName("getDureeEnHeures retourne 0 si heureDebut ou heureFin null") - void testDureeNull() { - EvenementResponse r = base(); - r.setHeureDebut(null); - assertThat(r.getDureeEnHeures()).isEqualTo(0); - r.setHeureDebut(LocalTime.of(9, 0)); - r.setHeureFin(null); - assertThat(r.getDureeEnHeures()).isEqualTo(0); - } - - @Test - @DisplayName("getDureeEnHeures calcule la durée") - void testDuree() { - EvenementResponse r = base(); - r.setHeureDebut(LocalTime.of(9, 0)); - r.setHeureFin(LocalTime.of(18, 0)); - assertThat(r.getDureeEnHeures()).isEqualTo(9); - } - - @Test - @DisplayName("estEvenementMultiJours true quand dateDebut != dateFin") - void testMultiJours() { - EvenementResponse r = base(); - r.setDateDebut(LocalDate.now()); - r.setDateFin(LocalDate.now().plusDays(2)); - assertThat(r.estEvenementMultiJours()).isTrue(); - } - - @Test - @DisplayName("getTypeEvenementLibelle retourne Non défini si type null") - void testTypeNull() { - EvenementResponse r = base(); - r.setTypeEvenement(null); - assertThat(r.getTypeEvenementLibelle()).isEqualTo("Non défini"); - } - - @Test - @DisplayName("getStatutLibelle retourne Non défini si statut null") - void testStatutNull() { - EvenementResponse r = base(); - r.setStatut(null); - assertThat(r.getStatutLibelle()).isEqualTo("Non défini"); - } - - @Test - @DisplayName("getPrioriteLibelle retourne Normale si priorite null") - void testPrioriteNull() { - EvenementResponse r = base(); - r.setPriorite(null); - assertThat(r.getPrioriteLibelle()).isEqualTo("Normale"); - } - } - - @Nested - @DisplayName("hasCoordonnees, getEcartBudgetaire, estBudgetDepasse") - class BudgetEtCoordonnees { - - @Test - @DisplayName("hasCoordonnees true quand latitude et longitude non null") - void testCoordonnees() { - EvenementResponse r = base(); - r.setLatitude(BigDecimal.ONE); - r.setLongitude(BigDecimal.ONE); - assertThat(r.hasCoordonnees()).isTrue(); - } - - @Test - @DisplayName("hasCoordonnees false si un des deux null") - void testCoordonneesNull() { - EvenementResponse r = base(); - assertThat(r.hasCoordonnees()).isFalse(); - r.setLatitude(BigDecimal.ONE); - assertThat(r.hasCoordonnees()).isFalse(); - } - - @Test - @DisplayName("getEcartBudgetaire retourne ZERO si budget ou coutReel null") - void testEcartNull() { - EvenementResponse r = base(); - assertThat(r.getEcartBudgetaire()).isEqualTo(BigDecimal.ZERO); - r.setBudget(BigDecimal.valueOf(1000)); - assertThat(r.getEcartBudgetaire()).isEqualTo(BigDecimal.ZERO); - } - - @Test - @DisplayName("getEcartBudgetaire calcule budget - coutReel") - void testEcart() { - EvenementResponse r = base(); - r.setBudget(BigDecimal.valueOf(1000)); - r.setCoutReel(BigDecimal.valueOf(800)); - assertThat(r.getEcartBudgetaire()).isEqualByComparingTo(BigDecimal.valueOf(200)); - } - - @Test - @DisplayName("estBudgetDepasse true quand coutReel > budget") - void testBudgetDepasse() { - EvenementResponse r = base(); - r.setBudget(BigDecimal.valueOf(1000)); - r.setCoutReel(BigDecimal.valueOf(1200)); - assertThat(r.estBudgetDepasse()).isTrue(); - } - - @Test - @DisplayName("estBudgetDepasse false quand budget >= coutReel") - void testBudgetOk() { - EvenementResponse r = base(); - r.setBudget(BigDecimal.valueOf(1000)); - r.setCoutReel(BigDecimal.valueOf(1000)); - assertThat(r.estBudgetDepasse()).isFalse(); - } - } - - @Nested - @DisplayName("getPlacesDisponibles") - class GetPlacesDisponibles { - - @Test - @DisplayName("retourne 0 quand capaciteMax null") - void testCapaciteNull() { - EvenementResponse r = base(); - r.setCapaciteMax(null); - r.setParticipantsInscrits(50); - assertThat(r.getPlacesDisponibles()).isEqualTo(0); - } - - @Test - @DisplayName("retourne 0 quand participantsInscrits null") - void testInscritsNull() { - EvenementResponse r = base(); - r.setCapaciteMax(100); - r.setParticipantsInscrits(null); - assertThat(r.getPlacesDisponibles()).isEqualTo(0); - } - - @Test - @DisplayName("retourne différence capaciteMax - participantsInscrits") - void testCalcul() { - EvenementResponse r = base(); - r.setCapaciteMax(100); - r.setParticipantsInscrits(70); - assertThat(r.getPlacesDisponibles()).isEqualTo(30); - } - - @Test - @DisplayName("retourne 0 quand participantsInscrits >= capaciteMax") - void testComplet() { - EvenementResponse r = base(); - r.setCapaciteMax(100); - r.setParticipantsInscrits(110); - assertThat(r.getPlacesDisponibles()).isEqualTo(0); - } - } - - @Nested - @DisplayName("getTauxRemplissage") - class GetTauxRemplissage { - - @Test - @DisplayName("retourne 0 quand capaciteMax null") - void testCapaciteNull() { - EvenementResponse r = base(); - r.setCapaciteMax(null); - r.setParticipantsInscrits(50); - assertThat(r.getTauxRemplissage()).isEqualTo(0); - } - - @Test - @DisplayName("retourne 0 quand capaciteMax = 0") - void testCapaciteZero() { - EvenementResponse r = base(); - r.setCapaciteMax(0); - r.setParticipantsInscrits(0); - assertThat(r.getTauxRemplissage()).isEqualTo(0); - } - - @Test - @DisplayName("retourne 0 quand participantsInscrits null") - void testInscritsNull() { - EvenementResponse r = base(); - r.setCapaciteMax(100); - r.setParticipantsInscrits(null); - assertThat(r.getTauxRemplissage()).isEqualTo(0); - } - - @Test - @DisplayName("calcule pourcentage remplissage") - void testCalcul() { - EvenementResponse r = base(); - r.setCapaciteMax(100); - r.setParticipantsInscrits(75); - assertThat(r.getTauxRemplissage()).isEqualTo(75); - } - - @Test - @DisplayName("retourne 100 quand capaciteMax = participantsInscrits") - void testComplet() { - EvenementResponse r = base(); - r.setCapaciteMax(100); - r.setParticipantsInscrits(100); - assertThat(r.getTauxRemplissage()).isEqualTo(100); - } - - @Test - @DisplayName("retourne > 100 quand participantsInscrits > capaciteMax") - void testSurReservation() { - EvenementResponse r = base(); - r.setCapaciteMax(100); - r.setParticipantsInscrits(120); - assertThat(r.getTauxRemplissage()).isEqualTo(120); - } - } - - @Nested - @DisplayName("Branches manquantes") - class BranchesManquantes { - - @Test - @DisplayName("getPrioriteLibelle retourne libellé quand priorite non null") - void testPrioriteNonNull() { - EvenementResponse r = base(); - r.setPriorite(PrioriteEvenement.HAUTE); - assertThat(r.getPrioriteLibelle()).isEqualTo(PrioriteEvenement.HAUTE.getLibelle()); - } - - @Test - @DisplayName("estEvenementMultiJours false quand dateFin null") - void testDateFinNull() { - EvenementResponse r = base(); - r.setDateFin(null); - assertThat(r.estEvenementMultiJours()).isFalse(); - } - - @Test - @DisplayName("estEvenementMultiJours false quand dateDebut = dateFin") - void testMemeJour() { - EvenementResponse r = base(); - LocalDate date = LocalDate.now(); - r.setDateDebut(date); - r.setDateFin(date); - assertThat(r.estEvenementMultiJours()).isFalse(); - } - - @Test - @DisplayName("estComplet false quand capaciteMax null") - void testCompletCapaciteNull() { - EvenementResponse r = base(); - r.setCapaciteMax(null); - r.setParticipantsInscrits(100); - assertThat(r.estComplet()).isFalse(); - } - - @Test - @DisplayName("estComplet false quand participantsInscrits null") - void testCompletInscritsNull() { - EvenementResponse r = base(); - r.setCapaciteMax(100); - r.setParticipantsInscrits(null); - assertThat(r.estComplet()).isFalse(); - } - } - - @Nested - @DisplayName("getTypeEvenementIcon") - class GetTypeEvenementIcon { - - @Test - @DisplayName("retourne icône par défaut quand type null") - void testNull() { - EvenementResponse r = EvenementResponse.builder().build(); - assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-calendar"); - } - - @Test - @DisplayName("ASSEMBLEE_GENERALE → pi pi-building") - void testAssembleeGenerale() { - EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.ASSEMBLEE_GENERALE).build(); - assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-building"); - } - - @Test - @DisplayName("FORMATION → pi pi-book") - void testFormation() { - EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.FORMATION).build(); - assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-book"); - } - - @Test - @DisplayName("REUNION_BUREAU → pi pi-users") - void testReunionBureau() { - EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.REUNION_BUREAU).build(); - assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-users"); - } - - @Test - @DisplayName("CONFERENCE → pi pi-microphone") - void testConference() { - EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.CONFERENCE).build(); - assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-microphone"); - } - - @Test - @DisplayName("ATELIER → pi pi-wrench") - void testAtelier() { - EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.ATELIER).build(); - assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-wrench"); - } - - @Test - @DisplayName("CEREMONIE → pi pi-flag") - void testCeremonie() { - EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.CEREMONIE).build(); - assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-flag"); - } - - @Test - @DisplayName("ACTIVITE_SOCIALE, ACTION_CARITATIVE, AUTRE → pi pi-calendar") - void testAutres() { - assertThat(EvenementResponse.builder().typeEvenement(TypeEvenementMetier.ACTIVITE_SOCIALE).build().getTypeEvenementIcon()).isEqualTo("pi pi-calendar"); - assertThat(EvenementResponse.builder().typeEvenement(TypeEvenementMetier.ACTION_CARITATIVE).build().getTypeEvenementIcon()).isEqualTo("pi pi-calendar"); - assertThat(EvenementResponse.builder().typeEvenement(TypeEvenementMetier.AUTRE).build().getTypeEvenementIcon()).isEqualTo("pi pi-calendar"); - } - } - - @Nested - @DisplayName("getTypeEvenementSeverity") - class GetTypeEvenementSeverity { - - @Test - @DisplayName("retourne secondary quand type null") - void testNull() { - EvenementResponse r = EvenementResponse.builder().build(); - assertThat(r.getTypeEvenementSeverity()).isEqualTo("secondary"); - } - - @Test - @DisplayName("ASSEMBLEE_GENERALE → warning") - void testAssembleeGenerale() { - EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.ASSEMBLEE_GENERALE).build(); - assertThat(r.getTypeEvenementSeverity()).isEqualTo("warning"); - } - - @Test - @DisplayName("FORMATION → info") - void testFormation() { - EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.FORMATION).build(); - assertThat(r.getTypeEvenementSeverity()).isEqualTo("info"); - } - - @Test - @DisplayName("autres types → secondary") - void testAutres() { - for (TypeEvenementMetier t : new TypeEvenementMetier[]{ - TypeEvenementMetier.ACTIVITE_SOCIALE, TypeEvenementMetier.ACTION_CARITATIVE, - TypeEvenementMetier.REUNION_BUREAU, TypeEvenementMetier.CONFERENCE, - TypeEvenementMetier.ATELIER, TypeEvenementMetier.CEREMONIE, TypeEvenementMetier.AUTRE}) { - assertThat(EvenementResponse.builder().typeEvenement(t).build().getTypeEvenementSeverity()) - .as("Type: %s", t).isEqualTo("secondary"); - } - } - } - - @Nested - @DisplayName("getStatutSeverity") - class GetStatutSeverity { - - @Test - @DisplayName("retourne secondary quand statut null") - void testNull() { - EvenementResponse r = EvenementResponse.builder().build(); - assertThat(r.getStatutSeverity()).isEqualTo("secondary"); - } - - @Test - @DisplayName("PLANIFIE → info") - void testPlanifie() { - assertThat(EvenementResponse.builder().statut(StatutEvenement.PLANIFIE).build().getStatutSeverity()).isEqualTo("info"); - } - - @Test - @DisplayName("EN_COURS → success") - void testEnCours() { - assertThat(EvenementResponse.builder().statut(StatutEvenement.EN_COURS).build().getStatutSeverity()).isEqualTo("success"); - } - - @Test - @DisplayName("TERMINE et CONFIRME → secondary") - void testTermineConfirme() { - assertThat(EvenementResponse.builder().statut(StatutEvenement.TERMINE).build().getStatutSeverity()).isEqualTo("secondary"); - assertThat(EvenementResponse.builder().statut(StatutEvenement.CONFIRME).build().getStatutSeverity()).isEqualTo("secondary"); - } - - @Test - @DisplayName("ANNULE → danger") - void testAnnule() { - assertThat(EvenementResponse.builder().statut(StatutEvenement.ANNULE).build().getStatutSeverity()).isEqualTo("danger"); - } - - @Test - @DisplayName("REPORTE → warning") - void testReporte() { - assertThat(EvenementResponse.builder().statut(StatutEvenement.REPORTE).build().getStatutSeverity()).isEqualTo("warning"); - } - } - - @Nested - @DisplayName("getStatutIcon") - class GetStatutIcon { - - @Test - @DisplayName("retourne pi pi-question quand statut null") - void testNull() { - EvenementResponse r = EvenementResponse.builder().build(); - assertThat(r.getStatutIcon()).isEqualTo("pi pi-question"); - } - - @Test - @DisplayName("tous les statuts retournent la bonne icône") - void testTousStatuts() { - assertThat(EvenementResponse.builder().statut(StatutEvenement.PLANIFIE).build().getStatutIcon()).isEqualTo("pi pi-clock"); - assertThat(EvenementResponse.builder().statut(StatutEvenement.CONFIRME).build().getStatutIcon()).isEqualTo("pi pi-check-circle"); - assertThat(EvenementResponse.builder().statut(StatutEvenement.EN_COURS).build().getStatutIcon()).isEqualTo("pi pi-play"); - assertThat(EvenementResponse.builder().statut(StatutEvenement.TERMINE).build().getStatutIcon()).isEqualTo("pi pi-check"); - assertThat(EvenementResponse.builder().statut(StatutEvenement.ANNULE).build().getStatutIcon()).isEqualTo("pi pi-times"); - assertThat(EvenementResponse.builder().statut(StatutEvenement.REPORTE).build().getStatutIcon()).isEqualTo("pi pi-refresh"); - } - } - - @Nested - @DisplayName("getPrioriteSeverity") - class GetPrioriteSeverity { - - @Test - @DisplayName("retourne secondary quand priorite null") - void testNull() { - EvenementResponse r = EvenementResponse.builder().build(); - assertThat(r.getPrioriteSeverity()).isEqualTo("secondary"); - } - - @Test - @DisplayName("toutes les priorités retournent la bonne sévérité") - void testToutesPriorites() { - assertThat(EvenementResponse.builder().priorite(PrioriteEvenement.CRITIQUE).build().getPrioriteSeverity()).isEqualTo("danger"); - assertThat(EvenementResponse.builder().priorite(PrioriteEvenement.HAUTE).build().getPrioriteSeverity()).isEqualTo("warning"); - assertThat(EvenementResponse.builder().priorite(PrioriteEvenement.NORMALE).build().getPrioriteSeverity()).isEqualTo("info"); - assertThat(EvenementResponse.builder().priorite(PrioriteEvenement.BASSE).build().getPrioriteSeverity()).isEqualTo("secondary"); - } - } - - @Nested - @DisplayName("getDateDebutFormatee, getHeureDebutFormatee, getHeureFinFormatee, getBudgetFormate") - class MethodesFormatage { - - @Test - @DisplayName("getDateDebutFormatee retourne — quand null") - void testDateDebutNull() { - EvenementResponse r = EvenementResponse.builder().build(); - assertThat(r.getDateDebutFormatee()).isEqualTo("—"); - } - - @Test - @DisplayName("getDateDebutFormatee formate en dd/MM/yyyy") - void testDateDebut() { - EvenementResponse r = EvenementResponse.builder().dateDebut(java.time.LocalDate.of(2026, 4, 7)).build(); - assertThat(r.getDateDebutFormatee()).isEqualTo("07/04/2026"); - } - - @Test - @DisplayName("getHeureDebutFormatee retourne — quand null") - void testHeureDebutNull() { - EvenementResponse r = EvenementResponse.builder().build(); - assertThat(r.getHeureDebutFormatee()).isEqualTo("—"); - } - - @Test - @DisplayName("getHeureDebutFormatee formate en HH:mm") - void testHeureDebut() { - EvenementResponse r = EvenementResponse.builder().heureDebut(java.time.LocalTime.of(9, 30)).build(); - assertThat(r.getHeureDebutFormatee()).isEqualTo("09:30"); - } - - @Test - @DisplayName("getHeureFinFormatee retourne — quand null") - void testHeureFinNull() { - EvenementResponse r = EvenementResponse.builder().build(); - assertThat(r.getHeureFinFormatee()).isEqualTo("—"); - } - - @Test - @DisplayName("getHeureFinFormatee formate en HH:mm") - void testHeureFin() { - EvenementResponse r = EvenementResponse.builder().heureFin(java.time.LocalTime.of(18, 0)).build(); - assertThat(r.getHeureFinFormatee()).isEqualTo("18:00"); - } - - @Test - @DisplayName("getBudgetFormate retourne — quand budget null") - void testBudgetNull() { - EvenementResponse r = EvenementResponse.builder().build(); - assertThat(r.getBudgetFormate()).isEqualTo("—"); - } - - @Test - @DisplayName("getBudgetFormate formate avec devise par défaut FCFA") - void testBudgetSansDevise() { - EvenementResponse r = EvenementResponse.builder().budget(java.math.BigDecimal.valueOf(50000)).build(); - assertThat(r.getBudgetFormate()).isEqualTo("50,000 FCFA"); - } - - @Test - @DisplayName("getBudgetFormate formate avec codeDevise fourni") - void testBudgetAvecDevise() { - EvenementResponse r = EvenementResponse.builder().budget(java.math.BigDecimal.valueOf(50000)).codeDevise("EUR").build(); - assertThat(r.getBudgetFormate()).isEqualTo("50,000 EUR"); - } - } -} +package dev.lions.unionflow.server.api.dto.evenement.response; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.time.LocalTime; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; +import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; +import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; + +/** + * Tests unitaires pour EvenementResponse. + * Couvre getAdresseComplete (toutes branches avec séparateur), getTauxPresence, + * sontInscriptionsOuvertes, estBudgetDepasse, getEcartBudgetaire, et autres méthodes. + */ +@DisplayName("Tests EvenementResponse") +class EvenementResponseTest { + + private static EvenementResponse base() { + return EvenementResponse.builder() + .titre("Event") + .typeEvenement(TypeEvenementMetier.CONFERENCE) + .statut(StatutEvenement.PLANIFIE) + .priorite(PrioriteEvenement.NORMALE) + .dateDebut(LocalDate.now().plusDays(1)) + .dateFin(LocalDate.now().plusDays(1)) + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(18, 0)) + .capaciteMax(100) + .participantsInscrits(10) + .build(); + } + + @Nested + @DisplayName("getAdresseComplete") + class GetAdresseComplete { + + @Test + @DisplayName("retourne chaîne vide quand tout null") + void testVide() { + EvenementResponse r = EvenementResponse.builder().build(); + assertThat(r.getAdresseComplete()).isEmpty(); + } + + @Test + @DisplayName("concatène lieu, adresse, ville, region avec séparateur") + void testAvecSeparateur() { + EvenementResponse r = EvenementResponse.builder() + .lieu("Salle A") + .adresse("1 rue Test") + .ville("Paris") + .region("Île-de-France") + .build(); + assertThat(r.getAdresseComplete()) + .isEqualTo("Salle A, 1 rue Test, Paris, Île-de-France"); + } + + @Test + @DisplayName("lieu seul sans virgule") + void testLieuSeul() { + EvenementResponse r = EvenementResponse.builder().lieu("Salle A").build(); + assertThat(r.getAdresseComplete()).isEqualTo("Salle A"); + } + + @Test + @DisplayName("adresse après lieu avec virgule") + void testLieuEtAdresse() { + EvenementResponse r = EvenementResponse.builder() + .lieu("Salle A") + .adresse("1 rue Test") + .build(); + assertThat(r.getAdresseComplete()).isEqualTo("Salle A, 1 rue Test"); + } + + @Test + @DisplayName("ville après adresse avec virgule") + void testAvecVille() { + EvenementResponse r = EvenementResponse.builder() + .lieu("Salle A") + .ville("Lyon") + .build(); + assertThat(r.getAdresseComplete()).isEqualTo("Salle A, Lyon"); + } + + @Test + @DisplayName("ignore champs vides ou blancs") + void testChampsVides() { + EvenementResponse r = EvenementResponse.builder() + .lieu(" ") + .adresse("") + .ville("Lyon") + .build(); + assertThat(r.getAdresseComplete()).isEqualTo("Lyon"); + } + + @Test + @DisplayName("adresse seule sans virgule (premier champ)") + void testAdresseSeule() { + EvenementResponse r = EvenementResponse.builder() + .adresse("1 rue Test") + .build(); + assertThat(r.getAdresseComplete()).isEqualTo("1 rue Test"); + } + + @Test + @DisplayName("ville avec espaces uniquement est ignorée") + void testVilleEspaces() { + EvenementResponse r = EvenementResponse.builder() + .lieu("Salle") + .ville(" ") + .build(); + assertThat(r.getAdresseComplete()).isEqualTo("Salle"); + } + + @Test + @DisplayName("region avec espaces uniquement est ignorée") + void testRegionEspaces() { + EvenementResponse r = EvenementResponse.builder() + .lieu("Salle") + .region(" ") + .build(); + assertThat(r.getAdresseComplete()).isEqualTo("Salle"); + } + + @Test + @DisplayName("region seule sans virgule (premier champ)") + void testRegionSeule() { + EvenementResponse r = EvenementResponse.builder() + .region("Île-de-France") + .build(); + assertThat(r.getAdresseComplete()).isEqualTo("Île-de-France"); + } + } + + @Nested + @DisplayName("getTauxPresence") + class GetTauxPresence { + + @Test + @DisplayName("retourne 0 quand participantsInscrits null") + void testInscritsNull() { + EvenementResponse r = base(); + r.setParticipantsInscrits(null); + r.setParticipantsPresents(5); + assertThat(r.getTauxPresence()).isEqualTo(0); + } + + @Test + @DisplayName("retourne 0 quand participantsInscrits 0") + void testInscritsZero() { + EvenementResponse r = base(); + r.setParticipantsInscrits(0); + r.setParticipantsPresents(0); + assertThat(r.getTauxPresence()).isEqualTo(0); + } + + @Test + @DisplayName("retourne 0 quand participantsPresents null") + void testPresentsNull() { + EvenementResponse r = base(); + r.setParticipantsInscrits(10); + r.setParticipantsPresents(null); + assertThat(r.getTauxPresence()).isEqualTo(0); + } + + @Test + @DisplayName("calcule pourcentage présence") + void testCalcul() { + EvenementResponse r = base(); + r.setParticipantsInscrits(100); + r.setParticipantsPresents(75); + assertThat(r.getTauxPresence()).isEqualTo(75); + } + } + + @Nested + @DisplayName("sontInscriptionsOuvertes") + class SontInscriptionsOuvertes { + + @Test + @DisplayName("false quand événement annulé") + void testAnnule() { + EvenementResponse r = base(); + r.setStatut(StatutEvenement.ANNULE); + assertThat(r.sontInscriptionsOuvertes()).isFalse(); + } + + @Test + @DisplayName("false quand événement terminé") + void testTermine() { + EvenementResponse r = base(); + r.setStatut(StatutEvenement.TERMINE); + assertThat(r.sontInscriptionsOuvertes()).isFalse(); + } + + @Test + @DisplayName("false quand dateLimiteInscription dépassée") + void testDateLimitePassee() { + EvenementResponse r = base(); + r.setDateLimiteInscription(LocalDate.now().minusDays(1)); + assertThat(r.sontInscriptionsOuvertes()).isFalse(); + } + + @Test + @DisplayName("false quand événement complet") + void testComplet() { + EvenementResponse r = base(); + r.setCapaciteMax(10); + r.setParticipantsInscrits(10); + assertThat(r.sontInscriptionsOuvertes()).isFalse(); + } + + @Test + @DisplayName("true quand inscriptions ouvertes") + void testOuvertes() { + EvenementResponse r = base(); + r.setDateLimiteInscription(LocalDate.now().plusDays(5)); + r.setCapaciteMax(100); + r.setParticipantsInscrits(50); + assertThat(r.sontInscriptionsOuvertes()).isTrue(); + } + } + + @Nested + @DisplayName("getDureeEnHeures, estEvenementMultiJours, getTypeEvenementLibelle, getStatutLibelle, getPrioriteLibelle") + class AutresMethodes { + + @Test + @DisplayName("getDureeEnHeures retourne 0 si heureDebut ou heureFin null") + void testDureeNull() { + EvenementResponse r = base(); + r.setHeureDebut(null); + assertThat(r.getDureeEnHeures()).isEqualTo(0); + r.setHeureDebut(LocalTime.of(9, 0)); + r.setHeureFin(null); + assertThat(r.getDureeEnHeures()).isEqualTo(0); + } + + @Test + @DisplayName("getDureeEnHeures calcule la durée") + void testDuree() { + EvenementResponse r = base(); + r.setHeureDebut(LocalTime.of(9, 0)); + r.setHeureFin(LocalTime.of(18, 0)); + assertThat(r.getDureeEnHeures()).isEqualTo(9); + } + + @Test + @DisplayName("estEvenementMultiJours true quand dateDebut != dateFin") + void testMultiJours() { + EvenementResponse r = base(); + r.setDateDebut(LocalDate.now()); + r.setDateFin(LocalDate.now().plusDays(2)); + assertThat(r.estEvenementMultiJours()).isTrue(); + } + + @Test + @DisplayName("getTypeEvenementLibelle retourne Non défini si type null") + void testTypeNull() { + EvenementResponse r = base(); + r.setTypeEvenement(null); + assertThat(r.getTypeEvenementLibelle()).isEqualTo("Non défini"); + } + + @Test + @DisplayName("getStatutLibelle retourne Non défini si statut null") + void testStatutNull() { + EvenementResponse r = base(); + r.setStatut(null); + assertThat(r.getStatutLibelle()).isEqualTo("Non défini"); + } + + @Test + @DisplayName("getPrioriteLibelle retourne Normale si priorite null") + void testPrioriteNull() { + EvenementResponse r = base(); + r.setPriorite(null); + assertThat(r.getPrioriteLibelle()).isEqualTo("Normale"); + } + } + + @Nested + @DisplayName("hasCoordonnees, getEcartBudgetaire, estBudgetDepasse") + class BudgetEtCoordonnees { + + @Test + @DisplayName("hasCoordonnees true quand latitude et longitude non null") + void testCoordonnees() { + EvenementResponse r = base(); + r.setLatitude(BigDecimal.ONE); + r.setLongitude(BigDecimal.ONE); + assertThat(r.hasCoordonnees()).isTrue(); + } + + @Test + @DisplayName("hasCoordonnees false si un des deux null") + void testCoordonneesNull() { + EvenementResponse r = base(); + assertThat(r.hasCoordonnees()).isFalse(); + r.setLatitude(BigDecimal.ONE); + assertThat(r.hasCoordonnees()).isFalse(); + } + + @Test + @DisplayName("getEcartBudgetaire retourne ZERO si budget ou coutReel null") + void testEcartNull() { + EvenementResponse r = base(); + assertThat(r.getEcartBudgetaire()).isEqualTo(BigDecimal.ZERO); + r.setBudget(BigDecimal.valueOf(1000)); + assertThat(r.getEcartBudgetaire()).isEqualTo(BigDecimal.ZERO); + } + + @Test + @DisplayName("getEcartBudgetaire calcule budget - coutReel") + void testEcart() { + EvenementResponse r = base(); + r.setBudget(BigDecimal.valueOf(1000)); + r.setCoutReel(BigDecimal.valueOf(800)); + assertThat(r.getEcartBudgetaire()).isEqualByComparingTo(BigDecimal.valueOf(200)); + } + + @Test + @DisplayName("estBudgetDepasse true quand coutReel > budget") + void testBudgetDepasse() { + EvenementResponse r = base(); + r.setBudget(BigDecimal.valueOf(1000)); + r.setCoutReel(BigDecimal.valueOf(1200)); + assertThat(r.estBudgetDepasse()).isTrue(); + } + + @Test + @DisplayName("estBudgetDepasse false quand budget >= coutReel") + void testBudgetOk() { + EvenementResponse r = base(); + r.setBudget(BigDecimal.valueOf(1000)); + r.setCoutReel(BigDecimal.valueOf(1000)); + assertThat(r.estBudgetDepasse()).isFalse(); + } + } + + @Nested + @DisplayName("getPlacesDisponibles") + class GetPlacesDisponibles { + + @Test + @DisplayName("retourne 0 quand capaciteMax null") + void testCapaciteNull() { + EvenementResponse r = base(); + r.setCapaciteMax(null); + r.setParticipantsInscrits(50); + assertThat(r.getPlacesDisponibles()).isEqualTo(0); + } + + @Test + @DisplayName("retourne 0 quand participantsInscrits null") + void testInscritsNull() { + EvenementResponse r = base(); + r.setCapaciteMax(100); + r.setParticipantsInscrits(null); + assertThat(r.getPlacesDisponibles()).isEqualTo(0); + } + + @Test + @DisplayName("retourne différence capaciteMax - participantsInscrits") + void testCalcul() { + EvenementResponse r = base(); + r.setCapaciteMax(100); + r.setParticipantsInscrits(70); + assertThat(r.getPlacesDisponibles()).isEqualTo(30); + } + + @Test + @DisplayName("retourne 0 quand participantsInscrits >= capaciteMax") + void testComplet() { + EvenementResponse r = base(); + r.setCapaciteMax(100); + r.setParticipantsInscrits(110); + assertThat(r.getPlacesDisponibles()).isEqualTo(0); + } + } + + @Nested + @DisplayName("getTauxRemplissage") + class GetTauxRemplissage { + + @Test + @DisplayName("retourne 0 quand capaciteMax null") + void testCapaciteNull() { + EvenementResponse r = base(); + r.setCapaciteMax(null); + r.setParticipantsInscrits(50); + assertThat(r.getTauxRemplissage()).isEqualTo(0); + } + + @Test + @DisplayName("retourne 0 quand capaciteMax = 0") + void testCapaciteZero() { + EvenementResponse r = base(); + r.setCapaciteMax(0); + r.setParticipantsInscrits(0); + assertThat(r.getTauxRemplissage()).isEqualTo(0); + } + + @Test + @DisplayName("retourne 0 quand participantsInscrits null") + void testInscritsNull() { + EvenementResponse r = base(); + r.setCapaciteMax(100); + r.setParticipantsInscrits(null); + assertThat(r.getTauxRemplissage()).isEqualTo(0); + } + + @Test + @DisplayName("calcule pourcentage remplissage") + void testCalcul() { + EvenementResponse r = base(); + r.setCapaciteMax(100); + r.setParticipantsInscrits(75); + assertThat(r.getTauxRemplissage()).isEqualTo(75); + } + + @Test + @DisplayName("retourne 100 quand capaciteMax = participantsInscrits") + void testComplet() { + EvenementResponse r = base(); + r.setCapaciteMax(100); + r.setParticipantsInscrits(100); + assertThat(r.getTauxRemplissage()).isEqualTo(100); + } + + @Test + @DisplayName("retourne > 100 quand participantsInscrits > capaciteMax") + void testSurReservation() { + EvenementResponse r = base(); + r.setCapaciteMax(100); + r.setParticipantsInscrits(120); + assertThat(r.getTauxRemplissage()).isEqualTo(120); + } + } + + @Nested + @DisplayName("Branches manquantes") + class BranchesManquantes { + + @Test + @DisplayName("getPrioriteLibelle retourne libellé quand priorite non null") + void testPrioriteNonNull() { + EvenementResponse r = base(); + r.setPriorite(PrioriteEvenement.HAUTE); + assertThat(r.getPrioriteLibelle()).isEqualTo(PrioriteEvenement.HAUTE.getLibelle()); + } + + @Test + @DisplayName("estEvenementMultiJours false quand dateFin null") + void testDateFinNull() { + EvenementResponse r = base(); + r.setDateFin(null); + assertThat(r.estEvenementMultiJours()).isFalse(); + } + + @Test + @DisplayName("estEvenementMultiJours false quand dateDebut = dateFin") + void testMemeJour() { + EvenementResponse r = base(); + LocalDate date = LocalDate.now(); + r.setDateDebut(date); + r.setDateFin(date); + assertThat(r.estEvenementMultiJours()).isFalse(); + } + + @Test + @DisplayName("estComplet false quand capaciteMax null") + void testCompletCapaciteNull() { + EvenementResponse r = base(); + r.setCapaciteMax(null); + r.setParticipantsInscrits(100); + assertThat(r.estComplet()).isFalse(); + } + + @Test + @DisplayName("estComplet false quand participantsInscrits null") + void testCompletInscritsNull() { + EvenementResponse r = base(); + r.setCapaciteMax(100); + r.setParticipantsInscrits(null); + assertThat(r.estComplet()).isFalse(); + } + } + + @Nested + @DisplayName("getTypeEvenementIcon") + class GetTypeEvenementIcon { + + @Test + @DisplayName("retourne icône par défaut quand type null") + void testNull() { + EvenementResponse r = EvenementResponse.builder().build(); + assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-calendar"); + } + + @Test + @DisplayName("ASSEMBLEE_GENERALE → pi pi-building") + void testAssembleeGenerale() { + EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.ASSEMBLEE_GENERALE).build(); + assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-building"); + } + + @Test + @DisplayName("FORMATION → pi pi-book") + void testFormation() { + EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.FORMATION).build(); + assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-book"); + } + + @Test + @DisplayName("REUNION_BUREAU → pi pi-users") + void testReunionBureau() { + EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.REUNION_BUREAU).build(); + assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-users"); + } + + @Test + @DisplayName("CONFERENCE → pi pi-microphone") + void testConference() { + EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.CONFERENCE).build(); + assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-microphone"); + } + + @Test + @DisplayName("ATELIER → pi pi-wrench") + void testAtelier() { + EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.ATELIER).build(); + assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-wrench"); + } + + @Test + @DisplayName("CEREMONIE → pi pi-flag") + void testCeremonie() { + EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.CEREMONIE).build(); + assertThat(r.getTypeEvenementIcon()).isEqualTo("pi pi-flag"); + } + + @Test + @DisplayName("ACTIVITE_SOCIALE, ACTION_CARITATIVE, AUTRE → pi pi-calendar") + void testAutres() { + assertThat(EvenementResponse.builder().typeEvenement(TypeEvenementMetier.ACTIVITE_SOCIALE).build().getTypeEvenementIcon()).isEqualTo("pi pi-calendar"); + assertThat(EvenementResponse.builder().typeEvenement(TypeEvenementMetier.ACTION_CARITATIVE).build().getTypeEvenementIcon()).isEqualTo("pi pi-calendar"); + assertThat(EvenementResponse.builder().typeEvenement(TypeEvenementMetier.AUTRE).build().getTypeEvenementIcon()).isEqualTo("pi pi-calendar"); + } + } + + @Nested + @DisplayName("getTypeEvenementSeverity") + class GetTypeEvenementSeverity { + + @Test + @DisplayName("retourne secondary quand type null") + void testNull() { + EvenementResponse r = EvenementResponse.builder().build(); + assertThat(r.getTypeEvenementSeverity()).isEqualTo("secondary"); + } + + @Test + @DisplayName("ASSEMBLEE_GENERALE → warning") + void testAssembleeGenerale() { + EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.ASSEMBLEE_GENERALE).build(); + assertThat(r.getTypeEvenementSeverity()).isEqualTo("warning"); + } + + @Test + @DisplayName("FORMATION → info") + void testFormation() { + EvenementResponse r = EvenementResponse.builder().typeEvenement(TypeEvenementMetier.FORMATION).build(); + assertThat(r.getTypeEvenementSeverity()).isEqualTo("info"); + } + + @Test + @DisplayName("autres types → secondary") + void testAutres() { + for (TypeEvenementMetier t : new TypeEvenementMetier[]{ + TypeEvenementMetier.ACTIVITE_SOCIALE, TypeEvenementMetier.ACTION_CARITATIVE, + TypeEvenementMetier.REUNION_BUREAU, TypeEvenementMetier.CONFERENCE, + TypeEvenementMetier.ATELIER, TypeEvenementMetier.CEREMONIE, TypeEvenementMetier.AUTRE}) { + assertThat(EvenementResponse.builder().typeEvenement(t).build().getTypeEvenementSeverity()) + .as("Type: %s", t).isEqualTo("secondary"); + } + } + } + + @Nested + @DisplayName("getStatutSeverity") + class GetStatutSeverity { + + @Test + @DisplayName("retourne secondary quand statut null") + void testNull() { + EvenementResponse r = EvenementResponse.builder().build(); + assertThat(r.getStatutSeverity()).isEqualTo("secondary"); + } + + @Test + @DisplayName("PLANIFIE → info") + void testPlanifie() { + assertThat(EvenementResponse.builder().statut(StatutEvenement.PLANIFIE).build().getStatutSeverity()).isEqualTo("info"); + } + + @Test + @DisplayName("EN_COURS → success") + void testEnCours() { + assertThat(EvenementResponse.builder().statut(StatutEvenement.EN_COURS).build().getStatutSeverity()).isEqualTo("success"); + } + + @Test + @DisplayName("TERMINE et CONFIRME → secondary") + void testTermineConfirme() { + assertThat(EvenementResponse.builder().statut(StatutEvenement.TERMINE).build().getStatutSeverity()).isEqualTo("secondary"); + assertThat(EvenementResponse.builder().statut(StatutEvenement.CONFIRME).build().getStatutSeverity()).isEqualTo("secondary"); + } + + @Test + @DisplayName("ANNULE → danger") + void testAnnule() { + assertThat(EvenementResponse.builder().statut(StatutEvenement.ANNULE).build().getStatutSeverity()).isEqualTo("danger"); + } + + @Test + @DisplayName("REPORTE → warning") + void testReporte() { + assertThat(EvenementResponse.builder().statut(StatutEvenement.REPORTE).build().getStatutSeverity()).isEqualTo("warning"); + } + } + + @Nested + @DisplayName("getStatutIcon") + class GetStatutIcon { + + @Test + @DisplayName("retourne pi pi-question quand statut null") + void testNull() { + EvenementResponse r = EvenementResponse.builder().build(); + assertThat(r.getStatutIcon()).isEqualTo("pi pi-question"); + } + + @Test + @DisplayName("tous les statuts retournent la bonne icône") + void testTousStatuts() { + assertThat(EvenementResponse.builder().statut(StatutEvenement.PLANIFIE).build().getStatutIcon()).isEqualTo("pi pi-clock"); + assertThat(EvenementResponse.builder().statut(StatutEvenement.CONFIRME).build().getStatutIcon()).isEqualTo("pi pi-check-circle"); + assertThat(EvenementResponse.builder().statut(StatutEvenement.EN_COURS).build().getStatutIcon()).isEqualTo("pi pi-play"); + assertThat(EvenementResponse.builder().statut(StatutEvenement.TERMINE).build().getStatutIcon()).isEqualTo("pi pi-check"); + assertThat(EvenementResponse.builder().statut(StatutEvenement.ANNULE).build().getStatutIcon()).isEqualTo("pi pi-times"); + assertThat(EvenementResponse.builder().statut(StatutEvenement.REPORTE).build().getStatutIcon()).isEqualTo("pi pi-refresh"); + } + } + + @Nested + @DisplayName("getPrioriteSeverity") + class GetPrioriteSeverity { + + @Test + @DisplayName("retourne secondary quand priorite null") + void testNull() { + EvenementResponse r = EvenementResponse.builder().build(); + assertThat(r.getPrioriteSeverity()).isEqualTo("secondary"); + } + + @Test + @DisplayName("toutes les priorités retournent la bonne sévérité") + void testToutesPriorites() { + assertThat(EvenementResponse.builder().priorite(PrioriteEvenement.CRITIQUE).build().getPrioriteSeverity()).isEqualTo("danger"); + assertThat(EvenementResponse.builder().priorite(PrioriteEvenement.HAUTE).build().getPrioriteSeverity()).isEqualTo("warning"); + assertThat(EvenementResponse.builder().priorite(PrioriteEvenement.NORMALE).build().getPrioriteSeverity()).isEqualTo("info"); + assertThat(EvenementResponse.builder().priorite(PrioriteEvenement.BASSE).build().getPrioriteSeverity()).isEqualTo("secondary"); + } + } + + @Nested + @DisplayName("getDateDebutFormatee, getHeureDebutFormatee, getHeureFinFormatee, getBudgetFormate") + class MethodesFormatage { + + @Test + @DisplayName("getDateDebutFormatee retourne — quand null") + void testDateDebutNull() { + EvenementResponse r = EvenementResponse.builder().build(); + assertThat(r.getDateDebutFormatee()).isEqualTo("—"); + } + + @Test + @DisplayName("getDateDebutFormatee formate en dd/MM/yyyy") + void testDateDebut() { + EvenementResponse r = EvenementResponse.builder().dateDebut(java.time.LocalDate.of(2026, 4, 7)).build(); + assertThat(r.getDateDebutFormatee()).isEqualTo("07/04/2026"); + } + + @Test + @DisplayName("getHeureDebutFormatee retourne — quand null") + void testHeureDebutNull() { + EvenementResponse r = EvenementResponse.builder().build(); + assertThat(r.getHeureDebutFormatee()).isEqualTo("—"); + } + + @Test + @DisplayName("getHeureDebutFormatee formate en HH:mm") + void testHeureDebut() { + EvenementResponse r = EvenementResponse.builder().heureDebut(java.time.LocalTime.of(9, 30)).build(); + assertThat(r.getHeureDebutFormatee()).isEqualTo("09:30"); + } + + @Test + @DisplayName("getHeureFinFormatee retourne — quand null") + void testHeureFinNull() { + EvenementResponse r = EvenementResponse.builder().build(); + assertThat(r.getHeureFinFormatee()).isEqualTo("—"); + } + + @Test + @DisplayName("getHeureFinFormatee formate en HH:mm") + void testHeureFin() { + EvenementResponse r = EvenementResponse.builder().heureFin(java.time.LocalTime.of(18, 0)).build(); + assertThat(r.getHeureFinFormatee()).isEqualTo("18:00"); + } + + @Test + @DisplayName("getBudgetFormate retourne — quand budget null") + void testBudgetNull() { + EvenementResponse r = EvenementResponse.builder().build(); + assertThat(r.getBudgetFormate()).isEqualTo("—"); + } + + @Test + @DisplayName("getBudgetFormate formate avec devise par défaut FCFA") + void testBudgetSansDevise() { + EvenementResponse r = EvenementResponse.builder().budget(java.math.BigDecimal.valueOf(50000)).build(); + assertThat(r.getBudgetFormate()).isEqualTo("50,000 FCFA"); + } + + @Test + @DisplayName("getBudgetFormate formate avec codeDevise fourni") + void testBudgetAvecDevise() { + EvenementResponse r = EvenementResponse.builder().budget(java.math.BigDecimal.valueOf(50000)).codeDevise("EUR").build(); + assertThat(r.getBudgetFormate()).isEqualTo("50,000 EUR"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/favoris/request/CreateFavoriRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/favoris/request/CreateFavoriRequestTest.java index 61dedfd..c9f4441 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/favoris/request/CreateFavoriRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/favoris/request/CreateFavoriRequestTest.java @@ -1,131 +1,131 @@ -package dev.lions.unionflow.server.api.dto.favoris.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateFavoriRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID utilisateurId = UUID.randomUUID(); - - CreateFavoriRequest request = CreateFavoriRequest.builder() - .utilisateurId(utilisateurId) - .typeFavori("PAGE") - .titre("Dashboard Principal") - .description("Tableau de bord principal avec statistiques") - .url("/dashboard") - .icon("pi-chart-bar") - .couleur("#3B82F6") - .categorie("ANALYTICS") - .ordre(1) - .nbVisites(25) - .derniereVisite("2026-03-15T10:30:00") - .estPlusUtilise(true) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.utilisateurId()).isEqualTo(utilisateurId); - assertThat(request.typeFavori()).isEqualTo("PAGE"); - assertThat(request.titre()).isEqualTo("Dashboard Principal"); - assertThat(request.description()).isEqualTo("Tableau de bord principal avec statistiques"); - assertThat(request.url()).isEqualTo("/dashboard"); - assertThat(request.icon()).isEqualTo("pi-chart-bar"); - assertThat(request.couleur()).isEqualTo("#3B82F6"); - assertThat(request.categorie()).isEqualTo("ANALYTICS"); - assertThat(request.ordre()).isEqualTo(1); - assertThat(request.nbVisites()).isEqualTo(25); - assertThat(request.derniereVisite()).isEqualTo("2026-03-15T10:30:00"); - assertThat(request.estPlusUtilise()).isTrue(); - } - - @Test - void testBuilder_MinimalFields() { - UUID utilisateurId = UUID.randomUUID(); - - CreateFavoriRequest request = CreateFavoriRequest.builder() - .utilisateurId(utilisateurId) - .typeFavori("LINK") - .titre("Lien rapide") - .url("/quick-link") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.utilisateurId()).isEqualTo(utilisateurId); - assertThat(request.typeFavori()).isEqualTo("LINK"); - assertThat(request.titre()).isEqualTo("Lien rapide"); - assertThat(request.url()).isEqualTo("/quick-link"); - } - - @Test - void testValidation_ValidFields() { - CreateFavoriRequest request = CreateFavoriRequest.builder() - .utilisateurId(UUID.randomUUID()) - .typeFavori("MODULE") - .titre("Module Membres") - .url("/membres") - .icon("pi-users") - .categorie("MODULES") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID utilisateurId = UUID.randomUUID(); - - CreateFavoriRequest request1 = CreateFavoriRequest.builder() - .utilisateurId(utilisateurId) - .typeFavori("PAGE") - .titre("Test Page") - .url("/test") - .build(); - - CreateFavoriRequest request2 = CreateFavoriRequest.builder() - .utilisateurId(utilisateurId) - .typeFavori("PAGE") - .titre("Test Page") - .url("/test") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateFavoriRequest request = CreateFavoriRequest.builder() - .utilisateurId(UUID.randomUUID()) - .typeFavori("PAGE") - .titre("Favorite Page") - .url("/favorite") - .icon("pi-star") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateFavoriRequest"); - assertThat(toString).contains("Favorite Page"); - assertThat(toString).contains("PAGE"); - } -} +package dev.lions.unionflow.server.api.dto.favoris.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateFavoriRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID utilisateurId = UUID.randomUUID(); + + CreateFavoriRequest request = CreateFavoriRequest.builder() + .utilisateurId(utilisateurId) + .typeFavori("PAGE") + .titre("Dashboard Principal") + .description("Tableau de bord principal avec statistiques") + .url("/dashboard") + .icon("pi-chart-bar") + .couleur("#3B82F6") + .categorie("ANALYTICS") + .ordre(1) + .nbVisites(25) + .derniereVisite("2026-03-15T10:30:00") + .estPlusUtilise(true) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.utilisateurId()).isEqualTo(utilisateurId); + assertThat(request.typeFavori()).isEqualTo("PAGE"); + assertThat(request.titre()).isEqualTo("Dashboard Principal"); + assertThat(request.description()).isEqualTo("Tableau de bord principal avec statistiques"); + assertThat(request.url()).isEqualTo("/dashboard"); + assertThat(request.icon()).isEqualTo("pi-chart-bar"); + assertThat(request.couleur()).isEqualTo("#3B82F6"); + assertThat(request.categorie()).isEqualTo("ANALYTICS"); + assertThat(request.ordre()).isEqualTo(1); + assertThat(request.nbVisites()).isEqualTo(25); + assertThat(request.derniereVisite()).isEqualTo("2026-03-15T10:30:00"); + assertThat(request.estPlusUtilise()).isTrue(); + } + + @Test + void testBuilder_MinimalFields() { + UUID utilisateurId = UUID.randomUUID(); + + CreateFavoriRequest request = CreateFavoriRequest.builder() + .utilisateurId(utilisateurId) + .typeFavori("LINK") + .titre("Lien rapide") + .url("/quick-link") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.utilisateurId()).isEqualTo(utilisateurId); + assertThat(request.typeFavori()).isEqualTo("LINK"); + assertThat(request.titre()).isEqualTo("Lien rapide"); + assertThat(request.url()).isEqualTo("/quick-link"); + } + + @Test + void testValidation_ValidFields() { + CreateFavoriRequest request = CreateFavoriRequest.builder() + .utilisateurId(UUID.randomUUID()) + .typeFavori("MODULE") + .titre("Module Membres") + .url("/membres") + .icon("pi-users") + .categorie("MODULES") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID utilisateurId = UUID.randomUUID(); + + CreateFavoriRequest request1 = CreateFavoriRequest.builder() + .utilisateurId(utilisateurId) + .typeFavori("PAGE") + .titre("Test Page") + .url("/test") + .build(); + + CreateFavoriRequest request2 = CreateFavoriRequest.builder() + .utilisateurId(utilisateurId) + .typeFavori("PAGE") + .titre("Test Page") + .url("/test") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateFavoriRequest request = CreateFavoriRequest.builder() + .utilisateurId(UUID.randomUUID()) + .typeFavori("PAGE") + .titre("Favorite Page") + .url("/favorite") + .icon("pi-star") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateFavoriRequest"); + assertThat(toString).contains("Favorite Page"); + assertThat(toString).contains("PAGE"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/finance/request/CreateAdhesionRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/finance/request/CreateAdhesionRequestTest.java index e3d2296..86bdf6d 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/finance/request/CreateAdhesionRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/finance/request/CreateAdhesionRequestTest.java @@ -1,185 +1,185 @@ -package dev.lions.unionflow.server.api.dto.finance.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateAdhesionRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID membreId = UUID.randomUUID(); - UUID organisationId = UUID.randomUUID(); - LocalDate dateDemande = LocalDate.now(); - - CreateAdhesionRequest request = CreateAdhesionRequest.builder() - .numeroReference("ADH-2026-001") - .membreId(membreId) - .organisationId(organisationId) - .dateDemande(dateDemande) - .fraisAdhesion(new BigDecimal("50000.00")) - .codeDevise("XOF") - .observations("Demande d'adhésion standard") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroReference()).isEqualTo("ADH-2026-001"); - assertThat(request.membreId()).isEqualTo(membreId); - assertThat(request.organisationId()).isEqualTo(organisationId); - assertThat(request.dateDemande()).isEqualTo(dateDemande); - assertThat(request.fraisAdhesion()).isEqualByComparingTo(new BigDecimal("50000.00")); - assertThat(request.codeDevise()).isEqualTo("XOF"); - assertThat(request.observations()).isEqualTo("Demande d'adhésion standard"); - } - - @Test - void testBuilder_MinimalFields() { - UUID membreId = UUID.randomUUID(); - UUID organisationId = UUID.randomUUID(); - - CreateAdhesionRequest request = CreateAdhesionRequest.builder() - .numeroReference("ADH-2026-002") - .membreId(membreId) - .organisationId(organisationId) - .dateDemande(LocalDate.now()) - .fraisAdhesion(new BigDecimal("25000.00")) - .codeDevise("XOF") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.numeroReference()).isEqualTo("ADH-2026-002"); - assertThat(request.membreId()).isEqualTo(membreId); - assertThat(request.organisationId()).isEqualTo(organisationId); - assertThat(request.fraisAdhesion()).isEqualByComparingTo(new BigDecimal("25000.00")); - assertThat(request.codeDevise()).isEqualTo("XOF"); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateAdhesionRequest request = CreateAdhesionRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroReference")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("membreId")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("organisationId")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateDemande")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("fraisAdhesion")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codeDevise")); - } - - @Test - void testValidation_InvalidDevise() { - CreateAdhesionRequest request = CreateAdhesionRequest.builder() - .numeroReference("ADH-2026-003") - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .dateDemande(LocalDate.now()) - .fraisAdhesion(new BigDecimal("50000.00")) - .codeDevise("INVALID") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codeDevise")); - } - - @Test - void testValidation_FraisAdhesionZero() { - CreateAdhesionRequest request = CreateAdhesionRequest.builder() - .numeroReference("ADH-2026-004") - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .dateDemande(LocalDate.now()) - .fraisAdhesion(BigDecimal.ZERO) - .codeDevise("XOF") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("fraisAdhesion")); - } - - @Test - void testValidation_ValidFields() { - CreateAdhesionRequest request = CreateAdhesionRequest.builder() - .numeroReference("ADH-2026-005") - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .dateDemande(LocalDate.now()) - .fraisAdhesion(new BigDecimal("50000.00")) - .codeDevise("XOF") - .observations("Observation valide") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID membreId = UUID.randomUUID(); - UUID organisationId = UUID.randomUUID(); - LocalDate dateDemande = LocalDate.now(); - - CreateAdhesionRequest request1 = CreateAdhesionRequest.builder() - .numeroReference("ADH-2026-006") - .membreId(membreId) - .organisationId(organisationId) - .dateDemande(dateDemande) - .fraisAdhesion(new BigDecimal("50000.00")) - .codeDevise("XOF") - .build(); - - CreateAdhesionRequest request2 = CreateAdhesionRequest.builder() - .numeroReference("ADH-2026-006") - .membreId(membreId) - .organisationId(organisationId) - .dateDemande(dateDemande) - .fraisAdhesion(new BigDecimal("50000.00")) - .codeDevise("XOF") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateAdhesionRequest request = CreateAdhesionRequest.builder() - .numeroReference("ADH-2026-007") - .membreId(UUID.randomUUID()) - .organisationId(UUID.randomUUID()) - .dateDemande(LocalDate.now()) - .fraisAdhesion(new BigDecimal("50000.00")) - .codeDevise("XOF") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateAdhesionRequest"); - assertThat(toString).contains("ADH-2026-007"); - } -} +package dev.lions.unionflow.server.api.dto.finance.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateAdhesionRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID membreId = UUID.randomUUID(); + UUID organisationId = UUID.randomUUID(); + LocalDate dateDemande = LocalDate.now(); + + CreateAdhesionRequest request = CreateAdhesionRequest.builder() + .numeroReference("ADH-2026-001") + .membreId(membreId) + .organisationId(organisationId) + .dateDemande(dateDemande) + .fraisAdhesion(new BigDecimal("50000.00")) + .codeDevise("XOF") + .observations("Demande d'adhésion standard") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroReference()).isEqualTo("ADH-2026-001"); + assertThat(request.membreId()).isEqualTo(membreId); + assertThat(request.organisationId()).isEqualTo(organisationId); + assertThat(request.dateDemande()).isEqualTo(dateDemande); + assertThat(request.fraisAdhesion()).isEqualByComparingTo(new BigDecimal("50000.00")); + assertThat(request.codeDevise()).isEqualTo("XOF"); + assertThat(request.observations()).isEqualTo("Demande d'adhésion standard"); + } + + @Test + void testBuilder_MinimalFields() { + UUID membreId = UUID.randomUUID(); + UUID organisationId = UUID.randomUUID(); + + CreateAdhesionRequest request = CreateAdhesionRequest.builder() + .numeroReference("ADH-2026-002") + .membreId(membreId) + .organisationId(organisationId) + .dateDemande(LocalDate.now()) + .fraisAdhesion(new BigDecimal("25000.00")) + .codeDevise("XOF") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.numeroReference()).isEqualTo("ADH-2026-002"); + assertThat(request.membreId()).isEqualTo(membreId); + assertThat(request.organisationId()).isEqualTo(organisationId); + assertThat(request.fraisAdhesion()).isEqualByComparingTo(new BigDecimal("25000.00")); + assertThat(request.codeDevise()).isEqualTo("XOF"); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateAdhesionRequest request = CreateAdhesionRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroReference")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("membreId")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("organisationId")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateDemande")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("fraisAdhesion")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codeDevise")); + } + + @Test + void testValidation_InvalidDevise() { + CreateAdhesionRequest request = CreateAdhesionRequest.builder() + .numeroReference("ADH-2026-003") + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .dateDemande(LocalDate.now()) + .fraisAdhesion(new BigDecimal("50000.00")) + .codeDevise("INVALID") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codeDevise")); + } + + @Test + void testValidation_FraisAdhesionZero() { + CreateAdhesionRequest request = CreateAdhesionRequest.builder() + .numeroReference("ADH-2026-004") + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .dateDemande(LocalDate.now()) + .fraisAdhesion(BigDecimal.ZERO) + .codeDevise("XOF") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("fraisAdhesion")); + } + + @Test + void testValidation_ValidFields() { + CreateAdhesionRequest request = CreateAdhesionRequest.builder() + .numeroReference("ADH-2026-005") + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .dateDemande(LocalDate.now()) + .fraisAdhesion(new BigDecimal("50000.00")) + .codeDevise("XOF") + .observations("Observation valide") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID membreId = UUID.randomUUID(); + UUID organisationId = UUID.randomUUID(); + LocalDate dateDemande = LocalDate.now(); + + CreateAdhesionRequest request1 = CreateAdhesionRequest.builder() + .numeroReference("ADH-2026-006") + .membreId(membreId) + .organisationId(organisationId) + .dateDemande(dateDemande) + .fraisAdhesion(new BigDecimal("50000.00")) + .codeDevise("XOF") + .build(); + + CreateAdhesionRequest request2 = CreateAdhesionRequest.builder() + .numeroReference("ADH-2026-006") + .membreId(membreId) + .organisationId(organisationId) + .dateDemande(dateDemande) + .fraisAdhesion(new BigDecimal("50000.00")) + .codeDevise("XOF") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateAdhesionRequest request = CreateAdhesionRequest.builder() + .numeroReference("ADH-2026-007") + .membreId(UUID.randomUUID()) + .organisationId(UUID.randomUUID()) + .dateDemande(LocalDate.now()) + .fraisAdhesion(new BigDecimal("50000.00")) + .codeDevise("XOF") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateAdhesionRequest"); + assertThat(toString).contains("ADH-2026-007"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/finance/request/UpdateAdhesionRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/finance/request/UpdateAdhesionRequestTest.java index 6bdb2d5..196224b 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/finance/request/UpdateAdhesionRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/finance/request/UpdateAdhesionRequestTest.java @@ -1,147 +1,147 @@ -package dev.lions.unionflow.server.api.dto.finance.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalDateTime; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateAdhesionRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDate dateApprobation = LocalDate.now(); - LocalDateTime datePaiement = LocalDateTime.now(); - LocalDate dateValidation = LocalDate.now(); - - UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() - .montantPaye(new BigDecimal("50000.00")) - .statut("APPROUVEE") - .dateApprobation(dateApprobation) - .datePaiement(datePaiement) - .methodePaiement("WAVE_MONEY") - .referencePaiement("REF-PAY-001") - .motifRejet(null) - .observations("Adhésion approuvée") - .approuvePar("Admin Principal") - .dateValidation(dateValidation) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.montantPaye()).isEqualByComparingTo(new BigDecimal("50000.00")); - assertThat(request.statut()).isEqualTo("APPROUVEE"); - assertThat(request.dateApprobation()).isEqualTo(dateApprobation); - assertThat(request.datePaiement()).isEqualTo(datePaiement); - assertThat(request.methodePaiement()).isEqualTo("WAVE_MONEY"); - assertThat(request.referencePaiement()).isEqualTo("REF-PAY-001"); - assertThat(request.observations()).isEqualTo("Adhésion approuvée"); - assertThat(request.approuvePar()).isEqualTo("Admin Principal"); - assertThat(request.dateValidation()).isEqualTo(dateValidation); - } - - @Test - void testBuilder_MinimalFields() { - UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() - .statut("EN_ATTENTE") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.statut()).isEqualTo("EN_ATTENTE"); - } - - @Test - void testValidation_InvalidStatut() { - UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() - .statut("INVALID_STATUS") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("statut")); - } - - @Test - void testValidation_InvalidMethodePaiement() { - UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() - .methodePaiement("INVALID_METHOD") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("methodePaiement")); - } - - @Test - void testValidation_MontantPayeNegatif() { - UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() - .montantPaye(new BigDecimal("-100.00")) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantPaye")); - } - - @Test - void testValidation_ValidFields() { - UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() - .montantPaye(new BigDecimal("50000.00")) - .statut("PAYEE") - .methodePaiement("VIREMENT") - .referencePaiement("REF-001") - .observations("Paiement effectué") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UpdateAdhesionRequest request1 = UpdateAdhesionRequest.builder() - .statut("APPROUVEE") - .montantPaye(new BigDecimal("50000.00")) - .build(); - - UpdateAdhesionRequest request2 = UpdateAdhesionRequest.builder() - .statut("APPROUVEE") - .montantPaye(new BigDecimal("50000.00")) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() - .statut("PAYEE") - .montantPaye(new BigDecimal("50000.00")) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateAdhesionRequest"); - assertThat(toString).contains("PAYEE"); - } -} +package dev.lions.unionflow.server.api.dto.finance.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateAdhesionRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDate dateApprobation = LocalDate.now(); + LocalDateTime datePaiement = LocalDateTime.now(); + LocalDate dateValidation = LocalDate.now(); + + UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() + .montantPaye(new BigDecimal("50000.00")) + .statut("APPROUVEE") + .dateApprobation(dateApprobation) + .datePaiement(datePaiement) + .methodePaiement("WAVE_MONEY") + .referencePaiement("REF-PAY-001") + .motifRejet(null) + .observations("Adhésion approuvée") + .approuvePar("Admin Principal") + .dateValidation(dateValidation) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.montantPaye()).isEqualByComparingTo(new BigDecimal("50000.00")); + assertThat(request.statut()).isEqualTo("APPROUVEE"); + assertThat(request.dateApprobation()).isEqualTo(dateApprobation); + assertThat(request.datePaiement()).isEqualTo(datePaiement); + assertThat(request.methodePaiement()).isEqualTo("WAVE_MONEY"); + assertThat(request.referencePaiement()).isEqualTo("REF-PAY-001"); + assertThat(request.observations()).isEqualTo("Adhésion approuvée"); + assertThat(request.approuvePar()).isEqualTo("Admin Principal"); + assertThat(request.dateValidation()).isEqualTo(dateValidation); + } + + @Test + void testBuilder_MinimalFields() { + UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() + .statut("EN_ATTENTE") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.statut()).isEqualTo("EN_ATTENTE"); + } + + @Test + void testValidation_InvalidStatut() { + UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() + .statut("INVALID_STATUS") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("statut")); + } + + @Test + void testValidation_InvalidMethodePaiement() { + UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() + .methodePaiement("INVALID_METHOD") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("methodePaiement")); + } + + @Test + void testValidation_MontantPayeNegatif() { + UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() + .montantPaye(new BigDecimal("-100.00")) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantPaye")); + } + + @Test + void testValidation_ValidFields() { + UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() + .montantPaye(new BigDecimal("50000.00")) + .statut("PAYEE") + .methodePaiement("VIREMENT") + .referencePaiement("REF-001") + .observations("Paiement effectué") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UpdateAdhesionRequest request1 = UpdateAdhesionRequest.builder() + .statut("APPROUVEE") + .montantPaye(new BigDecimal("50000.00")) + .build(); + + UpdateAdhesionRequest request2 = UpdateAdhesionRequest.builder() + .statut("APPROUVEE") + .montantPaye(new BigDecimal("50000.00")) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateAdhesionRequest request = UpdateAdhesionRequest.builder() + .statut("PAYEE") + .montantPaye(new BigDecimal("50000.00")) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateAdhesionRequest"); + assertThat(toString).contains("PAYEE"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/finance/response/AdhesionResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/finance/response/AdhesionResponseTest.java index 61ea2df..9a59609 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/finance/response/AdhesionResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/finance/response/AdhesionResponseTest.java @@ -1,413 +1,413 @@ -package dev.lions.unionflow.server.api.dto.finance.response; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalDateTime; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour AdhesionResponse. - * Couvre toutes les méthodes utilitaires et toutes les branches des switch (statut, méthode paiement). - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests AdhesionResponse") -class AdhesionResponseTest { - - @Nested - @DisplayName("isPayeeIntegralement") - class IsPayeeIntegralement { - - @Test - @DisplayName("retourne false quand montantPaye ou fraisAdhesion null") - void testNull() { - AdhesionResponse r = new AdhesionResponse(); - assertThat(r.isPayeeIntegralement()).isFalse(); - r.setFraisAdhesion(BigDecimal.TEN); - assertThat(r.isPayeeIntegralement()).isFalse(); - r.setMontantPaye(BigDecimal.TEN); - r.setFraisAdhesion(null); - assertThat(r.isPayeeIntegralement()).isFalse(); - } - - @Test - @DisplayName("retourne true quand montantPaye >= fraisAdhesion") - void testPaye() { - AdhesionResponse r = AdhesionResponse.builder() - .fraisAdhesion(BigDecimal.valueOf(100)) - .montantPaye(BigDecimal.valueOf(100)).build(); - assertThat(r.isPayeeIntegralement()).isTrue(); - r.setMontantPaye(BigDecimal.valueOf(150)); - assertThat(r.isPayeeIntegralement()).isTrue(); - } - - @Test - @DisplayName("retourne false quand montantPaye < fraisAdhesion") - void testNonPaye() { - AdhesionResponse r = AdhesionResponse.builder() - .fraisAdhesion(BigDecimal.valueOf(100)) - .montantPaye(BigDecimal.valueOf(50)).build(); - assertThat(r.isPayeeIntegralement()).isFalse(); - } - } - - @Nested - @DisplayName("isEnAttentePaiement") - class IsEnAttentePaiement { - - @Test - @DisplayName("retourne true quand APPROUVEE et pas payé intégralement") - void testEnAttente() { - AdhesionResponse r = AdhesionResponse.builder() - .statut("APPROUVEE") - .fraisAdhesion(BigDecimal.valueOf(100)) - .montantPaye(BigDecimal.valueOf(50)).build(); - assertThat(r.isEnAttentePaiement()).isTrue(); - } - - @Test - @DisplayName("retourne false quand payé intégralement") - void testPaye() { - AdhesionResponse r = AdhesionResponse.builder() - .statut("APPROUVEE") - .fraisAdhesion(BigDecimal.valueOf(100)) - .montantPaye(BigDecimal.valueOf(100)).build(); - assertThat(r.isEnAttentePaiement()).isFalse(); - } - - @Test - @DisplayName("retourne false quand statut différent de APPROUVEE") - void testAutreStatut() { - AdhesionResponse r = AdhesionResponse.builder() - .statut("EN_ATTENTE") - .fraisAdhesion(BigDecimal.valueOf(100)) - .montantPaye(BigDecimal.ZERO).build(); - assertThat(r.isEnAttentePaiement()).isFalse(); - } - } - - @Nested - @DisplayName("getMontantRestant") - class GetMontantRestant { - - @Test - @DisplayName("retourne 0 quand fraisAdhesion null") - void testFraisNull() { - AdhesionResponse r = new AdhesionResponse(); - assertThat(r.getMontantRestant()).isEqualByComparingTo(BigDecimal.ZERO); - } - - @Test - @DisplayName("retourne fraisAdhesion quand montantPaye null") - void testMontantPayeNull() { - AdhesionResponse r = AdhesionResponse.builder().fraisAdhesion(BigDecimal.valueOf(100)).build(); - assertThat(r.getMontantRestant()).isEqualByComparingTo(BigDecimal.valueOf(100)); - } - - @Test - @DisplayName("retourne frais - payé si positif") - void testRestant() { - AdhesionResponse r = AdhesionResponse.builder() - .fraisAdhesion(BigDecimal.valueOf(100)) - .montantPaye(BigDecimal.valueOf(30)).build(); - assertThat(r.getMontantRestant()).isEqualByComparingTo(BigDecimal.valueOf(70)); - } - - @Test - @DisplayName("retourne 0 quand payé >= frais") - void testZeroRestant() { - AdhesionResponse r = AdhesionResponse.builder() - .fraisAdhesion(BigDecimal.valueOf(100)) - .montantPaye(BigDecimal.valueOf(100)).build(); - assertThat(r.getMontantRestant()).isEqualByComparingTo(BigDecimal.ZERO); - r.setMontantPaye(BigDecimal.valueOf(150)); - assertThat(r.getMontantRestant()).isEqualByComparingTo(BigDecimal.ZERO); - } - } - - @Nested - @DisplayName("getPourcentagePaiement") - class GetPourcentagePaiement { - - @Test - @DisplayName("retourne 0 quand fraisAdhesion null ou zéro") - void testZero() { - AdhesionResponse r = new AdhesionResponse(); - assertThat(r.getPourcentagePaiement()).isEqualTo(0); - r.setFraisAdhesion(BigDecimal.ZERO); - r.setMontantPaye(BigDecimal.TEN); - assertThat(r.getPourcentagePaiement()).isEqualTo(0); - } - - @Test - @DisplayName("retourne 0 quand montantPaye null") - void testMontantNull() { - AdhesionResponse r = AdhesionResponse.builder().fraisAdhesion(BigDecimal.valueOf(100)).build(); - assertThat(r.getPourcentagePaiement()).isEqualTo(0); - } - - @Test - @DisplayName("retourne le pourcentage arrondi") - void testPourcentage() { - AdhesionResponse r = AdhesionResponse.builder() - .fraisAdhesion(BigDecimal.valueOf(100)) - .montantPaye(BigDecimal.valueOf(50)).build(); - assertThat(r.getPourcentagePaiement()).isEqualTo(50); - r.setMontantPaye(BigDecimal.valueOf(100)); - assertThat(r.getPourcentagePaiement()).isEqualTo(100); - } - } - - @Nested - @DisplayName("getJoursDepuisDemande") - class GetJoursDepuisDemande { - - @Test - @DisplayName("retourne 0 quand dateDemande null") - void testNull() { - AdhesionResponse r = new AdhesionResponse(); - assertThat(r.getJoursDepuisDemande()).isEqualTo(0); - } - - @Test - @DisplayName("retourne les jours entre dateDemande et aujourd'hui") - void testJours() { - AdhesionResponse r = AdhesionResponse.builder() - .dateDemande(LocalDate.now().minusDays(5)).build(); - assertThat(r.getJoursDepuisDemande()).isEqualTo(5); - } - } - - @Nested - @DisplayName("getStatutLibelle") - class GetStatutLibelle { - - @Test - @DisplayName("retourne Non défini quand statut null") - void testNull() { - AdhesionResponse r = new AdhesionResponse(); - assertThat(r.getStatutLibelle()).isEqualTo("Non défini"); - } - - @Test - @DisplayName("retourne le libellé pour chaque statut connu") - void testStatuts() { - assertThat(AdhesionResponse.builder().statut("EN_ATTENTE").build().getStatutLibelle()).isEqualTo("En attente"); - assertThat(AdhesionResponse.builder().statut("APPROUVEE").build().getStatutLibelle()).isEqualTo("Approuvée"); - assertThat(AdhesionResponse.builder().statut("REJETEE").build().getStatutLibelle()).isEqualTo("Rejetée"); - assertThat(AdhesionResponse.builder().statut("ANNULEE").build().getStatutLibelle()).isEqualTo("Annulée"); - assertThat(AdhesionResponse.builder().statut("EN_PAIEMENT").build().getStatutLibelle()).isEqualTo("En paiement"); - assertThat(AdhesionResponse.builder().statut("PAYEE").build().getStatutLibelle()).isEqualTo("Payée"); - } - - @Test - @DisplayName("retourne statut tel quel pour valeur inconnue") - void testDefault() { - AdhesionResponse r = AdhesionResponse.builder().statut("AUTRE").build(); - assertThat(r.getStatutLibelle()).isEqualTo("AUTRE"); - } - } - - @Nested - @DisplayName("getStatutSeverity") - class GetStatutSeverity { - - @Test - @DisplayName("retourne secondary quand statut null") - void testNull() { - AdhesionResponse r = new AdhesionResponse(); - assertThat(r.getStatutSeverity()).isEqualTo("secondary"); - } - - @Test - @DisplayName("retourne success pour APPROUVEE et PAYEE") - void testSuccess() { - assertThat(AdhesionResponse.builder().statut("APPROUVEE").build().getStatutSeverity()).isEqualTo("success"); - assertThat(AdhesionResponse.builder().statut("PAYEE").build().getStatutSeverity()).isEqualTo("success"); - } - - @Test - @DisplayName("retourne warning pour EN_ATTENTE et EN_PAIEMENT") - void testWarning() { - assertThat(AdhesionResponse.builder().statut("EN_ATTENTE").build().getStatutSeverity()).isEqualTo("warning"); - assertThat(AdhesionResponse.builder().statut("EN_PAIEMENT").build().getStatutSeverity()).isEqualTo("warning"); - } - - @Test - @DisplayName("retourne danger pour REJETEE") - void testDanger() { - assertThat(AdhesionResponse.builder().statut("REJETEE").build().getStatutSeverity()).isEqualTo("danger"); - } - - @Test - @DisplayName("retourne secondary pour ANNULEE et défaut") - void testSecondary() { - assertThat(AdhesionResponse.builder().statut("ANNULEE").build().getStatutSeverity()).isEqualTo("secondary"); - assertThat(AdhesionResponse.builder().statut("INCONNU").build().getStatutSeverity()).isEqualTo("secondary"); - } - } - - @Nested - @DisplayName("getStatutIcon") - class GetStatutIcon { - - @Test - @DisplayName("retourne pi-circle quand statut null") - void testNull() { - AdhesionResponse r = new AdhesionResponse(); - assertThat(r.getStatutIcon()).isEqualTo("pi-circle"); - } - - @Test - @DisplayName("retourne l'icône pour chaque statut") - void testIcons() { - assertThat(AdhesionResponse.builder().statut("APPROUVEE").build().getStatutIcon()).isEqualTo("pi-check"); - assertThat(AdhesionResponse.builder().statut("PAYEE").build().getStatutIcon()).isEqualTo("pi-check"); - assertThat(AdhesionResponse.builder().statut("EN_ATTENTE").build().getStatutIcon()).isEqualTo("pi-clock"); - assertThat(AdhesionResponse.builder().statut("EN_PAIEMENT").build().getStatutIcon()).isEqualTo("pi-credit-card"); - assertThat(AdhesionResponse.builder().statut("REJETEE").build().getStatutIcon()).isEqualTo("pi-times"); - assertThat(AdhesionResponse.builder().statut("ANNULEE").build().getStatutIcon()).isEqualTo("pi-ban"); - } - - @Test - @DisplayName("retourne pi-circle pour défaut") - void testDefault() { - assertThat(AdhesionResponse.builder().statut("INCONNU").build().getStatutIcon()).isEqualTo("pi-circle"); - } - } - - @Nested - @DisplayName("getMethodePaiementLibelle") - class GetMethodePaiementLibelle { - - @Test - @DisplayName("retourne Non défini quand methodePaiement null") - void testNull() { - AdhesionResponse r = new AdhesionResponse(); - assertThat(r.getMethodePaiementLibelle()).isEqualTo("Non défini"); - } - - @Test - @DisplayName("retourne le libellé pour chaque méthode") - void testMethodes() { - assertThat(AdhesionResponse.builder().methodePaiement("ESPECES").build().getMethodePaiementLibelle()).isEqualTo("Espèces"); - assertThat(AdhesionResponse.builder().methodePaiement("VIREMENT").build().getMethodePaiementLibelle()).isEqualTo("Virement bancaire"); - assertThat(AdhesionResponse.builder().methodePaiement("CHEQUE").build().getMethodePaiementLibelle()).isEqualTo("Chèque"); - assertThat(AdhesionResponse.builder().methodePaiement("WAVE_MONEY").build().getMethodePaiementLibelle()).isEqualTo("Wave Money"); - assertThat(AdhesionResponse.builder().methodePaiement("ORANGE_MONEY").build().getMethodePaiementLibelle()).isEqualTo("Orange Money"); - assertThat(AdhesionResponse.builder().methodePaiement("FREE_MONEY").build().getMethodePaiementLibelle()).isEqualTo("Free Money"); - assertThat(AdhesionResponse.builder().methodePaiement("CARTE_BANCAIRE").build().getMethodePaiementLibelle()).isEqualTo("Carte bancaire"); - } - - @Test - @DisplayName("retourne methodePaiement tel quel pour valeur inconnue") - void testDefault() { - AdhesionResponse r = AdhesionResponse.builder().methodePaiement("AUTRE").build(); - assertThat(r.getMethodePaiementLibelle()).isEqualTo("AUTRE"); - } - } - - @Nested - @DisplayName("Dates formatées") - class DatesFormatees { - - @Test - @DisplayName("getDateDemandeFormatee") - void testDateDemande() { - AdhesionResponse r = new AdhesionResponse(); - assertThat(r.getDateDemandeFormatee()).isEmpty(); - r.setDateDemande(LocalDate.of(2026, 2, 15)); - assertThat(r.getDateDemandeFormatee()).isEqualTo("15/02/2026"); - } - - @Test - @DisplayName("getDateApprobationFormatee") - void testDateApprobation() { - AdhesionResponse r = new AdhesionResponse(); - assertThat(r.getDateApprobationFormatee()).isEmpty(); - r.setDateApprobation(LocalDate.of(2026, 2, 16)); - assertThat(r.getDateApprobationFormatee()).isEqualTo("16/02/2026"); - } - - @Test - @DisplayName("getDatePaiementFormatee") - void testDatePaiement() { - AdhesionResponse r = new AdhesionResponse(); - assertThat(r.getDatePaiementFormatee()).isEmpty(); - r.setDatePaiement(LocalDateTime.of(2026, 2, 16, 14, 30)); - assertThat(r.getDatePaiementFormatee()).isEqualTo("16/02/2026 14:30"); - } - } - - @Nested - @DisplayName("Montants formatés") - class MontantsFormates { - - @Test - @DisplayName("getFraisAdhesionFormatte") - void testFrais() { - AdhesionResponse r = new AdhesionResponse(); - assertThat(r.getFraisAdhesionFormatte()).isEqualTo("0 FCFA"); - r.setFraisAdhesion(BigDecimal.valueOf(50000)); - assertThat(r.getFraisAdhesionFormatte()).contains("50"); - assertThat(r.getFraisAdhesionFormatte()).endsWith(" FCFA"); - } - - @Test - @DisplayName("getMontantPayeFormatte") - void testMontantPaye() { - AdhesionResponse r = new AdhesionResponse(); - assertThat(r.getMontantPayeFormatte()).isEqualTo("0 FCFA"); - r.setMontantPaye(BigDecimal.valueOf(25000)); - assertThat(r.getMontantPayeFormatte()).contains("25"); - assertThat(r.getMontantPayeFormatte()).endsWith(" FCFA"); - } - - @Test - @DisplayName("getMontantRestantFormatte") - void testMontantRestant() { - AdhesionResponse r = AdhesionResponse.builder() - .fraisAdhesion(BigDecimal.valueOf(100)) - .montantPaye(BigDecimal.valueOf(30)).build(); - assertThat(r.getMontantRestantFormatte()).contains("70"); - assertThat(r.getMontantRestantFormatte()).endsWith(" FCFA"); - } - } - - @Nested - @DisplayName("Builder et getters") - class BuilderGetters { - - @Test - @DisplayName("tous les champs sont accessibles") - void testBuilder() { - LocalDate dateDemande = LocalDate.of(2026, 1, 10); - AdhesionResponse r = AdhesionResponse.builder() - .numeroReference("REF-001") - .membreId(UUID.randomUUID()) - .numeroMembre("M1") - .nomMembre("Dupont") - .emailMembre("d@test.com") - .organisationId(UUID.randomUUID()) - .nomOrganisation("Org") - .dateDemande(dateDemande) - .fraisAdhesion(BigDecimal.valueOf(100)) - .montantPaye(BigDecimal.ZERO) - .codeDevise("XOF") - .statut("EN_ATTENTE") - .build(); - r.setId(UUID.randomUUID()); - assertThat(r.getNumeroReference()).isEqualTo("REF-001"); - assertThat(r.getNomMembre()).isEqualTo("Dupont"); - assertThat(r.getDateDemande()).isEqualTo(dateDemande); - assertThat(r.getStatut()).isEqualTo("EN_ATTENTE"); - } - } -} +package dev.lions.unionflow.server.api.dto.finance.response; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour AdhesionResponse. + * Couvre toutes les méthodes utilitaires et toutes les branches des switch (statut, méthode paiement). + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests AdhesionResponse") +class AdhesionResponseTest { + + @Nested + @DisplayName("isPayeeIntegralement") + class IsPayeeIntegralement { + + @Test + @DisplayName("retourne false quand montantPaye ou fraisAdhesion null") + void testNull() { + AdhesionResponse r = new AdhesionResponse(); + assertThat(r.isPayeeIntegralement()).isFalse(); + r.setFraisAdhesion(BigDecimal.TEN); + assertThat(r.isPayeeIntegralement()).isFalse(); + r.setMontantPaye(BigDecimal.TEN); + r.setFraisAdhesion(null); + assertThat(r.isPayeeIntegralement()).isFalse(); + } + + @Test + @DisplayName("retourne true quand montantPaye >= fraisAdhesion") + void testPaye() { + AdhesionResponse r = AdhesionResponse.builder() + .fraisAdhesion(BigDecimal.valueOf(100)) + .montantPaye(BigDecimal.valueOf(100)).build(); + assertThat(r.isPayeeIntegralement()).isTrue(); + r.setMontantPaye(BigDecimal.valueOf(150)); + assertThat(r.isPayeeIntegralement()).isTrue(); + } + + @Test + @DisplayName("retourne false quand montantPaye < fraisAdhesion") + void testNonPaye() { + AdhesionResponse r = AdhesionResponse.builder() + .fraisAdhesion(BigDecimal.valueOf(100)) + .montantPaye(BigDecimal.valueOf(50)).build(); + assertThat(r.isPayeeIntegralement()).isFalse(); + } + } + + @Nested + @DisplayName("isEnAttentePaiement") + class IsEnAttentePaiement { + + @Test + @DisplayName("retourne true quand APPROUVEE et pas payé intégralement") + void testEnAttente() { + AdhesionResponse r = AdhesionResponse.builder() + .statut("APPROUVEE") + .fraisAdhesion(BigDecimal.valueOf(100)) + .montantPaye(BigDecimal.valueOf(50)).build(); + assertThat(r.isEnAttentePaiement()).isTrue(); + } + + @Test + @DisplayName("retourne false quand payé intégralement") + void testPaye() { + AdhesionResponse r = AdhesionResponse.builder() + .statut("APPROUVEE") + .fraisAdhesion(BigDecimal.valueOf(100)) + .montantPaye(BigDecimal.valueOf(100)).build(); + assertThat(r.isEnAttentePaiement()).isFalse(); + } + + @Test + @DisplayName("retourne false quand statut différent de APPROUVEE") + void testAutreStatut() { + AdhesionResponse r = AdhesionResponse.builder() + .statut("EN_ATTENTE") + .fraisAdhesion(BigDecimal.valueOf(100)) + .montantPaye(BigDecimal.ZERO).build(); + assertThat(r.isEnAttentePaiement()).isFalse(); + } + } + + @Nested + @DisplayName("getMontantRestant") + class GetMontantRestant { + + @Test + @DisplayName("retourne 0 quand fraisAdhesion null") + void testFraisNull() { + AdhesionResponse r = new AdhesionResponse(); + assertThat(r.getMontantRestant()).isEqualByComparingTo(BigDecimal.ZERO); + } + + @Test + @DisplayName("retourne fraisAdhesion quand montantPaye null") + void testMontantPayeNull() { + AdhesionResponse r = AdhesionResponse.builder().fraisAdhesion(BigDecimal.valueOf(100)).build(); + assertThat(r.getMontantRestant()).isEqualByComparingTo(BigDecimal.valueOf(100)); + } + + @Test + @DisplayName("retourne frais - payé si positif") + void testRestant() { + AdhesionResponse r = AdhesionResponse.builder() + .fraisAdhesion(BigDecimal.valueOf(100)) + .montantPaye(BigDecimal.valueOf(30)).build(); + assertThat(r.getMontantRestant()).isEqualByComparingTo(BigDecimal.valueOf(70)); + } + + @Test + @DisplayName("retourne 0 quand payé >= frais") + void testZeroRestant() { + AdhesionResponse r = AdhesionResponse.builder() + .fraisAdhesion(BigDecimal.valueOf(100)) + .montantPaye(BigDecimal.valueOf(100)).build(); + assertThat(r.getMontantRestant()).isEqualByComparingTo(BigDecimal.ZERO); + r.setMontantPaye(BigDecimal.valueOf(150)); + assertThat(r.getMontantRestant()).isEqualByComparingTo(BigDecimal.ZERO); + } + } + + @Nested + @DisplayName("getPourcentagePaiement") + class GetPourcentagePaiement { + + @Test + @DisplayName("retourne 0 quand fraisAdhesion null ou zéro") + void testZero() { + AdhesionResponse r = new AdhesionResponse(); + assertThat(r.getPourcentagePaiement()).isEqualTo(0); + r.setFraisAdhesion(BigDecimal.ZERO); + r.setMontantPaye(BigDecimal.TEN); + assertThat(r.getPourcentagePaiement()).isEqualTo(0); + } + + @Test + @DisplayName("retourne 0 quand montantPaye null") + void testMontantNull() { + AdhesionResponse r = AdhesionResponse.builder().fraisAdhesion(BigDecimal.valueOf(100)).build(); + assertThat(r.getPourcentagePaiement()).isEqualTo(0); + } + + @Test + @DisplayName("retourne le pourcentage arrondi") + void testPourcentage() { + AdhesionResponse r = AdhesionResponse.builder() + .fraisAdhesion(BigDecimal.valueOf(100)) + .montantPaye(BigDecimal.valueOf(50)).build(); + assertThat(r.getPourcentagePaiement()).isEqualTo(50); + r.setMontantPaye(BigDecimal.valueOf(100)); + assertThat(r.getPourcentagePaiement()).isEqualTo(100); + } + } + + @Nested + @DisplayName("getJoursDepuisDemande") + class GetJoursDepuisDemande { + + @Test + @DisplayName("retourne 0 quand dateDemande null") + void testNull() { + AdhesionResponse r = new AdhesionResponse(); + assertThat(r.getJoursDepuisDemande()).isEqualTo(0); + } + + @Test + @DisplayName("retourne les jours entre dateDemande et aujourd'hui") + void testJours() { + AdhesionResponse r = AdhesionResponse.builder() + .dateDemande(LocalDate.now().minusDays(5)).build(); + assertThat(r.getJoursDepuisDemande()).isEqualTo(5); + } + } + + @Nested + @DisplayName("getStatutLibelle") + class GetStatutLibelle { + + @Test + @DisplayName("retourne Non défini quand statut null") + void testNull() { + AdhesionResponse r = new AdhesionResponse(); + assertThat(r.getStatutLibelle()).isEqualTo("Non défini"); + } + + @Test + @DisplayName("retourne le libellé pour chaque statut connu") + void testStatuts() { + assertThat(AdhesionResponse.builder().statut("EN_ATTENTE").build().getStatutLibelle()).isEqualTo("En attente"); + assertThat(AdhesionResponse.builder().statut("APPROUVEE").build().getStatutLibelle()).isEqualTo("Approuvée"); + assertThat(AdhesionResponse.builder().statut("REJETEE").build().getStatutLibelle()).isEqualTo("Rejetée"); + assertThat(AdhesionResponse.builder().statut("ANNULEE").build().getStatutLibelle()).isEqualTo("Annulée"); + assertThat(AdhesionResponse.builder().statut("EN_PAIEMENT").build().getStatutLibelle()).isEqualTo("En paiement"); + assertThat(AdhesionResponse.builder().statut("PAYEE").build().getStatutLibelle()).isEqualTo("Payée"); + } + + @Test + @DisplayName("retourne statut tel quel pour valeur inconnue") + void testDefault() { + AdhesionResponse r = AdhesionResponse.builder().statut("AUTRE").build(); + assertThat(r.getStatutLibelle()).isEqualTo("AUTRE"); + } + } + + @Nested + @DisplayName("getStatutSeverity") + class GetStatutSeverity { + + @Test + @DisplayName("retourne secondary quand statut null") + void testNull() { + AdhesionResponse r = new AdhesionResponse(); + assertThat(r.getStatutSeverity()).isEqualTo("secondary"); + } + + @Test + @DisplayName("retourne success pour APPROUVEE et PAYEE") + void testSuccess() { + assertThat(AdhesionResponse.builder().statut("APPROUVEE").build().getStatutSeverity()).isEqualTo("success"); + assertThat(AdhesionResponse.builder().statut("PAYEE").build().getStatutSeverity()).isEqualTo("success"); + } + + @Test + @DisplayName("retourne warning pour EN_ATTENTE et EN_PAIEMENT") + void testWarning() { + assertThat(AdhesionResponse.builder().statut("EN_ATTENTE").build().getStatutSeverity()).isEqualTo("warning"); + assertThat(AdhesionResponse.builder().statut("EN_PAIEMENT").build().getStatutSeverity()).isEqualTo("warning"); + } + + @Test + @DisplayName("retourne danger pour REJETEE") + void testDanger() { + assertThat(AdhesionResponse.builder().statut("REJETEE").build().getStatutSeverity()).isEqualTo("danger"); + } + + @Test + @DisplayName("retourne secondary pour ANNULEE et défaut") + void testSecondary() { + assertThat(AdhesionResponse.builder().statut("ANNULEE").build().getStatutSeverity()).isEqualTo("secondary"); + assertThat(AdhesionResponse.builder().statut("INCONNU").build().getStatutSeverity()).isEqualTo("secondary"); + } + } + + @Nested + @DisplayName("getStatutIcon") + class GetStatutIcon { + + @Test + @DisplayName("retourne pi-circle quand statut null") + void testNull() { + AdhesionResponse r = new AdhesionResponse(); + assertThat(r.getStatutIcon()).isEqualTo("pi-circle"); + } + + @Test + @DisplayName("retourne l'icône pour chaque statut") + void testIcons() { + assertThat(AdhesionResponse.builder().statut("APPROUVEE").build().getStatutIcon()).isEqualTo("pi-check"); + assertThat(AdhesionResponse.builder().statut("PAYEE").build().getStatutIcon()).isEqualTo("pi-check"); + assertThat(AdhesionResponse.builder().statut("EN_ATTENTE").build().getStatutIcon()).isEqualTo("pi-clock"); + assertThat(AdhesionResponse.builder().statut("EN_PAIEMENT").build().getStatutIcon()).isEqualTo("pi-credit-card"); + assertThat(AdhesionResponse.builder().statut("REJETEE").build().getStatutIcon()).isEqualTo("pi-times"); + assertThat(AdhesionResponse.builder().statut("ANNULEE").build().getStatutIcon()).isEqualTo("pi-ban"); + } + + @Test + @DisplayName("retourne pi-circle pour défaut") + void testDefault() { + assertThat(AdhesionResponse.builder().statut("INCONNU").build().getStatutIcon()).isEqualTo("pi-circle"); + } + } + + @Nested + @DisplayName("getMethodePaiementLibelle") + class GetMethodePaiementLibelle { + + @Test + @DisplayName("retourne Non défini quand methodePaiement null") + void testNull() { + AdhesionResponse r = new AdhesionResponse(); + assertThat(r.getMethodePaiementLibelle()).isEqualTo("Non défini"); + } + + @Test + @DisplayName("retourne le libellé pour chaque méthode") + void testMethodes() { + assertThat(AdhesionResponse.builder().methodePaiement("ESPECES").build().getMethodePaiementLibelle()).isEqualTo("Espèces"); + assertThat(AdhesionResponse.builder().methodePaiement("VIREMENT").build().getMethodePaiementLibelle()).isEqualTo("Virement bancaire"); + assertThat(AdhesionResponse.builder().methodePaiement("CHEQUE").build().getMethodePaiementLibelle()).isEqualTo("Chèque"); + assertThat(AdhesionResponse.builder().methodePaiement("WAVE_MONEY").build().getMethodePaiementLibelle()).isEqualTo("Wave Money"); + assertThat(AdhesionResponse.builder().methodePaiement("ORANGE_MONEY").build().getMethodePaiementLibelle()).isEqualTo("Orange Money"); + assertThat(AdhesionResponse.builder().methodePaiement("FREE_MONEY").build().getMethodePaiementLibelle()).isEqualTo("Free Money"); + assertThat(AdhesionResponse.builder().methodePaiement("CARTE_BANCAIRE").build().getMethodePaiementLibelle()).isEqualTo("Carte bancaire"); + } + + @Test + @DisplayName("retourne methodePaiement tel quel pour valeur inconnue") + void testDefault() { + AdhesionResponse r = AdhesionResponse.builder().methodePaiement("AUTRE").build(); + assertThat(r.getMethodePaiementLibelle()).isEqualTo("AUTRE"); + } + } + + @Nested + @DisplayName("Dates formatées") + class DatesFormatees { + + @Test + @DisplayName("getDateDemandeFormatee") + void testDateDemande() { + AdhesionResponse r = new AdhesionResponse(); + assertThat(r.getDateDemandeFormatee()).isEmpty(); + r.setDateDemande(LocalDate.of(2026, 2, 15)); + assertThat(r.getDateDemandeFormatee()).isEqualTo("15/02/2026"); + } + + @Test + @DisplayName("getDateApprobationFormatee") + void testDateApprobation() { + AdhesionResponse r = new AdhesionResponse(); + assertThat(r.getDateApprobationFormatee()).isEmpty(); + r.setDateApprobation(LocalDate.of(2026, 2, 16)); + assertThat(r.getDateApprobationFormatee()).isEqualTo("16/02/2026"); + } + + @Test + @DisplayName("getDatePaiementFormatee") + void testDatePaiement() { + AdhesionResponse r = new AdhesionResponse(); + assertThat(r.getDatePaiementFormatee()).isEmpty(); + r.setDatePaiement(LocalDateTime.of(2026, 2, 16, 14, 30)); + assertThat(r.getDatePaiementFormatee()).isEqualTo("16/02/2026 14:30"); + } + } + + @Nested + @DisplayName("Montants formatés") + class MontantsFormates { + + @Test + @DisplayName("getFraisAdhesionFormatte") + void testFrais() { + AdhesionResponse r = new AdhesionResponse(); + assertThat(r.getFraisAdhesionFormatte()).isEqualTo("0 FCFA"); + r.setFraisAdhesion(BigDecimal.valueOf(50000)); + assertThat(r.getFraisAdhesionFormatte()).contains("50"); + assertThat(r.getFraisAdhesionFormatte()).endsWith(" FCFA"); + } + + @Test + @DisplayName("getMontantPayeFormatte") + void testMontantPaye() { + AdhesionResponse r = new AdhesionResponse(); + assertThat(r.getMontantPayeFormatte()).isEqualTo("0 FCFA"); + r.setMontantPaye(BigDecimal.valueOf(25000)); + assertThat(r.getMontantPayeFormatte()).contains("25"); + assertThat(r.getMontantPayeFormatte()).endsWith(" FCFA"); + } + + @Test + @DisplayName("getMontantRestantFormatte") + void testMontantRestant() { + AdhesionResponse r = AdhesionResponse.builder() + .fraisAdhesion(BigDecimal.valueOf(100)) + .montantPaye(BigDecimal.valueOf(30)).build(); + assertThat(r.getMontantRestantFormatte()).contains("70"); + assertThat(r.getMontantRestantFormatte()).endsWith(" FCFA"); + } + } + + @Nested + @DisplayName("Builder et getters") + class BuilderGetters { + + @Test + @DisplayName("tous les champs sont accessibles") + void testBuilder() { + LocalDate dateDemande = LocalDate.of(2026, 1, 10); + AdhesionResponse r = AdhesionResponse.builder() + .numeroReference("REF-001") + .membreId(UUID.randomUUID()) + .numeroMembre("M1") + .nomMembre("Dupont") + .emailMembre("d@test.com") + .organisationId(UUID.randomUUID()) + .nomOrganisation("Org") + .dateDemande(dateDemande) + .fraisAdhesion(BigDecimal.valueOf(100)) + .montantPaye(BigDecimal.ZERO) + .codeDevise("XOF") + .statut("EN_ATTENTE") + .build(); + r.setId(UUID.randomUUID()); + assertThat(r.getNumeroReference()).isEqualTo("REF-001"); + assertThat(r.getNomMembre()).isEqualTo("Dupont"); + assertThat(r.getDateDemande()).isEqualTo(dateDemande); + assertThat(r.getStatut()).isEqualTo("EN_ATTENTE"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/CreateFormuleAbonnementRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/CreateFormuleAbonnementRequestTest.java index 92f811f..eef9967 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/CreateFormuleAbonnementRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/CreateFormuleAbonnementRequestTest.java @@ -1,281 +1,281 @@ -package dev.lions.unionflow.server.api.dto.formuleabonnement.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.formuleabonnement.StatutFormule; -import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateFormuleAbonnementRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDate dateDebut = LocalDate.now(); - LocalDate dateFin = LocalDate.now().plusYears(1); - - CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() - .nom("Formule Premium") - .code("PREMIUM_PLUS") - .description("Formule premium avec tous les avantages") - .type(TypeFormule.PREMIUM) - .statut(StatutFormule.ACTIVE) - .prixMensuel(new BigDecimal("50000.00")) - .prixAnnuel(new BigDecimal("500000.00")) - .devise("XOF") - .maxMembres(500) - .maxAdministrateurs(10) - .espaceStockageGB(new BigDecimal("500.00")) - .supportTechnique(true) - .niveauSupport("PREMIUM") - .fonctionnalitesAvancees(true) - .apiAccess(true) - .rapportsPersonnalises(true) - .integrationsTierces(true) - .sauvegardeAutomatique(true) - .multiLangues(true) - .personnalisationInterface(true) - .formationIncluse(true) - .heuresFormation(10) - .populaire(true) - .recommandee(true) - .periodeEssaiJours(30) - .dateDebutValidite(dateDebut) - .dateFinValidite(dateFin) - .ordreAffichage(1) - .couleur("#FF5733") - .icone("pi-star") - .notes("Formule recommandée") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.nom()).isEqualTo("Formule Premium"); - assertThat(request.code()).isEqualTo("PREMIUM_PLUS"); - assertThat(request.description()).isEqualTo("Formule premium avec tous les avantages"); - assertThat(request.type()).isEqualTo(TypeFormule.PREMIUM); - assertThat(request.statut()).isEqualTo(StatutFormule.ACTIVE); - assertThat(request.prixMensuel()).isEqualByComparingTo(new BigDecimal("50000.00")); - assertThat(request.prixAnnuel()).isEqualByComparingTo(new BigDecimal("500000.00")); - assertThat(request.devise()).isEqualTo("XOF"); - assertThat(request.maxMembres()).isEqualTo(500); - assertThat(request.maxAdministrateurs()).isEqualTo(10); - assertThat(request.espaceStockageGB()).isEqualByComparingTo(new BigDecimal("500.00")); - assertThat(request.supportTechnique()).isTrue(); - assertThat(request.niveauSupport()).isEqualTo("PREMIUM"); - assertThat(request.fonctionnalitesAvancees()).isTrue(); - assertThat(request.apiAccess()).isTrue(); - assertThat(request.rapportsPersonnalises()).isTrue(); - assertThat(request.integrationsTierces()).isTrue(); - assertThat(request.sauvegardeAutomatique()).isTrue(); - assertThat(request.multiLangues()).isTrue(); - assertThat(request.personnalisationInterface()).isTrue(); - assertThat(request.formationIncluse()).isTrue(); - assertThat(request.heuresFormation()).isEqualTo(10); - assertThat(request.populaire()).isTrue(); - assertThat(request.recommandee()).isTrue(); - assertThat(request.periodeEssaiJours()).isEqualTo(30); - assertThat(request.dateDebutValidite()).isEqualTo(dateDebut); - assertThat(request.dateFinValidite()).isEqualTo(dateFin); - assertThat(request.ordreAffichage()).isEqualTo(1); - assertThat(request.couleur()).isEqualTo("#FF5733"); - assertThat(request.icone()).isEqualTo("pi-star"); - assertThat(request.notes()).isEqualTo("Formule recommandée"); - } - - @Test - void testBuilder_MinimalFields() { - CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() - .nom("Basic") - .code("BASIC") - .type(TypeFormule.BASIC) - .statut(StatutFormule.ACTIVE) - .prixMensuel(new BigDecimal("10000.00")) - .devise("XOF") - .maxMembres(50) - .maxAdministrateurs(2) - .espaceStockageGB(new BigDecimal("10.00")) - .supportTechnique(false) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.nom()).isEqualTo("Basic"); - assertThat(request.code()).isEqualTo("BASIC"); - assertThat(request.type()).isEqualTo(TypeFormule.BASIC); - assertThat(request.statut()).isEqualTo(StatutFormule.ACTIVE); - assertThat(request.prixMensuel()).isEqualByComparingTo(new BigDecimal("10000.00")); - assertThat(request.devise()).isEqualTo("XOF"); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("type")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("statut")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prixMensuel")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("maxMembres")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("maxAdministrateurs")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("espaceStockageGB")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("supportTechnique")); - } - - @Test - void testValidation_InvalidCode() { - CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() - .nom("Test") - .code("invalid-code") - .type(TypeFormule.BASIC) - .statut(StatutFormule.ACTIVE) - .prixMensuel(new BigDecimal("10000.00")) - .devise("XOF") - .maxMembres(50) - .maxAdministrateurs(2) - .espaceStockageGB(new BigDecimal("10.00")) - .supportTechnique(false) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - } - - @Test - void testValidation_InvalidDevise() { - CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() - .nom("Test") - .code("TEST") - .type(TypeFormule.BASIC) - .statut(StatutFormule.ACTIVE) - .prixMensuel(new BigDecimal("10000.00")) - .devise("INVALID") - .maxMembres(50) - .maxAdministrateurs(2) - .espaceStockageGB(new BigDecimal("10.00")) - .supportTechnique(false) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); - } - - @Test - void testValidation_PrixMensuelZero() { - CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() - .nom("Test") - .code("TEST") - .type(TypeFormule.BASIC) - .statut(StatutFormule.ACTIVE) - .prixMensuel(BigDecimal.ZERO) - .devise("XOF") - .maxMembres(50) - .maxAdministrateurs(2) - .espaceStockageGB(new BigDecimal("10.00")) - .supportTechnique(false) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prixMensuel")); - } - - @Test - void testValidation_ValidFields() { - CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() - .nom("Premium") - .code("PREMIUM") - .type(TypeFormule.PREMIUM) - .statut(StatutFormule.ACTIVE) - .prixMensuel(new BigDecimal("50000.00")) - .devise("XOF") - .maxMembres(500) - .maxAdministrateurs(10) - .espaceStockageGB(new BigDecimal("500.00")) - .supportTechnique(true) - .niveauSupport("PREMIUM") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - CreateFormuleAbonnementRequest request1 = CreateFormuleAbonnementRequest.builder() - .nom("Premium") - .code("PREMIUM") - .type(TypeFormule.PREMIUM) - .statut(StatutFormule.ACTIVE) - .prixMensuel(new BigDecimal("50000.00")) - .devise("XOF") - .maxMembres(500) - .maxAdministrateurs(10) - .espaceStockageGB(new BigDecimal("500.00")) - .supportTechnique(true) - .build(); - - CreateFormuleAbonnementRequest request2 = CreateFormuleAbonnementRequest.builder() - .nom("Premium") - .code("PREMIUM") - .type(TypeFormule.PREMIUM) - .statut(StatutFormule.ACTIVE) - .prixMensuel(new BigDecimal("50000.00")) - .devise("XOF") - .maxMembres(500) - .maxAdministrateurs(10) - .espaceStockageGB(new BigDecimal("500.00")) - .supportTechnique(true) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() - .nom("Premium") - .code("PREMIUM") - .type(TypeFormule.PREMIUM) - .statut(StatutFormule.ACTIVE) - .prixMensuel(new BigDecimal("50000.00")) - .devise("XOF") - .maxMembres(500) - .maxAdministrateurs(10) - .espaceStockageGB(new BigDecimal("500.00")) - .supportTechnique(true) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateFormuleAbonnementRequest"); - assertThat(toString).contains("Premium"); - assertThat(toString).contains("PREMIUM"); - } -} +package dev.lions.unionflow.server.api.dto.formuleabonnement.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.formuleabonnement.StatutFormule; +import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateFormuleAbonnementRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDate dateDebut = LocalDate.now(); + LocalDate dateFin = LocalDate.now().plusYears(1); + + CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() + .nom("Formule Premium") + .code("PREMIUM_PLUS") + .description("Formule premium avec tous les avantages") + .type(TypeFormule.PREMIUM) + .statut(StatutFormule.ACTIVE) + .prixMensuel(new BigDecimal("50000.00")) + .prixAnnuel(new BigDecimal("500000.00")) + .devise("XOF") + .maxMembres(500) + .maxAdministrateurs(10) + .espaceStockageGB(new BigDecimal("500.00")) + .supportTechnique(true) + .niveauSupport("PREMIUM") + .fonctionnalitesAvancees(true) + .apiAccess(true) + .rapportsPersonnalises(true) + .integrationsTierces(true) + .sauvegardeAutomatique(true) + .multiLangues(true) + .personnalisationInterface(true) + .formationIncluse(true) + .heuresFormation(10) + .populaire(true) + .recommandee(true) + .periodeEssaiJours(30) + .dateDebutValidite(dateDebut) + .dateFinValidite(dateFin) + .ordreAffichage(1) + .couleur("#FF5733") + .icone("pi-star") + .notes("Formule recommandée") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.nom()).isEqualTo("Formule Premium"); + assertThat(request.code()).isEqualTo("PREMIUM_PLUS"); + assertThat(request.description()).isEqualTo("Formule premium avec tous les avantages"); + assertThat(request.type()).isEqualTo(TypeFormule.PREMIUM); + assertThat(request.statut()).isEqualTo(StatutFormule.ACTIVE); + assertThat(request.prixMensuel()).isEqualByComparingTo(new BigDecimal("50000.00")); + assertThat(request.prixAnnuel()).isEqualByComparingTo(new BigDecimal("500000.00")); + assertThat(request.devise()).isEqualTo("XOF"); + assertThat(request.maxMembres()).isEqualTo(500); + assertThat(request.maxAdministrateurs()).isEqualTo(10); + assertThat(request.espaceStockageGB()).isEqualByComparingTo(new BigDecimal("500.00")); + assertThat(request.supportTechnique()).isTrue(); + assertThat(request.niveauSupport()).isEqualTo("PREMIUM"); + assertThat(request.fonctionnalitesAvancees()).isTrue(); + assertThat(request.apiAccess()).isTrue(); + assertThat(request.rapportsPersonnalises()).isTrue(); + assertThat(request.integrationsTierces()).isTrue(); + assertThat(request.sauvegardeAutomatique()).isTrue(); + assertThat(request.multiLangues()).isTrue(); + assertThat(request.personnalisationInterface()).isTrue(); + assertThat(request.formationIncluse()).isTrue(); + assertThat(request.heuresFormation()).isEqualTo(10); + assertThat(request.populaire()).isTrue(); + assertThat(request.recommandee()).isTrue(); + assertThat(request.periodeEssaiJours()).isEqualTo(30); + assertThat(request.dateDebutValidite()).isEqualTo(dateDebut); + assertThat(request.dateFinValidite()).isEqualTo(dateFin); + assertThat(request.ordreAffichage()).isEqualTo(1); + assertThat(request.couleur()).isEqualTo("#FF5733"); + assertThat(request.icone()).isEqualTo("pi-star"); + assertThat(request.notes()).isEqualTo("Formule recommandée"); + } + + @Test + void testBuilder_MinimalFields() { + CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() + .nom("Basic") + .code("BASIC") + .type(TypeFormule.BASIC) + .statut(StatutFormule.ACTIVE) + .prixMensuel(new BigDecimal("10000.00")) + .devise("XOF") + .maxMembres(50) + .maxAdministrateurs(2) + .espaceStockageGB(new BigDecimal("10.00")) + .supportTechnique(false) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.nom()).isEqualTo("Basic"); + assertThat(request.code()).isEqualTo("BASIC"); + assertThat(request.type()).isEqualTo(TypeFormule.BASIC); + assertThat(request.statut()).isEqualTo(StatutFormule.ACTIVE); + assertThat(request.prixMensuel()).isEqualByComparingTo(new BigDecimal("10000.00")); + assertThat(request.devise()).isEqualTo("XOF"); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("type")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("statut")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prixMensuel")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("maxMembres")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("maxAdministrateurs")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("espaceStockageGB")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("supportTechnique")); + } + + @Test + void testValidation_InvalidCode() { + CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() + .nom("Test") + .code("invalid-code") + .type(TypeFormule.BASIC) + .statut(StatutFormule.ACTIVE) + .prixMensuel(new BigDecimal("10000.00")) + .devise("XOF") + .maxMembres(50) + .maxAdministrateurs(2) + .espaceStockageGB(new BigDecimal("10.00")) + .supportTechnique(false) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + } + + @Test + void testValidation_InvalidDevise() { + CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() + .nom("Test") + .code("TEST") + .type(TypeFormule.BASIC) + .statut(StatutFormule.ACTIVE) + .prixMensuel(new BigDecimal("10000.00")) + .devise("INVALID") + .maxMembres(50) + .maxAdministrateurs(2) + .espaceStockageGB(new BigDecimal("10.00")) + .supportTechnique(false) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); + } + + @Test + void testValidation_PrixMensuelZero() { + CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() + .nom("Test") + .code("TEST") + .type(TypeFormule.BASIC) + .statut(StatutFormule.ACTIVE) + .prixMensuel(BigDecimal.ZERO) + .devise("XOF") + .maxMembres(50) + .maxAdministrateurs(2) + .espaceStockageGB(new BigDecimal("10.00")) + .supportTechnique(false) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prixMensuel")); + } + + @Test + void testValidation_ValidFields() { + CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() + .nom("Premium") + .code("PREMIUM") + .type(TypeFormule.PREMIUM) + .statut(StatutFormule.ACTIVE) + .prixMensuel(new BigDecimal("50000.00")) + .devise("XOF") + .maxMembres(500) + .maxAdministrateurs(10) + .espaceStockageGB(new BigDecimal("500.00")) + .supportTechnique(true) + .niveauSupport("PREMIUM") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + CreateFormuleAbonnementRequest request1 = CreateFormuleAbonnementRequest.builder() + .nom("Premium") + .code("PREMIUM") + .type(TypeFormule.PREMIUM) + .statut(StatutFormule.ACTIVE) + .prixMensuel(new BigDecimal("50000.00")) + .devise("XOF") + .maxMembres(500) + .maxAdministrateurs(10) + .espaceStockageGB(new BigDecimal("500.00")) + .supportTechnique(true) + .build(); + + CreateFormuleAbonnementRequest request2 = CreateFormuleAbonnementRequest.builder() + .nom("Premium") + .code("PREMIUM") + .type(TypeFormule.PREMIUM) + .statut(StatutFormule.ACTIVE) + .prixMensuel(new BigDecimal("50000.00")) + .devise("XOF") + .maxMembres(500) + .maxAdministrateurs(10) + .espaceStockageGB(new BigDecimal("500.00")) + .supportTechnique(true) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateFormuleAbonnementRequest request = CreateFormuleAbonnementRequest.builder() + .nom("Premium") + .code("PREMIUM") + .type(TypeFormule.PREMIUM) + .statut(StatutFormule.ACTIVE) + .prixMensuel(new BigDecimal("50000.00")) + .devise("XOF") + .maxMembres(500) + .maxAdministrateurs(10) + .espaceStockageGB(new BigDecimal("500.00")) + .supportTechnique(true) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateFormuleAbonnementRequest"); + assertThat(toString).contains("Premium"); + assertThat(toString).contains("PREMIUM"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/UpdateFormuleAbonnementRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/UpdateFormuleAbonnementRequestTest.java index 32c2737..f96d03a 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/UpdateFormuleAbonnementRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/formuleabonnement/request/UpdateFormuleAbonnementRequestTest.java @@ -1,176 +1,176 @@ -package dev.lions.unionflow.server.api.dto.formuleabonnement.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.formuleabonnement.StatutFormule; -import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateFormuleAbonnementRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDate dateDebut = LocalDate.now(); - LocalDate dateFin = LocalDate.now().plusYears(1); - - UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() - .nom("Formule Premium Updated") - .code("PREMIUM_UPDATED") - .description("Description mise à jour") - .type(TypeFormule.PREMIUM) - .statut(StatutFormule.ACTIVE) - .prixMensuel(new BigDecimal("55000.00")) - .prixAnnuel(new BigDecimal("550000.00")) - .devise("XOF") - .maxMembres(600) - .maxAdministrateurs(12) - .espaceStockageGB(new BigDecimal("600.00")) - .supportTechnique(true) - .niveauSupport("PREMIUM") - .fonctionnalitesAvancees(true) - .apiAccess(true) - .rapportsPersonnalises(true) - .integrationsTierces(true) - .sauvegardeAutomatique(true) - .multiLangues(true) - .personnalisationInterface(true) - .formationIncluse(true) - .heuresFormation(15) - .populaire(true) - .recommandee(true) - .periodeEssaiJours(45) - .dateDebutValidite(dateDebut) - .dateFinValidite(dateFin) - .ordreAffichage(2) - .couleur("#00FF00") - .icone("pi-crown") - .notes("Notes mises à jour") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.nom()).isEqualTo("Formule Premium Updated"); - assertThat(request.code()).isEqualTo("PREMIUM_UPDATED"); - assertThat(request.description()).isEqualTo("Description mise à jour"); - assertThat(request.type()).isEqualTo(TypeFormule.PREMIUM); - assertThat(request.statut()).isEqualTo(StatutFormule.ACTIVE); - assertThat(request.prixMensuel()).isEqualByComparingTo(new BigDecimal("55000.00")); - assertThat(request.prixAnnuel()).isEqualByComparingTo(new BigDecimal("550000.00")); - assertThat(request.devise()).isEqualTo("XOF"); - assertThat(request.maxMembres()).isEqualTo(600); - assertThat(request.maxAdministrateurs()).isEqualTo(12); - assertThat(request.espaceStockageGB()).isEqualByComparingTo(new BigDecimal("600.00")); - assertThat(request.supportTechnique()).isTrue(); - assertThat(request.niveauSupport()).isEqualTo("PREMIUM"); - assertThat(request.couleur()).isEqualTo("#00FF00"); - assertThat(request.icone()).isEqualTo("pi-crown"); - } - - @Test - void testBuilder_MinimalFields() { - UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() - .statut(StatutFormule.INACTIVE) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.statut()).isEqualTo(StatutFormule.INACTIVE); - } - - @Test - void testValidation_InvalidCode() { - UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() - .code("invalid-code") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - } - - @Test - void testValidation_InvalidDevise() { - UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() - .devise("INVALID") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); - } - - @Test - void testValidation_PrixMensuelZero() { - UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() - .prixMensuel(BigDecimal.ZERO) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prixMensuel")); - } - - @Test - void testValidation_ValidFields() { - UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() - .nom("Premium Updated") - .code("PREMIUM_UPD") - .prixMensuel(new BigDecimal("55000.00")) - .devise("XOF") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UpdateFormuleAbonnementRequest request1 = UpdateFormuleAbonnementRequest.builder() - .nom("Premium") - .code("PREMIUM") - .statut(StatutFormule.ACTIVE) - .build(); - - UpdateFormuleAbonnementRequest request2 = UpdateFormuleAbonnementRequest.builder() - .nom("Premium") - .code("PREMIUM") - .statut(StatutFormule.ACTIVE) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() - .nom("Premium") - .code("PREMIUM") - .statut(StatutFormule.ACTIVE) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateFormuleAbonnementRequest"); - assertThat(toString).contains("Premium"); - } -} +package dev.lions.unionflow.server.api.dto.formuleabonnement.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.formuleabonnement.StatutFormule; +import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateFormuleAbonnementRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDate dateDebut = LocalDate.now(); + LocalDate dateFin = LocalDate.now().plusYears(1); + + UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() + .nom("Formule Premium Updated") + .code("PREMIUM_UPDATED") + .description("Description mise à jour") + .type(TypeFormule.PREMIUM) + .statut(StatutFormule.ACTIVE) + .prixMensuel(new BigDecimal("55000.00")) + .prixAnnuel(new BigDecimal("550000.00")) + .devise("XOF") + .maxMembres(600) + .maxAdministrateurs(12) + .espaceStockageGB(new BigDecimal("600.00")) + .supportTechnique(true) + .niveauSupport("PREMIUM") + .fonctionnalitesAvancees(true) + .apiAccess(true) + .rapportsPersonnalises(true) + .integrationsTierces(true) + .sauvegardeAutomatique(true) + .multiLangues(true) + .personnalisationInterface(true) + .formationIncluse(true) + .heuresFormation(15) + .populaire(true) + .recommandee(true) + .periodeEssaiJours(45) + .dateDebutValidite(dateDebut) + .dateFinValidite(dateFin) + .ordreAffichage(2) + .couleur("#00FF00") + .icone("pi-crown") + .notes("Notes mises à jour") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.nom()).isEqualTo("Formule Premium Updated"); + assertThat(request.code()).isEqualTo("PREMIUM_UPDATED"); + assertThat(request.description()).isEqualTo("Description mise à jour"); + assertThat(request.type()).isEqualTo(TypeFormule.PREMIUM); + assertThat(request.statut()).isEqualTo(StatutFormule.ACTIVE); + assertThat(request.prixMensuel()).isEqualByComparingTo(new BigDecimal("55000.00")); + assertThat(request.prixAnnuel()).isEqualByComparingTo(new BigDecimal("550000.00")); + assertThat(request.devise()).isEqualTo("XOF"); + assertThat(request.maxMembres()).isEqualTo(600); + assertThat(request.maxAdministrateurs()).isEqualTo(12); + assertThat(request.espaceStockageGB()).isEqualByComparingTo(new BigDecimal("600.00")); + assertThat(request.supportTechnique()).isTrue(); + assertThat(request.niveauSupport()).isEqualTo("PREMIUM"); + assertThat(request.couleur()).isEqualTo("#00FF00"); + assertThat(request.icone()).isEqualTo("pi-crown"); + } + + @Test + void testBuilder_MinimalFields() { + UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() + .statut(StatutFormule.INACTIVE) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.statut()).isEqualTo(StatutFormule.INACTIVE); + } + + @Test + void testValidation_InvalidCode() { + UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() + .code("invalid-code") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + } + + @Test + void testValidation_InvalidDevise() { + UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() + .devise("INVALID") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); + } + + @Test + void testValidation_PrixMensuelZero() { + UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() + .prixMensuel(BigDecimal.ZERO) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prixMensuel")); + } + + @Test + void testValidation_ValidFields() { + UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() + .nom("Premium Updated") + .code("PREMIUM_UPD") + .prixMensuel(new BigDecimal("55000.00")) + .devise("XOF") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UpdateFormuleAbonnementRequest request1 = UpdateFormuleAbonnementRequest.builder() + .nom("Premium") + .code("PREMIUM") + .statut(StatutFormule.ACTIVE) + .build(); + + UpdateFormuleAbonnementRequest request2 = UpdateFormuleAbonnementRequest.builder() + .nom("Premium") + .code("PREMIUM") + .statut(StatutFormule.ACTIVE) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateFormuleAbonnementRequest request = UpdateFormuleAbonnementRequest.builder() + .nom("Premium") + .code("PREMIUM") + .statut(StatutFormule.ACTIVE) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateFormuleAbonnementRequest"); + assertThat(toString).contains("Premium"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/formuleabonnement/response/FormuleAbonnementResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/formuleabonnement/response/FormuleAbonnementResponseTest.java index 117e380..002626e 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/formuleabonnement/response/FormuleAbonnementResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/formuleabonnement/response/FormuleAbonnementResponseTest.java @@ -1,598 +1,598 @@ -package dev.lions.unionflow.server.api.dto.formuleabonnement.response; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.math.BigDecimal; -import java.time.LocalDate; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import dev.lions.unionflow.server.api.enums.formuleabonnement.StatutFormule; -import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; - -/** - * Tests unitaires pour FormuleAbonnementResponse. - * Couvre toutes les branches : isActive, isInactive, isArchivee, isValide, getEconomieAnnuelle, - * getPourcentageEconomieAnnuelle (y compris coutMensuelAnnuel <= 0), hasPeriodeEssai, hasFormation, - * isMiseEnAvant, getBadge (4 branches), getScoreFonctionnalites, getCssClass (type null + switch). - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests FormuleAbonnementResponse") -class FormuleAbonnementResponseTest { - - @Nested - @DisplayName("isValide") - class IsValide { - - @Test - @DisplayName("false quand statut pas ACTIVE") - void testNonActive() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .statut(StatutFormule.INACTIVE) - .build(); - assertThat(r.isValide()).isFalse(); - } - - @Test - @DisplayName("false quand dateDebutValidite dans le futur") - void testDateDebutFuture() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .statut(StatutFormule.ACTIVE) - .dateDebutValidite(LocalDate.now().plusDays(1)) - .build(); - assertThat(r.isValide()).isFalse(); - } - - @Test - @DisplayName("false quand dateFinValidite dans le passé") - void testDateFinPassee() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .statut(StatutFormule.ACTIVE) - .dateFinValidite(LocalDate.now().minusDays(1)) - .build(); - assertThat(r.isValide()).isFalse(); - } - - @Test - @DisplayName("true quand ACTIVE et dates OK") - void testValide() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .statut(StatutFormule.ACTIVE) - .dateDebutValidite(LocalDate.now().minusDays(1)) - .dateFinValidite(LocalDate.now().plusDays(1)) - .build(); - assertThat(r.isValide()).isTrue(); - } - - @Test - @DisplayName("true quand ACTIVE et dateDebutValidite null") - void testDateDebutNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .statut(StatutFormule.ACTIVE) - .dateDebutValidite(null) - .dateFinValidite(LocalDate.now().plusDays(1)) - .build(); - assertThat(r.isValide()).isTrue(); - } - - @Test - @DisplayName("true quand ACTIVE et dateFinValidite null") - void testDateFinNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .statut(StatutFormule.ACTIVE) - .dateDebutValidite(LocalDate.now().minusDays(1)) - .dateFinValidite(null) - .build(); - assertThat(r.isValide()).isTrue(); - } - } - - @Nested - @DisplayName("getEconomieAnnuelle") - class GetEconomieAnnuelle { - - @Test - @DisplayName("retourne ZERO quand prixMensuel null") - void testPrixMensuelNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .prixMensuel(null) - .prixAnnuel(BigDecimal.valueOf(100)) - .build(); - assertThat(r.getEconomieAnnuelle()).isEqualByComparingTo(BigDecimal.ZERO); - } - - @Test - @DisplayName("retourne ZERO quand prixAnnuel null") - void testPrixAnnuelNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .prixMensuel(BigDecimal.valueOf(10)) - .prixAnnuel(null) - .build(); - assertThat(r.getEconomieAnnuelle()).isEqualByComparingTo(BigDecimal.ZERO); - } - - @Test - @DisplayName("calcule économie quand les deux prix sont non-null") - void testCalculEconomie() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .prixMensuel(BigDecimal.valueOf(10)) - .prixAnnuel(BigDecimal.valueOf(100)) - .build(); - // 10*12 - 100 = 120 - 100 = 20 - assertThat(r.getEconomieAnnuelle()).isEqualByComparingTo(BigDecimal.valueOf(20)); - } - } - - @Nested - @DisplayName("getPourcentageEconomieAnnuelle") - class GetPourcentageEconomieAnnuelle { - - @Test - @DisplayName("retourne 0 quand prixMensuel null") - void testPrixMensuelNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().prixAnnuel(BigDecimal.TEN).build(); - assertThat(r.getPourcentageEconomieAnnuelle()).isEqualTo(0); - } - - @Test - @DisplayName("retourne 0 quand prixAnnuel null") - void testPrixAnnuelNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().prixMensuel(BigDecimal.TEN).build(); - assertThat(r.getPourcentageEconomieAnnuelle()).isEqualTo(0); - } - - @Test - @DisplayName("retourne 0 quand coutMensuelAnnuel <= 0") - void testCoutMensuelZero() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .prixMensuel(BigDecimal.ZERO) - .prixAnnuel(BigDecimal.ZERO) - .build(); - assertThat(r.getPourcentageEconomieAnnuelle()).isEqualTo(0); - } - - @Test - @DisplayName("calcule pourcentage quand économie positive") - void testPourcentagePositif() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .prixMensuel(BigDecimal.valueOf(10)) - .prixAnnuel(BigDecimal.valueOf(100)) - .build(); - assertThat(r.getPourcentageEconomieAnnuelle()).isGreaterThan(0); - } - } - - @Nested - @DisplayName("getBadge") - class GetBadge { - - @Test - @DisplayName("POPULAIRE quand populaire true") - void testPopulaire() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .populaire(true) - .recommandee(false) - .periodeEssaiJours(0) - .build(); - assertThat(r.getBadge()).isEqualTo("POPULAIRE"); - } - - @Test - @DisplayName("RECOMMANDÉE quand recommandee true et pas populaire") - void testRecommandee() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .populaire(false) - .recommandee(true) - .periodeEssaiJours(0) - .build(); - assertThat(r.getBadge()).isEqualTo("RECOMMANDÉE"); - } - - @Test - @DisplayName("ESSAI GRATUIT quand periodeEssaiJours > 0 et pas populaire/recommandee") - void testEssaiGratuit() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .populaire(false) - .recommandee(false) - .periodeEssaiJours(7) - .build(); - assertThat(r.getBadge()).isEqualTo("ESSAI GRATUIT"); - } - - @Test - @DisplayName("null quand aucun badge") - void testAucunBadge() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .populaire(false) - .recommandee(false) - .periodeEssaiJours(0) - .build(); - assertThat(r.getBadge()).isNull(); - } - } - - @Nested - @DisplayName("getScoreFonctionnalites") - class GetScoreFonctionnalites { - - @Test - @DisplayName("0 quand tous les booléens false") - void testTousFalse() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .supportTechnique(false) - .sauvegardeAutomatique(false) - .fonctionnalitesAvancees(false) - .apiAccess(false) - .rapportsPersonnalises(false) - .integrationsTierces(false) - .multiLangues(false) - .personnalisationInterface(false) - .build(); - assertThat(r.getScoreFonctionnalites()).isEqualTo(0); - } - - @Test - @DisplayName("0 quand toutes les fonctionnalités sont null (aucune config)") - void testToutesFonctionnalitesNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().build(); - assertThat(r.getScoreFonctionnalites()).isEqualTo(0); - } - - @Test - @DisplayName("score > 0 quand supportTechnique true") - void testSupportTechnique() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .supportTechnique(true) - .sauvegardeAutomatique(false) - .fonctionnalitesAvancees(false) - .apiAccess(false) - .rapportsPersonnalises(false) - .integrationsTierces(false) - .multiLangues(false) - .personnalisationInterface(false) - .build(); - assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); - } - - @Test - @DisplayName("score > 0 quand sauvegardeAutomatique true") - void testSauvegardeAutomatique() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .supportTechnique(false) - .sauvegardeAutomatique(true) - .fonctionnalitesAvancees(false) - .apiAccess(false) - .rapportsPersonnalises(false) - .integrationsTierces(false) - .multiLangues(false) - .personnalisationInterface(false) - .build(); - assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); - } - - @Test - @DisplayName("score > 0 quand fonctionnalitesAvancees true") - void testFonctionnalitesAvancees() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .supportTechnique(false) - .sauvegardeAutomatique(false) - .fonctionnalitesAvancees(true) - .apiAccess(false) - .rapportsPersonnalises(false) - .integrationsTierces(false) - .multiLangues(false) - .personnalisationInterface(false) - .build(); - assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); - } - - @Test - @DisplayName("score > 0 quand apiAccess true") - void testApiAccess() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .supportTechnique(false) - .sauvegardeAutomatique(false) - .fonctionnalitesAvancees(false) - .apiAccess(true) - .rapportsPersonnalises(false) - .integrationsTierces(false) - .multiLangues(false) - .personnalisationInterface(false) - .build(); - assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); - } - - @Test - @DisplayName("score > 0 quand rapportsPersonnalises true") - void testRapportsPersonnalises() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .supportTechnique(false) - .sauvegardeAutomatique(false) - .fonctionnalitesAvancees(false) - .apiAccess(false) - .rapportsPersonnalises(true) - .integrationsTierces(false) - .multiLangues(false) - .personnalisationInterface(false) - .build(); - assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); - } - - @Test - @DisplayName("score > 0 quand integrationsTierces true") - void testIntegrationsTierces() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .supportTechnique(false) - .sauvegardeAutomatique(false) - .fonctionnalitesAvancees(false) - .apiAccess(false) - .rapportsPersonnalises(false) - .integrationsTierces(true) - .multiLangues(false) - .personnalisationInterface(false) - .build(); - assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); - } - - @Test - @DisplayName("score > 0 quand multiLangues et personnalisationInterface true") - void testMultiLanguesEtPersonnalisation() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .supportTechnique(false) - .sauvegardeAutomatique(false) - .fonctionnalitesAvancees(false) - .apiAccess(false) - .rapportsPersonnalises(false) - .integrationsTierces(false) - .multiLangues(true) - .personnalisationInterface(true) - .build(); - assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); - } - - @Test - @DisplayName("score = 100 quand toutes les fonctionnalités true") - void testToutesTrue() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .supportTechnique(true) - .sauvegardeAutomatique(true) - .fonctionnalitesAvancees(true) - .apiAccess(true) - .rapportsPersonnalises(true) - .integrationsTierces(true) - .multiLangues(true) - .personnalisationInterface(true) - .build(); - assertThat(r.getScoreFonctionnalites()).isEqualTo(100); - } - - @Test - @DisplayName("score calculé quand premier champ non null, reste null") - void testSupportTechniqueNonNullRestNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .supportTechnique(true) - // Les autres champs restent null - .build(); - assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); - } - - @Test - @DisplayName("score calculé quand deuxième champ non null, reste null") - void testSauvegardeNonNullRestNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .sauvegardeAutomatique(false) - // Les autres champs restent null - .build(); - assertThat(r.getScoreFonctionnalites()).isEqualTo(0); - } - - @Test - @DisplayName("score calculé quand troisième champ non null, reste null") - void testFonctionnalitesAvanceesNonNullRestNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .fonctionnalitesAvancees(true) - // Les autres champs restent null - .build(); - assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); - } - - @Test - @DisplayName("score calculé quand quatrième champ non null, reste null") - void testApiAccessNonNullRestNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .apiAccess(false) - // Les autres champs restent null - .build(); - assertThat(r.getScoreFonctionnalites()).isEqualTo(0); - } - - @Test - @DisplayName("score calculé quand cinquième champ non null, reste null") - void testRapportsNonNullRestNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .rapportsPersonnalises(true) - // Les autres champs restent null - .build(); - assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); - } - - @Test - @DisplayName("score calculé quand sixième champ non null, reste null") - void testIntegrationsNonNullRestNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .integrationsTierces(false) - // Les autres champs restent null - .build(); - assertThat(r.getScoreFonctionnalites()).isEqualTo(0); - } - - @Test - @DisplayName("score calculé quand septième champ non null, reste null") - void testMultiLanguesNonNullRestNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .multiLangues(true) - // Les autres champs restent null - .build(); - assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); - } - - @Test - @DisplayName("score calculé quand huitième champ non null, reste null") - void testPersonnalisationNonNullRestNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .personnalisationInterface(false) - // Les autres champs restent null - .build(); - assertThat(r.getScoreFonctionnalites()).isEqualTo(0); - } - } - - @Nested - @DisplayName("getCssClass") - class GetCssClass { - - @Test - @DisplayName("formule-default quand type null") - void testTypeNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().type(null).build(); - assertThat(r.getCssClass()).isEqualTo("formule-default"); - } - - @Test - @DisplayName("formule-basic pour BASIC") - void testBasic() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().type(TypeFormule.BASIC).build(); - assertThat(r.getCssClass()).isEqualTo("formule-basic"); - } - - @Test - @DisplayName("formule-standard pour STANDARD") - void testStandard() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().type(TypeFormule.STANDARD).build(); - assertThat(r.getCssClass()).isEqualTo("formule-standard"); - } - - @Test - @DisplayName("formule-premium pour PREMIUM") - void testPremium() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().type(TypeFormule.PREMIUM).build(); - assertThat(r.getCssClass()).isEqualTo("formule-premium"); - } - - @Test - @DisplayName("formule-enterprise pour ENTERPRISE") - void testEnterprise() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().type(TypeFormule.ENTERPRISE).build(); - assertThat(r.getCssClass()).isEqualTo("formule-enterprise"); - } - } - - @Nested - @DisplayName("isActive, isInactive, isArchivee") - class Statut { - - @Test - @DisplayName("isActive true pour ACTIVE") - void testActive() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().statut(StatutFormule.ACTIVE).build(); - assertThat(r.isActive()).isTrue(); - } - - @Test - @DisplayName("isInactive true pour INACTIVE") - void testInactive() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().statut(StatutFormule.INACTIVE).build(); - assertThat(r.isInactive()).isTrue(); - } - - @Test - @DisplayName("isArchivee true pour ARCHIVEE") - void testArchivee() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().statut(StatutFormule.ARCHIVEE).build(); - assertThat(r.isArchivee()).isTrue(); - } - } - - @Nested - @DisplayName("hasPeriodeEssai, hasFormation, isMiseEnAvant") - class AutresBranches { - - @Test - @DisplayName("hasPeriodeEssai true quand periodeEssaiJours > 0") - void testHasPeriodeEssai() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().periodeEssaiJours(14).build(); - assertThat(r.hasPeriodeEssai()).isTrue(); - } - - @Test - @DisplayName("hasPeriodeEssai false quand periodeEssaiJours null") - void testHasPeriodeEssaiNull() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().periodeEssaiJours(null).build(); - assertThat(r.hasPeriodeEssai()).isFalse(); - } - - @Test - @DisplayName("hasPeriodeEssai false quand periodeEssaiJours <= 0") - void testHasPeriodeEssaiZeroOuNegatif() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().periodeEssaiJours(0).build(); - assertThat(r.hasPeriodeEssai()).isFalse(); - r.setPeriodeEssaiJours(-1); - assertThat(r.hasPeriodeEssai()).isFalse(); - } - - @Test - @DisplayName("hasFormation true quand formationIncluse et heuresFormation > 0") - void testHasFormation() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .formationIncluse(true) - .heuresFormation(10) - .build(); - assertThat(r.hasFormation()).isTrue(); - } - - @Test - @DisplayName("hasFormation false quand formationIncluse false") - void testHasFormationFalse() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .formationIncluse(false) - .heuresFormation(10) - .build(); - assertThat(r.hasFormation()).isFalse(); - } - - @Test - @DisplayName("hasFormation false quand heuresFormation null ou 0") - void testHasFormationHeuresNullOuZero() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .formationIncluse(true) - .heuresFormation(null) - .build(); - assertThat(r.hasFormation()).isFalse(); - r.setHeuresFormation(0); - assertThat(r.hasFormation()).isFalse(); - } - - @Test - @DisplayName("isMiseEnAvant true quand populaire ou recommandee") - void testMiseEnAvant() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().populaire(true).build(); - assertThat(r.isMiseEnAvant()).isTrue(); - r.setPopulaire(false); - r.setRecommandee(true); - assertThat(r.isMiseEnAvant()).isTrue(); - } - - @Test - @DisplayName("isMiseEnAvant false quand ni populaire ni recommandee") - void testPasMiseEnAvant() { - FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() - .populaire(false) - .recommandee(false) - .build(); - assertThat(r.isMiseEnAvant()).isFalse(); - } - } -} +package dev.lions.unionflow.server.api.dto.formuleabonnement.response; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.math.BigDecimal; +import java.time.LocalDate; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import dev.lions.unionflow.server.api.enums.formuleabonnement.StatutFormule; +import dev.lions.unionflow.server.api.enums.formuleabonnement.TypeFormule; + +/** + * Tests unitaires pour FormuleAbonnementResponse. + * Couvre toutes les branches : isActive, isInactive, isArchivee, isValide, getEconomieAnnuelle, + * getPourcentageEconomieAnnuelle (y compris coutMensuelAnnuel <= 0), hasPeriodeEssai, hasFormation, + * isMiseEnAvant, getBadge (4 branches), getScoreFonctionnalites, getCssClass (type null + switch). + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests FormuleAbonnementResponse") +class FormuleAbonnementResponseTest { + + @Nested + @DisplayName("isValide") + class IsValide { + + @Test + @DisplayName("false quand statut pas ACTIVE") + void testNonActive() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .statut(StatutFormule.INACTIVE) + .build(); + assertThat(r.isValide()).isFalse(); + } + + @Test + @DisplayName("false quand dateDebutValidite dans le futur") + void testDateDebutFuture() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .statut(StatutFormule.ACTIVE) + .dateDebutValidite(LocalDate.now().plusDays(1)) + .build(); + assertThat(r.isValide()).isFalse(); + } + + @Test + @DisplayName("false quand dateFinValidite dans le passé") + void testDateFinPassee() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .statut(StatutFormule.ACTIVE) + .dateFinValidite(LocalDate.now().minusDays(1)) + .build(); + assertThat(r.isValide()).isFalse(); + } + + @Test + @DisplayName("true quand ACTIVE et dates OK") + void testValide() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .statut(StatutFormule.ACTIVE) + .dateDebutValidite(LocalDate.now().minusDays(1)) + .dateFinValidite(LocalDate.now().plusDays(1)) + .build(); + assertThat(r.isValide()).isTrue(); + } + + @Test + @DisplayName("true quand ACTIVE et dateDebutValidite null") + void testDateDebutNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .statut(StatutFormule.ACTIVE) + .dateDebutValidite(null) + .dateFinValidite(LocalDate.now().plusDays(1)) + .build(); + assertThat(r.isValide()).isTrue(); + } + + @Test + @DisplayName("true quand ACTIVE et dateFinValidite null") + void testDateFinNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .statut(StatutFormule.ACTIVE) + .dateDebutValidite(LocalDate.now().minusDays(1)) + .dateFinValidite(null) + .build(); + assertThat(r.isValide()).isTrue(); + } + } + + @Nested + @DisplayName("getEconomieAnnuelle") + class GetEconomieAnnuelle { + + @Test + @DisplayName("retourne ZERO quand prixMensuel null") + void testPrixMensuelNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .prixMensuel(null) + .prixAnnuel(BigDecimal.valueOf(100)) + .build(); + assertThat(r.getEconomieAnnuelle()).isEqualByComparingTo(BigDecimal.ZERO); + } + + @Test + @DisplayName("retourne ZERO quand prixAnnuel null") + void testPrixAnnuelNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .prixMensuel(BigDecimal.valueOf(10)) + .prixAnnuel(null) + .build(); + assertThat(r.getEconomieAnnuelle()).isEqualByComparingTo(BigDecimal.ZERO); + } + + @Test + @DisplayName("calcule économie quand les deux prix sont non-null") + void testCalculEconomie() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .prixMensuel(BigDecimal.valueOf(10)) + .prixAnnuel(BigDecimal.valueOf(100)) + .build(); + // 10*12 - 100 = 120 - 100 = 20 + assertThat(r.getEconomieAnnuelle()).isEqualByComparingTo(BigDecimal.valueOf(20)); + } + } + + @Nested + @DisplayName("getPourcentageEconomieAnnuelle") + class GetPourcentageEconomieAnnuelle { + + @Test + @DisplayName("retourne 0 quand prixMensuel null") + void testPrixMensuelNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().prixAnnuel(BigDecimal.TEN).build(); + assertThat(r.getPourcentageEconomieAnnuelle()).isEqualTo(0); + } + + @Test + @DisplayName("retourne 0 quand prixAnnuel null") + void testPrixAnnuelNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().prixMensuel(BigDecimal.TEN).build(); + assertThat(r.getPourcentageEconomieAnnuelle()).isEqualTo(0); + } + + @Test + @DisplayName("retourne 0 quand coutMensuelAnnuel <= 0") + void testCoutMensuelZero() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .prixMensuel(BigDecimal.ZERO) + .prixAnnuel(BigDecimal.ZERO) + .build(); + assertThat(r.getPourcentageEconomieAnnuelle()).isEqualTo(0); + } + + @Test + @DisplayName("calcule pourcentage quand économie positive") + void testPourcentagePositif() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .prixMensuel(BigDecimal.valueOf(10)) + .prixAnnuel(BigDecimal.valueOf(100)) + .build(); + assertThat(r.getPourcentageEconomieAnnuelle()).isGreaterThan(0); + } + } + + @Nested + @DisplayName("getBadge") + class GetBadge { + + @Test + @DisplayName("POPULAIRE quand populaire true") + void testPopulaire() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .populaire(true) + .recommandee(false) + .periodeEssaiJours(0) + .build(); + assertThat(r.getBadge()).isEqualTo("POPULAIRE"); + } + + @Test + @DisplayName("RECOMMANDÉE quand recommandee true et pas populaire") + void testRecommandee() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .populaire(false) + .recommandee(true) + .periodeEssaiJours(0) + .build(); + assertThat(r.getBadge()).isEqualTo("RECOMMANDÉE"); + } + + @Test + @DisplayName("ESSAI GRATUIT quand periodeEssaiJours > 0 et pas populaire/recommandee") + void testEssaiGratuit() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .populaire(false) + .recommandee(false) + .periodeEssaiJours(7) + .build(); + assertThat(r.getBadge()).isEqualTo("ESSAI GRATUIT"); + } + + @Test + @DisplayName("null quand aucun badge") + void testAucunBadge() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .populaire(false) + .recommandee(false) + .periodeEssaiJours(0) + .build(); + assertThat(r.getBadge()).isNull(); + } + } + + @Nested + @DisplayName("getScoreFonctionnalites") + class GetScoreFonctionnalites { + + @Test + @DisplayName("0 quand tous les booléens false") + void testTousFalse() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .supportTechnique(false) + .sauvegardeAutomatique(false) + .fonctionnalitesAvancees(false) + .apiAccess(false) + .rapportsPersonnalises(false) + .integrationsTierces(false) + .multiLangues(false) + .personnalisationInterface(false) + .build(); + assertThat(r.getScoreFonctionnalites()).isEqualTo(0); + } + + @Test + @DisplayName("0 quand toutes les fonctionnalités sont null (aucune config)") + void testToutesFonctionnalitesNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().build(); + assertThat(r.getScoreFonctionnalites()).isEqualTo(0); + } + + @Test + @DisplayName("score > 0 quand supportTechnique true") + void testSupportTechnique() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .supportTechnique(true) + .sauvegardeAutomatique(false) + .fonctionnalitesAvancees(false) + .apiAccess(false) + .rapportsPersonnalises(false) + .integrationsTierces(false) + .multiLangues(false) + .personnalisationInterface(false) + .build(); + assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); + } + + @Test + @DisplayName("score > 0 quand sauvegardeAutomatique true") + void testSauvegardeAutomatique() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .supportTechnique(false) + .sauvegardeAutomatique(true) + .fonctionnalitesAvancees(false) + .apiAccess(false) + .rapportsPersonnalises(false) + .integrationsTierces(false) + .multiLangues(false) + .personnalisationInterface(false) + .build(); + assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); + } + + @Test + @DisplayName("score > 0 quand fonctionnalitesAvancees true") + void testFonctionnalitesAvancees() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .supportTechnique(false) + .sauvegardeAutomatique(false) + .fonctionnalitesAvancees(true) + .apiAccess(false) + .rapportsPersonnalises(false) + .integrationsTierces(false) + .multiLangues(false) + .personnalisationInterface(false) + .build(); + assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); + } + + @Test + @DisplayName("score > 0 quand apiAccess true") + void testApiAccess() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .supportTechnique(false) + .sauvegardeAutomatique(false) + .fonctionnalitesAvancees(false) + .apiAccess(true) + .rapportsPersonnalises(false) + .integrationsTierces(false) + .multiLangues(false) + .personnalisationInterface(false) + .build(); + assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); + } + + @Test + @DisplayName("score > 0 quand rapportsPersonnalises true") + void testRapportsPersonnalises() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .supportTechnique(false) + .sauvegardeAutomatique(false) + .fonctionnalitesAvancees(false) + .apiAccess(false) + .rapportsPersonnalises(true) + .integrationsTierces(false) + .multiLangues(false) + .personnalisationInterface(false) + .build(); + assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); + } + + @Test + @DisplayName("score > 0 quand integrationsTierces true") + void testIntegrationsTierces() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .supportTechnique(false) + .sauvegardeAutomatique(false) + .fonctionnalitesAvancees(false) + .apiAccess(false) + .rapportsPersonnalises(false) + .integrationsTierces(true) + .multiLangues(false) + .personnalisationInterface(false) + .build(); + assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); + } + + @Test + @DisplayName("score > 0 quand multiLangues et personnalisationInterface true") + void testMultiLanguesEtPersonnalisation() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .supportTechnique(false) + .sauvegardeAutomatique(false) + .fonctionnalitesAvancees(false) + .apiAccess(false) + .rapportsPersonnalises(false) + .integrationsTierces(false) + .multiLangues(true) + .personnalisationInterface(true) + .build(); + assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); + } + + @Test + @DisplayName("score = 100 quand toutes les fonctionnalités true") + void testToutesTrue() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .supportTechnique(true) + .sauvegardeAutomatique(true) + .fonctionnalitesAvancees(true) + .apiAccess(true) + .rapportsPersonnalises(true) + .integrationsTierces(true) + .multiLangues(true) + .personnalisationInterface(true) + .build(); + assertThat(r.getScoreFonctionnalites()).isEqualTo(100); + } + + @Test + @DisplayName("score calculé quand premier champ non null, reste null") + void testSupportTechniqueNonNullRestNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .supportTechnique(true) + // Les autres champs restent null + .build(); + assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); + } + + @Test + @DisplayName("score calculé quand deuxième champ non null, reste null") + void testSauvegardeNonNullRestNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .sauvegardeAutomatique(false) + // Les autres champs restent null + .build(); + assertThat(r.getScoreFonctionnalites()).isEqualTo(0); + } + + @Test + @DisplayName("score calculé quand troisième champ non null, reste null") + void testFonctionnalitesAvanceesNonNullRestNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .fonctionnalitesAvancees(true) + // Les autres champs restent null + .build(); + assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); + } + + @Test + @DisplayName("score calculé quand quatrième champ non null, reste null") + void testApiAccessNonNullRestNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .apiAccess(false) + // Les autres champs restent null + .build(); + assertThat(r.getScoreFonctionnalites()).isEqualTo(0); + } + + @Test + @DisplayName("score calculé quand cinquième champ non null, reste null") + void testRapportsNonNullRestNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .rapportsPersonnalises(true) + // Les autres champs restent null + .build(); + assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); + } + + @Test + @DisplayName("score calculé quand sixième champ non null, reste null") + void testIntegrationsNonNullRestNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .integrationsTierces(false) + // Les autres champs restent null + .build(); + assertThat(r.getScoreFonctionnalites()).isEqualTo(0); + } + + @Test + @DisplayName("score calculé quand septième champ non null, reste null") + void testMultiLanguesNonNullRestNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .multiLangues(true) + // Les autres champs restent null + .build(); + assertThat(r.getScoreFonctionnalites()).isGreaterThan(0); + } + + @Test + @DisplayName("score calculé quand huitième champ non null, reste null") + void testPersonnalisationNonNullRestNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .personnalisationInterface(false) + // Les autres champs restent null + .build(); + assertThat(r.getScoreFonctionnalites()).isEqualTo(0); + } + } + + @Nested + @DisplayName("getCssClass") + class GetCssClass { + + @Test + @DisplayName("formule-default quand type null") + void testTypeNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().type(null).build(); + assertThat(r.getCssClass()).isEqualTo("formule-default"); + } + + @Test + @DisplayName("formule-basic pour BASIC") + void testBasic() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().type(TypeFormule.BASIC).build(); + assertThat(r.getCssClass()).isEqualTo("formule-basic"); + } + + @Test + @DisplayName("formule-standard pour STANDARD") + void testStandard() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().type(TypeFormule.STANDARD).build(); + assertThat(r.getCssClass()).isEqualTo("formule-standard"); + } + + @Test + @DisplayName("formule-premium pour PREMIUM") + void testPremium() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().type(TypeFormule.PREMIUM).build(); + assertThat(r.getCssClass()).isEqualTo("formule-premium"); + } + + @Test + @DisplayName("formule-enterprise pour ENTERPRISE") + void testEnterprise() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().type(TypeFormule.ENTERPRISE).build(); + assertThat(r.getCssClass()).isEqualTo("formule-enterprise"); + } + } + + @Nested + @DisplayName("isActive, isInactive, isArchivee") + class Statut { + + @Test + @DisplayName("isActive true pour ACTIVE") + void testActive() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().statut(StatutFormule.ACTIVE).build(); + assertThat(r.isActive()).isTrue(); + } + + @Test + @DisplayName("isInactive true pour INACTIVE") + void testInactive() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().statut(StatutFormule.INACTIVE).build(); + assertThat(r.isInactive()).isTrue(); + } + + @Test + @DisplayName("isArchivee true pour ARCHIVEE") + void testArchivee() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().statut(StatutFormule.ARCHIVEE).build(); + assertThat(r.isArchivee()).isTrue(); + } + } + + @Nested + @DisplayName("hasPeriodeEssai, hasFormation, isMiseEnAvant") + class AutresBranches { + + @Test + @DisplayName("hasPeriodeEssai true quand periodeEssaiJours > 0") + void testHasPeriodeEssai() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().periodeEssaiJours(14).build(); + assertThat(r.hasPeriodeEssai()).isTrue(); + } + + @Test + @DisplayName("hasPeriodeEssai false quand periodeEssaiJours null") + void testHasPeriodeEssaiNull() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().periodeEssaiJours(null).build(); + assertThat(r.hasPeriodeEssai()).isFalse(); + } + + @Test + @DisplayName("hasPeriodeEssai false quand periodeEssaiJours <= 0") + void testHasPeriodeEssaiZeroOuNegatif() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().periodeEssaiJours(0).build(); + assertThat(r.hasPeriodeEssai()).isFalse(); + r.setPeriodeEssaiJours(-1); + assertThat(r.hasPeriodeEssai()).isFalse(); + } + + @Test + @DisplayName("hasFormation true quand formationIncluse et heuresFormation > 0") + void testHasFormation() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .formationIncluse(true) + .heuresFormation(10) + .build(); + assertThat(r.hasFormation()).isTrue(); + } + + @Test + @DisplayName("hasFormation false quand formationIncluse false") + void testHasFormationFalse() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .formationIncluse(false) + .heuresFormation(10) + .build(); + assertThat(r.hasFormation()).isFalse(); + } + + @Test + @DisplayName("hasFormation false quand heuresFormation null ou 0") + void testHasFormationHeuresNullOuZero() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .formationIncluse(true) + .heuresFormation(null) + .build(); + assertThat(r.hasFormation()).isFalse(); + r.setHeuresFormation(0); + assertThat(r.hasFormation()).isFalse(); + } + + @Test + @DisplayName("isMiseEnAvant true quand populaire ou recommandee") + void testMiseEnAvant() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder().populaire(true).build(); + assertThat(r.isMiseEnAvant()).isTrue(); + r.setPopulaire(false); + r.setRecommandee(true); + assertThat(r.isMiseEnAvant()).isTrue(); + } + + @Test + @DisplayName("isMiseEnAvant false quand ni populaire ni recommandee") + void testPasMiseEnAvant() { + FormuleAbonnementResponse r = FormuleAbonnementResponse.builder() + .populaire(false) + .recommandee(false) + .build(); + assertThat(r.isMiseEnAvant()).isFalse(); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchCriteriaTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchCriteriaTest.java index 6b0c7b1..280ceb9 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchCriteriaTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchCriteriaTest.java @@ -1,499 +1,499 @@ -package dev.lions.unionflow.server.api.dto.membre; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalDate; -import java.util.List; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour MembreSearchCriteria. - * Couvre toutes les branches : hasAnyCriteria, isValid, sanitize, getDescription. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests MembreSearchCriteria") -class MembreSearchCriteriaTest { - - @Nested - @DisplayName("hasAnyCriteria") - class HasAnyCriteria { - - @Test - @DisplayName("false quand tous les champs null ou vides") - void testAucunCritere() { - MembreSearchCriteria c = new MembreSearchCriteria(); - assertThat(c.hasAnyCriteria()).isFalse(); - } - - @Test - @DisplayName("true quand query non vide") - void testQuery() { - MembreSearchCriteria c = MembreSearchCriteria.builder().query("x").build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("false quand query vide après trim") - void testQueryVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder().query(" ").build(); - assertThat(c.hasAnyCriteria()).isFalse(); - } - - @Test - @DisplayName("true quand nom défini") - void testNom() { - MembreSearchCriteria c = MembreSearchCriteria.builder().nom("Dupont").build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand prenom défini") - void testPrenom() { - MembreSearchCriteria c = MembreSearchCriteria.builder().prenom("Marie").build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand email défini") - void testEmail() { - MembreSearchCriteria c = MembreSearchCriteria.builder().email("@x.com").build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand telephone défini") - void testTelephone() { - MembreSearchCriteria c = MembreSearchCriteria.builder().telephone("+221").build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand organisationIds non vide") - void testOrganisationIds() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .organisationIds(List.of(UUID.randomUUID())) - .build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("false quand organisationIds vide") - void testOrganisationIdsVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .organisationIds(List.of()) - .build(); - assertThat(c.hasAnyCriteria()).isFalse(); - } - - @Test - @DisplayName("true quand roles non vide") - void testRoles() { - MembreSearchCriteria c = MembreSearchCriteria.builder().roles(List.of("ADMIN")).build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand statut défini") - void testStatut() { - MembreSearchCriteria c = MembreSearchCriteria.builder().statut("ACTIF").build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand dateAdhesionMin défini") - void testDateAdhesionMin() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .dateAdhesionMin(LocalDate.of(2020, 1, 1)) - .build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand dateAdhesionMax défini") - void testDateAdhesionMax() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .dateAdhesionMax(LocalDate.of(2025, 12, 31)) - .build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand ageMin défini") - void testAgeMin() { - MembreSearchCriteria c = MembreSearchCriteria.builder().ageMin(18).build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand ageMax défini") - void testAgeMax() { - MembreSearchCriteria c = MembreSearchCriteria.builder().ageMax(65).build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand region défini") - void testRegion() { - MembreSearchCriteria c = MembreSearchCriteria.builder().region("Dakar").build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand ville défini") - void testVille() { - MembreSearchCriteria c = MembreSearchCriteria.builder().ville("Dakar").build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand profession défini") - void testProfession() { - MembreSearchCriteria c = MembreSearchCriteria.builder().profession("Ingénieur").build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand nationalite défini") - void testNationalite() { - MembreSearchCriteria c = MembreSearchCriteria.builder().nationalite("Sénégalaise").build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand membreBureau défini") - void testMembreBureau() { - MembreSearchCriteria c = MembreSearchCriteria.builder().membreBureau(true).build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("true quand responsable défini") - void testResponsable() { - MembreSearchCriteria c = MembreSearchCriteria.builder().responsable(true).build(); - assertThat(c.hasAnyCriteria()).isTrue(); - } - - @Test - @DisplayName("false quand nom vide après trim") - void testNomVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder().nom(" ").build(); - assertThat(c.hasAnyCriteria()).isFalse(); - } - - @Test - @DisplayName("false quand prenom vide après trim") - void testPrenomVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder().prenom(" ").build(); - assertThat(c.hasAnyCriteria()).isFalse(); - } - - @Test - @DisplayName("false quand email vide après trim") - void testEmailVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder().email(" ").build(); - assertThat(c.hasAnyCriteria()).isFalse(); - } - - @Test - @DisplayName("false quand telephone vide après trim") - void testTelephoneVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder().telephone(" ").build(); - assertThat(c.hasAnyCriteria()).isFalse(); - } - - @Test - @DisplayName("false quand statut vide après trim") - void testStatutVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder().statut(" ").build(); - assertThat(c.hasAnyCriteria()).isFalse(); - } - - @Test - @DisplayName("false quand region vide après trim") - void testRegionVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder().region(" ").build(); - assertThat(c.hasAnyCriteria()).isFalse(); - } - - @Test - @DisplayName("false quand ville vide après trim") - void testVilleVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder().ville(" ").build(); - assertThat(c.hasAnyCriteria()).isFalse(); - } - - @Test - @DisplayName("false quand profession vide après trim") - void testProfessionVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder().profession(" ").build(); - assertThat(c.hasAnyCriteria()).isFalse(); - } - - @Test - @DisplayName("false quand nationalite vide après trim") - void testNationaliteVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder().nationalite(" ").build(); - assertThat(c.hasAnyCriteria()).isFalse(); - } - - @Test - @DisplayName("false quand roles vide") - void testRolesVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder().roles(List.of()).build(); - assertThat(c.hasAnyCriteria()).isFalse(); - } - } - - @Nested - @DisplayName("isValid") - class IsValid { - - @Test - @DisplayName("true quand pas de dates ni âges") - void testSansContraintes() { - MembreSearchCriteria c = MembreSearchCriteria.builder().query("x").build(); - assertThat(c.isValid()).isTrue(); - } - - @Test - @DisplayName("false quand dateAdhesionMin après dateAdhesionMax") - void testDatesIncoherentes() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .dateAdhesionMin(LocalDate.of(2025, 1, 1)) - .dateAdhesionMax(LocalDate.of(2020, 1, 1)) - .build(); - assertThat(c.isValid()).isFalse(); - } - - @Test - @DisplayName("true quand dateAdhesionMin avant dateAdhesionMax") - void testDatesCoherentes() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .dateAdhesionMin(LocalDate.of(2020, 1, 1)) - .dateAdhesionMax(LocalDate.of(2025, 1, 1)) - .build(); - assertThat(c.isValid()).isTrue(); - } - - @Test - @DisplayName("false quand ageMin > ageMax") - void testAgesIncoherents() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .ageMin(65) - .ageMax(18) - .build(); - assertThat(c.isValid()).isFalse(); - } - - @Test - @DisplayName("true quand ageMin <= ageMax") - void testAgesCoherents() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .ageMin(18) - .ageMax(65) - .build(); - assertThat(c.isValid()).isTrue(); - } - - @Test - @DisplayName("true quand seulement dateAdhesionMin défini") - void testSeulementDateAdhesionMin() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .dateAdhesionMin(LocalDate.of(2020, 1, 1)) - .build(); - assertThat(c.isValid()).isTrue(); - } - - @Test - @DisplayName("true quand seulement dateAdhesionMax défini") - void testSeulementDateAdhesionMax() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .dateAdhesionMax(LocalDate.of(2025, 12, 31)) - .build(); - assertThat(c.isValid()).isTrue(); - } - - @Test - @DisplayName("true quand seulement ageMin défini") - void testSeulementAgeMin() { - MembreSearchCriteria c = MembreSearchCriteria.builder().ageMin(18).build(); - assertThat(c.isValid()).isTrue(); - } - - @Test - @DisplayName("true quand seulement ageMax défini") - void testSeulementAgeMax() { - MembreSearchCriteria c = MembreSearchCriteria.builder().ageMax(65).build(); - assertThat(c.isValid()).isTrue(); - } - } - - @Nested - @DisplayName("sanitize") - class Sanitize { - - @Test - @DisplayName("trim et null si vide") - void testSanitize() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .query(" ab ") - .nom(" ") - .build(); - c.sanitize(); - assertThat(c.getQuery()).isEqualTo("ab"); - assertThat(c.getNom()).isNull(); - } - - @Test - @DisplayName("null reste null") - void testSanitizeNull() { - MembreSearchCriteria c = new MembreSearchCriteria(); - c.sanitize(); - assertThat(c.getQuery()).isNull(); - } - } - - @Nested - @DisplayName("getDescription") - class GetDescription { - - @Test - @DisplayName("vide quand aucun critère") - void testVide() { - MembreSearchCriteria c = new MembreSearchCriteria(); - assertThat(c.getDescription()).isEmpty(); - } - - @Test - @DisplayName("contient query") - void testAvecQuery() { - MembreSearchCriteria c = MembreSearchCriteria.builder().query("marie").build(); - assertThat(c.getDescription()).contains("marie"); - } - - @Test - @DisplayName("contient nom et prénom") - void testAvecNomPrenom() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .nom("Dupont") - .prenom("Marie") - .build(); - String d = c.getDescription(); - assertThat(d).contains("Dupont"); - assertThat(d).contains("Marie"); - } - - @Test - @DisplayName("contient statut") - void testAvecStatut() { - MembreSearchCriteria c = MembreSearchCriteria.builder().statut("ACTIF").build(); - assertThat(c.getDescription()).contains("ACTIF"); - } - - @Test - @DisplayName("contient organisationIds size") - void testAvecOrganisationIds() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .organisationIds(List.of(UUID.randomUUID(), UUID.randomUUID())) - .build(); - assertThat(c.getDescription()).contains("2"); - } - - @Test - @DisplayName("contient roles") - void testAvecRoles() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .roles(List.of("ADMIN", "USER")) - .build(); - assertThat(c.getDescription()).contains("ADMIN"); - assertThat(c.getDescription()).contains("USER"); - } - - @Test - @DisplayName("contient dates et âges") - void testAvecDatesAges() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .dateAdhesionMin(LocalDate.of(2020, 1, 1)) - .dateAdhesionMax(LocalDate.of(2025, 12, 31)) - .ageMin(18) - .ageMax(65) - .build(); - String d = c.getDescription(); - assertThat(d).contains("2020-01-01"); - assertThat(d).contains("2025-12-31"); - assertThat(d).contains("18"); - assertThat(d).contains("65"); - } - - @Test - @DisplayName("contient region, ville, profession, nationalite") - void testAvecLieu() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .region("Dakar") - .ville("Plateau") - .profession("Ingénieur") - .nationalite("Sénégalaise") - .build(); - String d = c.getDescription(); - assertThat(d).contains("Dakar"); - assertThat(d).contains("Plateau"); - assertThat(d).contains("Ingénieur"); - assertThat(d).contains("Sénégalaise"); - } - - @Test - @DisplayName("contient Membre bureau et Responsable") - void testAvecMembreBureauResponsable() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .membreBureau(true) - .responsable(true) - .build(); - String d = c.getDescription(); - assertThat(d).contains("Membre bureau"); - assertThat(d).contains("Responsable"); - } - - @Test - @DisplayName("membreBureau false pas affiché") - void testMembreBureauFalse() { - MembreSearchCriteria c = MembreSearchCriteria.builder().membreBureau(false).build(); - assertThat(c.getDescription()).doesNotContain("Membre bureau"); - } - - @Test - @DisplayName("contient email") - void testAvecEmail() { - MembreSearchCriteria c = MembreSearchCriteria.builder().email("test@example.com").build(); - assertThat(c.getDescription()).contains("test@example.com"); - } - - @Test - @DisplayName("organisationIds vide pas affiché") - void testOrganisationIdsVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder() - .organisationIds(List.of()) - .build(); - assertThat(c.getDescription()).doesNotContain("Organisations"); - } - - @Test - @DisplayName("roles vide pas affiché") - void testRolesVide() { - MembreSearchCriteria c = MembreSearchCriteria.builder().roles(List.of()).build(); - assertThat(c.getDescription()).doesNotContain("Rôles"); - } - - @Test - @DisplayName("responsable false pas affiché") - void testResponsableFalse() { - MembreSearchCriteria c = MembreSearchCriteria.builder().responsable(false).build(); - assertThat(c.getDescription()).doesNotContain("Responsable"); - } - } -} +package dev.lions.unionflow.server.api.dto.membre; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalDate; +import java.util.List; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour MembreSearchCriteria. + * Couvre toutes les branches : hasAnyCriteria, isValid, sanitize, getDescription. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests MembreSearchCriteria") +class MembreSearchCriteriaTest { + + @Nested + @DisplayName("hasAnyCriteria") + class HasAnyCriteria { + + @Test + @DisplayName("false quand tous les champs null ou vides") + void testAucunCritere() { + MembreSearchCriteria c = new MembreSearchCriteria(); + assertThat(c.hasAnyCriteria()).isFalse(); + } + + @Test + @DisplayName("true quand query non vide") + void testQuery() { + MembreSearchCriteria c = MembreSearchCriteria.builder().query("x").build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("false quand query vide après trim") + void testQueryVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder().query(" ").build(); + assertThat(c.hasAnyCriteria()).isFalse(); + } + + @Test + @DisplayName("true quand nom défini") + void testNom() { + MembreSearchCriteria c = MembreSearchCriteria.builder().nom("Dupont").build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand prenom défini") + void testPrenom() { + MembreSearchCriteria c = MembreSearchCriteria.builder().prenom("Marie").build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand email défini") + void testEmail() { + MembreSearchCriteria c = MembreSearchCriteria.builder().email("@x.com").build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand telephone défini") + void testTelephone() { + MembreSearchCriteria c = MembreSearchCriteria.builder().telephone("+221").build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand organisationIds non vide") + void testOrganisationIds() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .organisationIds(List.of(UUID.randomUUID())) + .build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("false quand organisationIds vide") + void testOrganisationIdsVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .organisationIds(List.of()) + .build(); + assertThat(c.hasAnyCriteria()).isFalse(); + } + + @Test + @DisplayName("true quand roles non vide") + void testRoles() { + MembreSearchCriteria c = MembreSearchCriteria.builder().roles(List.of("ADMIN")).build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand statut défini") + void testStatut() { + MembreSearchCriteria c = MembreSearchCriteria.builder().statut("ACTIF").build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand dateAdhesionMin défini") + void testDateAdhesionMin() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .dateAdhesionMin(LocalDate.of(2020, 1, 1)) + .build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand dateAdhesionMax défini") + void testDateAdhesionMax() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .dateAdhesionMax(LocalDate.of(2025, 12, 31)) + .build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand ageMin défini") + void testAgeMin() { + MembreSearchCriteria c = MembreSearchCriteria.builder().ageMin(18).build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand ageMax défini") + void testAgeMax() { + MembreSearchCriteria c = MembreSearchCriteria.builder().ageMax(65).build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand region défini") + void testRegion() { + MembreSearchCriteria c = MembreSearchCriteria.builder().region("Dakar").build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand ville défini") + void testVille() { + MembreSearchCriteria c = MembreSearchCriteria.builder().ville("Dakar").build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand profession défini") + void testProfession() { + MembreSearchCriteria c = MembreSearchCriteria.builder().profession("Ingénieur").build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand nationalite défini") + void testNationalite() { + MembreSearchCriteria c = MembreSearchCriteria.builder().nationalite("Sénégalaise").build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand membreBureau défini") + void testMembreBureau() { + MembreSearchCriteria c = MembreSearchCriteria.builder().membreBureau(true).build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("true quand responsable défini") + void testResponsable() { + MembreSearchCriteria c = MembreSearchCriteria.builder().responsable(true).build(); + assertThat(c.hasAnyCriteria()).isTrue(); + } + + @Test + @DisplayName("false quand nom vide après trim") + void testNomVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder().nom(" ").build(); + assertThat(c.hasAnyCriteria()).isFalse(); + } + + @Test + @DisplayName("false quand prenom vide après trim") + void testPrenomVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder().prenom(" ").build(); + assertThat(c.hasAnyCriteria()).isFalse(); + } + + @Test + @DisplayName("false quand email vide après trim") + void testEmailVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder().email(" ").build(); + assertThat(c.hasAnyCriteria()).isFalse(); + } + + @Test + @DisplayName("false quand telephone vide après trim") + void testTelephoneVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder().telephone(" ").build(); + assertThat(c.hasAnyCriteria()).isFalse(); + } + + @Test + @DisplayName("false quand statut vide après trim") + void testStatutVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder().statut(" ").build(); + assertThat(c.hasAnyCriteria()).isFalse(); + } + + @Test + @DisplayName("false quand region vide après trim") + void testRegionVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder().region(" ").build(); + assertThat(c.hasAnyCriteria()).isFalse(); + } + + @Test + @DisplayName("false quand ville vide après trim") + void testVilleVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder().ville(" ").build(); + assertThat(c.hasAnyCriteria()).isFalse(); + } + + @Test + @DisplayName("false quand profession vide après trim") + void testProfessionVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder().profession(" ").build(); + assertThat(c.hasAnyCriteria()).isFalse(); + } + + @Test + @DisplayName("false quand nationalite vide après trim") + void testNationaliteVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder().nationalite(" ").build(); + assertThat(c.hasAnyCriteria()).isFalse(); + } + + @Test + @DisplayName("false quand roles vide") + void testRolesVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder().roles(List.of()).build(); + assertThat(c.hasAnyCriteria()).isFalse(); + } + } + + @Nested + @DisplayName("isValid") + class IsValid { + + @Test + @DisplayName("true quand pas de dates ni âges") + void testSansContraintes() { + MembreSearchCriteria c = MembreSearchCriteria.builder().query("x").build(); + assertThat(c.isValid()).isTrue(); + } + + @Test + @DisplayName("false quand dateAdhesionMin après dateAdhesionMax") + void testDatesIncoherentes() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .dateAdhesionMin(LocalDate.of(2025, 1, 1)) + .dateAdhesionMax(LocalDate.of(2020, 1, 1)) + .build(); + assertThat(c.isValid()).isFalse(); + } + + @Test + @DisplayName("true quand dateAdhesionMin avant dateAdhesionMax") + void testDatesCoherentes() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .dateAdhesionMin(LocalDate.of(2020, 1, 1)) + .dateAdhesionMax(LocalDate.of(2025, 1, 1)) + .build(); + assertThat(c.isValid()).isTrue(); + } + + @Test + @DisplayName("false quand ageMin > ageMax") + void testAgesIncoherents() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .ageMin(65) + .ageMax(18) + .build(); + assertThat(c.isValid()).isFalse(); + } + + @Test + @DisplayName("true quand ageMin <= ageMax") + void testAgesCoherents() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .ageMin(18) + .ageMax(65) + .build(); + assertThat(c.isValid()).isTrue(); + } + + @Test + @DisplayName("true quand seulement dateAdhesionMin défini") + void testSeulementDateAdhesionMin() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .dateAdhesionMin(LocalDate.of(2020, 1, 1)) + .build(); + assertThat(c.isValid()).isTrue(); + } + + @Test + @DisplayName("true quand seulement dateAdhesionMax défini") + void testSeulementDateAdhesionMax() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .dateAdhesionMax(LocalDate.of(2025, 12, 31)) + .build(); + assertThat(c.isValid()).isTrue(); + } + + @Test + @DisplayName("true quand seulement ageMin défini") + void testSeulementAgeMin() { + MembreSearchCriteria c = MembreSearchCriteria.builder().ageMin(18).build(); + assertThat(c.isValid()).isTrue(); + } + + @Test + @DisplayName("true quand seulement ageMax défini") + void testSeulementAgeMax() { + MembreSearchCriteria c = MembreSearchCriteria.builder().ageMax(65).build(); + assertThat(c.isValid()).isTrue(); + } + } + + @Nested + @DisplayName("sanitize") + class Sanitize { + + @Test + @DisplayName("trim et null si vide") + void testSanitize() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .query(" ab ") + .nom(" ") + .build(); + c.sanitize(); + assertThat(c.getQuery()).isEqualTo("ab"); + assertThat(c.getNom()).isNull(); + } + + @Test + @DisplayName("null reste null") + void testSanitizeNull() { + MembreSearchCriteria c = new MembreSearchCriteria(); + c.sanitize(); + assertThat(c.getQuery()).isNull(); + } + } + + @Nested + @DisplayName("getDescription") + class GetDescription { + + @Test + @DisplayName("vide quand aucun critère") + void testVide() { + MembreSearchCriteria c = new MembreSearchCriteria(); + assertThat(c.getDescription()).isEmpty(); + } + + @Test + @DisplayName("contient query") + void testAvecQuery() { + MembreSearchCriteria c = MembreSearchCriteria.builder().query("marie").build(); + assertThat(c.getDescription()).contains("marie"); + } + + @Test + @DisplayName("contient nom et prénom") + void testAvecNomPrenom() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .nom("Dupont") + .prenom("Marie") + .build(); + String d = c.getDescription(); + assertThat(d).contains("Dupont"); + assertThat(d).contains("Marie"); + } + + @Test + @DisplayName("contient statut") + void testAvecStatut() { + MembreSearchCriteria c = MembreSearchCriteria.builder().statut("ACTIF").build(); + assertThat(c.getDescription()).contains("ACTIF"); + } + + @Test + @DisplayName("contient organisationIds size") + void testAvecOrganisationIds() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .organisationIds(List.of(UUID.randomUUID(), UUID.randomUUID())) + .build(); + assertThat(c.getDescription()).contains("2"); + } + + @Test + @DisplayName("contient roles") + void testAvecRoles() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .roles(List.of("ADMIN", "USER")) + .build(); + assertThat(c.getDescription()).contains("ADMIN"); + assertThat(c.getDescription()).contains("USER"); + } + + @Test + @DisplayName("contient dates et âges") + void testAvecDatesAges() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .dateAdhesionMin(LocalDate.of(2020, 1, 1)) + .dateAdhesionMax(LocalDate.of(2025, 12, 31)) + .ageMin(18) + .ageMax(65) + .build(); + String d = c.getDescription(); + assertThat(d).contains("2020-01-01"); + assertThat(d).contains("2025-12-31"); + assertThat(d).contains("18"); + assertThat(d).contains("65"); + } + + @Test + @DisplayName("contient region, ville, profession, nationalite") + void testAvecLieu() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .region("Dakar") + .ville("Plateau") + .profession("Ingénieur") + .nationalite("Sénégalaise") + .build(); + String d = c.getDescription(); + assertThat(d).contains("Dakar"); + assertThat(d).contains("Plateau"); + assertThat(d).contains("Ingénieur"); + assertThat(d).contains("Sénégalaise"); + } + + @Test + @DisplayName("contient Membre bureau et Responsable") + void testAvecMembreBureauResponsable() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .membreBureau(true) + .responsable(true) + .build(); + String d = c.getDescription(); + assertThat(d).contains("Membre bureau"); + assertThat(d).contains("Responsable"); + } + + @Test + @DisplayName("membreBureau false pas affiché") + void testMembreBureauFalse() { + MembreSearchCriteria c = MembreSearchCriteria.builder().membreBureau(false).build(); + assertThat(c.getDescription()).doesNotContain("Membre bureau"); + } + + @Test + @DisplayName("contient email") + void testAvecEmail() { + MembreSearchCriteria c = MembreSearchCriteria.builder().email("test@example.com").build(); + assertThat(c.getDescription()).contains("test@example.com"); + } + + @Test + @DisplayName("organisationIds vide pas affiché") + void testOrganisationIdsVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder() + .organisationIds(List.of()) + .build(); + assertThat(c.getDescription()).doesNotContain("Organisations"); + } + + @Test + @DisplayName("roles vide pas affiché") + void testRolesVide() { + MembreSearchCriteria c = MembreSearchCriteria.builder().roles(List.of()).build(); + assertThat(c.getDescription()).doesNotContain("Rôles"); + } + + @Test + @DisplayName("responsable false pas affiché") + void testResponsableFalse() { + MembreSearchCriteria c = MembreSearchCriteria.builder().responsable(false).build(); + assertThat(c.getDescription()).doesNotContain("Responsable"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchResultDTOTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchResultDTOTest.java index 4c6a98d..62cce5c 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchResultDTOTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/membre/MembreSearchResultDTOTest.java @@ -1,243 +1,243 @@ -package dev.lions.unionflow.server.api.dto.membre; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.util.List; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import dev.lions.unionflow.server.api.dto.membre.response.MembreSummaryResponse; - -/** - * Tests unitaires pour MembreSearchResultDTO. - * Couvre toutes les branches : calculatePaginationFlags, isEmpty, getResultDescription, - * getNextPageNumber, getPreviousPageNumber, empty (2 surcharges). - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests MembreSearchResultDTO") -class MembreSearchResultDTOTest { - - private static MembreSummaryResponse unMembre() { - return new MembreSummaryResponse( - UUID.randomUUID(), null, "Prenom", "Nom", null, null, null, null, null, null, true, List.of(), null, null, null); - } - - @Nested - @DisplayName("calculatePaginationFlags") - class CalculatePaginationFlags { - - @Test - @DisplayName("isFirst true quand currentPage 0") - void testFirstPage() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setCurrentPage(0); - r.setTotalPages(5); - r.setMembres(List.of(unMembre())); - r.calculatePaginationFlags(); - assertThat(r.isFirst()).isTrue(); - assertThat(r.isHasPrevious()).isFalse(); - } - - @Test - @DisplayName("isLast true quand currentPage dernière") - void testLastPage() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setCurrentPage(4); - r.setTotalPages(5); - r.setMembres(List.of(unMembre())); - r.calculatePaginationFlags(); - assertThat(r.isLast()).isTrue(); - assertThat(r.isHasNext()).isFalse(); - } - - @Test - @DisplayName("numberOfElements 0 quand membres null") - void testMembresNull() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setMembres(null); - r.setCurrentPage(0); - r.setTotalPages(1); - r.calculatePaginationFlags(); - assertThat(r.getNumberOfElements()).isEqualTo(0); - } - - @Test - @DisplayName("numberOfElements = size quand membres non null") - void testMembresNonVide() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setMembres(List.of(unMembre(), unMembre())); - r.setCurrentPage(0); - r.setTotalPages(1); - r.calculatePaginationFlags(); - assertThat(r.getNumberOfElements()).isEqualTo(2); - } - } - - @Nested - @DisplayName("isEmpty") - class IsEmpty { - - @Test - @DisplayName("true quand membres null") - void testMembresNull() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setMembres(null); - assertThat(r.isEmpty()).isTrue(); - } - - @Test - @DisplayName("true quand membres vide") - void testMembresVide() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setMembres(List.of()); - assertThat(r.isEmpty()).isTrue(); - } - - @Test - @DisplayName("false quand membres non vide") - void testMembresNonVide() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setMembres(List.of(unMembre())); - assertThat(r.isEmpty()).isFalse(); - } - } - - @Nested - @DisplayName("getResultDescription") - class GetResultDescription { - - @Test - @DisplayName("Aucun membre trouvé quand vide") - void testVide() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setMembres(List.of()); - r.setTotalElements(0); - assertThat(r.getResultDescription()).isEqualTo("Aucun membre trouvé"); - } - - @Test - @DisplayName("1 membre trouvé quand totalElements 1") - void testUnSeul() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setMembres(List.of(unMembre())); - r.setTotalElements(1); - r.setTotalPages(1); - r.setCurrentPage(0); - r.setPageSize(20); - r.setNumberOfElements(1); - assertThat(r.getResultDescription()).isEqualTo("1 membre trouvé"); - } - - @Test - @DisplayName("X membres trouvés quand une seule page") - void testUnePage() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setMembres(List.of(unMembre(), unMembre())); - r.setTotalElements(2); - r.setTotalPages(1); - r.setCurrentPage(0); - r.setPageSize(20); - r.setNumberOfElements(2); - assertThat(r.getResultDescription()).isEqualTo("2 membres trouvés"); - } - - @Test - @DisplayName("Membres X-Y sur Z quand plusieurs pages") - void testPlusieursPages() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setMembres(List.of(unMembre(), unMembre())); - r.setTotalElements(50); - r.setTotalPages(5); - r.setCurrentPage(1); - r.setPageSize(20); - r.setNumberOfElements(2); - r.calculatePaginationFlags(); - String d = r.getResultDescription(); - assertThat(d).contains("21"); - assertThat(d).contains("22"); - assertThat(d).contains("50"); - assertThat(d).contains("2"); - assertThat(d).contains("5"); - } - } - - @Nested - @DisplayName("getNextPageNumber") - class GetNextPageNumber { - - @Test - @DisplayName("retourne currentPage+2 (1-based) quand hasNext true") - void testHasNext() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setHasNext(true); - r.setCurrentPage(0); - assertThat(r.getNextPageNumber()).isEqualTo(2); - } - - @Test - @DisplayName("retourne -1 quand hasNext false") - void testNoNext() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setHasNext(false); - assertThat(r.getNextPageNumber()).isEqualTo(-1); - } - } - - @Nested - @DisplayName("getPreviousPageNumber") - class GetPreviousPageNumber { - - @Test - @DisplayName("retourne currentPage (1-based) quand hasPrevious true") - void testHasPrevious() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setHasPrevious(true); - r.setCurrentPage(2); - assertThat(r.getPreviousPageNumber()).isEqualTo(2); - } - - @Test - @DisplayName("retourne -1 quand hasPrevious false") - void testNoPrevious() { - MembreSearchResultDTO r = new MembreSearchResultDTO(); - r.setHasPrevious(false); - assertThat(r.getPreviousPageNumber()).isEqualTo(-1); - } - } - - @Nested - @DisplayName("empty") - class Empty { - - @Test - @DisplayName("empty(criteria) utilise pageSize 20 et currentPage 0") - void testEmptyAvecCriteria() { - MembreSearchCriteria criteria = MembreSearchCriteria.builder().query("x").build(); - MembreSearchResultDTO r = MembreSearchResultDTO.empty(criteria); - assertThat(r.getMembres()).isEmpty(); - assertThat(r.getTotalElements()).isEqualTo(0); - assertThat(r.getPageSize()).isEqualTo(20); - assertThat(r.getCurrentPage()).isEqualTo(0); - assertThat(r.isFirst()).isTrue(); - assertThat(r.isLast()).isTrue(); - assertThat(r.getCriteria()).isEqualTo(criteria); - assertThat(r.getStatistics()).isNotNull(); - } - - @Test - @DisplayName("empty(criteria, pageSize, currentPage) remplit tous les champs") - void testEmptyAvecPageSize() { - MembreSearchCriteria criteria = MembreSearchCriteria.builder().nom("Dupont").build(); - MembreSearchResultDTO r = MembreSearchResultDTO.empty(criteria, 10, 0); - assertThat(r.getPageSize()).isEqualTo(10); - assertThat(r.getCurrentPage()).isEqualTo(0); - assertThat(r.getTotalPages()).isEqualTo(0); - assertThat(r.getNumberOfElements()).isEqualTo(0); - assertThat(r.getStatistics().getMembresActifs()).isEqualTo(0); - } - } -} +package dev.lions.unionflow.server.api.dto.membre; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.List; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import dev.lions.unionflow.server.api.dto.membre.response.MembreSummaryResponse; + +/** + * Tests unitaires pour MembreSearchResultDTO. + * Couvre toutes les branches : calculatePaginationFlags, isEmpty, getResultDescription, + * getNextPageNumber, getPreviousPageNumber, empty (2 surcharges). + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests MembreSearchResultDTO") +class MembreSearchResultDTOTest { + + private static MembreSummaryResponse unMembre() { + return new MembreSummaryResponse( + UUID.randomUUID(), null, "Prenom", "Nom", null, null, null, null, null, null, true, List.of(), null, null, null); + } + + @Nested + @DisplayName("calculatePaginationFlags") + class CalculatePaginationFlags { + + @Test + @DisplayName("isFirst true quand currentPage 0") + void testFirstPage() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setCurrentPage(0); + r.setTotalPages(5); + r.setMembres(List.of(unMembre())); + r.calculatePaginationFlags(); + assertThat(r.isFirst()).isTrue(); + assertThat(r.isHasPrevious()).isFalse(); + } + + @Test + @DisplayName("isLast true quand currentPage dernière") + void testLastPage() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setCurrentPage(4); + r.setTotalPages(5); + r.setMembres(List.of(unMembre())); + r.calculatePaginationFlags(); + assertThat(r.isLast()).isTrue(); + assertThat(r.isHasNext()).isFalse(); + } + + @Test + @DisplayName("numberOfElements 0 quand membres null") + void testMembresNull() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setMembres(null); + r.setCurrentPage(0); + r.setTotalPages(1); + r.calculatePaginationFlags(); + assertThat(r.getNumberOfElements()).isEqualTo(0); + } + + @Test + @DisplayName("numberOfElements = size quand membres non null") + void testMembresNonVide() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setMembres(List.of(unMembre(), unMembre())); + r.setCurrentPage(0); + r.setTotalPages(1); + r.calculatePaginationFlags(); + assertThat(r.getNumberOfElements()).isEqualTo(2); + } + } + + @Nested + @DisplayName("isEmpty") + class IsEmpty { + + @Test + @DisplayName("true quand membres null") + void testMembresNull() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setMembres(null); + assertThat(r.isEmpty()).isTrue(); + } + + @Test + @DisplayName("true quand membres vide") + void testMembresVide() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setMembres(List.of()); + assertThat(r.isEmpty()).isTrue(); + } + + @Test + @DisplayName("false quand membres non vide") + void testMembresNonVide() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setMembres(List.of(unMembre())); + assertThat(r.isEmpty()).isFalse(); + } + } + + @Nested + @DisplayName("getResultDescription") + class GetResultDescription { + + @Test + @DisplayName("Aucun membre trouvé quand vide") + void testVide() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setMembres(List.of()); + r.setTotalElements(0); + assertThat(r.getResultDescription()).isEqualTo("Aucun membre trouvé"); + } + + @Test + @DisplayName("1 membre trouvé quand totalElements 1") + void testUnSeul() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setMembres(List.of(unMembre())); + r.setTotalElements(1); + r.setTotalPages(1); + r.setCurrentPage(0); + r.setPageSize(20); + r.setNumberOfElements(1); + assertThat(r.getResultDescription()).isEqualTo("1 membre trouvé"); + } + + @Test + @DisplayName("X membres trouvés quand une seule page") + void testUnePage() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setMembres(List.of(unMembre(), unMembre())); + r.setTotalElements(2); + r.setTotalPages(1); + r.setCurrentPage(0); + r.setPageSize(20); + r.setNumberOfElements(2); + assertThat(r.getResultDescription()).isEqualTo("2 membres trouvés"); + } + + @Test + @DisplayName("Membres X-Y sur Z quand plusieurs pages") + void testPlusieursPages() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setMembres(List.of(unMembre(), unMembre())); + r.setTotalElements(50); + r.setTotalPages(5); + r.setCurrentPage(1); + r.setPageSize(20); + r.setNumberOfElements(2); + r.calculatePaginationFlags(); + String d = r.getResultDescription(); + assertThat(d).contains("21"); + assertThat(d).contains("22"); + assertThat(d).contains("50"); + assertThat(d).contains("2"); + assertThat(d).contains("5"); + } + } + + @Nested + @DisplayName("getNextPageNumber") + class GetNextPageNumber { + + @Test + @DisplayName("retourne currentPage+2 (1-based) quand hasNext true") + void testHasNext() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setHasNext(true); + r.setCurrentPage(0); + assertThat(r.getNextPageNumber()).isEqualTo(2); + } + + @Test + @DisplayName("retourne -1 quand hasNext false") + void testNoNext() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setHasNext(false); + assertThat(r.getNextPageNumber()).isEqualTo(-1); + } + } + + @Nested + @DisplayName("getPreviousPageNumber") + class GetPreviousPageNumber { + + @Test + @DisplayName("retourne currentPage (1-based) quand hasPrevious true") + void testHasPrevious() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setHasPrevious(true); + r.setCurrentPage(2); + assertThat(r.getPreviousPageNumber()).isEqualTo(2); + } + + @Test + @DisplayName("retourne -1 quand hasPrevious false") + void testNoPrevious() { + MembreSearchResultDTO r = new MembreSearchResultDTO(); + r.setHasPrevious(false); + assertThat(r.getPreviousPageNumber()).isEqualTo(-1); + } + } + + @Nested + @DisplayName("empty") + class Empty { + + @Test + @DisplayName("empty(criteria) utilise pageSize 20 et currentPage 0") + void testEmptyAvecCriteria() { + MembreSearchCriteria criteria = MembreSearchCriteria.builder().query("x").build(); + MembreSearchResultDTO r = MembreSearchResultDTO.empty(criteria); + assertThat(r.getMembres()).isEmpty(); + assertThat(r.getTotalElements()).isEqualTo(0); + assertThat(r.getPageSize()).isEqualTo(20); + assertThat(r.getCurrentPage()).isEqualTo(0); + assertThat(r.isFirst()).isTrue(); + assertThat(r.isLast()).isTrue(); + assertThat(r.getCriteria()).isEqualTo(criteria); + assertThat(r.getStatistics()).isNotNull(); + } + + @Test + @DisplayName("empty(criteria, pageSize, currentPage) remplit tous les champs") + void testEmptyAvecPageSize() { + MembreSearchCriteria criteria = MembreSearchCriteria.builder().nom("Dupont").build(); + MembreSearchResultDTO r = MembreSearchResultDTO.empty(criteria, 10, 0); + assertThat(r.getPageSize()).isEqualTo(10); + assertThat(r.getCurrentPage()).isEqualTo(0); + assertThat(r.getTotalPages()).isEqualTo(0); + assertThat(r.getNumberOfElements()).isEqualTo(0); + assertThat(r.getStatistics().getMembresActifs()).isEqualTo(0); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/membre/request/CreateMembreRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/membre/request/CreateMembreRequestTest.java index b63ecff..7724c3a 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/membre/request/CreateMembreRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/membre/request/CreateMembreRequestTest.java @@ -1,231 +1,231 @@ -package dev.lions.unionflow.server.api.dto.membre.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.time.LocalDate; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateMembreRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDate dateNaissance = LocalDate.of(1985, 5, 20); - - CreateMembreRequest request = CreateMembreRequest.builder() - .prenom("Amadou") - .nom("Diallo") - .email("amadou.diallo@example.com") - .telephone("+221 77 123 45 67") - .telephoneWave("+221771234567") - .dateNaissance(dateNaissance) - .profession("Ingénieur Informatique") - .photoUrl("https://example.com/photos/amadou.jpg") - .statutMatrimonial("MARIE") - .nationalite("Sénégalaise") - .typeIdentite("CNI") - .numeroIdentite("1234567890123") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.prenom()).isEqualTo("Amadou"); - assertThat(request.nom()).isEqualTo("Diallo"); - assertThat(request.email()).isEqualTo("amadou.diallo@example.com"); - assertThat(request.telephone()).isEqualTo("+221 77 123 45 67"); - assertThat(request.telephoneWave()).isEqualTo("+221771234567"); - assertThat(request.dateNaissance()).isEqualTo(dateNaissance); - assertThat(request.profession()).isEqualTo("Ingénieur Informatique"); - assertThat(request.photoUrl()).contains("amadou.jpg"); - assertThat(request.statutMatrimonial()).isEqualTo("MARIE"); - assertThat(request.nationalite()).isEqualTo("Sénégalaise"); - assertThat(request.typeIdentite()).isEqualTo("CNI"); - assertThat(request.numeroIdentite()).isEqualTo("1234567890123"); - } - - @Test - void testBuilder_MinimalFields() { - LocalDate dateNaissance = LocalDate.of(1990, 1, 1); - - CreateMembreRequest request = CreateMembreRequest.builder() - .prenom("Fatou") - .nom("Sow") - .email("fatou.sow@example.com") - .dateNaissance(dateNaissance) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.prenom()).isEqualTo("Fatou"); - assertThat(request.nom()).isEqualTo("Sow"); - assertThat(request.email()).isEqualTo("fatou.sow@example.com"); - assertThat(request.dateNaissance()).isEqualTo(dateNaissance); - assertThat(request.telephone()).isNull(); - assertThat(request.telephoneWave()).isNull(); - assertThat(request.profession()).isNull(); - assertThat(request.photoUrl()).isNull(); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateMembreRequest request = CreateMembreRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prenom")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateNaissance")); - } - - @Test - void testValidation_EmptyPrenom() { - CreateMembreRequest request = CreateMembreRequest.builder() - .prenom("") - .nom("Test") - .email("test@example.com") - .dateNaissance(LocalDate.of(1990, 1, 1)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prenom")); - } - - @Test - void testValidation_EmptyNom() { - CreateMembreRequest request = CreateMembreRequest.builder() - .prenom("Test") - .nom("") - .email("test@example.com") - .dateNaissance(LocalDate.of(1990, 1, 1)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); - } - - @Test - void testValidation_EmailInvalide() { - CreateMembreRequest request = CreateMembreRequest.builder() - .prenom("Test") - .nom("User") - .email("not-a-valid-email") - .dateNaissance(LocalDate.of(1990, 1, 1)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); - } - - @Test - void testValidation_PrenomTooLong() { - String longPrenom = "A".repeat(101); - CreateMembreRequest request = CreateMembreRequest.builder() - .prenom(longPrenom) - .nom("Test") - .email("test@example.com") - .dateNaissance(LocalDate.of(1990, 1, 1)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prenom")); - } - - @Test - void testValidation_TelephoneWaveTooLong() { - CreateMembreRequest request = CreateMembreRequest.builder() - .prenom("Test") - .nom("User") - .email("test@example.com") - .dateNaissance(LocalDate.of(1990, 1, 1)) - .telephoneWave("+221771234567890123456") // 22 chars > max 20 - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("telephoneWave")); - } - - @Test - void testValidation_ValidFields() { - CreateMembreRequest request = CreateMembreRequest.builder() - .prenom("Moussa") - .nom("Ba") - .email("moussa.ba@example.com") - .telephone("+221 33 987 65 43") - .telephoneWave("+221339876543") - .dateNaissance(LocalDate.of(1988, 3, 15)) - .profession("Médecin") - .nationalite("Sénégalaise") - .typeIdentite("PASSEPORT") - .numeroIdentite("SN123456789") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - LocalDate dateNaissance = LocalDate.of(1995, 7, 10); - - CreateMembreRequest request1 = CreateMembreRequest.builder() - .prenom("Aissatou") - .nom("Ndiaye") - .email("aissatou@example.com") - .dateNaissance(dateNaissance) - .build(); - - CreateMembreRequest request2 = CreateMembreRequest.builder() - .prenom("Aissatou") - .nom("Ndiaye") - .email("aissatou@example.com") - .dateNaissance(dateNaissance) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateMembreRequest request = CreateMembreRequest.builder() - .prenom("Ibrahima") - .nom("Sarr") - .email("ibrahima.sarr@example.com") - .dateNaissance(LocalDate.of(1992, 11, 5)) - .profession("Avocat") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateMembreRequest"); - assertThat(toString).contains("Ibrahima"); - assertThat(toString).contains("Sarr"); - assertThat(toString).contains("ibrahima.sarr@example.com"); - assertThat(toString).contains("Avocat"); - } -} +package dev.lions.unionflow.server.api.dto.membre.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.time.LocalDate; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateMembreRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDate dateNaissance = LocalDate.of(1985, 5, 20); + + CreateMembreRequest request = CreateMembreRequest.builder() + .prenom("Amadou") + .nom("Diallo") + .email("amadou.diallo@example.com") + .telephone("+221 77 123 45 67") + .telephoneWave("+221771234567") + .dateNaissance(dateNaissance) + .profession("Ingénieur Informatique") + .photoUrl("https://example.com/photos/amadou.jpg") + .statutMatrimonial("MARIE") + .nationalite("Sénégalaise") + .typeIdentite("CNI") + .numeroIdentite("1234567890123") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.prenom()).isEqualTo("Amadou"); + assertThat(request.nom()).isEqualTo("Diallo"); + assertThat(request.email()).isEqualTo("amadou.diallo@example.com"); + assertThat(request.telephone()).isEqualTo("+221 77 123 45 67"); + assertThat(request.telephoneWave()).isEqualTo("+221771234567"); + assertThat(request.dateNaissance()).isEqualTo(dateNaissance); + assertThat(request.profession()).isEqualTo("Ingénieur Informatique"); + assertThat(request.photoUrl()).contains("amadou.jpg"); + assertThat(request.statutMatrimonial()).isEqualTo("MARIE"); + assertThat(request.nationalite()).isEqualTo("Sénégalaise"); + assertThat(request.typeIdentite()).isEqualTo("CNI"); + assertThat(request.numeroIdentite()).isEqualTo("1234567890123"); + } + + @Test + void testBuilder_MinimalFields() { + LocalDate dateNaissance = LocalDate.of(1990, 1, 1); + + CreateMembreRequest request = CreateMembreRequest.builder() + .prenom("Fatou") + .nom("Sow") + .email("fatou.sow@example.com") + .dateNaissance(dateNaissance) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.prenom()).isEqualTo("Fatou"); + assertThat(request.nom()).isEqualTo("Sow"); + assertThat(request.email()).isEqualTo("fatou.sow@example.com"); + assertThat(request.dateNaissance()).isEqualTo(dateNaissance); + assertThat(request.telephone()).isNull(); + assertThat(request.telephoneWave()).isNull(); + assertThat(request.profession()).isNull(); + assertThat(request.photoUrl()).isNull(); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateMembreRequest request = CreateMembreRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prenom")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateNaissance")); + } + + @Test + void testValidation_EmptyPrenom() { + CreateMembreRequest request = CreateMembreRequest.builder() + .prenom("") + .nom("Test") + .email("test@example.com") + .dateNaissance(LocalDate.of(1990, 1, 1)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prenom")); + } + + @Test + void testValidation_EmptyNom() { + CreateMembreRequest request = CreateMembreRequest.builder() + .prenom("Test") + .nom("") + .email("test@example.com") + .dateNaissance(LocalDate.of(1990, 1, 1)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); + } + + @Test + void testValidation_EmailInvalide() { + CreateMembreRequest request = CreateMembreRequest.builder() + .prenom("Test") + .nom("User") + .email("not-a-valid-email") + .dateNaissance(LocalDate.of(1990, 1, 1)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); + } + + @Test + void testValidation_PrenomTooLong() { + String longPrenom = "A".repeat(101); + CreateMembreRequest request = CreateMembreRequest.builder() + .prenom(longPrenom) + .nom("Test") + .email("test@example.com") + .dateNaissance(LocalDate.of(1990, 1, 1)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prenom")); + } + + @Test + void testValidation_TelephoneWaveTooLong() { + CreateMembreRequest request = CreateMembreRequest.builder() + .prenom("Test") + .nom("User") + .email("test@example.com") + .dateNaissance(LocalDate.of(1990, 1, 1)) + .telephoneWave("+221771234567890123456") // 22 chars > max 20 + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("telephoneWave")); + } + + @Test + void testValidation_ValidFields() { + CreateMembreRequest request = CreateMembreRequest.builder() + .prenom("Moussa") + .nom("Ba") + .email("moussa.ba@example.com") + .telephone("+221 33 987 65 43") + .telephoneWave("+221339876543") + .dateNaissance(LocalDate.of(1988, 3, 15)) + .profession("Médecin") + .nationalite("Sénégalaise") + .typeIdentite("PASSEPORT") + .numeroIdentite("SN123456789") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + LocalDate dateNaissance = LocalDate.of(1995, 7, 10); + + CreateMembreRequest request1 = CreateMembreRequest.builder() + .prenom("Aissatou") + .nom("Ndiaye") + .email("aissatou@example.com") + .dateNaissance(dateNaissance) + .build(); + + CreateMembreRequest request2 = CreateMembreRequest.builder() + .prenom("Aissatou") + .nom("Ndiaye") + .email("aissatou@example.com") + .dateNaissance(dateNaissance) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateMembreRequest request = CreateMembreRequest.builder() + .prenom("Ibrahima") + .nom("Sarr") + .email("ibrahima.sarr@example.com") + .dateNaissance(LocalDate.of(1992, 11, 5)) + .profession("Avocat") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateMembreRequest"); + assertThat(toString).contains("Ibrahima"); + assertThat(toString).contains("Sarr"); + assertThat(toString).contains("ibrahima.sarr@example.com"); + assertThat(toString).contains("Avocat"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/membre/request/UpdateMembreRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/membre/request/UpdateMembreRequestTest.java index 238e7ef..ffa438c 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/membre/request/UpdateMembreRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/membre/request/UpdateMembreRequestTest.java @@ -1,220 +1,220 @@ -package dev.lions.unionflow.server.api.dto.membre.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.time.LocalDate; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateMembreRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDate dateNaissance = LocalDate.of(1987, 8, 25); - - UpdateMembreRequest request = UpdateMembreRequest.builder() - .prenom("Cheikh") - .nom("Fall") - .email("cheikh.fall@updated.com") - .telephone("+221 77 999 88 77") - .telephoneWave("+221779998877") - .dateNaissance(dateNaissance) - .profession("Entrepreneur") - .photoUrl("https://example.com/photos/cheikh_updated.jpg") - .statutMatrimonial("CELIBATAIRE") - .nationalite("Sénégalaise") - .typeIdentite("CNI") - .numeroIdentite("9876543210987") - .actif(true) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.prenom()).isEqualTo("Cheikh"); - assertThat(request.nom()).isEqualTo("Fall"); - assertThat(request.email()).isEqualTo("cheikh.fall@updated.com"); - assertThat(request.telephone()).isEqualTo("+221 77 999 88 77"); - assertThat(request.telephoneWave()).isEqualTo("+221779998877"); - assertThat(request.dateNaissance()).isEqualTo(dateNaissance); - assertThat(request.profession()).isEqualTo("Entrepreneur"); - assertThat(request.photoUrl()).contains("cheikh_updated.jpg"); - assertThat(request.statutMatrimonial()).isEqualTo("CELIBATAIRE"); - assertThat(request.nationalite()).isEqualTo("Sénégalaise"); - assertThat(request.typeIdentite()).isEqualTo("CNI"); - assertThat(request.numeroIdentite()).isEqualTo("9876543210987"); - assertThat(request.actif()).isTrue(); - } - - @Test - void testBuilder_MinimalFields() { - LocalDate dateNaissance = LocalDate.of(1993, 2, 14); - - UpdateMembreRequest request = UpdateMembreRequest.builder() - .prenom("Mariama") - .nom("Diop") - .email("mariama.diop@example.com") - .dateNaissance(dateNaissance) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.prenom()).isEqualTo("Mariama"); - assertThat(request.nom()).isEqualTo("Diop"); - assertThat(request.email()).isEqualTo("mariama.diop@example.com"); - assertThat(request.dateNaissance()).isEqualTo(dateNaissance); - assertThat(request.actif()).isNull(); - assertThat(request.profession()).isNull(); - } - - @Test - void testValidation_MissingRequiredFields() { - UpdateMembreRequest request = UpdateMembreRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prenom")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateNaissance")); - } - - @Test - void testValidation_EmptyPrenom() { - UpdateMembreRequest request = UpdateMembreRequest.builder() - .prenom("") - .nom("Test") - .email("test@example.com") - .dateNaissance(LocalDate.of(1990, 1, 1)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prenom")); - } - - @Test - void testValidation_EmptyNom() { - UpdateMembreRequest request = UpdateMembreRequest.builder() - .prenom("Test") - .nom("") - .email("test@example.com") - .dateNaissance(LocalDate.of(1990, 1, 1)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); - } - - @Test - void testValidation_EmailInvalide() { - UpdateMembreRequest request = UpdateMembreRequest.builder() - .prenom("Test") - .nom("User") - .email("invalid-email-format") - .dateNaissance(LocalDate.of(1990, 1, 1)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); - } - - @Test - void testValidation_NomTooLong() { - String longNom = "B".repeat(101); - UpdateMembreRequest request = UpdateMembreRequest.builder() - .prenom("Test") - .nom(longNom) - .email("test@example.com") - .dateNaissance(LocalDate.of(1990, 1, 1)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); - } - - @Test - void testValidation_ValidFields() { - UpdateMembreRequest request = UpdateMembreRequest.builder() - .prenom("Omar") - .nom("Sy") - .email("omar.sy@example.com") - .telephone("+221 33 444 55 66") - .telephoneWave("+221334445566") - .dateNaissance(LocalDate.of(1985, 12, 20)) - .profession("Artiste") - .statutMatrimonial("MARIE") - .nationalite("Française") - .typeIdentite("PASSEPORT") - .numeroIdentite("FR987654321") - .actif(false) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - LocalDate dateNaissance = LocalDate.of(1991, 4, 18); - - UpdateMembreRequest request1 = UpdateMembreRequest.builder() - .prenom("Khadija") - .nom("Thiam") - .email("khadija@example.com") - .dateNaissance(dateNaissance) - .actif(true) - .build(); - - UpdateMembreRequest request2 = UpdateMembreRequest.builder() - .prenom("Khadija") - .nom("Thiam") - .email("khadija@example.com") - .dateNaissance(dateNaissance) - .actif(true) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateMembreRequest request = UpdateMembreRequest.builder() - .prenom("Mamadou") - .nom("Cisse") - .email("mamadou.cisse@example.com") - .dateNaissance(LocalDate.of(1989, 9, 30)) - .profession("Professeur") - .actif(true) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateMembreRequest"); - assertThat(toString).contains("Mamadou"); - assertThat(toString).contains("Cisse"); - assertThat(toString).contains("mamadou.cisse@example.com"); - assertThat(toString).contains("Professeur"); - } -} +package dev.lions.unionflow.server.api.dto.membre.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.time.LocalDate; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateMembreRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDate dateNaissance = LocalDate.of(1987, 8, 25); + + UpdateMembreRequest request = UpdateMembreRequest.builder() + .prenom("Cheikh") + .nom("Fall") + .email("cheikh.fall@updated.com") + .telephone("+221 77 999 88 77") + .telephoneWave("+221779998877") + .dateNaissance(dateNaissance) + .profession("Entrepreneur") + .photoUrl("https://example.com/photos/cheikh_updated.jpg") + .statutMatrimonial("CELIBATAIRE") + .nationalite("Sénégalaise") + .typeIdentite("CNI") + .numeroIdentite("9876543210987") + .actif(true) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.prenom()).isEqualTo("Cheikh"); + assertThat(request.nom()).isEqualTo("Fall"); + assertThat(request.email()).isEqualTo("cheikh.fall@updated.com"); + assertThat(request.telephone()).isEqualTo("+221 77 999 88 77"); + assertThat(request.telephoneWave()).isEqualTo("+221779998877"); + assertThat(request.dateNaissance()).isEqualTo(dateNaissance); + assertThat(request.profession()).isEqualTo("Entrepreneur"); + assertThat(request.photoUrl()).contains("cheikh_updated.jpg"); + assertThat(request.statutMatrimonial()).isEqualTo("CELIBATAIRE"); + assertThat(request.nationalite()).isEqualTo("Sénégalaise"); + assertThat(request.typeIdentite()).isEqualTo("CNI"); + assertThat(request.numeroIdentite()).isEqualTo("9876543210987"); + assertThat(request.actif()).isTrue(); + } + + @Test + void testBuilder_MinimalFields() { + LocalDate dateNaissance = LocalDate.of(1993, 2, 14); + + UpdateMembreRequest request = UpdateMembreRequest.builder() + .prenom("Mariama") + .nom("Diop") + .email("mariama.diop@example.com") + .dateNaissance(dateNaissance) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.prenom()).isEqualTo("Mariama"); + assertThat(request.nom()).isEqualTo("Diop"); + assertThat(request.email()).isEqualTo("mariama.diop@example.com"); + assertThat(request.dateNaissance()).isEqualTo(dateNaissance); + assertThat(request.actif()).isNull(); + assertThat(request.profession()).isNull(); + } + + @Test + void testValidation_MissingRequiredFields() { + UpdateMembreRequest request = UpdateMembreRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prenom")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dateNaissance")); + } + + @Test + void testValidation_EmptyPrenom() { + UpdateMembreRequest request = UpdateMembreRequest.builder() + .prenom("") + .nom("Test") + .email("test@example.com") + .dateNaissance(LocalDate.of(1990, 1, 1)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prenom")); + } + + @Test + void testValidation_EmptyNom() { + UpdateMembreRequest request = UpdateMembreRequest.builder() + .prenom("Test") + .nom("") + .email("test@example.com") + .dateNaissance(LocalDate.of(1990, 1, 1)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); + } + + @Test + void testValidation_EmailInvalide() { + UpdateMembreRequest request = UpdateMembreRequest.builder() + .prenom("Test") + .nom("User") + .email("invalid-email-format") + .dateNaissance(LocalDate.of(1990, 1, 1)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); + } + + @Test + void testValidation_NomTooLong() { + String longNom = "B".repeat(101); + UpdateMembreRequest request = UpdateMembreRequest.builder() + .prenom("Test") + .nom(longNom) + .email("test@example.com") + .dateNaissance(LocalDate.of(1990, 1, 1)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); + } + + @Test + void testValidation_ValidFields() { + UpdateMembreRequest request = UpdateMembreRequest.builder() + .prenom("Omar") + .nom("Sy") + .email("omar.sy@example.com") + .telephone("+221 33 444 55 66") + .telephoneWave("+221334445566") + .dateNaissance(LocalDate.of(1985, 12, 20)) + .profession("Artiste") + .statutMatrimonial("MARIE") + .nationalite("Française") + .typeIdentite("PASSEPORT") + .numeroIdentite("FR987654321") + .actif(false) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + LocalDate dateNaissance = LocalDate.of(1991, 4, 18); + + UpdateMembreRequest request1 = UpdateMembreRequest.builder() + .prenom("Khadija") + .nom("Thiam") + .email("khadija@example.com") + .dateNaissance(dateNaissance) + .actif(true) + .build(); + + UpdateMembreRequest request2 = UpdateMembreRequest.builder() + .prenom("Khadija") + .nom("Thiam") + .email("khadija@example.com") + .dateNaissance(dateNaissance) + .actif(true) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateMembreRequest request = UpdateMembreRequest.builder() + .prenom("Mamadou") + .nom("Cisse") + .email("mamadou.cisse@example.com") + .dateNaissance(LocalDate.of(1989, 9, 30)) + .profession("Professeur") + .actif(true) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateMembreRequest"); + assertThat(toString).contains("Mamadou"); + assertThat(toString).contains("Cisse"); + assertThat(toString).contains("mamadou.cisse@example.com"); + assertThat(toString).contains("Professeur"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/notification/ActionNotificationDTOTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/notification/ActionNotificationDTOTest.java index 93ab47b..2ea060c 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/notification/ActionNotificationDTOTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/notification/ActionNotificationDTOTest.java @@ -1,513 +1,513 @@ -package dev.lions.unionflow.server.api.dto.notification; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.util.Map; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour ActionNotificationDTO. - * Couvre incrementerExecutions (nombreExecutions null), getCouleurParDefaut (default), - * getIconeParDefaut (tous les cas), constructeurs, peutEtreExecutee, utilisateurAutorise. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests ActionNotificationDTO") -class ActionNotificationDTOTest { - - @Nested - @DisplayName("incrementerExecutions") - class IncrementerExecutions { - - @Test - @DisplayName("initialise à 0 puis incrémente quand nombreExecutions null") - void testQuandNull() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "Lib", "confirm"); - action.setNombreExecutions(null); - action.incrementerExecutions(); - assertThat(action.getNombreExecutions()).isEqualTo(1); - } - - @Test - @DisplayName("incrémente quand nombreExecutions déjà défini") - void testQuandDefini() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "Lib", "confirm"); - action.setNombreExecutions(2); - action.incrementerExecutions(); - assertThat(action.getNombreExecutions()).isEqualTo(3); - } - } - - @Nested - @DisplayName("getCouleurParDefaut") - class GetCouleurParDefaut { - - @Test - @DisplayName("retourne couleur si définie") - void testCouleurDefinie() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "Lib", "confirm"); - action.setCouleur("#000000"); - assertThat(action.getCouleurParDefaut()).isEqualTo("#000000"); - } - - @Test - @DisplayName("retourne vert pour confirm") - void testConfirm() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - assertThat(action.getCouleurParDefaut()).isEqualTo("#4CAF50"); - } - - @Test - @DisplayName("retourne rouge pour cancel") - void testCancel() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "cancel"); - assertThat(action.getCouleurParDefaut()).isEqualTo("#F44336"); - } - - @Test - @DisplayName("retourne bleu pour info") - void testInfo() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "info"); - assertThat(action.getCouleurParDefaut()).isEqualTo("#2196F3"); - } - - @Test - @DisplayName("retourne orange pour warning") - void testWarning() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "warning"); - assertThat(action.getCouleurParDefaut()).isEqualTo("#FF9800"); - } - - @Test - @DisplayName("retourne bleu pour url") - void testUrl() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "url"); - assertThat(action.getCouleurParDefaut()).isEqualTo("#2196F3"); - } - - @Test - @DisplayName("retourne bleu pour route") - void testRoute() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "route"); - assertThat(action.getCouleurParDefaut()).isEqualTo("#2196F3"); - } - - @Test - @DisplayName("retourne gris par défaut pour type inconnu") - void testDefault() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "Lib", "unknown_type"); - assertThat(action.getCouleurParDefaut()).isEqualTo("#9E9E9E"); - } - } - - @Nested - @DisplayName("getIconeParDefaut") - class GetIconeParDefaut { - - @Test - @DisplayName("retourne icone si définie") - void testIconeDefinie() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "Lib", "confirm"); - action.setIcone("custom"); - assertThat(action.getIconeParDefaut()).isEqualTo("custom"); - } - - @Test - @DisplayName("retourne check pour confirm") - void testConfirm() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - assertThat(action.getIconeParDefaut()).isEqualTo("check"); - } - - @Test - @DisplayName("retourne close pour cancel") - void testCancel() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "cancel"); - assertThat(action.getIconeParDefaut()).isEqualTo("close"); - } - - @Test - @DisplayName("retourne info pour info") - void testInfo() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "info"); - assertThat(action.getIconeParDefaut()).isEqualTo("info"); - } - - @Test - @DisplayName("retourne warning pour warning") - void testWarning() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "warning"); - assertThat(action.getIconeParDefaut()).isEqualTo("warning"); - } - - @Test - @DisplayName("retourne open_in_new pour url") - void testUrl() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "url"); - assertThat(action.getIconeParDefaut()).isEqualTo("open_in_new"); - } - - @Test - @DisplayName("retourne arrow_forward pour route") - void testRoute() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "route"); - assertThat(action.getIconeParDefaut()).isEqualTo("arrow_forward"); - } - - @Test - @DisplayName("retourne phone pour call") - void testCall() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "call"); - assertThat(action.getIconeParDefaut()).isEqualTo("phone"); - } - - @Test - @DisplayName("retourne message pour message") - void testMessage() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "message"); - assertThat(action.getIconeParDefaut()).isEqualTo("message"); - } - - @Test - @DisplayName("retourne email pour email") - void testEmail() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "email"); - assertThat(action.getIconeParDefaut()).isEqualTo("email"); - } - - @Test - @DisplayName("retourne share pour share") - void testShare() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "share"); - assertThat(action.getIconeParDefaut()).isEqualTo("share"); - } - - @Test - @DisplayName("retourne touch_app pour type inconnu") - void testDefault() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "Lib", "unknown"); - assertThat(action.getIconeParDefaut()).isEqualTo("touch_app"); - } - } - - @Nested - @DisplayName("Constructeurs") - class Constructeurs { - - @Test - @DisplayName("constructeur URL remplit url et icone") - void testConstructeurUrl() { - ActionNotificationDTO action = new ActionNotificationDTO("id", "Ouvrir", "http://url", "open"); - assertThat(action.getId()).isEqualTo("id"); - assertThat(action.getLibelle()).isEqualTo("Ouvrir"); - assertThat(action.getTypeAction()).isEqualTo("url"); - assertThat(action.getUrl()).isEqualTo("http://url"); - assertThat(action.getIcone()).isEqualTo("open"); - } - - @Test - @DisplayName("constructeur route remplit route, icone et parametres") - void testConstructeurRoute() { - ActionNotificationDTO action = new ActionNotificationDTO( - "id", "Aller", "/page", "arrow", Map.of("p", "v")); - assertThat(action.getTypeAction()).isEqualTo("route"); - assertThat(action.getRoute()).isEqualTo("/page"); - assertThat(action.getIcone()).isEqualTo("arrow"); - assertThat(action.getParametres()).containsEntry("p", "v"); - } - } - - @Nested - @DisplayName("peutEtreExecutee") - class PeutEtreExecutee { - - @Test - @DisplayName("true quand estActivee et nombreExecutions < maxExecutions") - void testPeutExecuter() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - assertThat(action.peutEtreExecutee()).isTrue(); - } - - @Test - @DisplayName("true quand peutEtreRepetee même si nombreExecutions >= maxExecutions") - void testRepetee() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - action.setNombreExecutions(1); - action.setMaxExecutions(1); - action.setPeutEtreRepetee(true); - assertThat(action.peutEtreExecutee()).isTrue(); - } - - @Test - @DisplayName("false quand nombreExecutions >= maxExecutions et peutEtreRepetee false") - void testMaxAtteint() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - action.setNombreExecutions(1); - action.setMaxExecutions(1); - action.setPeutEtreRepetee(false); - assertThat(action.peutEtreExecutee()).isFalse(); - } - - @Test - @DisplayName("false quand estActivee false") - void testDesactivee() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - action.setEstActivee(false); - assertThat(action.peutEtreExecutee()).isFalse(); - } - } - - @Nested - @DisplayName("utilisateurAutorise") - class UtilisateurAutorise { - - @Test - @DisplayName("true quand pas de rôles ni permissions requis") - void testSansRestriction() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isTrue(); - } - - @Test - @DisplayName("true quand utilisateur a le rôle requis") - void testAvecRole() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - action.setRolesAutorises(new String[] { "ADMIN" }); - assertThat(action.utilisateurAutorise(new String[] { "ADMIN" }, new String[] {})).isTrue(); - } - - @Test - @DisplayName("false quand utilisateur n'a pas le rôle requis") - void testSansRole() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - action.setRolesAutorises(new String[] { "ADMIN" }); - assertThat(action.utilisateurAutorise(new String[] { "USER" }, new String[] {})).isFalse(); - } - - @Test - @DisplayName("true quand utilisateur a la permission requise") - void testAvecPermission() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - action.setPermissionsRequises(new String[] { "write" }); - assertThat(action.utilisateurAutorise(new String[] {}, new String[] { "write" })).isTrue(); - } - - @Test - @DisplayName("false quand utilisateur n'a pas la permission requise") - void testSansPermission() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - action.setPermissionsRequises(new String[] { "write" }); - assertThat(action.utilisateurAutorise(new String[] {}, new String[] { "read" })).isFalse(); - } - - @Test - @DisplayName("true quand rolesAutorises null") - void testRolesNull() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - action.setRolesAutorises(null); - assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isTrue(); - } - - @Test - @DisplayName("true quand permissionsRequises null") - void testPermissionsNull() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - action.setPermissionsRequises(null); - assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isTrue(); - } - - @Test - @DisplayName("false quand rolesAutorises requis mais rolesUtilisateur vide") - void testRolesRequisUtilisateurVide() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - action.setRolesAutorises(new String[] { "ADMIN" }); - assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isFalse(); - } - - @Test - @DisplayName("false quand permissionsRequises requises mais permissionsUtilisateur vides") - void testPermissionsRequisesUtilisateurVides() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - action.setPermissionsRequises(new String[] { "write" }); - assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isFalse(); - } - - @Test - @DisplayName("true quand rolesAutorises tableau vide (length == 0)") - void testRolesTableauVide() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - action.setRolesAutorises(new String[] {}); - assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isTrue(); - } - - @Test - @DisplayName("true quand permissionsRequises tableau vide (length == 0)") - void testPermissionsTableauVide() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - action.setPermissionsRequises(new String[] {}); - assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isTrue(); - } - } - - @Nested - @DisplayName("isExpiree") - class IsExpiree { - - @Test - @DisplayName("retourne false (non implémenté)") - void testRetourneFalse() { - ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); - assertThat(action.isExpiree()).isFalse(); - } - } - - @Nested - @DisplayName("toString") - class ToString { - - @Test - @DisplayName("contient id, libelle et type") - void testToString() { - ActionNotificationDTO action = new ActionNotificationDTO("x", "Label", "confirm"); - String s = action.toString(); - assertThat(s).contains("x"); - assertThat(s).contains("Label"); - assertThat(s).contains("confirm"); - } - } - - @Nested - @DisplayName("Méthodes statiques") - class MethodesStatiques { - - @Test - @DisplayName("creerActionConfirmation") - void testCreerConfirmation() { - ActionNotificationDTO a = ActionNotificationDTO.creerActionConfirmation("c1", "OK"); - assertThat(a.getId()).isEqualTo("c1"); - assertThat(a.getLibelle()).isEqualTo("OK"); - assertThat(a.getTypeAction()).isEqualTo("confirm"); - assertThat(a.getCouleur()).isEqualTo("#4CAF50"); - assertThat(a.getIcone()).isEqualTo("check"); - } - - @Test - @DisplayName("creerActionAnnulation") - void testCreerAnnulation() { - ActionNotificationDTO a = ActionNotificationDTO.creerActionAnnulation("c2", "Annuler"); - assertThat(a.getTypeAction()).isEqualTo("cancel"); - assertThat(a.getEstDestructive()).isTrue(); - } - - @Test - @DisplayName("creerActionNavigation") - void testCreerNavigation() { - ActionNotificationDTO a = ActionNotificationDTO.creerActionNavigation("n1", "Voir", "/detail"); - assertThat(a.getRoute()).isEqualTo("/detail"); - assertThat(a.getTypeAction()).isEqualTo("route"); - } - } - - @Nested - @DisplayName("Getters et Setters") - class GettersEtSetters { - - @Test - @DisplayName("tous les getters et setters fonctionnent correctement") - void testTousLesGettersSetters() { - ActionNotificationDTO dto = new ActionNotificationDTO(); - - // Test id - dto.setId("act-123"); - assertThat(dto.getId()).isEqualTo("act-123"); - - // Test libelle - dto.setLibelle("Cliquer ici"); - assertThat(dto.getLibelle()).isEqualTo("Cliquer ici"); - - // Test typeAction - dto.setTypeAction("custom"); - assertThat(dto.getTypeAction()).isEqualTo("custom"); - - // Test url - dto.setUrl("https://example.com"); - assertThat(dto.getUrl()).isEqualTo("https://example.com"); - - // Test estActivee - dto.setEstActivee(false); - assertThat(dto.getEstActivee()).isFalse(); - - // Test rolesAutorises - String[] roles = new String[] {"ADMIN", "MODERATOR"}; - dto.setRolesAutorises(roles); - assertThat(dto.getRolesAutorises()).isEqualTo(roles); - - // Test permissionsRequises - String[] permissions = new String[] {"read", "write"}; - dto.setPermissionsRequises(permissions); - assertThat(dto.getPermissionsRequises()).isEqualTo(permissions); - - // Test maxExecutions - dto.setMaxExecutions(5); - assertThat(dto.getMaxExecutions()).isEqualTo(5); - - // Test peutEtreRepetee - dto.setPeutEtreRepetee(true); - assertThat(dto.getPeutEtreRepetee()).isTrue(); - - // Test description - dto.setDescription("Description détaillée de l'action"); - assertThat(dto.getDescription()).isEqualTo("Description détaillée de l'action"); - - // Test parametres - Map params = Map.of("key1", "val1", "key2", "val2"); - dto.setParametres(params); - assertThat(dto.getParametres()).isEqualTo(params); - - // Test fermeNotification - dto.setFermeNotification(false); - assertThat(dto.getFermeNotification()).isFalse(); - - // Test necessiteConfirmation - dto.setNecessiteConfirmation(true); - assertThat(dto.getNecessiteConfirmation()).isTrue(); - - // Test messageConfirmation - dto.setMessageConfirmation("Êtes-vous sûr ?"); - assertThat(dto.getMessageConfirmation()).isEqualTo("Êtes-vous sûr ?"); - - // Test ordre - dto.setOrdre(5); - assertThat(dto.getOrdre()).isEqualTo(5); - - // Test conditionAffichage - dto.setConditionAffichage("user.role === 'ADMIN'"); - assertThat(dto.getConditionAffichage()).isEqualTo("user.role === 'ADMIN'"); - - // Test delaiExpirationMinutes - dto.setDelaiExpirationMinutes(120); - assertThat(dto.getDelaiExpirationMinutes()).isEqualTo(120); - - // Test styleBouton - dto.setStyleBouton("outline"); - assertThat(dto.getStyleBouton()).isEqualTo("outline"); - - // Test tailleBouton - dto.setTailleBouton("large"); - assertThat(dto.getTailleBouton()).isEqualTo("large"); - - // Test positionBouton - dto.setPositionBouton("center"); - assertThat(dto.getPositionBouton()).isEqualTo("center"); - - // Test donneesPersonnalisees - Map donneesPerso = Map.of("custom", "value", "count", 42); - dto.setDonneesPersonnalisees(donneesPerso); - assertThat(dto.getDonneesPersonnalisees()).isEqualTo(donneesPerso); - } - } -} +package dev.lions.unionflow.server.api.dto.notification; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.Map; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour ActionNotificationDTO. + * Couvre incrementerExecutions (nombreExecutions null), getCouleurParDefaut (default), + * getIconeParDefaut (tous les cas), constructeurs, peutEtreExecutee, utilisateurAutorise. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests ActionNotificationDTO") +class ActionNotificationDTOTest { + + @Nested + @DisplayName("incrementerExecutions") + class IncrementerExecutions { + + @Test + @DisplayName("initialise à 0 puis incrémente quand nombreExecutions null") + void testQuandNull() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "Lib", "confirm"); + action.setNombreExecutions(null); + action.incrementerExecutions(); + assertThat(action.getNombreExecutions()).isEqualTo(1); + } + + @Test + @DisplayName("incrémente quand nombreExecutions déjà défini") + void testQuandDefini() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "Lib", "confirm"); + action.setNombreExecutions(2); + action.incrementerExecutions(); + assertThat(action.getNombreExecutions()).isEqualTo(3); + } + } + + @Nested + @DisplayName("getCouleurParDefaut") + class GetCouleurParDefaut { + + @Test + @DisplayName("retourne couleur si définie") + void testCouleurDefinie() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "Lib", "confirm"); + action.setCouleur("#000000"); + assertThat(action.getCouleurParDefaut()).isEqualTo("#000000"); + } + + @Test + @DisplayName("retourne vert pour confirm") + void testConfirm() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + assertThat(action.getCouleurParDefaut()).isEqualTo("#4CAF50"); + } + + @Test + @DisplayName("retourne rouge pour cancel") + void testCancel() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "cancel"); + assertThat(action.getCouleurParDefaut()).isEqualTo("#F44336"); + } + + @Test + @DisplayName("retourne bleu pour info") + void testInfo() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "info"); + assertThat(action.getCouleurParDefaut()).isEqualTo("#2196F3"); + } + + @Test + @DisplayName("retourne orange pour warning") + void testWarning() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "warning"); + assertThat(action.getCouleurParDefaut()).isEqualTo("#FF9800"); + } + + @Test + @DisplayName("retourne bleu pour url") + void testUrl() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "url"); + assertThat(action.getCouleurParDefaut()).isEqualTo("#2196F3"); + } + + @Test + @DisplayName("retourne bleu pour route") + void testRoute() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "route"); + assertThat(action.getCouleurParDefaut()).isEqualTo("#2196F3"); + } + + @Test + @DisplayName("retourne gris par défaut pour type inconnu") + void testDefault() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "Lib", "unknown_type"); + assertThat(action.getCouleurParDefaut()).isEqualTo("#9E9E9E"); + } + } + + @Nested + @DisplayName("getIconeParDefaut") + class GetIconeParDefaut { + + @Test + @DisplayName("retourne icone si définie") + void testIconeDefinie() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "Lib", "confirm"); + action.setIcone("custom"); + assertThat(action.getIconeParDefaut()).isEqualTo("custom"); + } + + @Test + @DisplayName("retourne check pour confirm") + void testConfirm() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + assertThat(action.getIconeParDefaut()).isEqualTo("check"); + } + + @Test + @DisplayName("retourne close pour cancel") + void testCancel() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "cancel"); + assertThat(action.getIconeParDefaut()).isEqualTo("close"); + } + + @Test + @DisplayName("retourne info pour info") + void testInfo() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "info"); + assertThat(action.getIconeParDefaut()).isEqualTo("info"); + } + + @Test + @DisplayName("retourne warning pour warning") + void testWarning() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "warning"); + assertThat(action.getIconeParDefaut()).isEqualTo("warning"); + } + + @Test + @DisplayName("retourne open_in_new pour url") + void testUrl() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "url"); + assertThat(action.getIconeParDefaut()).isEqualTo("open_in_new"); + } + + @Test + @DisplayName("retourne arrow_forward pour route") + void testRoute() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "route"); + assertThat(action.getIconeParDefaut()).isEqualTo("arrow_forward"); + } + + @Test + @DisplayName("retourne phone pour call") + void testCall() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "call"); + assertThat(action.getIconeParDefaut()).isEqualTo("phone"); + } + + @Test + @DisplayName("retourne message pour message") + void testMessage() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "message"); + assertThat(action.getIconeParDefaut()).isEqualTo("message"); + } + + @Test + @DisplayName("retourne email pour email") + void testEmail() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "email"); + assertThat(action.getIconeParDefaut()).isEqualTo("email"); + } + + @Test + @DisplayName("retourne share pour share") + void testShare() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "share"); + assertThat(action.getIconeParDefaut()).isEqualTo("share"); + } + + @Test + @DisplayName("retourne touch_app pour type inconnu") + void testDefault() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "Lib", "unknown"); + assertThat(action.getIconeParDefaut()).isEqualTo("touch_app"); + } + } + + @Nested + @DisplayName("Constructeurs") + class Constructeurs { + + @Test + @DisplayName("constructeur URL remplit url et icone") + void testConstructeurUrl() { + ActionNotificationDTO action = new ActionNotificationDTO("id", "Ouvrir", "http://url", "open"); + assertThat(action.getId()).isEqualTo("id"); + assertThat(action.getLibelle()).isEqualTo("Ouvrir"); + assertThat(action.getTypeAction()).isEqualTo("url"); + assertThat(action.getUrl()).isEqualTo("http://url"); + assertThat(action.getIcone()).isEqualTo("open"); + } + + @Test + @DisplayName("constructeur route remplit route, icone et parametres") + void testConstructeurRoute() { + ActionNotificationDTO action = new ActionNotificationDTO( + "id", "Aller", "/page", "arrow", Map.of("p", "v")); + assertThat(action.getTypeAction()).isEqualTo("route"); + assertThat(action.getRoute()).isEqualTo("/page"); + assertThat(action.getIcone()).isEqualTo("arrow"); + assertThat(action.getParametres()).containsEntry("p", "v"); + } + } + + @Nested + @DisplayName("peutEtreExecutee") + class PeutEtreExecutee { + + @Test + @DisplayName("true quand estActivee et nombreExecutions < maxExecutions") + void testPeutExecuter() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + assertThat(action.peutEtreExecutee()).isTrue(); + } + + @Test + @DisplayName("true quand peutEtreRepetee même si nombreExecutions >= maxExecutions") + void testRepetee() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + action.setNombreExecutions(1); + action.setMaxExecutions(1); + action.setPeutEtreRepetee(true); + assertThat(action.peutEtreExecutee()).isTrue(); + } + + @Test + @DisplayName("false quand nombreExecutions >= maxExecutions et peutEtreRepetee false") + void testMaxAtteint() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + action.setNombreExecutions(1); + action.setMaxExecutions(1); + action.setPeutEtreRepetee(false); + assertThat(action.peutEtreExecutee()).isFalse(); + } + + @Test + @DisplayName("false quand estActivee false") + void testDesactivee() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + action.setEstActivee(false); + assertThat(action.peutEtreExecutee()).isFalse(); + } + } + + @Nested + @DisplayName("utilisateurAutorise") + class UtilisateurAutorise { + + @Test + @DisplayName("true quand pas de rôles ni permissions requis") + void testSansRestriction() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isTrue(); + } + + @Test + @DisplayName("true quand utilisateur a le rôle requis") + void testAvecRole() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + action.setRolesAutorises(new String[] { "ADMIN" }); + assertThat(action.utilisateurAutorise(new String[] { "ADMIN" }, new String[] {})).isTrue(); + } + + @Test + @DisplayName("false quand utilisateur n'a pas le rôle requis") + void testSansRole() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + action.setRolesAutorises(new String[] { "ADMIN" }); + assertThat(action.utilisateurAutorise(new String[] { "USER" }, new String[] {})).isFalse(); + } + + @Test + @DisplayName("true quand utilisateur a la permission requise") + void testAvecPermission() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + action.setPermissionsRequises(new String[] { "write" }); + assertThat(action.utilisateurAutorise(new String[] {}, new String[] { "write" })).isTrue(); + } + + @Test + @DisplayName("false quand utilisateur n'a pas la permission requise") + void testSansPermission() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + action.setPermissionsRequises(new String[] { "write" }); + assertThat(action.utilisateurAutorise(new String[] {}, new String[] { "read" })).isFalse(); + } + + @Test + @DisplayName("true quand rolesAutorises null") + void testRolesNull() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + action.setRolesAutorises(null); + assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isTrue(); + } + + @Test + @DisplayName("true quand permissionsRequises null") + void testPermissionsNull() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + action.setPermissionsRequises(null); + assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isTrue(); + } + + @Test + @DisplayName("false quand rolesAutorises requis mais rolesUtilisateur vide") + void testRolesRequisUtilisateurVide() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + action.setRolesAutorises(new String[] { "ADMIN" }); + assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isFalse(); + } + + @Test + @DisplayName("false quand permissionsRequises requises mais permissionsUtilisateur vides") + void testPermissionsRequisesUtilisateurVides() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + action.setPermissionsRequises(new String[] { "write" }); + assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isFalse(); + } + + @Test + @DisplayName("true quand rolesAutorises tableau vide (length == 0)") + void testRolesTableauVide() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + action.setRolesAutorises(new String[] {}); + assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isTrue(); + } + + @Test + @DisplayName("true quand permissionsRequises tableau vide (length == 0)") + void testPermissionsTableauVide() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + action.setPermissionsRequises(new String[] {}); + assertThat(action.utilisateurAutorise(new String[] {}, new String[] {})).isTrue(); + } + } + + @Nested + @DisplayName("isExpiree") + class IsExpiree { + + @Test + @DisplayName("retourne false (non implémenté)") + void testRetourneFalse() { + ActionNotificationDTO action = new ActionNotificationDTO("a", "L", "confirm"); + assertThat(action.isExpiree()).isFalse(); + } + } + + @Nested + @DisplayName("toString") + class ToString { + + @Test + @DisplayName("contient id, libelle et type") + void testToString() { + ActionNotificationDTO action = new ActionNotificationDTO("x", "Label", "confirm"); + String s = action.toString(); + assertThat(s).contains("x"); + assertThat(s).contains("Label"); + assertThat(s).contains("confirm"); + } + } + + @Nested + @DisplayName("Méthodes statiques") + class MethodesStatiques { + + @Test + @DisplayName("creerActionConfirmation") + void testCreerConfirmation() { + ActionNotificationDTO a = ActionNotificationDTO.creerActionConfirmation("c1", "OK"); + assertThat(a.getId()).isEqualTo("c1"); + assertThat(a.getLibelle()).isEqualTo("OK"); + assertThat(a.getTypeAction()).isEqualTo("confirm"); + assertThat(a.getCouleur()).isEqualTo("#4CAF50"); + assertThat(a.getIcone()).isEqualTo("check"); + } + + @Test + @DisplayName("creerActionAnnulation") + void testCreerAnnulation() { + ActionNotificationDTO a = ActionNotificationDTO.creerActionAnnulation("c2", "Annuler"); + assertThat(a.getTypeAction()).isEqualTo("cancel"); + assertThat(a.getEstDestructive()).isTrue(); + } + + @Test + @DisplayName("creerActionNavigation") + void testCreerNavigation() { + ActionNotificationDTO a = ActionNotificationDTO.creerActionNavigation("n1", "Voir", "/detail"); + assertThat(a.getRoute()).isEqualTo("/detail"); + assertThat(a.getTypeAction()).isEqualTo("route"); + } + } + + @Nested + @DisplayName("Getters et Setters") + class GettersEtSetters { + + @Test + @DisplayName("tous les getters et setters fonctionnent correctement") + void testTousLesGettersSetters() { + ActionNotificationDTO dto = new ActionNotificationDTO(); + + // Test id + dto.setId("act-123"); + assertThat(dto.getId()).isEqualTo("act-123"); + + // Test libelle + dto.setLibelle("Cliquer ici"); + assertThat(dto.getLibelle()).isEqualTo("Cliquer ici"); + + // Test typeAction + dto.setTypeAction("custom"); + assertThat(dto.getTypeAction()).isEqualTo("custom"); + + // Test url + dto.setUrl("https://example.com"); + assertThat(dto.getUrl()).isEqualTo("https://example.com"); + + // Test estActivee + dto.setEstActivee(false); + assertThat(dto.getEstActivee()).isFalse(); + + // Test rolesAutorises + String[] roles = new String[] {"ADMIN", "MODERATOR"}; + dto.setRolesAutorises(roles); + assertThat(dto.getRolesAutorises()).isEqualTo(roles); + + // Test permissionsRequises + String[] permissions = new String[] {"read", "write"}; + dto.setPermissionsRequises(permissions); + assertThat(dto.getPermissionsRequises()).isEqualTo(permissions); + + // Test maxExecutions + dto.setMaxExecutions(5); + assertThat(dto.getMaxExecutions()).isEqualTo(5); + + // Test peutEtreRepetee + dto.setPeutEtreRepetee(true); + assertThat(dto.getPeutEtreRepetee()).isTrue(); + + // Test description + dto.setDescription("Description détaillée de l'action"); + assertThat(dto.getDescription()).isEqualTo("Description détaillée de l'action"); + + // Test parametres + Map params = Map.of("key1", "val1", "key2", "val2"); + dto.setParametres(params); + assertThat(dto.getParametres()).isEqualTo(params); + + // Test fermeNotification + dto.setFermeNotification(false); + assertThat(dto.getFermeNotification()).isFalse(); + + // Test necessiteConfirmation + dto.setNecessiteConfirmation(true); + assertThat(dto.getNecessiteConfirmation()).isTrue(); + + // Test messageConfirmation + dto.setMessageConfirmation("Êtes-vous sûr ?"); + assertThat(dto.getMessageConfirmation()).isEqualTo("Êtes-vous sûr ?"); + + // Test ordre + dto.setOrdre(5); + assertThat(dto.getOrdre()).isEqualTo(5); + + // Test conditionAffichage + dto.setConditionAffichage("user.role === 'ADMIN'"); + assertThat(dto.getConditionAffichage()).isEqualTo("user.role === 'ADMIN'"); + + // Test delaiExpirationMinutes + dto.setDelaiExpirationMinutes(120); + assertThat(dto.getDelaiExpirationMinutes()).isEqualTo(120); + + // Test styleBouton + dto.setStyleBouton("outline"); + assertThat(dto.getStyleBouton()).isEqualTo("outline"); + + // Test tailleBouton + dto.setTailleBouton("large"); + assertThat(dto.getTailleBouton()).isEqualTo("large"); + + // Test positionBouton + dto.setPositionBouton("center"); + assertThat(dto.getPositionBouton()).isEqualTo("center"); + + // Test donneesPersonnalisees + Map donneesPerso = Map.of("custom", "value", "count", 42); + dto.setDonneesPersonnalisees(donneesPerso); + assertThat(dto.getDonneesPersonnalisees()).isEqualTo(donneesPerso); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/notification/PreferenceCanalNotificationDTOTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/notification/PreferenceCanalNotificationDTOTest.java index 38a0758..d318474 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/notification/PreferenceCanalNotificationDTOTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/notification/PreferenceCanalNotificationDTOTest.java @@ -1,97 +1,97 @@ -package dev.lions.unionflow.server.api.dto.notification; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class PreferenceCanalNotificationDTOTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testConstructorAndGettersSetters() { - PreferenceCanalNotificationDTO dto = new PreferenceCanalNotificationDTO(); - - dto.setActive(true); - dto.setImportance(3); - dto.setSonPersonnalise("custom_sound.mp3"); - dto.setPatternVibration(new long[]{100, 200, 100}); - dto.setCouleurLED("#FF0000"); - dto.setSonActive(true); - dto.setVibrationActive(false); - dto.setLedActive(true); - dto.setPeutEtreDesactive(true); - - assertThat(dto.getActive()).isTrue(); - assertThat(dto.getImportance()).isEqualTo(3); - assertThat(dto.getSonPersonnalise()).isEqualTo("custom_sound.mp3"); - assertThat(dto.getPatternVibration()).containsExactly(100L, 200L, 100L); - assertThat(dto.getCouleurLED()).isEqualTo("#FF0000"); - assertThat(dto.getSonActive()).isTrue(); - assertThat(dto.getVibrationActive()).isFalse(); - assertThat(dto.getLedActive()).isTrue(); - assertThat(dto.getPeutEtreDesactive()).isTrue(); - } - - @Test - void testValidation_ImportanceTooLow() { - PreferenceCanalNotificationDTO dto = new PreferenceCanalNotificationDTO(); - dto.setImportance(0); - - Set> violations = validator.validate(dto); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("importance")); - } - - @Test - void testValidation_ImportanceTooHigh() { - PreferenceCanalNotificationDTO dto = new PreferenceCanalNotificationDTO(); - dto.setImportance(6); - - Set> violations = validator.validate(dto); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("importance")); - } - - @Test - void testValidation_ValidImportance() { - PreferenceCanalNotificationDTO dto = new PreferenceCanalNotificationDTO(); - dto.setImportance(1); - - Set> violations1 = validator.validate(dto); - assertThat(violations1).isEmpty(); - - dto.setImportance(5); - Set> violations2 = validator.validate(dto); - assertThat(violations2).isEmpty(); - } - - @Test - void testAllFieldsNull() { - PreferenceCanalNotificationDTO dto = new PreferenceCanalNotificationDTO(); - - assertThat(dto.getActive()).isNull(); - assertThat(dto.getImportance()).isNull(); - assertThat(dto.getSonPersonnalise()).isNull(); - assertThat(dto.getPatternVibration()).isNull(); - assertThat(dto.getCouleurLED()).isNull(); - assertThat(dto.getSonActive()).isNull(); - assertThat(dto.getVibrationActive()).isNull(); - assertThat(dto.getLedActive()).isNull(); - assertThat(dto.getPeutEtreDesactive()).isNull(); - } -} +package dev.lions.unionflow.server.api.dto.notification; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class PreferenceCanalNotificationDTOTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testConstructorAndGettersSetters() { + PreferenceCanalNotificationDTO dto = new PreferenceCanalNotificationDTO(); + + dto.setActive(true); + dto.setImportance(3); + dto.setSonPersonnalise("custom_sound.mp3"); + dto.setPatternVibration(new long[]{100, 200, 100}); + dto.setCouleurLED("#FF0000"); + dto.setSonActive(true); + dto.setVibrationActive(false); + dto.setLedActive(true); + dto.setPeutEtreDesactive(true); + + assertThat(dto.getActive()).isTrue(); + assertThat(dto.getImportance()).isEqualTo(3); + assertThat(dto.getSonPersonnalise()).isEqualTo("custom_sound.mp3"); + assertThat(dto.getPatternVibration()).containsExactly(100L, 200L, 100L); + assertThat(dto.getCouleurLED()).isEqualTo("#FF0000"); + assertThat(dto.getSonActive()).isTrue(); + assertThat(dto.getVibrationActive()).isFalse(); + assertThat(dto.getLedActive()).isTrue(); + assertThat(dto.getPeutEtreDesactive()).isTrue(); + } + + @Test + void testValidation_ImportanceTooLow() { + PreferenceCanalNotificationDTO dto = new PreferenceCanalNotificationDTO(); + dto.setImportance(0); + + Set> violations = validator.validate(dto); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("importance")); + } + + @Test + void testValidation_ImportanceTooHigh() { + PreferenceCanalNotificationDTO dto = new PreferenceCanalNotificationDTO(); + dto.setImportance(6); + + Set> violations = validator.validate(dto); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("importance")); + } + + @Test + void testValidation_ValidImportance() { + PreferenceCanalNotificationDTO dto = new PreferenceCanalNotificationDTO(); + dto.setImportance(1); + + Set> violations1 = validator.validate(dto); + assertThat(violations1).isEmpty(); + + dto.setImportance(5); + Set> violations2 = validator.validate(dto); + assertThat(violations2).isEmpty(); + } + + @Test + void testAllFieldsNull() { + PreferenceCanalNotificationDTO dto = new PreferenceCanalNotificationDTO(); + + assertThat(dto.getActive()).isNull(); + assertThat(dto.getImportance()).isNull(); + assertThat(dto.getSonPersonnalise()).isNull(); + assertThat(dto.getPatternVibration()).isNull(); + assertThat(dto.getCouleurLED()).isNull(); + assertThat(dto.getSonActive()).isNull(); + assertThat(dto.getVibrationActive()).isNull(); + assertThat(dto.getLedActive()).isNull(); + assertThat(dto.getPeutEtreDesactive()).isNull(); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/notification/PreferenceTypeNotificationDTOTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/notification/PreferenceTypeNotificationDTOTest.java index cd82c2f..f6086e4 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/notification/PreferenceTypeNotificationDTOTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/notification/PreferenceTypeNotificationDTOTest.java @@ -1,124 +1,124 @@ -package dev.lions.unionflow.server.api.dto.notification; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class PreferenceTypeNotificationDTOTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testConstructorAndGettersSetters() { - PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); - - dto.setActive(true); - dto.setPriorite(4); - dto.setSonPersonnalise("alert.mp3"); - dto.setPatternVibration(new long[]{50, 100, 50}); - dto.setCouleurLED("#00FF00"); - dto.setDureeAffichageSecondes(60); - dto.setDoitVibrer(true); - dto.setDoitEmettreSon(true); - dto.setDoitAllumerLED(false); - dto.setIgnoreModeSilencieux(true); - - assertThat(dto.getActive()).isTrue(); - assertThat(dto.getPriorite()).isEqualTo(4); - assertThat(dto.getSonPersonnalise()).isEqualTo("alert.mp3"); - assertThat(dto.getPatternVibration()).containsExactly(50L, 100L, 50L); - assertThat(dto.getCouleurLED()).isEqualTo("#00FF00"); - assertThat(dto.getDureeAffichageSecondes()).isEqualTo(60); - assertThat(dto.getDoitVibrer()).isTrue(); - assertThat(dto.getDoitEmettreSon()).isTrue(); - assertThat(dto.getDoitAllumerLED()).isFalse(); - assertThat(dto.getIgnoreModeSilencieux()).isTrue(); - } - - @Test - void testValidation_PrioriteTooLow() { - PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); - dto.setPriorite(0); - - Set> violations = validator.validate(dto); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("priorite")); - } - - @Test - void testValidation_PrioriteTooHigh() { - PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); - dto.setPriorite(6); - - Set> violations = validator.validate(dto); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("priorite")); - } - - @Test - void testValidation_DureeAffichageTooLow() { - PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); - dto.setDureeAffichageSecondes(0); - - Set> violations = validator.validate(dto); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dureeAffichageSecondes")); - } - - @Test - void testValidation_DureeAffichageTooHigh() { - PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); - dto.setDureeAffichageSecondes(301); - - Set> violations = validator.validate(dto); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dureeAffichageSecondes")); - } - - @Test - void testValidation_ValidFields() { - PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); - dto.setPriorite(1); - dto.setDureeAffichageSecondes(1); - - Set> violations1 = validator.validate(dto); - assertThat(violations1).isEmpty(); - - dto.setPriorite(5); - dto.setDureeAffichageSecondes(300); - Set> violations2 = validator.validate(dto); - assertThat(violations2).isEmpty(); - } - - @Test - void testAllFieldsNull() { - PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); - - assertThat(dto.getActive()).isNull(); - assertThat(dto.getPriorite()).isNull(); - assertThat(dto.getSonPersonnalise()).isNull(); - assertThat(dto.getPatternVibration()).isNull(); - assertThat(dto.getCouleurLED()).isNull(); - assertThat(dto.getDureeAffichageSecondes()).isNull(); - assertThat(dto.getDoitVibrer()).isNull(); - assertThat(dto.getDoitEmettreSon()).isNull(); - assertThat(dto.getDoitAllumerLED()).isNull(); - assertThat(dto.getIgnoreModeSilencieux()).isNull(); - } -} +package dev.lions.unionflow.server.api.dto.notification; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class PreferenceTypeNotificationDTOTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testConstructorAndGettersSetters() { + PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); + + dto.setActive(true); + dto.setPriorite(4); + dto.setSonPersonnalise("alert.mp3"); + dto.setPatternVibration(new long[]{50, 100, 50}); + dto.setCouleurLED("#00FF00"); + dto.setDureeAffichageSecondes(60); + dto.setDoitVibrer(true); + dto.setDoitEmettreSon(true); + dto.setDoitAllumerLED(false); + dto.setIgnoreModeSilencieux(true); + + assertThat(dto.getActive()).isTrue(); + assertThat(dto.getPriorite()).isEqualTo(4); + assertThat(dto.getSonPersonnalise()).isEqualTo("alert.mp3"); + assertThat(dto.getPatternVibration()).containsExactly(50L, 100L, 50L); + assertThat(dto.getCouleurLED()).isEqualTo("#00FF00"); + assertThat(dto.getDureeAffichageSecondes()).isEqualTo(60); + assertThat(dto.getDoitVibrer()).isTrue(); + assertThat(dto.getDoitEmettreSon()).isTrue(); + assertThat(dto.getDoitAllumerLED()).isFalse(); + assertThat(dto.getIgnoreModeSilencieux()).isTrue(); + } + + @Test + void testValidation_PrioriteTooLow() { + PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); + dto.setPriorite(0); + + Set> violations = validator.validate(dto); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("priorite")); + } + + @Test + void testValidation_PrioriteTooHigh() { + PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); + dto.setPriorite(6); + + Set> violations = validator.validate(dto); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("priorite")); + } + + @Test + void testValidation_DureeAffichageTooLow() { + PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); + dto.setDureeAffichageSecondes(0); + + Set> violations = validator.validate(dto); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dureeAffichageSecondes")); + } + + @Test + void testValidation_DureeAffichageTooHigh() { + PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); + dto.setDureeAffichageSecondes(301); + + Set> violations = validator.validate(dto); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("dureeAffichageSecondes")); + } + + @Test + void testValidation_ValidFields() { + PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); + dto.setPriorite(1); + dto.setDureeAffichageSecondes(1); + + Set> violations1 = validator.validate(dto); + assertThat(violations1).isEmpty(); + + dto.setPriorite(5); + dto.setDureeAffichageSecondes(300); + Set> violations2 = validator.validate(dto); + assertThat(violations2).isEmpty(); + } + + @Test + void testAllFieldsNull() { + PreferenceTypeNotificationDTO dto = new PreferenceTypeNotificationDTO(); + + assertThat(dto.getActive()).isNull(); + assertThat(dto.getPriorite()).isNull(); + assertThat(dto.getSonPersonnalise()).isNull(); + assertThat(dto.getPatternVibration()).isNull(); + assertThat(dto.getCouleurLED()).isNull(); + assertThat(dto.getDureeAffichageSecondes()).isNull(); + assertThat(dto.getDoitVibrer()).isNull(); + assertThat(dto.getDoitEmettreSon()).isNull(); + assertThat(dto.getDoitAllumerLED()).isNull(); + assertThat(dto.getIgnoreModeSilencieux()).isNull(); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/notification/PreferencesNotificationDTOTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/notification/PreferencesNotificationDTOTest.java index afa32eb..2419ce8 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/notification/PreferencesNotificationDTOTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/notification/PreferencesNotificationDTOTest.java @@ -1,519 +1,519 @@ -package dev.lions.unionflow.server.api.dto.notification; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalTime; -import java.util.Set; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import dev.lions.unionflow.server.api.enums.notification.CanalNotification; -import dev.lions.unionflow.server.api.enums.notification.TypeNotification; - -/** - * Tests unitaires pour PreferencesNotificationDTO. - * Couvre constructeur(String), isTypeActive (toutes branches), isCanalActif (toutes branches), - * isEnModeSilencieux(LocalTime) (traverse minuit, plage normale, null), - * isExpediteurBloque, isExpediteurPrioritaire, toString. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests PreferencesNotificationDTO") -class PreferencesNotificationDTOTest { - - @Nested - @DisplayName("Constructeurs") - class Constructeurs { - - @Test - @DisplayName("constructeur par défaut initialise les champs") - void testConstructeurParDefaut() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - assertThat(dto.getNotificationsActivees()).isTrue(); - assertThat(dto.getPushActivees()).isTrue(); - assertThat(dto.getEmailActivees()).isTrue(); - assertThat(dto.getSmsActivees()).isFalse(); - assertThat(dto.getInAppActivees()).isTrue(); - assertThat(dto.getModeSilencieux()).isFalse(); - assertThat(dto.getFrequenceRegroupementMinutes()).isEqualTo(5); - assertThat(dto.getMaxNotificationsSimultanees()).isEqualTo(10); - assertThat(dto.getDureeAffichageSecondes()).isEqualTo(10); - assertThat(dto.getLangue()).isEqualTo("fr"); - } - - @Test - @DisplayName("constructeur avec utilisateurId appelle this() et set utilisateurId") - void testConstructeurAvecUtilisateur() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO("user-123"); - assertThat(dto.getUtilisateurId()).isEqualTo("user-123"); - assertThat(dto.getNotificationsActivees()).isTrue(); - } - } - - @Nested - @DisplayName("isTypeActive") - class IsTypeActive { - - @Test - @DisplayName("retourne false quand notificationsActivees false") - void testNotificationsDesactivees() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setNotificationsActivees(false); - assertThat(dto.isTypeActive(TypeNotification.EMAIL)).isFalse(); - } - - @Test - @DisplayName("retourne false quand type dans typesDesactivees") - void testTypeDesactive() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setTypesDesactivees(Set.of(TypeNotification.EMAIL)); - assertThat(dto.isTypeActive(TypeNotification.EMAIL)).isFalse(); - } - - @Test - @DisplayName("retourne true quand type dans typesActives") - void testTypeActif() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setTypesActives(Set.of(TypeNotification.EMAIL)); - assertThat(dto.isTypeActive(TypeNotification.EMAIL)).isTrue(); - } - - @Test - @DisplayName("retourne type.isActiveeParDefaut() quand typesActives null et type pas dans typesDesactivees") - void testDefautType() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setTypesActives(null); - dto.setTypesDesactivees(null); - TypeNotification type = TypeNotification.EMAIL; - assertThat(dto.isTypeActive(type)).isEqualTo(type.isActiveeParDefaut()); - } - - @Test - @DisplayName("retourne false quand type pas dans typesActives (typesActives non vide)") - void testTypePasDansActives() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setTypesActives(Set.of(TypeNotification.IN_APP)); - assertThat(dto.isTypeActive(TypeNotification.EMAIL)).isFalse(); - } - - @Test - @DisplayName("retourne type.isActiveeParDefaut() quand typesDesactivees non null (mais vide) et typesActives null") - void testTypesDesactiveesVideTypesActivesNull() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setTypesActives(null); - dto.setTypesDesactivees(Set.of()); - TypeNotification type = TypeNotification.EMAIL; - assertThat(dto.isTypeActive(type)).isEqualTo(type.isActiveeParDefaut()); - } - } - - @Nested - @DisplayName("isCanalActif") - class IsCanalActif { - - @Test - @DisplayName("retourne false quand notificationsActivees false") - void testNotificationsDesactivees() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setNotificationsActivees(false); - assertThat(dto.isCanalActif(CanalNotification.DEFAULT_CHANNEL)).isFalse(); - } - - @Test - @DisplayName("retourne false quand canal dans canauxDesactives") - void testCanalDesactive() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setCanauxDesactives(Set.of(CanalNotification.DEFAULT_CHANNEL)); - assertThat(dto.isCanalActif(CanalNotification.DEFAULT_CHANNEL)).isFalse(); - } - - @Test - @DisplayName("retourne true quand canal dans canauxActifs") - void testCanalActif() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setCanauxActifs(Set.of(CanalNotification.DEFAULT_CHANNEL)); - assertThat(dto.isCanalActif(CanalNotification.DEFAULT_CHANNEL)).isTrue(); - } - - @Test - @DisplayName("retourne true quand canauxActifs null (défaut)") - void testCanauxActifsNull() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setCanauxActifs(null); - dto.setCanauxDesactives(null); - assertThat(dto.isCanalActif(CanalNotification.DEFAULT_CHANNEL)).isTrue(); - } - - @Test - @DisplayName("retourne false quand canal pas dans canauxActifs (canauxActifs non vide)") - void testCanalPasDansActifs() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setCanauxActifs(Set.of(CanalNotification.REMINDER_CHANNEL)); - assertThat(dto.isCanalActif(CanalNotification.DEFAULT_CHANNEL)).isFalse(); - } - - @Test - @DisplayName("retourne true quand canauxDesactives non null (mais vide) et canauxActifs null") - void testCanauxDesactivesVideCanauxActifsNull() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setCanauxActifs(null); - dto.setCanauxDesactives(Set.of()); - assertThat(dto.isCanalActif(CanalNotification.DEFAULT_CHANNEL)).isTrue(); - } - } - - @Nested - @DisplayName("isEnModeSilencieux (package)") - class IsEnModeSilencieux { - - @Test - @DisplayName("retourne false quand modeSilencieux false") - void testModeDesactive() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setModeSilencieux(false); - assertThat(dto.isEnModeSilencieux(LocalTime.NOON)).isFalse(); - } - - @Test - @DisplayName("retourne false quand heureDebut ou heureFin null") - void testHeuresNull() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setModeSilencieux(true); - dto.setHeureDebutSilencieux(null); - dto.setHeureFinSilencieux(LocalTime.of(18, 0)); - assertThat(dto.isEnModeSilencieux(LocalTime.NOON)).isFalse(); - dto.setHeureDebutSilencieux(LocalTime.of(22, 0)); - dto.setHeureFinSilencieux(null); - assertThat(dto.isEnModeSilencieux(LocalTime.of(23, 0))).isFalse(); - } - - @Test - @DisplayName("période normale (début < fin): true dans la plage") - void testPlageNormaleDansPlage() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setModeSilencieux(true); - dto.setHeureDebutSilencieux(LocalTime.of(9, 0)); - dto.setHeureFinSilencieux(LocalTime.of(12, 0)); - assertThat(dto.isEnModeSilencieux(LocalTime.of(10, 30))).isTrue(); - } - - @Test - @DisplayName("période normale: false en dehors de la plage") - void testPlageNormaleHorsPlage() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setModeSilencieux(true); - dto.setHeureDebutSilencieux(LocalTime.of(9, 0)); - dto.setHeureFinSilencieux(LocalTime.of(12, 0)); - assertThat(dto.isEnModeSilencieux(LocalTime.of(8, 0))).isFalse(); - assertThat(dto.isEnModeSilencieux(LocalTime.of(13, 0))).isFalse(); - assertThat(dto.isEnModeSilencieux(LocalTime.of(9, 0))).isFalse(); - assertThat(dto.isEnModeSilencieux(LocalTime.of(12, 0))).isFalse(); - } - - @Test - @DisplayName("période traverse minuit (début > fin): true après début ou avant fin") - void testTraverseMinuit() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setModeSilencieux(true); - dto.setHeureDebutSilencieux(LocalTime.of(22, 0)); - dto.setHeureFinSilencieux(LocalTime.of(7, 0)); - assertThat(dto.isEnModeSilencieux(LocalTime.of(23, 0))).isTrue(); - assertThat(dto.isEnModeSilencieux(LocalTime.of(2, 0))).isTrue(); - } - - @Test - @DisplayName("période traverse minuit: false entre fin et début") - void testTraverseMinuitHorsPlage() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setModeSilencieux(true); - dto.setHeureDebutSilencieux(LocalTime.of(22, 0)); - dto.setHeureFinSilencieux(LocalTime.of(7, 0)); - assertThat(dto.isEnModeSilencieux(LocalTime.of(10, 0))).isFalse(); - } - - @Test - @DisplayName("méthode publique sans paramètre appelle version avec LocalTime.now()") - void testPublicNoArg() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setModeSilencieux(false); - // Devrait retourner false car modeSilencieux est false - assertThat(dto.isEnModeSilencieux()).isFalse(); - } - } - - @Nested - @DisplayName("isExpediteurBloque") - class IsExpediteurBloque { - - @Test - @DisplayName("retourne false quand expediteursBloqués null") - void testNull() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setExpediteursBloques(null); - assertThat(dto.isExpediteurBloque("exp-1")).isFalse(); - } - - @Test - @DisplayName("retourne true quand expediteur dans la liste") - void testBloque() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setExpediteursBloques(Set.of("exp-1", "exp-2")); - assertThat(dto.isExpediteurBloque("exp-1")).isTrue(); - } - - @Test - @DisplayName("retourne false quand expediteur pas dans la liste") - void testPasBloque() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setExpediteursBloques(Set.of("exp-1")); - assertThat(dto.isExpediteurBloque("exp-2")).isFalse(); - } - } - - @Nested - @DisplayName("isExpediteurPrioritaire") - class IsExpediteurPrioritaire { - - @Test - @DisplayName("retourne false quand expediteursPrioritaires null") - void testNull() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setExpediteursPrioritaires(null); - assertThat(dto.isExpediteurPrioritaire("exp-1")).isFalse(); - } - - @Test - @DisplayName("retourne true quand expediteur dans la liste") - void testPrioritaire() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setExpediteursPrioritaires(Set.of("exp-1")); - assertThat(dto.isExpediteurPrioritaire("exp-1")).isTrue(); - } - - @Test - @DisplayName("retourne false quand expediteur pas dans la liste") - void testPasPrioritaire() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - dto.setExpediteursPrioritaires(Set.of("exp-1")); - assertThat(dto.isExpediteurPrioritaire("exp-2")).isFalse(); - } - } - - @Nested - @DisplayName("toString") - class ToString { - - @Test - @DisplayName("contient utilisateurId et notificationsActivees") - void testToString() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO("u1"); - String s = dto.toString(); - assertThat(s).contains("u1"); - assertThat(s).contains("true"); - } - } - - @Nested - @DisplayName("Getters et Setters") - class GettersEtSetters { - - @Test - @DisplayName("tous les getters et setters fonctionnent correctement") - void testTousLesGettersSetters() { - PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); - - // Test id - dto.setId("pref-123"); - assertThat(dto.getId()).isEqualTo("pref-123"); - - // Test utilisateurId - dto.setUtilisateurId("user-789"); - assertThat(dto.getUtilisateurId()).isEqualTo("user-789"); - - // Test organisationId - dto.setOrganisationId("org-456"); - assertThat(dto.getOrganisationId()).isEqualTo("org-456"); - - // Test pushActivees - dto.setPushActivees(false); - assertThat(dto.getPushActivees()).isFalse(); - - // Test emailActivees - dto.setEmailActivees(false); - assertThat(dto.getEmailActivees()).isFalse(); - - // Test smsActivees - dto.setSmsActivees(true); - assertThat(dto.getSmsActivees()).isTrue(); - - // Test inAppActivees - dto.setInAppActivees(false); - assertThat(dto.getInAppActivees()).isFalse(); - - // Test typesActives - Set types = Set.of(TypeNotification.EMAIL); - dto.setTypesActives(types); - assertThat(dto.getTypesActives()).isEqualTo(types); - - // Test typesDesactivees - Set typesDesac = Set.of(TypeNotification.IN_APP); - dto.setTypesDesactivees(typesDesac); - assertThat(dto.getTypesDesactivees()).isEqualTo(typesDesac); - - // Test canauxActifs - Set canaux = Set.of(CanalNotification.DEFAULT_CHANNEL); - dto.setCanauxActifs(canaux); - assertThat(dto.getCanauxActifs()).isEqualTo(canaux); - - // Test canauxDesactives - Set canauxDesac = Set.of(CanalNotification.REMINDER_CHANNEL); - dto.setCanauxDesactives(canauxDesac); - assertThat(dto.getCanauxDesactives()).isEqualTo(canauxDesac); - - // Test heureDebutSilencieux - dto.setHeureDebutSilencieux(LocalTime.of(22, 30)); - assertThat(dto.getHeureDebutSilencieux()).isEqualTo(LocalTime.of(22, 30)); - - // Test heureFinSilencieux - dto.setHeureFinSilencieux(LocalTime.of(7, 0)); - assertThat(dto.getHeureFinSilencieux()).isEqualTo(LocalTime.of(7, 0)); - - // Test joursSilencieux - Set jours = Set.of(1, 2, 3, 4, 5); - dto.setJoursSilencieux(jours); - assertThat(dto.getJoursSilencieux()).isEqualTo(jours); - - // Test urgentesIgnorentSilencieux - dto.setUrgentesIgnorentSilencieux(false); - assertThat(dto.getUrgentesIgnorentSilencieux()).isFalse(); - - // Test frequenceRegroupementMinutes - dto.setFrequenceRegroupementMinutes(15); - assertThat(dto.getFrequenceRegroupementMinutes()).isEqualTo(15); - - // Test maxNotificationsSimultanees - dto.setMaxNotificationsSimultanees(20); - assertThat(dto.getMaxNotificationsSimultanees()).isEqualTo(20); - - // Test dureeAffichageSecondes - dto.setDureeAffichageSecondes(5); - assertThat(dto.getDureeAffichageSecondes()).isEqualTo(5); - - // Test langue - dto.setLangue("en"); - assertThat(dto.getLangue()).isEqualTo("en"); - - // Test vibrationActivee - dto.setVibrationActivee(false); - assertThat(dto.getVibrationActivee()).isFalse(); - - // Test sonActive - dto.setSonActive(false); - assertThat(dto.getSonActive()).isFalse(); - - // Test ledActivee - dto.setLedActivee(false); - assertThat(dto.getLedActivee()).isFalse(); - - // Test sonPersonnalise - dto.setSonPersonnalise("custom_sound.mp3"); - assertThat(dto.getSonPersonnalise()).isEqualTo("custom_sound.mp3"); - - // Test patternVibrationPersonnalise - long[] pattern = new long[]{100L, 200L, 300L}; - dto.setPatternVibrationPersonnalise(pattern); - assertThat(dto.getPatternVibrationPersonnalise()).isEqualTo(pattern); - - // Test couleurLEDPersonnalisee - dto.setCouleurLEDPersonnalisee("#FF5733"); - assertThat(dto.getCouleurLEDPersonnalisee()).isEqualTo("#FF5733"); - - // Test apercuEcranVerrouillage - dto.setApercuEcranVerrouillage(false); - assertThat(dto.getApercuEcranVerrouillage()).isFalse(); - - // Test affichageHistorique - dto.setAffichageHistorique(false); - assertThat(dto.getAffichageHistorique()).isFalse(); - - // Test dureeConservationJours - dto.setDureeConservationJours(60); - assertThat(dto.getDureeConservationJours()).isEqualTo(60); - - // Test marquageLectureAutomatique - dto.setMarquageLectureAutomatique(true); - assertThat(dto.getMarquageLectureAutomatique()).isTrue(); - - // Test delaiMarquageLectureSecondes - dto.setDelaiMarquageLectureSecondes(30); - assertThat(dto.getDelaiMarquageLectureSecondes()).isEqualTo(30); - - // Test archivageAutomatique - dto.setArchivageAutomatique(false); - assertThat(dto.getArchivageAutomatique()).isFalse(); - - // Test delaiArchivageHeures - dto.setDelaiArchivageHeures(72); - assertThat(dto.getDelaiArchivageHeures()).isEqualTo(72); - - // Test preferencesParType - java.util.Map prefsType = new java.util.HashMap<>(); - prefsType.put(TypeNotification.EMAIL, new PreferenceTypeNotificationDTO()); - dto.setPreferencesParType(prefsType); - assertThat(dto.getPreferencesParType()).isEqualTo(prefsType); - - // Test preferencesParCanal - java.util.Map prefsCanal = new java.util.HashMap<>(); - prefsCanal.put(CanalNotification.DEFAULT_CHANNEL, new PreferenceCanalNotificationDTO()); - dto.setPreferencesParCanal(prefsCanal); - assertThat(dto.getPreferencesParCanal()).isEqualTo(prefsCanal); - - // Test motsClesFiltre - Set motsCles = Set.of("urgent", "important"); - dto.setMotsClesFiltre(motsCles); - assertThat(dto.getMotsClesFiltre()).isEqualTo(motsCles); - - // Test expediteursBloques - Set bloques = Set.of("exp-block-1", "exp-block-2"); - dto.setExpediteursBloques(bloques); - assertThat(dto.getExpediteursBloques()).isEqualTo(bloques); - - // Test expediteursPrioritaires - Set prioritaires = Set.of("exp-prio-1", "exp-prio-2"); - dto.setExpediteursPrioritaires(prioritaires); - assertThat(dto.getExpediteursPrioritaires()).isEqualTo(prioritaires); - - // Test notificationsTestActivees - dto.setNotificationsTestActivees(true); - assertThat(dto.getNotificationsTestActivees()).isTrue(); - - // Test niveauLog - dto.setNiveauLog("DEBUG"); - assertThat(dto.getNiveauLog()).isEqualTo("DEBUG"); - - // Test tokenFCM - dto.setTokenFCM("fcm-token-12345"); - assertThat(dto.getTokenFCM()).isEqualTo("fcm-token-12345"); - - // Test plateforme - dto.setPlateforme("android"); - assertThat(dto.getPlateforme()).isEqualTo("android"); - - // Test versionApp - dto.setVersionApp("1.2.3"); - assertThat(dto.getVersionApp()).isEqualTo("1.2.3"); - - // Test fuseauHoraire - dto.setFuseauHoraire("Europe/Paris"); - assertThat(dto.getFuseauHoraire()).isEqualTo("Europe/Paris"); - - // Test metadonnees - java.util.Map metadata = new java.util.HashMap<>(); - metadata.put("custom_key", "custom_value"); - dto.setMetadonnees(metadata); - assertThat(dto.getMetadonnees()).isEqualTo(metadata); - } - } -} +package dev.lions.unionflow.server.api.dto.notification; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalTime; +import java.util.Set; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import dev.lions.unionflow.server.api.enums.notification.CanalNotification; +import dev.lions.unionflow.server.api.enums.notification.TypeNotification; + +/** + * Tests unitaires pour PreferencesNotificationDTO. + * Couvre constructeur(String), isTypeActive (toutes branches), isCanalActif (toutes branches), + * isEnModeSilencieux(LocalTime) (traverse minuit, plage normale, null), + * isExpediteurBloque, isExpediteurPrioritaire, toString. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests PreferencesNotificationDTO") +class PreferencesNotificationDTOTest { + + @Nested + @DisplayName("Constructeurs") + class Constructeurs { + + @Test + @DisplayName("constructeur par défaut initialise les champs") + void testConstructeurParDefaut() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + assertThat(dto.getNotificationsActivees()).isTrue(); + assertThat(dto.getPushActivees()).isTrue(); + assertThat(dto.getEmailActivees()).isTrue(); + assertThat(dto.getSmsActivees()).isFalse(); + assertThat(dto.getInAppActivees()).isTrue(); + assertThat(dto.getModeSilencieux()).isFalse(); + assertThat(dto.getFrequenceRegroupementMinutes()).isEqualTo(5); + assertThat(dto.getMaxNotificationsSimultanees()).isEqualTo(10); + assertThat(dto.getDureeAffichageSecondes()).isEqualTo(10); + assertThat(dto.getLangue()).isEqualTo("fr"); + } + + @Test + @DisplayName("constructeur avec utilisateurId appelle this() et set utilisateurId") + void testConstructeurAvecUtilisateur() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO("user-123"); + assertThat(dto.getUtilisateurId()).isEqualTo("user-123"); + assertThat(dto.getNotificationsActivees()).isTrue(); + } + } + + @Nested + @DisplayName("isTypeActive") + class IsTypeActive { + + @Test + @DisplayName("retourne false quand notificationsActivees false") + void testNotificationsDesactivees() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setNotificationsActivees(false); + assertThat(dto.isTypeActive(TypeNotification.EMAIL)).isFalse(); + } + + @Test + @DisplayName("retourne false quand type dans typesDesactivees") + void testTypeDesactive() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setTypesDesactivees(Set.of(TypeNotification.EMAIL)); + assertThat(dto.isTypeActive(TypeNotification.EMAIL)).isFalse(); + } + + @Test + @DisplayName("retourne true quand type dans typesActives") + void testTypeActif() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setTypesActives(Set.of(TypeNotification.EMAIL)); + assertThat(dto.isTypeActive(TypeNotification.EMAIL)).isTrue(); + } + + @Test + @DisplayName("retourne type.isActiveeParDefaut() quand typesActives null et type pas dans typesDesactivees") + void testDefautType() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setTypesActives(null); + dto.setTypesDesactivees(null); + TypeNotification type = TypeNotification.EMAIL; + assertThat(dto.isTypeActive(type)).isEqualTo(type.isActiveeParDefaut()); + } + + @Test + @DisplayName("retourne false quand type pas dans typesActives (typesActives non vide)") + void testTypePasDansActives() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setTypesActives(Set.of(TypeNotification.IN_APP)); + assertThat(dto.isTypeActive(TypeNotification.EMAIL)).isFalse(); + } + + @Test + @DisplayName("retourne type.isActiveeParDefaut() quand typesDesactivees non null (mais vide) et typesActives null") + void testTypesDesactiveesVideTypesActivesNull() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setTypesActives(null); + dto.setTypesDesactivees(Set.of()); + TypeNotification type = TypeNotification.EMAIL; + assertThat(dto.isTypeActive(type)).isEqualTo(type.isActiveeParDefaut()); + } + } + + @Nested + @DisplayName("isCanalActif") + class IsCanalActif { + + @Test + @DisplayName("retourne false quand notificationsActivees false") + void testNotificationsDesactivees() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setNotificationsActivees(false); + assertThat(dto.isCanalActif(CanalNotification.DEFAULT_CHANNEL)).isFalse(); + } + + @Test + @DisplayName("retourne false quand canal dans canauxDesactives") + void testCanalDesactive() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setCanauxDesactives(Set.of(CanalNotification.DEFAULT_CHANNEL)); + assertThat(dto.isCanalActif(CanalNotification.DEFAULT_CHANNEL)).isFalse(); + } + + @Test + @DisplayName("retourne true quand canal dans canauxActifs") + void testCanalActif() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setCanauxActifs(Set.of(CanalNotification.DEFAULT_CHANNEL)); + assertThat(dto.isCanalActif(CanalNotification.DEFAULT_CHANNEL)).isTrue(); + } + + @Test + @DisplayName("retourne true quand canauxActifs null (défaut)") + void testCanauxActifsNull() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setCanauxActifs(null); + dto.setCanauxDesactives(null); + assertThat(dto.isCanalActif(CanalNotification.DEFAULT_CHANNEL)).isTrue(); + } + + @Test + @DisplayName("retourne false quand canal pas dans canauxActifs (canauxActifs non vide)") + void testCanalPasDansActifs() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setCanauxActifs(Set.of(CanalNotification.REMINDER_CHANNEL)); + assertThat(dto.isCanalActif(CanalNotification.DEFAULT_CHANNEL)).isFalse(); + } + + @Test + @DisplayName("retourne true quand canauxDesactives non null (mais vide) et canauxActifs null") + void testCanauxDesactivesVideCanauxActifsNull() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setCanauxActifs(null); + dto.setCanauxDesactives(Set.of()); + assertThat(dto.isCanalActif(CanalNotification.DEFAULT_CHANNEL)).isTrue(); + } + } + + @Nested + @DisplayName("isEnModeSilencieux (package)") + class IsEnModeSilencieux { + + @Test + @DisplayName("retourne false quand modeSilencieux false") + void testModeDesactive() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setModeSilencieux(false); + assertThat(dto.isEnModeSilencieux(LocalTime.NOON)).isFalse(); + } + + @Test + @DisplayName("retourne false quand heureDebut ou heureFin null") + void testHeuresNull() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setModeSilencieux(true); + dto.setHeureDebutSilencieux(null); + dto.setHeureFinSilencieux(LocalTime.of(18, 0)); + assertThat(dto.isEnModeSilencieux(LocalTime.NOON)).isFalse(); + dto.setHeureDebutSilencieux(LocalTime.of(22, 0)); + dto.setHeureFinSilencieux(null); + assertThat(dto.isEnModeSilencieux(LocalTime.of(23, 0))).isFalse(); + } + + @Test + @DisplayName("période normale (début < fin): true dans la plage") + void testPlageNormaleDansPlage() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setModeSilencieux(true); + dto.setHeureDebutSilencieux(LocalTime.of(9, 0)); + dto.setHeureFinSilencieux(LocalTime.of(12, 0)); + assertThat(dto.isEnModeSilencieux(LocalTime.of(10, 30))).isTrue(); + } + + @Test + @DisplayName("période normale: false en dehors de la plage") + void testPlageNormaleHorsPlage() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setModeSilencieux(true); + dto.setHeureDebutSilencieux(LocalTime.of(9, 0)); + dto.setHeureFinSilencieux(LocalTime.of(12, 0)); + assertThat(dto.isEnModeSilencieux(LocalTime.of(8, 0))).isFalse(); + assertThat(dto.isEnModeSilencieux(LocalTime.of(13, 0))).isFalse(); + assertThat(dto.isEnModeSilencieux(LocalTime.of(9, 0))).isFalse(); + assertThat(dto.isEnModeSilencieux(LocalTime.of(12, 0))).isFalse(); + } + + @Test + @DisplayName("période traverse minuit (début > fin): true après début ou avant fin") + void testTraverseMinuit() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setModeSilencieux(true); + dto.setHeureDebutSilencieux(LocalTime.of(22, 0)); + dto.setHeureFinSilencieux(LocalTime.of(7, 0)); + assertThat(dto.isEnModeSilencieux(LocalTime.of(23, 0))).isTrue(); + assertThat(dto.isEnModeSilencieux(LocalTime.of(2, 0))).isTrue(); + } + + @Test + @DisplayName("période traverse minuit: false entre fin et début") + void testTraverseMinuitHorsPlage() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setModeSilencieux(true); + dto.setHeureDebutSilencieux(LocalTime.of(22, 0)); + dto.setHeureFinSilencieux(LocalTime.of(7, 0)); + assertThat(dto.isEnModeSilencieux(LocalTime.of(10, 0))).isFalse(); + } + + @Test + @DisplayName("méthode publique sans paramètre appelle version avec LocalTime.now()") + void testPublicNoArg() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setModeSilencieux(false); + // Devrait retourner false car modeSilencieux est false + assertThat(dto.isEnModeSilencieux()).isFalse(); + } + } + + @Nested + @DisplayName("isExpediteurBloque") + class IsExpediteurBloque { + + @Test + @DisplayName("retourne false quand expediteursBloqués null") + void testNull() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setExpediteursBloques(null); + assertThat(dto.isExpediteurBloque("exp-1")).isFalse(); + } + + @Test + @DisplayName("retourne true quand expediteur dans la liste") + void testBloque() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setExpediteursBloques(Set.of("exp-1", "exp-2")); + assertThat(dto.isExpediteurBloque("exp-1")).isTrue(); + } + + @Test + @DisplayName("retourne false quand expediteur pas dans la liste") + void testPasBloque() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setExpediteursBloques(Set.of("exp-1")); + assertThat(dto.isExpediteurBloque("exp-2")).isFalse(); + } + } + + @Nested + @DisplayName("isExpediteurPrioritaire") + class IsExpediteurPrioritaire { + + @Test + @DisplayName("retourne false quand expediteursPrioritaires null") + void testNull() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setExpediteursPrioritaires(null); + assertThat(dto.isExpediteurPrioritaire("exp-1")).isFalse(); + } + + @Test + @DisplayName("retourne true quand expediteur dans la liste") + void testPrioritaire() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setExpediteursPrioritaires(Set.of("exp-1")); + assertThat(dto.isExpediteurPrioritaire("exp-1")).isTrue(); + } + + @Test + @DisplayName("retourne false quand expediteur pas dans la liste") + void testPasPrioritaire() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + dto.setExpediteursPrioritaires(Set.of("exp-1")); + assertThat(dto.isExpediteurPrioritaire("exp-2")).isFalse(); + } + } + + @Nested + @DisplayName("toString") + class ToString { + + @Test + @DisplayName("contient utilisateurId et notificationsActivees") + void testToString() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO("u1"); + String s = dto.toString(); + assertThat(s).contains("u1"); + assertThat(s).contains("true"); + } + } + + @Nested + @DisplayName("Getters et Setters") + class GettersEtSetters { + + @Test + @DisplayName("tous les getters et setters fonctionnent correctement") + void testTousLesGettersSetters() { + PreferencesNotificationDTO dto = new PreferencesNotificationDTO(); + + // Test id + dto.setId("pref-123"); + assertThat(dto.getId()).isEqualTo("pref-123"); + + // Test utilisateurId + dto.setUtilisateurId("user-789"); + assertThat(dto.getUtilisateurId()).isEqualTo("user-789"); + + // Test organisationId + dto.setOrganisationId("org-456"); + assertThat(dto.getOrganisationId()).isEqualTo("org-456"); + + // Test pushActivees + dto.setPushActivees(false); + assertThat(dto.getPushActivees()).isFalse(); + + // Test emailActivees + dto.setEmailActivees(false); + assertThat(dto.getEmailActivees()).isFalse(); + + // Test smsActivees + dto.setSmsActivees(true); + assertThat(dto.getSmsActivees()).isTrue(); + + // Test inAppActivees + dto.setInAppActivees(false); + assertThat(dto.getInAppActivees()).isFalse(); + + // Test typesActives + Set types = Set.of(TypeNotification.EMAIL); + dto.setTypesActives(types); + assertThat(dto.getTypesActives()).isEqualTo(types); + + // Test typesDesactivees + Set typesDesac = Set.of(TypeNotification.IN_APP); + dto.setTypesDesactivees(typesDesac); + assertThat(dto.getTypesDesactivees()).isEqualTo(typesDesac); + + // Test canauxActifs + Set canaux = Set.of(CanalNotification.DEFAULT_CHANNEL); + dto.setCanauxActifs(canaux); + assertThat(dto.getCanauxActifs()).isEqualTo(canaux); + + // Test canauxDesactives + Set canauxDesac = Set.of(CanalNotification.REMINDER_CHANNEL); + dto.setCanauxDesactives(canauxDesac); + assertThat(dto.getCanauxDesactives()).isEqualTo(canauxDesac); + + // Test heureDebutSilencieux + dto.setHeureDebutSilencieux(LocalTime.of(22, 30)); + assertThat(dto.getHeureDebutSilencieux()).isEqualTo(LocalTime.of(22, 30)); + + // Test heureFinSilencieux + dto.setHeureFinSilencieux(LocalTime.of(7, 0)); + assertThat(dto.getHeureFinSilencieux()).isEqualTo(LocalTime.of(7, 0)); + + // Test joursSilencieux + Set jours = Set.of(1, 2, 3, 4, 5); + dto.setJoursSilencieux(jours); + assertThat(dto.getJoursSilencieux()).isEqualTo(jours); + + // Test urgentesIgnorentSilencieux + dto.setUrgentesIgnorentSilencieux(false); + assertThat(dto.getUrgentesIgnorentSilencieux()).isFalse(); + + // Test frequenceRegroupementMinutes + dto.setFrequenceRegroupementMinutes(15); + assertThat(dto.getFrequenceRegroupementMinutes()).isEqualTo(15); + + // Test maxNotificationsSimultanees + dto.setMaxNotificationsSimultanees(20); + assertThat(dto.getMaxNotificationsSimultanees()).isEqualTo(20); + + // Test dureeAffichageSecondes + dto.setDureeAffichageSecondes(5); + assertThat(dto.getDureeAffichageSecondes()).isEqualTo(5); + + // Test langue + dto.setLangue("en"); + assertThat(dto.getLangue()).isEqualTo("en"); + + // Test vibrationActivee + dto.setVibrationActivee(false); + assertThat(dto.getVibrationActivee()).isFalse(); + + // Test sonActive + dto.setSonActive(false); + assertThat(dto.getSonActive()).isFalse(); + + // Test ledActivee + dto.setLedActivee(false); + assertThat(dto.getLedActivee()).isFalse(); + + // Test sonPersonnalise + dto.setSonPersonnalise("custom_sound.mp3"); + assertThat(dto.getSonPersonnalise()).isEqualTo("custom_sound.mp3"); + + // Test patternVibrationPersonnalise + long[] pattern = new long[]{100L, 200L, 300L}; + dto.setPatternVibrationPersonnalise(pattern); + assertThat(dto.getPatternVibrationPersonnalise()).isEqualTo(pattern); + + // Test couleurLEDPersonnalisee + dto.setCouleurLEDPersonnalisee("#FF5733"); + assertThat(dto.getCouleurLEDPersonnalisee()).isEqualTo("#FF5733"); + + // Test apercuEcranVerrouillage + dto.setApercuEcranVerrouillage(false); + assertThat(dto.getApercuEcranVerrouillage()).isFalse(); + + // Test affichageHistorique + dto.setAffichageHistorique(false); + assertThat(dto.getAffichageHistorique()).isFalse(); + + // Test dureeConservationJours + dto.setDureeConservationJours(60); + assertThat(dto.getDureeConservationJours()).isEqualTo(60); + + // Test marquageLectureAutomatique + dto.setMarquageLectureAutomatique(true); + assertThat(dto.getMarquageLectureAutomatique()).isTrue(); + + // Test delaiMarquageLectureSecondes + dto.setDelaiMarquageLectureSecondes(30); + assertThat(dto.getDelaiMarquageLectureSecondes()).isEqualTo(30); + + // Test archivageAutomatique + dto.setArchivageAutomatique(false); + assertThat(dto.getArchivageAutomatique()).isFalse(); + + // Test delaiArchivageHeures + dto.setDelaiArchivageHeures(72); + assertThat(dto.getDelaiArchivageHeures()).isEqualTo(72); + + // Test preferencesParType + java.util.Map prefsType = new java.util.HashMap<>(); + prefsType.put(TypeNotification.EMAIL, new PreferenceTypeNotificationDTO()); + dto.setPreferencesParType(prefsType); + assertThat(dto.getPreferencesParType()).isEqualTo(prefsType); + + // Test preferencesParCanal + java.util.Map prefsCanal = new java.util.HashMap<>(); + prefsCanal.put(CanalNotification.DEFAULT_CHANNEL, new PreferenceCanalNotificationDTO()); + dto.setPreferencesParCanal(prefsCanal); + assertThat(dto.getPreferencesParCanal()).isEqualTo(prefsCanal); + + // Test motsClesFiltre + Set motsCles = Set.of("urgent", "important"); + dto.setMotsClesFiltre(motsCles); + assertThat(dto.getMotsClesFiltre()).isEqualTo(motsCles); + + // Test expediteursBloques + Set bloques = Set.of("exp-block-1", "exp-block-2"); + dto.setExpediteursBloques(bloques); + assertThat(dto.getExpediteursBloques()).isEqualTo(bloques); + + // Test expediteursPrioritaires + Set prioritaires = Set.of("exp-prio-1", "exp-prio-2"); + dto.setExpediteursPrioritaires(prioritaires); + assertThat(dto.getExpediteursPrioritaires()).isEqualTo(prioritaires); + + // Test notificationsTestActivees + dto.setNotificationsTestActivees(true); + assertThat(dto.getNotificationsTestActivees()).isTrue(); + + // Test niveauLog + dto.setNiveauLog("DEBUG"); + assertThat(dto.getNiveauLog()).isEqualTo("DEBUG"); + + // Test tokenFCM + dto.setTokenFCM("fcm-token-12345"); + assertThat(dto.getTokenFCM()).isEqualTo("fcm-token-12345"); + + // Test plateforme + dto.setPlateforme("android"); + assertThat(dto.getPlateforme()).isEqualTo("android"); + + // Test versionApp + dto.setVersionApp("1.2.3"); + assertThat(dto.getVersionApp()).isEqualTo("1.2.3"); + + // Test fuseauHoraire + dto.setFuseauHoraire("Europe/Paris"); + assertThat(dto.getFuseauHoraire()).isEqualTo("Europe/Paris"); + + // Test metadonnees + java.util.Map metadata = new java.util.HashMap<>(); + metadata.put("custom_key", "custom_value"); + dto.setMetadonnees(metadata); + assertThat(dto.getMetadonnees()).isEqualTo(metadata); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/CreateNotificationRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/CreateNotificationRequestTest.java index 235f12d..89de171 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/CreateNotificationRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/CreateNotificationRequestTest.java @@ -1,130 +1,130 @@ -package dev.lions.unionflow.server.api.dto.notification.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.time.LocalDateTime; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateNotificationRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID membreId = UUID.randomUUID(); - UUID organisationId = UUID.randomUUID(); - UUID templateId = UUID.randomUUID(); - LocalDateTime dateEnvoi = LocalDateTime.now().plusDays(1); - - CreateNotificationRequest request = CreateNotificationRequest.builder() - .typeNotification("EMAIL") - .priorite("HAUTE") - .sujet("Notification importante") - .corps("Corps du message") - .dateEnvoiPrevue(dateEnvoi) - .donneesAdditionnelles("{\"key\":\"value\"}") - .membreId(membreId) - .organisationId(organisationId) - .templateId(templateId) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.typeNotification()).isEqualTo("EMAIL"); - assertThat(request.priorite()).isEqualTo("HAUTE"); - assertThat(request.sujet()).isEqualTo("Notification importante"); - assertThat(request.corps()).isEqualTo("Corps du message"); - assertThat(request.dateEnvoiPrevue()).isEqualTo(dateEnvoi); - assertThat(request.donneesAdditionnelles()).isEqualTo("{\"key\":\"value\"}"); - assertThat(request.membreId()).isEqualTo(membreId); - assertThat(request.organisationId()).isEqualTo(organisationId); - assertThat(request.templateId()).isEqualTo(templateId); - } - - @Test - void testBuilder_MinimalFields() { - CreateNotificationRequest request = CreateNotificationRequest.builder() - .typeNotification("SMS") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.typeNotification()).isEqualTo("SMS"); - assertThat(request.priorite()).isNull(); - assertThat(request.sujet()).isNull(); - assertThat(request.corps()).isNull(); - assertThat(request.dateEnvoiPrevue()).isNull(); - assertThat(request.donneesAdditionnelles()).isNull(); - assertThat(request.membreId()).isNull(); - assertThat(request.organisationId()).isNull(); - assertThat(request.templateId()).isNull(); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateNotificationRequest request = CreateNotificationRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeNotification")); - } - - @Test - void testValidation_ValidFields() { - CreateNotificationRequest request = CreateNotificationRequest.builder() - .typeNotification("PUSH") - .priorite("NORMALE") - .sujet("Sujet") - .corps("Corps") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID membreId = UUID.randomUUID(); - - CreateNotificationRequest request1 = CreateNotificationRequest.builder() - .typeNotification("EMAIL") - .membreId(membreId) - .build(); - - CreateNotificationRequest request2 = CreateNotificationRequest.builder() - .typeNotification("EMAIL") - .membreId(membreId) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateNotificationRequest request = CreateNotificationRequest.builder() - .typeNotification("EMAIL") - .sujet("Test") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateNotificationRequest"); - assertThat(toString).contains("EMAIL"); - assertThat(toString).contains("Test"); - } -} +package dev.lions.unionflow.server.api.dto.notification.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.time.LocalDateTime; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateNotificationRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID membreId = UUID.randomUUID(); + UUID organisationId = UUID.randomUUID(); + UUID templateId = UUID.randomUUID(); + LocalDateTime dateEnvoi = LocalDateTime.now().plusDays(1); + + CreateNotificationRequest request = CreateNotificationRequest.builder() + .typeNotification("EMAIL") + .priorite("HAUTE") + .sujet("Notification importante") + .corps("Corps du message") + .dateEnvoiPrevue(dateEnvoi) + .donneesAdditionnelles("{\"key\":\"value\"}") + .membreId(membreId) + .organisationId(organisationId) + .templateId(templateId) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.typeNotification()).isEqualTo("EMAIL"); + assertThat(request.priorite()).isEqualTo("HAUTE"); + assertThat(request.sujet()).isEqualTo("Notification importante"); + assertThat(request.corps()).isEqualTo("Corps du message"); + assertThat(request.dateEnvoiPrevue()).isEqualTo(dateEnvoi); + assertThat(request.donneesAdditionnelles()).isEqualTo("{\"key\":\"value\"}"); + assertThat(request.membreId()).isEqualTo(membreId); + assertThat(request.organisationId()).isEqualTo(organisationId); + assertThat(request.templateId()).isEqualTo(templateId); + } + + @Test + void testBuilder_MinimalFields() { + CreateNotificationRequest request = CreateNotificationRequest.builder() + .typeNotification("SMS") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.typeNotification()).isEqualTo("SMS"); + assertThat(request.priorite()).isNull(); + assertThat(request.sujet()).isNull(); + assertThat(request.corps()).isNull(); + assertThat(request.dateEnvoiPrevue()).isNull(); + assertThat(request.donneesAdditionnelles()).isNull(); + assertThat(request.membreId()).isNull(); + assertThat(request.organisationId()).isNull(); + assertThat(request.templateId()).isNull(); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateNotificationRequest request = CreateNotificationRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeNotification")); + } + + @Test + void testValidation_ValidFields() { + CreateNotificationRequest request = CreateNotificationRequest.builder() + .typeNotification("PUSH") + .priorite("NORMALE") + .sujet("Sujet") + .corps("Corps") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID membreId = UUID.randomUUID(); + + CreateNotificationRequest request1 = CreateNotificationRequest.builder() + .typeNotification("EMAIL") + .membreId(membreId) + .build(); + + CreateNotificationRequest request2 = CreateNotificationRequest.builder() + .typeNotification("EMAIL") + .membreId(membreId) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateNotificationRequest request = CreateNotificationRequest.builder() + .typeNotification("EMAIL") + .sujet("Test") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateNotificationRequest"); + assertThat(toString).contains("EMAIL"); + assertThat(toString).contains("Test"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/CreateTemplateNotificationRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/CreateTemplateNotificationRequestTest.java index 1331de2..89c8f6a 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/CreateTemplateNotificationRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/CreateTemplateNotificationRequestTest.java @@ -1,145 +1,145 @@ -package dev.lions.unionflow.server.api.dto.notification.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateTemplateNotificationRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder() - .code("WELCOME_EMAIL") - .sujet("Bienvenue sur UnionFlow") - .corpsTexte("Bonjour {{prenom}},\nBienvenue!") - .corpsHtml("

Bienvenue {{prenom}}

") - .variablesDisponibles("prenom,nom,email") - .canauxSupportes("EMAIL,SMS") - .langue("fr") - .description("Template de bienvenue") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.code()).isEqualTo("WELCOME_EMAIL"); - assertThat(request.sujet()).isEqualTo("Bienvenue sur UnionFlow"); - assertThat(request.corpsTexte()).contains("Bonjour"); - assertThat(request.corpsHtml()).contains("

"); - assertThat(request.variablesDisponibles()).isEqualTo("prenom,nom,email"); - assertThat(request.canauxSupportes()).isEqualTo("EMAIL,SMS"); - assertThat(request.langue()).isEqualTo("fr"); - assertThat(request.description()).isEqualTo("Template de bienvenue"); - } - - @Test - void testBuilder_MinimalFields() { - CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder() - .code("SIMPLE_NOTIF") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.code()).isEqualTo("SIMPLE_NOTIF"); - assertThat(request.sujet()).isNull(); - assertThat(request.corpsTexte()).isNull(); - assertThat(request.corpsHtml()).isNull(); - assertThat(request.variablesDisponibles()).isNull(); - assertThat(request.canauxSupportes()).isNull(); - assertThat(request.langue()).isNull(); - assertThat(request.description()).isNull(); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder().build(); - - Set> violations = - validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - } - - @Test - void testValidation_EmptyCode() { - CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder() - .code("") - .build(); - - Set> violations = - validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - } - - @Test - void testValidation_BlankCode() { - CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder() - .code(" ") - .build(); - - Set> violations = - validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - } - - @Test - void testValidation_ValidFields() { - CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder() - .code("VALID_CODE") - .sujet("Sujet") - .corpsTexte("Corps") - .build(); - - Set> violations = - validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - CreateTemplateNotificationRequest request1 = CreateTemplateNotificationRequest.builder() - .code("CODE1") - .sujet("Sujet") - .build(); - - CreateTemplateNotificationRequest request2 = CreateTemplateNotificationRequest.builder() - .code("CODE1") - .sujet("Sujet") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder() - .code("TEST_CODE") - .sujet("Test Subject") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateTemplateNotificationRequest"); - assertThat(toString).contains("TEST_CODE"); - assertThat(toString).contains("Test Subject"); - } -} +package dev.lions.unionflow.server.api.dto.notification.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateTemplateNotificationRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder() + .code("WELCOME_EMAIL") + .sujet("Bienvenue sur UnionFlow") + .corpsTexte("Bonjour {{prenom}},\nBienvenue!") + .corpsHtml("

Bienvenue {{prenom}}

") + .variablesDisponibles("prenom,nom,email") + .canauxSupportes("EMAIL,SMS") + .langue("fr") + .description("Template de bienvenue") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.code()).isEqualTo("WELCOME_EMAIL"); + assertThat(request.sujet()).isEqualTo("Bienvenue sur UnionFlow"); + assertThat(request.corpsTexte()).contains("Bonjour"); + assertThat(request.corpsHtml()).contains("

"); + assertThat(request.variablesDisponibles()).isEqualTo("prenom,nom,email"); + assertThat(request.canauxSupportes()).isEqualTo("EMAIL,SMS"); + assertThat(request.langue()).isEqualTo("fr"); + assertThat(request.description()).isEqualTo("Template de bienvenue"); + } + + @Test + void testBuilder_MinimalFields() { + CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder() + .code("SIMPLE_NOTIF") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.code()).isEqualTo("SIMPLE_NOTIF"); + assertThat(request.sujet()).isNull(); + assertThat(request.corpsTexte()).isNull(); + assertThat(request.corpsHtml()).isNull(); + assertThat(request.variablesDisponibles()).isNull(); + assertThat(request.canauxSupportes()).isNull(); + assertThat(request.langue()).isNull(); + assertThat(request.description()).isNull(); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder().build(); + + Set> violations = + validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + } + + @Test + void testValidation_EmptyCode() { + CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder() + .code("") + .build(); + + Set> violations = + validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + } + + @Test + void testValidation_BlankCode() { + CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder() + .code(" ") + .build(); + + Set> violations = + validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + } + + @Test + void testValidation_ValidFields() { + CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder() + .code("VALID_CODE") + .sujet("Sujet") + .corpsTexte("Corps") + .build(); + + Set> violations = + validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + CreateTemplateNotificationRequest request1 = CreateTemplateNotificationRequest.builder() + .code("CODE1") + .sujet("Sujet") + .build(); + + CreateTemplateNotificationRequest request2 = CreateTemplateNotificationRequest.builder() + .code("CODE1") + .sujet("Sujet") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateTemplateNotificationRequest request = CreateTemplateNotificationRequest.builder() + .code("TEST_CODE") + .sujet("Test Subject") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateTemplateNotificationRequest"); + assertThat(toString).contains("TEST_CODE"); + assertThat(toString).contains("Test Subject"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateNotificationRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateNotificationRequestTest.java index d33f51c..387734d 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateNotificationRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateNotificationRequestTest.java @@ -1,96 +1,96 @@ -package dev.lions.unionflow.server.api.dto.notification.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.time.LocalDateTime; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateNotificationRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDateTime dateLecture = LocalDateTime.now(); - - UpdateNotificationRequest request = UpdateNotificationRequest.builder() - .statut("LU") - .dateLecture(dateLecture) - .nombreTentatives(3) - .messageErreur("Erreur temporaire") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.statut()).isEqualTo("LU"); - assertThat(request.dateLecture()).isEqualTo(dateLecture); - assertThat(request.nombreTentatives()).isEqualTo(3); - assertThat(request.messageErreur()).isEqualTo("Erreur temporaire"); - } - - @Test - void testBuilder_MinimalFields() { - UpdateNotificationRequest request = UpdateNotificationRequest.builder().build(); - - assertThat(request).isNotNull(); - assertThat(request.statut()).isNull(); - assertThat(request.dateLecture()).isNull(); - assertThat(request.nombreTentatives()).isNull(); - assertThat(request.messageErreur()).isNull(); - } - - @Test - void testValidation_ValidFields() { - UpdateNotificationRequest request = UpdateNotificationRequest.builder() - .statut("ENVOYE") - .nombreTentatives(1) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - LocalDateTime dateLecture = LocalDateTime.now(); - - UpdateNotificationRequest request1 = UpdateNotificationRequest.builder() - .statut("LU") - .dateLecture(dateLecture) - .build(); - - UpdateNotificationRequest request2 = UpdateNotificationRequest.builder() - .statut("LU") - .dateLecture(dateLecture) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateNotificationRequest request = UpdateNotificationRequest.builder() - .statut("ENVOYE") - .nombreTentatives(2) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateNotificationRequest"); - assertThat(toString).contains("ENVOYE"); - } -} +package dev.lions.unionflow.server.api.dto.notification.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.time.LocalDateTime; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateNotificationRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDateTime dateLecture = LocalDateTime.now(); + + UpdateNotificationRequest request = UpdateNotificationRequest.builder() + .statut("LU") + .dateLecture(dateLecture) + .nombreTentatives(3) + .messageErreur("Erreur temporaire") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.statut()).isEqualTo("LU"); + assertThat(request.dateLecture()).isEqualTo(dateLecture); + assertThat(request.nombreTentatives()).isEqualTo(3); + assertThat(request.messageErreur()).isEqualTo("Erreur temporaire"); + } + + @Test + void testBuilder_MinimalFields() { + UpdateNotificationRequest request = UpdateNotificationRequest.builder().build(); + + assertThat(request).isNotNull(); + assertThat(request.statut()).isNull(); + assertThat(request.dateLecture()).isNull(); + assertThat(request.nombreTentatives()).isNull(); + assertThat(request.messageErreur()).isNull(); + } + + @Test + void testValidation_ValidFields() { + UpdateNotificationRequest request = UpdateNotificationRequest.builder() + .statut("ENVOYE") + .nombreTentatives(1) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + LocalDateTime dateLecture = LocalDateTime.now(); + + UpdateNotificationRequest request1 = UpdateNotificationRequest.builder() + .statut("LU") + .dateLecture(dateLecture) + .build(); + + UpdateNotificationRequest request2 = UpdateNotificationRequest.builder() + .statut("LU") + .dateLecture(dateLecture) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateNotificationRequest request = UpdateNotificationRequest.builder() + .statut("ENVOYE") + .nombreTentatives(2) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateNotificationRequest"); + assertThat(toString).contains("ENVOYE"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateTemplateNotificationRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateTemplateNotificationRequestTest.java index b328f90..f671b36 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateTemplateNotificationRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/notification/request/UpdateTemplateNotificationRequestTest.java @@ -1,144 +1,144 @@ -package dev.lions.unionflow.server.api.dto.notification.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateTemplateNotificationRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder() - .code("UPDATED_CODE") - .sujet("Nouveau sujet") - .corpsTexte("Nouveau corps texte") - .corpsHtml("

Nouveau corps HTML

") - .variablesDisponibles("var1,var2") - .canauxSupportes("EMAIL,PUSH") - .langue("en") - .description("Description mise à jour") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.code()).isEqualTo("UPDATED_CODE"); - assertThat(request.sujet()).isEqualTo("Nouveau sujet"); - assertThat(request.corpsTexte()).isEqualTo("Nouveau corps texte"); - assertThat(request.corpsHtml()).isEqualTo("

Nouveau corps HTML

"); - assertThat(request.variablesDisponibles()).isEqualTo("var1,var2"); - assertThat(request.canauxSupportes()).isEqualTo("EMAIL,PUSH"); - assertThat(request.langue()).isEqualTo("en"); - assertThat(request.description()).isEqualTo("Description mise à jour"); - } - - @Test - void testBuilder_MinimalFields() { - UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder() - .code("MIN_CODE") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.code()).isEqualTo("MIN_CODE"); - assertThat(request.sujet()).isNull(); - assertThat(request.corpsTexte()).isNull(); - assertThat(request.corpsHtml()).isNull(); - assertThat(request.variablesDisponibles()).isNull(); - assertThat(request.canauxSupportes()).isNull(); - assertThat(request.langue()).isNull(); - assertThat(request.description()).isNull(); - } - - @Test - void testValidation_MissingRequiredFields() { - UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder().build(); - - Set> violations = - validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - } - - @Test - void testValidation_EmptyCode() { - UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder() - .code("") - .build(); - - Set> violations = - validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - } - - @Test - void testValidation_BlankCode() { - UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder() - .code(" ") - .build(); - - Set> violations = - validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - } - - @Test - void testValidation_ValidFields() { - UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder() - .code("VALID_UPDATE") - .sujet("Nouveau sujet") - .build(); - - Set> violations = - validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UpdateTemplateNotificationRequest request1 = UpdateTemplateNotificationRequest.builder() - .code("SAME_CODE") - .sujet("Sujet") - .build(); - - UpdateTemplateNotificationRequest request2 = UpdateTemplateNotificationRequest.builder() - .code("SAME_CODE") - .sujet("Sujet") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder() - .code("TO_STRING_CODE") - .description("Description test") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateTemplateNotificationRequest"); - assertThat(toString).contains("TO_STRING_CODE"); - assertThat(toString).contains("Description test"); - } -} +package dev.lions.unionflow.server.api.dto.notification.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateTemplateNotificationRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder() + .code("UPDATED_CODE") + .sujet("Nouveau sujet") + .corpsTexte("Nouveau corps texte") + .corpsHtml("

Nouveau corps HTML

") + .variablesDisponibles("var1,var2") + .canauxSupportes("EMAIL,PUSH") + .langue("en") + .description("Description mise à jour") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.code()).isEqualTo("UPDATED_CODE"); + assertThat(request.sujet()).isEqualTo("Nouveau sujet"); + assertThat(request.corpsTexte()).isEqualTo("Nouveau corps texte"); + assertThat(request.corpsHtml()).isEqualTo("

Nouveau corps HTML

"); + assertThat(request.variablesDisponibles()).isEqualTo("var1,var2"); + assertThat(request.canauxSupportes()).isEqualTo("EMAIL,PUSH"); + assertThat(request.langue()).isEqualTo("en"); + assertThat(request.description()).isEqualTo("Description mise à jour"); + } + + @Test + void testBuilder_MinimalFields() { + UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder() + .code("MIN_CODE") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.code()).isEqualTo("MIN_CODE"); + assertThat(request.sujet()).isNull(); + assertThat(request.corpsTexte()).isNull(); + assertThat(request.corpsHtml()).isNull(); + assertThat(request.variablesDisponibles()).isNull(); + assertThat(request.canauxSupportes()).isNull(); + assertThat(request.langue()).isNull(); + assertThat(request.description()).isNull(); + } + + @Test + void testValidation_MissingRequiredFields() { + UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder().build(); + + Set> violations = + validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + } + + @Test + void testValidation_EmptyCode() { + UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder() + .code("") + .build(); + + Set> violations = + validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + } + + @Test + void testValidation_BlankCode() { + UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder() + .code(" ") + .build(); + + Set> violations = + validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + } + + @Test + void testValidation_ValidFields() { + UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder() + .code("VALID_UPDATE") + .sujet("Nouveau sujet") + .build(); + + Set> violations = + validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UpdateTemplateNotificationRequest request1 = UpdateTemplateNotificationRequest.builder() + .code("SAME_CODE") + .sujet("Sujet") + .build(); + + UpdateTemplateNotificationRequest request2 = UpdateTemplateNotificationRequest.builder() + .code("SAME_CODE") + .sujet("Sujet") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateTemplateNotificationRequest request = UpdateTemplateNotificationRequest.builder() + .code("TO_STRING_CODE") + .description("Description test") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateTemplateNotificationRequest"); + assertThat(toString).contains("TO_STRING_CODE"); + assertThat(toString).contains("Description test"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/organisation/request/CreateOrganisationRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/organisation/request/CreateOrganisationRequestTest.java index 89d4d4f..82d6cd5 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/organisation/request/CreateOrganisationRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/organisation/request/CreateOrganisationRequestTest.java @@ -1,293 +1,293 @@ -package dev.lions.unionflow.server.api.dto.organisation.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateOrganisationRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDate dateFondation = LocalDate.of(2020, 1, 15); - - CreateOrganisationRequest request = CreateOrganisationRequest.builder() - .nom("Union des Entrepreneurs du Sénégal") - .nomCourt("UES") - .description("Association regroupant les entrepreneurs sénégalais") - .email("contact@ues.sn") - .telephone("+221 33 123 45 67") - .telephoneSecondaire("+221 77 987 65 43") - .emailSecondaire("info@ues.sn") - .siteWeb("https://www.ues.sn") - .logo("https://www.ues.sn/logo.png") - .reseauxSociaux("{\"facebook\":\"UES.Senegal\",\"twitter\":\"@UES_SN\"}") - .typeOrganisation("ASSOCIATION") - .statut("ACTIF") - .dateFondation(dateFondation) - .numeroEnregistrement("SN-ASSOC-2020-001") - .devise("XOF") - .budgetAnnuel(new BigDecimal("50000000.00")) - .cotisationObligatoire(true) - .montantCotisationAnnuelle(new BigDecimal("25000.00")) - .objectifs("Promouvoir l'entrepreneuriat au Sénégal") - .activitesPrincipales("Formation, networking, advocacy") - .certifications("ISO 9001") - .partenaires("Ministère du Commerce, Banque Mondiale") - .notes("Organisation de référence dans le secteur") - .latitude(new BigDecimal("14.6937")) - .longitude(new BigDecimal("-17.4441")) - .adresse("123 Rue des Entreprises, Plateau") - .ville("Dakar") - .region("Dakar") - .pays("Sénégal") - .codePostal("BP 3456") - .organisationPublique(true) - .accepteNouveauxMembres(false) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.nom()).isEqualTo("Union des Entrepreneurs du Sénégal"); - assertThat(request.nomCourt()).isEqualTo("UES"); - assertThat(request.description()).contains("entrepreneurs sénégalais"); - assertThat(request.email()).isEqualTo("contact@ues.sn"); - assertThat(request.telephone()).isEqualTo("+221 33 123 45 67"); - assertThat(request.telephoneSecondaire()).isEqualTo("+221 77 987 65 43"); - assertThat(request.emailSecondaire()).isEqualTo("info@ues.sn"); - assertThat(request.siteWeb()).isEqualTo("https://www.ues.sn"); - assertThat(request.logo()).contains("logo.png"); - assertThat(request.typeOrganisation()).isEqualTo("ASSOCIATION"); - assertThat(request.statut()).isEqualTo("ACTIF"); - assertThat(request.dateFondation()).isEqualTo(dateFondation); - assertThat(request.numeroEnregistrement()).isEqualTo("SN-ASSOC-2020-001"); - assertThat(request.devise()).isEqualTo("XOF"); - assertThat(request.budgetAnnuel()).isEqualByComparingTo(new BigDecimal("50000000.00")); - assertThat(request.cotisationObligatoire()).isTrue(); - assertThat(request.montantCotisationAnnuelle()).isEqualByComparingTo(new BigDecimal("25000.00")); - assertThat(request.objectifs()).contains("entrepreneuriat"); - assertThat(request.certifications()).isEqualTo("ISO 9001"); - assertThat(request.latitude()).isEqualByComparingTo(new BigDecimal("14.6937")); - assertThat(request.longitude()).isEqualByComparingTo(new BigDecimal("-17.4441")); - assertThat(request.adresse()).isEqualTo("123 Rue des Entreprises, Plateau"); - assertThat(request.ville()).isEqualTo("Dakar"); - assertThat(request.region()).isEqualTo("Dakar"); - assertThat(request.pays()).isEqualTo("Sénégal"); - assertThat(request.codePostal()).isEqualTo("BP 3456"); - assertThat(request.organisationPublique()).isTrue(); - assertThat(request.accepteNouveauxMembres()).isFalse(); - } - - @Test - void testBuilder_MinimalFields() { - CreateOrganisationRequest request = CreateOrganisationRequest.builder() - .nom("Organisation Simple") - .email("simple@org.sn") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.nom()).isEqualTo("Organisation Simple"); - assertThat(request.email()).isEqualTo("simple@org.sn"); - assertThat(request.nomCourt()).isNull(); - assertThat(request.description()).isNull(); - assertThat(request.telephone()).isNull(); - assertThat(request.siteWeb()).isNull(); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateOrganisationRequest request = CreateOrganisationRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); - } - - @Test - void testValidation_EmptyNom() { - CreateOrganisationRequest request = CreateOrganisationRequest.builder() - .nom("") - .email("test@org.sn") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); - } - - @Test - void testValidation_EmailInvalide() { - CreateOrganisationRequest request = CreateOrganisationRequest.builder() - .nom("Organisation Test") - .email("not-an-email") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); - } - - @Test - void testValidation_EmailSecondaireInvalide() { - CreateOrganisationRequest request = CreateOrganisationRequest.builder() - .nom("Organisation Test") - .email("valid@test.sn") - .emailSecondaire("invalid-email") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations) - .anyMatch(v -> v.getPropertyPath().toString().equals("emailSecondaire")); - } - - @Test - void testValidation_NomTooLong() { - String longNom = "A".repeat(256); - CreateOrganisationRequest request = CreateOrganisationRequest.builder() - .nom(longNom) - .email("test@org.sn") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); - } - - @Test - void testValidation_DeviseTooLong() { - CreateOrganisationRequest request = CreateOrganisationRequest.builder() - .nom("Organisation Test") - .email("test@org.sn") - .devise("XOFF") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); - } - - @Test - void testValidation_ValidFields() { - CreateOrganisationRequest request = CreateOrganisationRequest.builder() - .nom("Organisation Valide") - .nomCourt("OV") - .email("contact@valide.org") - .emailSecondaire("info@valide.org") - .telephone("+221 33 111 22 33") - .devise("XOF") - .cotisationObligatoire(false) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testBuilder_AdresseFields() { - CreateOrganisationRequest request = CreateOrganisationRequest.builder() - .nom("ONG Dakar Centre") - .email("contact@ongdc.sn") - .adresse("Rue 10, Médina") - .ville("Dakar") - .region("Dakar") - .pays("Sénégal") - .codePostal("BP 1234") - .organisationPublique(false) - .accepteNouveauxMembres(true) - .build(); - - assertThat(request.adresse()).isEqualTo("Rue 10, Médina"); - assertThat(request.ville()).isEqualTo("Dakar"); - assertThat(request.region()).isEqualTo("Dakar"); - assertThat(request.pays()).isEqualTo("Sénégal"); - assertThat(request.codePostal()).isEqualTo("BP 1234"); - assertThat(request.organisationPublique()).isFalse(); - assertThat(request.accepteNouveauxMembres()).isTrue(); - } - - @Test - void testBuilder_AdresseFieldsNull_WhenNotProvided() { - CreateOrganisationRequest request = CreateOrganisationRequest.builder() - .nom("Org Minimal") - .email("min@org.sn") - .build(); - - assertThat(request.adresse()).isNull(); - assertThat(request.ville()).isNull(); - assertThat(request.region()).isNull(); - assertThat(request.pays()).isNull(); - assertThat(request.codePostal()).isNull(); - assertThat(request.organisationPublique()).isNull(); - assertThat(request.accepteNouveauxMembres()).isNull(); - } - - @Test - void testValidation_CodePostalTooLong() { - CreateOrganisationRequest request = CreateOrganisationRequest.builder() - .nom("Organisation Test") - .email("test@org.sn") - .codePostal("A".repeat(21)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codePostal")); - } - - @Test - void testEquals() { - CreateOrganisationRequest request1 = CreateOrganisationRequest.builder() - .nom("Même Organisation") - .email("same@org.sn") - .build(); - - CreateOrganisationRequest request2 = CreateOrganisationRequest.builder() - .nom("Même Organisation") - .email("same@org.sn") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateOrganisationRequest request = CreateOrganisationRequest.builder() - .nom("Test ToString Organisation") - .email("tostring@test.sn") - .nomCourt("TTO") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateOrganisationRequest"); - assertThat(toString).contains("Test ToString Organisation"); - assertThat(toString).contains("tostring@test.sn"); - assertThat(toString).contains("TTO"); - } -} +package dev.lions.unionflow.server.api.dto.organisation.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateOrganisationRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDate dateFondation = LocalDate.of(2020, 1, 15); + + CreateOrganisationRequest request = CreateOrganisationRequest.builder() + .nom("Union des Entrepreneurs du Sénégal") + .nomCourt("UES") + .description("Association regroupant les entrepreneurs sénégalais") + .email("contact@ues.sn") + .telephone("+221 33 123 45 67") + .telephoneSecondaire("+221 77 987 65 43") + .emailSecondaire("info@ues.sn") + .siteWeb("https://www.ues.sn") + .logo("https://www.ues.sn/logo.png") + .reseauxSociaux("{\"facebook\":\"UES.Senegal\",\"twitter\":\"@UES_SN\"}") + .typeOrganisation("ASSOCIATION") + .statut("ACTIF") + .dateFondation(dateFondation) + .numeroEnregistrement("SN-ASSOC-2020-001") + .devise("XOF") + .budgetAnnuel(new BigDecimal("50000000.00")) + .cotisationObligatoire(true) + .montantCotisationAnnuelle(new BigDecimal("25000.00")) + .objectifs("Promouvoir l'entrepreneuriat au Sénégal") + .activitesPrincipales("Formation, networking, advocacy") + .certifications("ISO 9001") + .partenaires("Ministère du Commerce, Banque Mondiale") + .notes("Organisation de référence dans le secteur") + .latitude(new BigDecimal("14.6937")) + .longitude(new BigDecimal("-17.4441")) + .adresse("123 Rue des Entreprises, Plateau") + .ville("Dakar") + .region("Dakar") + .pays("Sénégal") + .codePostal("BP 3456") + .organisationPublique(true) + .accepteNouveauxMembres(false) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.nom()).isEqualTo("Union des Entrepreneurs du Sénégal"); + assertThat(request.nomCourt()).isEqualTo("UES"); + assertThat(request.description()).contains("entrepreneurs sénégalais"); + assertThat(request.email()).isEqualTo("contact@ues.sn"); + assertThat(request.telephone()).isEqualTo("+221 33 123 45 67"); + assertThat(request.telephoneSecondaire()).isEqualTo("+221 77 987 65 43"); + assertThat(request.emailSecondaire()).isEqualTo("info@ues.sn"); + assertThat(request.siteWeb()).isEqualTo("https://www.ues.sn"); + assertThat(request.logo()).contains("logo.png"); + assertThat(request.typeOrganisation()).isEqualTo("ASSOCIATION"); + assertThat(request.statut()).isEqualTo("ACTIF"); + assertThat(request.dateFondation()).isEqualTo(dateFondation); + assertThat(request.numeroEnregistrement()).isEqualTo("SN-ASSOC-2020-001"); + assertThat(request.devise()).isEqualTo("XOF"); + assertThat(request.budgetAnnuel()).isEqualByComparingTo(new BigDecimal("50000000.00")); + assertThat(request.cotisationObligatoire()).isTrue(); + assertThat(request.montantCotisationAnnuelle()).isEqualByComparingTo(new BigDecimal("25000.00")); + assertThat(request.objectifs()).contains("entrepreneuriat"); + assertThat(request.certifications()).isEqualTo("ISO 9001"); + assertThat(request.latitude()).isEqualByComparingTo(new BigDecimal("14.6937")); + assertThat(request.longitude()).isEqualByComparingTo(new BigDecimal("-17.4441")); + assertThat(request.adresse()).isEqualTo("123 Rue des Entreprises, Plateau"); + assertThat(request.ville()).isEqualTo("Dakar"); + assertThat(request.region()).isEqualTo("Dakar"); + assertThat(request.pays()).isEqualTo("Sénégal"); + assertThat(request.codePostal()).isEqualTo("BP 3456"); + assertThat(request.organisationPublique()).isTrue(); + assertThat(request.accepteNouveauxMembres()).isFalse(); + } + + @Test + void testBuilder_MinimalFields() { + CreateOrganisationRequest request = CreateOrganisationRequest.builder() + .nom("Organisation Simple") + .email("simple@org.sn") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.nom()).isEqualTo("Organisation Simple"); + assertThat(request.email()).isEqualTo("simple@org.sn"); + assertThat(request.nomCourt()).isNull(); + assertThat(request.description()).isNull(); + assertThat(request.telephone()).isNull(); + assertThat(request.siteWeb()).isNull(); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateOrganisationRequest request = CreateOrganisationRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); + } + + @Test + void testValidation_EmptyNom() { + CreateOrganisationRequest request = CreateOrganisationRequest.builder() + .nom("") + .email("test@org.sn") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); + } + + @Test + void testValidation_EmailInvalide() { + CreateOrganisationRequest request = CreateOrganisationRequest.builder() + .nom("Organisation Test") + .email("not-an-email") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); + } + + @Test + void testValidation_EmailSecondaireInvalide() { + CreateOrganisationRequest request = CreateOrganisationRequest.builder() + .nom("Organisation Test") + .email("valid@test.sn") + .emailSecondaire("invalid-email") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations) + .anyMatch(v -> v.getPropertyPath().toString().equals("emailSecondaire")); + } + + @Test + void testValidation_NomTooLong() { + String longNom = "A".repeat(256); + CreateOrganisationRequest request = CreateOrganisationRequest.builder() + .nom(longNom) + .email("test@org.sn") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); + } + + @Test + void testValidation_DeviseTooLong() { + CreateOrganisationRequest request = CreateOrganisationRequest.builder() + .nom("Organisation Test") + .email("test@org.sn") + .devise("XOFF") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); + } + + @Test + void testValidation_ValidFields() { + CreateOrganisationRequest request = CreateOrganisationRequest.builder() + .nom("Organisation Valide") + .nomCourt("OV") + .email("contact@valide.org") + .emailSecondaire("info@valide.org") + .telephone("+221 33 111 22 33") + .devise("XOF") + .cotisationObligatoire(false) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testBuilder_AdresseFields() { + CreateOrganisationRequest request = CreateOrganisationRequest.builder() + .nom("ONG Dakar Centre") + .email("contact@ongdc.sn") + .adresse("Rue 10, Médina") + .ville("Dakar") + .region("Dakar") + .pays("Sénégal") + .codePostal("BP 1234") + .organisationPublique(false) + .accepteNouveauxMembres(true) + .build(); + + assertThat(request.adresse()).isEqualTo("Rue 10, Médina"); + assertThat(request.ville()).isEqualTo("Dakar"); + assertThat(request.region()).isEqualTo("Dakar"); + assertThat(request.pays()).isEqualTo("Sénégal"); + assertThat(request.codePostal()).isEqualTo("BP 1234"); + assertThat(request.organisationPublique()).isFalse(); + assertThat(request.accepteNouveauxMembres()).isTrue(); + } + + @Test + void testBuilder_AdresseFieldsNull_WhenNotProvided() { + CreateOrganisationRequest request = CreateOrganisationRequest.builder() + .nom("Org Minimal") + .email("min@org.sn") + .build(); + + assertThat(request.adresse()).isNull(); + assertThat(request.ville()).isNull(); + assertThat(request.region()).isNull(); + assertThat(request.pays()).isNull(); + assertThat(request.codePostal()).isNull(); + assertThat(request.organisationPublique()).isNull(); + assertThat(request.accepteNouveauxMembres()).isNull(); + } + + @Test + void testValidation_CodePostalTooLong() { + CreateOrganisationRequest request = CreateOrganisationRequest.builder() + .nom("Organisation Test") + .email("test@org.sn") + .codePostal("A".repeat(21)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codePostal")); + } + + @Test + void testEquals() { + CreateOrganisationRequest request1 = CreateOrganisationRequest.builder() + .nom("Même Organisation") + .email("same@org.sn") + .build(); + + CreateOrganisationRequest request2 = CreateOrganisationRequest.builder() + .nom("Même Organisation") + .email("same@org.sn") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateOrganisationRequest request = CreateOrganisationRequest.builder() + .nom("Test ToString Organisation") + .email("tostring@test.sn") + .nomCourt("TTO") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateOrganisationRequest"); + assertThat(toString).contains("Test ToString Organisation"); + assertThat(toString).contains("tostring@test.sn"); + assertThat(toString).contains("TTO"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/organisation/request/UpdateOrganisationRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/organisation/request/UpdateOrganisationRequestTest.java index ef64981..0e6a01c 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/organisation/request/UpdateOrganisationRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/organisation/request/UpdateOrganisationRequestTest.java @@ -1,258 +1,258 @@ -package dev.lions.unionflow.server.api.dto.organisation.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateOrganisationRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDate dateFondation = LocalDate.of(2018, 6, 10); - - UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() - .nom("Organisation Mise à Jour") - .nomCourt("OMJ") - .description("Description mise à jour de l'organisation") - .email("updated@org.sn") - .telephone("+221 33 999 88 77") - .telephoneSecondaire("+221 77 666 55 44") - .emailSecondaire("secondary@org.sn") - .siteWeb("https://www.updated.org") - .logo("https://www.updated.org/new-logo.png") - .reseauxSociaux("{\"linkedin\":\"updated-org\"}") - .typeOrganisation("ONG") - .statut("EN_REVISION") - .dateFondation(dateFondation) - .numeroEnregistrement("SN-ONG-2018-045") - .devise("EUR") - .budgetAnnuel(new BigDecimal("75000000.00")) - .cotisationObligatoire(false) - .montantCotisationAnnuelle(new BigDecimal("50000.00")) - .objectifs("Nouveaux objectifs stratégiques") - .activitesPrincipales("Nouvelles activités") - .certifications("ISO 14001") - .partenaires("Nouveaux partenaires internationaux") - .notes("Notes mises à jour") - .latitude(new BigDecimal("12.5")) - .longitude(new BigDecimal("-15.5")) - .adresse("Avenue Cheikh Anta Diop, Fann") - .ville("Dakar") - .region("Dakar") - .pays("Sénégal") - .codePostal("BP 5000") - .organisationPublique(false) - .accepteNouveauxMembres(true) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.nom()).isEqualTo("Organisation Mise à Jour"); - assertThat(request.nomCourt()).isEqualTo("OMJ"); - assertThat(request.description()).contains("mise à jour"); - assertThat(request.email()).isEqualTo("updated@org.sn"); - assertThat(request.telephone()).isEqualTo("+221 33 999 88 77"); - assertThat(request.emailSecondaire()).isEqualTo("secondary@org.sn"); - assertThat(request.siteWeb()).contains("updated.org"); - assertThat(request.typeOrganisation()).isEqualTo("ONG"); - assertThat(request.statut()).isEqualTo("EN_REVISION"); - assertThat(request.dateFondation()).isEqualTo(dateFondation); - assertThat(request.devise()).isEqualTo("EUR"); - assertThat(request.budgetAnnuel()).isEqualByComparingTo(new BigDecimal("75000000.00")); - assertThat(request.cotisationObligatoire()).isFalse(); - assertThat(request.certifications()).isEqualTo("ISO 14001"); - assertThat(request.adresse()).isEqualTo("Avenue Cheikh Anta Diop, Fann"); - assertThat(request.ville()).isEqualTo("Dakar"); - assertThat(request.region()).isEqualTo("Dakar"); - assertThat(request.pays()).isEqualTo("Sénégal"); - assertThat(request.codePostal()).isEqualTo("BP 5000"); - assertThat(request.organisationPublique()).isFalse(); - assertThat(request.accepteNouveauxMembres()).isTrue(); - } - - @Test - void testBuilder_MinimalFields() { - UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() - .nom("Simple Update") - .email("simple@update.org") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.nom()).isEqualTo("Simple Update"); - assertThat(request.email()).isEqualTo("simple@update.org"); - assertThat(request.nomCourt()).isNull(); - assertThat(request.description()).isNull(); - } - - @Test - void testValidation_MissingRequiredFields() { - UpdateOrganisationRequest request = UpdateOrganisationRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); - } - - @Test - void testValidation_EmptyNom() { - UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() - .nom("") - .email("test@org.sn") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); - } - - @Test - void testValidation_EmailInvalide() { - UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() - .nom("Test Org") - .email("invalid-email-format") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); - } - - @Test - void testValidation_EmailSecondaireInvalide() { - UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() - .nom("Test Org") - .email("valid@org.sn") - .emailSecondaire("bad-email") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations) - .anyMatch(v -> v.getPropertyPath().toString().equals("emailSecondaire")); - } - - @Test - void testValidation_DeviseTooLong() { - UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() - .nom("Test Org") - .email("test@org.sn") - .devise("XOFF") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); - } - - @Test - void testValidation_ValidFields() { - UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() - .nom("Organisation Valide") - .email("valid@organisation.sn") - .emailSecondaire("info@organisation.sn") - .telephone("+221 33 222 33 44") - .devise("USD") - .cotisationObligatoire(true) - .montantCotisationAnnuelle(new BigDecimal("10000.00")) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testBuilder_AdresseFields() { - UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() - .nom("Association Abidjan Nord") - .email("contact@abn.ci") - .adresse("Quartier Deux Plateaux, Rue des Jardins") - .ville("Abidjan") - .region("Lagunes") - .pays("Côte d'Ivoire") - .codePostal("01 BP 1234") - .organisationPublique(true) - .accepteNouveauxMembres(true) - .build(); - - assertThat(request.adresse()).isEqualTo("Quartier Deux Plateaux, Rue des Jardins"); - assertThat(request.ville()).isEqualTo("Abidjan"); - assertThat(request.region()).isEqualTo("Lagunes"); - assertThat(request.pays()).isEqualTo("Côte d'Ivoire"); - assertThat(request.codePostal()).isEqualTo("01 BP 1234"); - assertThat(request.organisationPublique()).isTrue(); - assertThat(request.accepteNouveauxMembres()).isTrue(); - } - - @Test - void testValidation_VilleTooLong() { - UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() - .nom("Test Org") - .email("test@org.ci") - .ville("A".repeat(101)) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ville")); - } - - @Test - void testEquals() { - UpdateOrganisationRequest request1 = UpdateOrganisationRequest.builder() - .nom("Identique") - .email("same@test.org") - .statut("ACTIF") - .build(); - - UpdateOrganisationRequest request2 = UpdateOrganisationRequest.builder() - .nom("Identique") - .email("same@test.org") - .statut("ACTIF") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() - .nom("ToString Test Org") - .email("toString@test.org") - .nomCourt("TTO") - .statut("INACTIF") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateOrganisationRequest"); - assertThat(toString).contains("ToString Test Org"); - assertThat(toString).contains("toString@test.org"); - assertThat(toString).contains("TTO"); - assertThat(toString).contains("INACTIF"); - } -} +package dev.lions.unionflow.server.api.dto.organisation.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateOrganisationRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDate dateFondation = LocalDate.of(2018, 6, 10); + + UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() + .nom("Organisation Mise à Jour") + .nomCourt("OMJ") + .description("Description mise à jour de l'organisation") + .email("updated@org.sn") + .telephone("+221 33 999 88 77") + .telephoneSecondaire("+221 77 666 55 44") + .emailSecondaire("secondary@org.sn") + .siteWeb("https://www.updated.org") + .logo("https://www.updated.org/new-logo.png") + .reseauxSociaux("{\"linkedin\":\"updated-org\"}") + .typeOrganisation("ONG") + .statut("EN_REVISION") + .dateFondation(dateFondation) + .numeroEnregistrement("SN-ONG-2018-045") + .devise("EUR") + .budgetAnnuel(new BigDecimal("75000000.00")) + .cotisationObligatoire(false) + .montantCotisationAnnuelle(new BigDecimal("50000.00")) + .objectifs("Nouveaux objectifs stratégiques") + .activitesPrincipales("Nouvelles activités") + .certifications("ISO 14001") + .partenaires("Nouveaux partenaires internationaux") + .notes("Notes mises à jour") + .latitude(new BigDecimal("12.5")) + .longitude(new BigDecimal("-15.5")) + .adresse("Avenue Cheikh Anta Diop, Fann") + .ville("Dakar") + .region("Dakar") + .pays("Sénégal") + .codePostal("BP 5000") + .organisationPublique(false) + .accepteNouveauxMembres(true) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.nom()).isEqualTo("Organisation Mise à Jour"); + assertThat(request.nomCourt()).isEqualTo("OMJ"); + assertThat(request.description()).contains("mise à jour"); + assertThat(request.email()).isEqualTo("updated@org.sn"); + assertThat(request.telephone()).isEqualTo("+221 33 999 88 77"); + assertThat(request.emailSecondaire()).isEqualTo("secondary@org.sn"); + assertThat(request.siteWeb()).contains("updated.org"); + assertThat(request.typeOrganisation()).isEqualTo("ONG"); + assertThat(request.statut()).isEqualTo("EN_REVISION"); + assertThat(request.dateFondation()).isEqualTo(dateFondation); + assertThat(request.devise()).isEqualTo("EUR"); + assertThat(request.budgetAnnuel()).isEqualByComparingTo(new BigDecimal("75000000.00")); + assertThat(request.cotisationObligatoire()).isFalse(); + assertThat(request.certifications()).isEqualTo("ISO 14001"); + assertThat(request.adresse()).isEqualTo("Avenue Cheikh Anta Diop, Fann"); + assertThat(request.ville()).isEqualTo("Dakar"); + assertThat(request.region()).isEqualTo("Dakar"); + assertThat(request.pays()).isEqualTo("Sénégal"); + assertThat(request.codePostal()).isEqualTo("BP 5000"); + assertThat(request.organisationPublique()).isFalse(); + assertThat(request.accepteNouveauxMembres()).isTrue(); + } + + @Test + void testBuilder_MinimalFields() { + UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() + .nom("Simple Update") + .email("simple@update.org") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.nom()).isEqualTo("Simple Update"); + assertThat(request.email()).isEqualTo("simple@update.org"); + assertThat(request.nomCourt()).isNull(); + assertThat(request.description()).isNull(); + } + + @Test + void testValidation_MissingRequiredFields() { + UpdateOrganisationRequest request = UpdateOrganisationRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); + } + + @Test + void testValidation_EmptyNom() { + UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() + .nom("") + .email("test@org.sn") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); + } + + @Test + void testValidation_EmailInvalide() { + UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() + .nom("Test Org") + .email("invalid-email-format") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); + } + + @Test + void testValidation_EmailSecondaireInvalide() { + UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() + .nom("Test Org") + .email("valid@org.sn") + .emailSecondaire("bad-email") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations) + .anyMatch(v -> v.getPropertyPath().toString().equals("emailSecondaire")); + } + + @Test + void testValidation_DeviseTooLong() { + UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() + .nom("Test Org") + .email("test@org.sn") + .devise("XOFF") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); + } + + @Test + void testValidation_ValidFields() { + UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() + .nom("Organisation Valide") + .email("valid@organisation.sn") + .emailSecondaire("info@organisation.sn") + .telephone("+221 33 222 33 44") + .devise("USD") + .cotisationObligatoire(true) + .montantCotisationAnnuelle(new BigDecimal("10000.00")) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testBuilder_AdresseFields() { + UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() + .nom("Association Abidjan Nord") + .email("contact@abn.ci") + .adresse("Quartier Deux Plateaux, Rue des Jardins") + .ville("Abidjan") + .region("Lagunes") + .pays("Côte d'Ivoire") + .codePostal("01 BP 1234") + .organisationPublique(true) + .accepteNouveauxMembres(true) + .build(); + + assertThat(request.adresse()).isEqualTo("Quartier Deux Plateaux, Rue des Jardins"); + assertThat(request.ville()).isEqualTo("Abidjan"); + assertThat(request.region()).isEqualTo("Lagunes"); + assertThat(request.pays()).isEqualTo("Côte d'Ivoire"); + assertThat(request.codePostal()).isEqualTo("01 BP 1234"); + assertThat(request.organisationPublique()).isTrue(); + assertThat(request.accepteNouveauxMembres()).isTrue(); + } + + @Test + void testValidation_VilleTooLong() { + UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() + .nom("Test Org") + .email("test@org.ci") + .ville("A".repeat(101)) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("ville")); + } + + @Test + void testEquals() { + UpdateOrganisationRequest request1 = UpdateOrganisationRequest.builder() + .nom("Identique") + .email("same@test.org") + .statut("ACTIF") + .build(); + + UpdateOrganisationRequest request2 = UpdateOrganisationRequest.builder() + .nom("Identique") + .email("same@test.org") + .statut("ACTIF") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateOrganisationRequest request = UpdateOrganisationRequest.builder() + .nom("ToString Test Org") + .email("toString@test.org") + .nomCourt("TTO") + .statut("INACTIF") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateOrganisationRequest"); + assertThat(toString).contains("ToString Test Org"); + assertThat(toString).contains("toString@test.org"); + assertThat(toString).contains("TTO"); + assertThat(toString).contains("INACTIF"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/paiement/WaveBalanceDTOTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/paiement/WaveBalanceDTOTest.java index 9a62aa7..726aa7c 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/paiement/WaveBalanceDTOTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/paiement/WaveBalanceDTOTest.java @@ -1,319 +1,319 @@ -package dev.lions.unionflow.server.api.dto.paiement; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.math.BigDecimal; -import java.time.LocalDateTime; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour WaveBalanceDTO. - * Couvre toutes les branches : calculerSoldeTotal (via setters), isWalletActif, - * isSoldeSuffisant, getSoldeDisponibleAujourdhui, mettreAJourApresTransaction. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests WaveBalanceDTO") -class WaveBalanceDTOTest { - - @Nested - @DisplayName("Constructeurs") - class Constructeurs { - - @Test - @DisplayName("constructeur par défaut initialise devise et statut") - void testConstructeurVide() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - assertThat(dto.getDevise()).isEqualTo("XOF"); - assertThat(dto.getStatutWallet()).isEqualTo("ACTIVE"); - assertThat(dto.getSoldeEnAttente()).isEqualTo(BigDecimal.ZERO); - assertThat(dto.getNombreTransactionsAujourdhui()).isEqualTo(0); - } - - @Test - @DisplayName("constructeur avec wallet et solde calcule soldeTotal") - void testConstructeurAvecParams() { - WaveBalanceDTO dto = new WaveBalanceDTO("wallet-1", BigDecimal.valueOf(1000)); - assertThat(dto.getNumeroWallet()).isEqualTo("wallet-1"); - assertThat(dto.getSoldeDisponible()).isEqualByComparingTo(BigDecimal.valueOf(1000)); - assertThat(dto.getSoldeTotal()).isEqualByComparingTo(BigDecimal.valueOf(1000)); - } - } - - @Nested - @DisplayName("setSoldeDisponible / setSoldeEnAttente (calculerSoldeTotal)") - class CalculerSoldeTotal { - - @Test - @DisplayName("soldeTotal = disponible + enAttente quand les deux sont définis") - void testCalculSoldeTotal() { - WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(100)); - dto.setSoldeEnAttente(BigDecimal.valueOf(50)); - assertThat(dto.getSoldeTotal()).isEqualByComparingTo(BigDecimal.valueOf(150)); - } - - @Test - @DisplayName("setSoldeDisponible recalcule soldeTotal") - void testSetSoldeDisponible() { - WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(100)); - dto.setSoldeEnAttente(BigDecimal.valueOf(20)); - dto.setSoldeDisponible(BigDecimal.valueOf(200)); - assertThat(dto.getSoldeTotal()).isEqualByComparingTo(BigDecimal.valueOf(220)); - } - - @Test - @DisplayName("ne calcule pas soldeTotal si soldeDisponible null") - void testCalculSoldeTotalAvecDisponibleNull() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - BigDecimal soldeInitial = dto.getSoldeTotal(); // null au départ - dto.setSoldeDisponible(null); - dto.setSoldeEnAttente(BigDecimal.valueOf(50)); - // soldeTotal ne devrait pas être calculé car soldeDisponible est null - assertThat(dto.getSoldeTotal()).isEqualTo(soldeInitial); - } - - @Test - @DisplayName("ne calcule pas soldeTotal si soldeEnAttente null après calcul initial") - void testCalculSoldeTotalAvecEnAttenteNull() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - dto.setSoldeDisponible(BigDecimal.valueOf(100)); - // À ce stade soldeTotal = 100 + 0 = 100 (car soldeEnAttente initialisé à ZERO) - BigDecimal soldeAvantNull = dto.getSoldeTotal(); - dto.setSoldeEnAttente(null); - // soldeTotal ne devrait pas être recalculé, garde sa valeur précédente - assertThat(dto.getSoldeTotal()).isEqualTo(soldeAvantNull); - } - } - - @Nested - @DisplayName("isWalletActif") - class IsWalletActif { - - @Test - @DisplayName("true quand statut ACTIVE") - void testActif() { - WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.ZERO); - dto.setStatutWallet("ACTIVE"); - assertThat(dto.isWalletActif()).isTrue(); - } - - @Test - @DisplayName("false quand statut INACTIVE") - void testInactif() { - WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.ZERO); - dto.setStatutWallet("INACTIVE"); - assertThat(dto.isWalletActif()).isFalse(); - } - } - - @Nested - @DisplayName("isSoldeSuffisant") - class IsSoldeSuffisant { - - @Test - @DisplayName("false quand soldeDisponible null") - void testSoldeNull() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - dto.setSoldeDisponible(null); - assertThat(dto.isSoldeSuffisant(BigDecimal.ONE)).isFalse(); - } - - @Test - @DisplayName("true quand solde >= montant") - void testSuffisant() { - WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(100)); - assertThat(dto.isSoldeSuffisant(BigDecimal.valueOf(50))).isTrue(); - assertThat(dto.isSoldeSuffisant(BigDecimal.valueOf(100))).isTrue(); - } - - @Test - @DisplayName("false quand solde < montant") - void testInsuffisant() { - WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(100)); - assertThat(dto.isSoldeSuffisant(BigDecimal.valueOf(101))).isFalse(); - } - } - - @Nested - @DisplayName("getSoldeDisponibleAujourdhui") - class GetSoldeDisponibleAujourdhui { - - @Test - @DisplayName("retourne soldeDisponible quand limiteQuotidienne null") - void testLimiteNull() { - WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(500)); - dto.setLimiteQuotidienne(null); - dto.setMontantUtiliseAujourdhui(BigDecimal.ZERO); - assertThat(dto.getSoldeDisponibleAujourdhui()).isEqualByComparingTo(BigDecimal.valueOf(500)); - } - - @Test - @DisplayName("retourne soldeDisponible quand montantUtiliseAujourdhui null") - void testMontantUtiliseNull() { - WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(500)); - dto.setLimiteQuotidienne(BigDecimal.valueOf(1000)); - dto.setMontantUtiliseAujourdhui(null); - assertThat(dto.getSoldeDisponibleAujourdhui()).isEqualByComparingTo(BigDecimal.valueOf(500)); - } - - @Test - @DisplayName("retourne soldeDisponible null quand soldeDisponible null") - void testSoldeDisponibleNull() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - dto.setSoldeDisponible(null); - dto.setLimiteQuotidienne(BigDecimal.valueOf(1000)); - dto.setMontantUtiliseAujourdhui(BigDecimal.valueOf(100)); - assertThat(dto.getSoldeDisponibleAujourdhui()).isNull(); - } - - @Test - @DisplayName("retourne le minimum entre solde et limite restante") - void testMinimum() { - WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(500)); - dto.setLimiteQuotidienne(BigDecimal.valueOf(1000)); - dto.setMontantUtiliseAujourdhui(BigDecimal.valueOf(700)); - assertThat(dto.getSoldeDisponibleAujourdhui()).isEqualByComparingTo(BigDecimal.valueOf(300)); - } - } - - @Nested - @DisplayName("mettreAJourApresTransaction") - class MettreAJourApresTransaction { - - @Test - @DisplayName("initialise les champs null puis incrémente") - void testAvecChampsNull() { - WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(1000)); - dto.setMontantUtiliseAujourdhui(null); - dto.setMontantUtiliseCeMois(null); - dto.setNombreTransactionsAujourdhui(null); - dto.setNombreTransactionsCeMois(null); - dto.mettreAJourApresTransaction(BigDecimal.valueOf(50)); - assertThat(dto.getMontantUtiliseAujourdhui()).isEqualByComparingTo(BigDecimal.valueOf(50)); - assertThat(dto.getMontantUtiliseCeMois()).isEqualByComparingTo(BigDecimal.valueOf(50)); - assertThat(dto.getNombreTransactionsAujourdhui()).isEqualTo(1); - assertThat(dto.getNombreTransactionsCeMois()).isEqualTo(1); - assertThat(dto.getDateDerniereMiseAJour()).isNotNull(); - } - - @Test - @DisplayName("ajoute au montant existant") - void testAvecValeursExistantes() { - WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(1000)); - dto.setMontantUtiliseAujourdhui(BigDecimal.valueOf(100)); - dto.setMontantUtiliseCeMois(BigDecimal.valueOf(200)); - dto.setNombreTransactionsAujourdhui(2); - dto.setNombreTransactionsCeMois(3); - dto.mettreAJourApresTransaction(BigDecimal.valueOf(25)); - assertThat(dto.getMontantUtiliseAujourdhui()).isEqualByComparingTo(BigDecimal.valueOf(125)); - assertThat(dto.getMontantUtiliseCeMois()).isEqualByComparingTo(BigDecimal.valueOf(225)); - assertThat(dto.getNombreTransactionsAujourdhui()).isEqualTo(3); - assertThat(dto.getNombreTransactionsCeMois()).isEqualTo(4); - } - } - - @Nested - @DisplayName("toString") - class ToString { - - @Test - @DisplayName("contient numeroWallet et solde") - void testToString() { - WaveBalanceDTO dto = new WaveBalanceDTO("wallet-1", BigDecimal.valueOf(500)); - String s = dto.toString(); - assertThat(s).contains("wallet-1"); - assertThat(s).contains("500"); - } - } - - @Nested - @DisplayName("Getters et Setters complémentaires") - class GettersSettersComplementaires { - - @Test - @DisplayName("setSoldeTotal / getSoldeTotal") - void testSoldeTotal() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - dto.setSoldeTotal(BigDecimal.valueOf(1500)); - assertThat(dto.getSoldeTotal()).isEqualByComparingTo(BigDecimal.valueOf(1500)); - } - - @Test - @DisplayName("setDevise / getDevise") - void testDevise() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - dto.setDevise("USD"); - assertThat(dto.getDevise()).isEqualTo("USD"); - } - - @Test - @DisplayName("setNumeroWallet / getNumeroWallet") - void testNumeroWallet() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - dto.setNumeroWallet("+221771234567"); - assertThat(dto.getNumeroWallet()).isEqualTo("+221771234567"); - } - - @Test - @DisplayName("setNomBusiness / getNomBusiness") - void testNomBusiness() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - dto.setNomBusiness("UnionFlow Business"); - assertThat(dto.getNomBusiness()).isEqualTo("UnionFlow Business"); - } - - @Test - @DisplayName("setDateDerniereMiseAJour / getDateDerniereMiseAJour") - void testDateDerniereMiseAJour() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - LocalDateTime now = LocalDateTime.now(); - dto.setDateDerniereMiseAJour(now); - assertThat(dto.getDateDerniereMiseAJour()).isEqualTo(now); - } - - @Test - @DisplayName("setDateDerniereSynchronisation / getDateDerniereSynchronisation") - void testDateDerniereSynchronisation() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - LocalDateTime dateSync = LocalDateTime.of(2025, 1, 15, 10, 30); - dto.setDateDerniereSynchronisation(dateSync); - assertThat(dto.getDateDerniereSynchronisation()).isEqualTo(dateSync); - } - - @Test - @DisplayName("setLimiteQuotidienne / getLimiteQuotidienne") - void testLimiteQuotidienne() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - dto.setLimiteQuotidienne(BigDecimal.valueOf(50000)); - assertThat(dto.getLimiteQuotidienne()).isEqualByComparingTo(BigDecimal.valueOf(50000)); - } - - @Test - @DisplayName("setLimiteMensuelle / getLimiteMensuelle") - void testLimiteMensuelle() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - dto.setLimiteMensuelle(BigDecimal.valueOf(500000)); - assertThat(dto.getLimiteMensuelle()).isEqualByComparingTo(BigDecimal.valueOf(500000)); - } - - @Test - @DisplayName("setDerniereErreur / getDerniereErreur") - void testDerniereErreur() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - dto.setDerniereErreur("Erreur de synchronisation avec Wave API"); - assertThat(dto.getDerniereErreur()).isEqualTo("Erreur de synchronisation avec Wave API"); - } - - @Test - @DisplayName("setCodeDerniereErreur / getCodeDerniereErreur") - void testCodeDerniereErreur() { - WaveBalanceDTO dto = new WaveBalanceDTO(); - dto.setCodeDerniereErreur("ERR_WAVE_500"); - assertThat(dto.getCodeDerniereErreur()).isEqualTo("ERR_WAVE_500"); - } - } -} +package dev.lions.unionflow.server.api.dto.paiement; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.math.BigDecimal; +import java.time.LocalDateTime; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour WaveBalanceDTO. + * Couvre toutes les branches : calculerSoldeTotal (via setters), isWalletActif, + * isSoldeSuffisant, getSoldeDisponibleAujourdhui, mettreAJourApresTransaction. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests WaveBalanceDTO") +class WaveBalanceDTOTest { + + @Nested + @DisplayName("Constructeurs") + class Constructeurs { + + @Test + @DisplayName("constructeur par défaut initialise devise et statut") + void testConstructeurVide() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + assertThat(dto.getDevise()).isEqualTo("XOF"); + assertThat(dto.getStatutWallet()).isEqualTo("ACTIVE"); + assertThat(dto.getSoldeEnAttente()).isEqualTo(BigDecimal.ZERO); + assertThat(dto.getNombreTransactionsAujourdhui()).isEqualTo(0); + } + + @Test + @DisplayName("constructeur avec wallet et solde calcule soldeTotal") + void testConstructeurAvecParams() { + WaveBalanceDTO dto = new WaveBalanceDTO("wallet-1", BigDecimal.valueOf(1000)); + assertThat(dto.getNumeroWallet()).isEqualTo("wallet-1"); + assertThat(dto.getSoldeDisponible()).isEqualByComparingTo(BigDecimal.valueOf(1000)); + assertThat(dto.getSoldeTotal()).isEqualByComparingTo(BigDecimal.valueOf(1000)); + } + } + + @Nested + @DisplayName("setSoldeDisponible / setSoldeEnAttente (calculerSoldeTotal)") + class CalculerSoldeTotal { + + @Test + @DisplayName("soldeTotal = disponible + enAttente quand les deux sont définis") + void testCalculSoldeTotal() { + WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(100)); + dto.setSoldeEnAttente(BigDecimal.valueOf(50)); + assertThat(dto.getSoldeTotal()).isEqualByComparingTo(BigDecimal.valueOf(150)); + } + + @Test + @DisplayName("setSoldeDisponible recalcule soldeTotal") + void testSetSoldeDisponible() { + WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(100)); + dto.setSoldeEnAttente(BigDecimal.valueOf(20)); + dto.setSoldeDisponible(BigDecimal.valueOf(200)); + assertThat(dto.getSoldeTotal()).isEqualByComparingTo(BigDecimal.valueOf(220)); + } + + @Test + @DisplayName("ne calcule pas soldeTotal si soldeDisponible null") + void testCalculSoldeTotalAvecDisponibleNull() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + BigDecimal soldeInitial = dto.getSoldeTotal(); // null au départ + dto.setSoldeDisponible(null); + dto.setSoldeEnAttente(BigDecimal.valueOf(50)); + // soldeTotal ne devrait pas être calculé car soldeDisponible est null + assertThat(dto.getSoldeTotal()).isEqualTo(soldeInitial); + } + + @Test + @DisplayName("ne calcule pas soldeTotal si soldeEnAttente null après calcul initial") + void testCalculSoldeTotalAvecEnAttenteNull() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + dto.setSoldeDisponible(BigDecimal.valueOf(100)); + // À ce stade soldeTotal = 100 + 0 = 100 (car soldeEnAttente initialisé à ZERO) + BigDecimal soldeAvantNull = dto.getSoldeTotal(); + dto.setSoldeEnAttente(null); + // soldeTotal ne devrait pas être recalculé, garde sa valeur précédente + assertThat(dto.getSoldeTotal()).isEqualTo(soldeAvantNull); + } + } + + @Nested + @DisplayName("isWalletActif") + class IsWalletActif { + + @Test + @DisplayName("true quand statut ACTIVE") + void testActif() { + WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.ZERO); + dto.setStatutWallet("ACTIVE"); + assertThat(dto.isWalletActif()).isTrue(); + } + + @Test + @DisplayName("false quand statut INACTIVE") + void testInactif() { + WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.ZERO); + dto.setStatutWallet("INACTIVE"); + assertThat(dto.isWalletActif()).isFalse(); + } + } + + @Nested + @DisplayName("isSoldeSuffisant") + class IsSoldeSuffisant { + + @Test + @DisplayName("false quand soldeDisponible null") + void testSoldeNull() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + dto.setSoldeDisponible(null); + assertThat(dto.isSoldeSuffisant(BigDecimal.ONE)).isFalse(); + } + + @Test + @DisplayName("true quand solde >= montant") + void testSuffisant() { + WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(100)); + assertThat(dto.isSoldeSuffisant(BigDecimal.valueOf(50))).isTrue(); + assertThat(dto.isSoldeSuffisant(BigDecimal.valueOf(100))).isTrue(); + } + + @Test + @DisplayName("false quand solde < montant") + void testInsuffisant() { + WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(100)); + assertThat(dto.isSoldeSuffisant(BigDecimal.valueOf(101))).isFalse(); + } + } + + @Nested + @DisplayName("getSoldeDisponibleAujourdhui") + class GetSoldeDisponibleAujourdhui { + + @Test + @DisplayName("retourne soldeDisponible quand limiteQuotidienne null") + void testLimiteNull() { + WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(500)); + dto.setLimiteQuotidienne(null); + dto.setMontantUtiliseAujourdhui(BigDecimal.ZERO); + assertThat(dto.getSoldeDisponibleAujourdhui()).isEqualByComparingTo(BigDecimal.valueOf(500)); + } + + @Test + @DisplayName("retourne soldeDisponible quand montantUtiliseAujourdhui null") + void testMontantUtiliseNull() { + WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(500)); + dto.setLimiteQuotidienne(BigDecimal.valueOf(1000)); + dto.setMontantUtiliseAujourdhui(null); + assertThat(dto.getSoldeDisponibleAujourdhui()).isEqualByComparingTo(BigDecimal.valueOf(500)); + } + + @Test + @DisplayName("retourne soldeDisponible null quand soldeDisponible null") + void testSoldeDisponibleNull() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + dto.setSoldeDisponible(null); + dto.setLimiteQuotidienne(BigDecimal.valueOf(1000)); + dto.setMontantUtiliseAujourdhui(BigDecimal.valueOf(100)); + assertThat(dto.getSoldeDisponibleAujourdhui()).isNull(); + } + + @Test + @DisplayName("retourne le minimum entre solde et limite restante") + void testMinimum() { + WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(500)); + dto.setLimiteQuotidienne(BigDecimal.valueOf(1000)); + dto.setMontantUtiliseAujourdhui(BigDecimal.valueOf(700)); + assertThat(dto.getSoldeDisponibleAujourdhui()).isEqualByComparingTo(BigDecimal.valueOf(300)); + } + } + + @Nested + @DisplayName("mettreAJourApresTransaction") + class MettreAJourApresTransaction { + + @Test + @DisplayName("initialise les champs null puis incrémente") + void testAvecChampsNull() { + WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(1000)); + dto.setMontantUtiliseAujourdhui(null); + dto.setMontantUtiliseCeMois(null); + dto.setNombreTransactionsAujourdhui(null); + dto.setNombreTransactionsCeMois(null); + dto.mettreAJourApresTransaction(BigDecimal.valueOf(50)); + assertThat(dto.getMontantUtiliseAujourdhui()).isEqualByComparingTo(BigDecimal.valueOf(50)); + assertThat(dto.getMontantUtiliseCeMois()).isEqualByComparingTo(BigDecimal.valueOf(50)); + assertThat(dto.getNombreTransactionsAujourdhui()).isEqualTo(1); + assertThat(dto.getNombreTransactionsCeMois()).isEqualTo(1); + assertThat(dto.getDateDerniereMiseAJour()).isNotNull(); + } + + @Test + @DisplayName("ajoute au montant existant") + void testAvecValeursExistantes() { + WaveBalanceDTO dto = new WaveBalanceDTO("w", BigDecimal.valueOf(1000)); + dto.setMontantUtiliseAujourdhui(BigDecimal.valueOf(100)); + dto.setMontantUtiliseCeMois(BigDecimal.valueOf(200)); + dto.setNombreTransactionsAujourdhui(2); + dto.setNombreTransactionsCeMois(3); + dto.mettreAJourApresTransaction(BigDecimal.valueOf(25)); + assertThat(dto.getMontantUtiliseAujourdhui()).isEqualByComparingTo(BigDecimal.valueOf(125)); + assertThat(dto.getMontantUtiliseCeMois()).isEqualByComparingTo(BigDecimal.valueOf(225)); + assertThat(dto.getNombreTransactionsAujourdhui()).isEqualTo(3); + assertThat(dto.getNombreTransactionsCeMois()).isEqualTo(4); + } + } + + @Nested + @DisplayName("toString") + class ToString { + + @Test + @DisplayName("contient numeroWallet et solde") + void testToString() { + WaveBalanceDTO dto = new WaveBalanceDTO("wallet-1", BigDecimal.valueOf(500)); + String s = dto.toString(); + assertThat(s).contains("wallet-1"); + assertThat(s).contains("500"); + } + } + + @Nested + @DisplayName("Getters et Setters complémentaires") + class GettersSettersComplementaires { + + @Test + @DisplayName("setSoldeTotal / getSoldeTotal") + void testSoldeTotal() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + dto.setSoldeTotal(BigDecimal.valueOf(1500)); + assertThat(dto.getSoldeTotal()).isEqualByComparingTo(BigDecimal.valueOf(1500)); + } + + @Test + @DisplayName("setDevise / getDevise") + void testDevise() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + dto.setDevise("USD"); + assertThat(dto.getDevise()).isEqualTo("USD"); + } + + @Test + @DisplayName("setNumeroWallet / getNumeroWallet") + void testNumeroWallet() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + dto.setNumeroWallet("+221771234567"); + assertThat(dto.getNumeroWallet()).isEqualTo("+221771234567"); + } + + @Test + @DisplayName("setNomBusiness / getNomBusiness") + void testNomBusiness() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + dto.setNomBusiness("UnionFlow Business"); + assertThat(dto.getNomBusiness()).isEqualTo("UnionFlow Business"); + } + + @Test + @DisplayName("setDateDerniereMiseAJour / getDateDerniereMiseAJour") + void testDateDerniereMiseAJour() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + LocalDateTime now = LocalDateTime.now(); + dto.setDateDerniereMiseAJour(now); + assertThat(dto.getDateDerniereMiseAJour()).isEqualTo(now); + } + + @Test + @DisplayName("setDateDerniereSynchronisation / getDateDerniereSynchronisation") + void testDateDerniereSynchronisation() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + LocalDateTime dateSync = LocalDateTime.of(2025, 1, 15, 10, 30); + dto.setDateDerniereSynchronisation(dateSync); + assertThat(dto.getDateDerniereSynchronisation()).isEqualTo(dateSync); + } + + @Test + @DisplayName("setLimiteQuotidienne / getLimiteQuotidienne") + void testLimiteQuotidienne() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + dto.setLimiteQuotidienne(BigDecimal.valueOf(50000)); + assertThat(dto.getLimiteQuotidienne()).isEqualByComparingTo(BigDecimal.valueOf(50000)); + } + + @Test + @DisplayName("setLimiteMensuelle / getLimiteMensuelle") + void testLimiteMensuelle() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + dto.setLimiteMensuelle(BigDecimal.valueOf(500000)); + assertThat(dto.getLimiteMensuelle()).isEqualByComparingTo(BigDecimal.valueOf(500000)); + } + + @Test + @DisplayName("setDerniereErreur / getDerniereErreur") + void testDerniereErreur() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + dto.setDerniereErreur("Erreur de synchronisation avec Wave API"); + assertThat(dto.getDerniereErreur()).isEqualTo("Erreur de synchronisation avec Wave API"); + } + + @Test + @DisplayName("setCodeDerniereErreur / getCodeDerniereErreur") + void testCodeDerniereErreur() { + WaveBalanceDTO dto = new WaveBalanceDTO(); + dto.setCodeDerniereErreur("ERR_WAVE_500"); + assertThat(dto.getCodeDerniereErreur()).isEqualTo("ERR_WAVE_500"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/paiement/WaveCheckoutSessionDTOTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/paiement/WaveCheckoutSessionDTOTest.java index 16ef7da..7d2f98c 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/paiement/WaveCheckoutSessionDTOTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/paiement/WaveCheckoutSessionDTOTest.java @@ -1,54 +1,54 @@ -package dev.lions.unionflow.server.api.dto.paiement; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.math.BigDecimal; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import dev.lions.unionflow.server.api.enums.paiement.StatutSession; - -/** - * Tests unitaires pour WaveCheckoutSessionDTO. - * Couvre constructeurs et getters pour 100% instructions. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests WaveCheckoutSessionDTO") -class WaveCheckoutSessionDTOTest { - - @Nested - @DisplayName("Constructeur par défaut") - class ConstructeurDefaut { - - @Test - @DisplayName("initialise devise, statut et flags") - void testConstructeurVide() { - WaveCheckoutSessionDTO dto = new WaveCheckoutSessionDTO(); - assertThat(dto.getDevise()).isEqualTo("XOF"); - assertThat(dto.getStatut()).isEqualTo(StatutSession.PENDING); - assertThat(dto.getNombreTentatives()).isEqualTo(0); - assertThat(dto.getWebhookRecu()).isFalse(); - } - } - - @Nested - @DisplayName("Constructeur avec URLs") - class ConstructeurAvecUrls { - - @Test - @DisplayName("remplit montant, successUrl, errorUrl") - void testConstructeurAvecUrls() { - WaveCheckoutSessionDTO dto = new WaveCheckoutSessionDTO( - BigDecimal.valueOf(5000), - "https://example.com/success", - "https://example.com/error"); - assertThat(dto.getMontant()).isEqualByComparingTo(BigDecimal.valueOf(5000)); - assertThat(dto.getSuccessUrl()).isEqualTo("https://example.com/success"); - assertThat(dto.getErrorUrl()).isEqualTo("https://example.com/error"); - assertThat(dto.getStatut()).isEqualTo(StatutSession.PENDING); - } - } -} +package dev.lions.unionflow.server.api.dto.paiement; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.math.BigDecimal; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import dev.lions.unionflow.server.api.enums.paiement.StatutSession; + +/** + * Tests unitaires pour WaveCheckoutSessionDTO. + * Couvre constructeurs et getters pour 100% instructions. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests WaveCheckoutSessionDTO") +class WaveCheckoutSessionDTOTest { + + @Nested + @DisplayName("Constructeur par défaut") + class ConstructeurDefaut { + + @Test + @DisplayName("initialise devise, statut et flags") + void testConstructeurVide() { + WaveCheckoutSessionDTO dto = new WaveCheckoutSessionDTO(); + assertThat(dto.getDevise()).isEqualTo("XOF"); + assertThat(dto.getStatut()).isEqualTo(StatutSession.PENDING); + assertThat(dto.getNombreTentatives()).isEqualTo(0); + assertThat(dto.getWebhookRecu()).isFalse(); + } + } + + @Nested + @DisplayName("Constructeur avec URLs") + class ConstructeurAvecUrls { + + @Test + @DisplayName("remplit montant, successUrl, errorUrl") + void testConstructeurAvecUrls() { + WaveCheckoutSessionDTO dto = new WaveCheckoutSessionDTO( + BigDecimal.valueOf(5000), + "https://example.com/success", + "https://example.com/error"); + assertThat(dto.getMontant()).isEqualByComparingTo(BigDecimal.valueOf(5000)); + assertThat(dto.getSuccessUrl()).isEqualTo("https://example.com/success"); + assertThat(dto.getErrorUrl()).isEqualTo("https://example.com/error"); + assertThat(dto.getStatut()).isEqualTo(StatutSession.PENDING); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/paiement/WaveWebhookDTOTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/paiement/WaveWebhookDTOTest.java index dfd8db3..5ea2cd6 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/paiement/WaveWebhookDTOTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/paiement/WaveWebhookDTOTest.java @@ -1,340 +1,340 @@ -package dev.lions.unionflow.server.api.dto.paiement; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.math.BigDecimal; -import java.time.LocalDateTime; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import dev.lions.unionflow.server.api.enums.paiement.StatutTraitement; -import dev.lions.unionflow.server.api.enums.paiement.TypeEvenement; - -/** - * Tests unitaires pour WaveWebhookDTO. - * Couvre toutes les branches : setTypeEvenement/setCodeEvenement, isEvenementCheckout, - * isEvenementPayout, marquerCommeTraite, marquerCommeEchec, demarrerTraitement. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests WaveWebhookDTO") -class WaveWebhookDTOTest { - - @Nested - @DisplayName("Constructeurs") - class Constructeurs { - - @Test - @DisplayName("constructeur par défaut initialise statut et date") - void testConstructeurVide() { - WaveWebhookDTO dto = new WaveWebhookDTO(); - assertThat(dto.getStatutTraitement()).isEqualTo(StatutTraitement.RECU); - assertThat(dto.getDateReception()).isNotNull(); - assertThat(dto.getNombreTentativesTraitement()).isEqualTo(0); - assertThat(dto.getTraitementAutomatique()).isTrue(); - } - - @Test - @DisplayName("constructeur avec paramètres remplit type et code") - void testConstructeurAvecParams() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); - assertThat(dto.getWebhookId()).isEqualTo("wh-1"); - assertThat(dto.getTypeEvenement()).isEqualTo(TypeEvenement.CHECKOUT_COMPLETE); - assertThat(dto.getCodeEvenement()).isEqualTo("checkout.complete"); - assertThat(dto.getPayloadJson()).isEqualTo("{}"); - } - } - - @Nested - @DisplayName("setTypeEvenement") - class SetTypeEvenement { - - @Test - @DisplayName("met à jour codeEvenement quand type non null") - void testTypeNonNull() { - WaveWebhookDTO dto = new WaveWebhookDTO(); - dto.setTypeEvenement(TypeEvenement.PAYOUT_COMPLETE); - assertThat(dto.getTypeEvenement()).isEqualTo(TypeEvenement.PAYOUT_COMPLETE); - assertThat(dto.getCodeEvenement()).isEqualTo("payout.complete"); - } - - @Test - @DisplayName("ne modifie pas codeEvenement quand type null") - void testTypeNull() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); - dto.setCodeEvenement("custom.code"); - dto.setTypeEvenement(null); - assertThat(dto.getCodeEvenement()).isEqualTo("custom.code"); - } - } - - @Nested - @DisplayName("setCodeEvenement") - class SetCodeEvenement { - - @Test - @DisplayName("définit typeEvenement via fromCode") - void testFromCode() { - WaveWebhookDTO dto = new WaveWebhookDTO(); - dto.setCodeEvenement("checkout.cancelled"); - assertThat(dto.getTypeEvenement()).isEqualTo(TypeEvenement.CHECKOUT_CANCELLED); - assertThat(dto.getCodeEvenement()).isEqualTo("checkout.cancelled"); - } - - @Test - @DisplayName("code inconnu met typeEvenement à null") - void testCodeInconnu() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); - dto.setCodeEvenement("unknown.event"); - assertThat(dto.getTypeEvenement()).isNull(); - } - } - - @Nested - @DisplayName("isEvenementCheckout") - class IsEvenementCheckout { - - @Test - @DisplayName("true pour CHECKOUT_COMPLETE") - void testCheckoutComplete() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); - assertThat(dto.isEvenementCheckout()).isTrue(); - } - - @Test - @DisplayName("true pour CHECKOUT_CANCELLED") - void testCheckoutCancelled() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_CANCELLED, "{}"); - assertThat(dto.isEvenementCheckout()).isTrue(); - } - - @Test - @DisplayName("true pour CHECKOUT_EXPIRED") - void testCheckoutExpired() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_EXPIRED, "{}"); - assertThat(dto.isEvenementCheckout()).isTrue(); - } - - @Test - @DisplayName("false pour PAYOUT_COMPLETE") - void testPayout() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.PAYOUT_COMPLETE, "{}"); - assertThat(dto.isEvenementCheckout()).isFalse(); - } - } - - @Nested - @DisplayName("isEvenementPayout") - class IsEvenementPayout { - - @Test - @DisplayName("true pour PAYOUT_COMPLETE") - void testPayoutComplete() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.PAYOUT_COMPLETE, "{}"); - assertThat(dto.isEvenementPayout()).isTrue(); - } - - @Test - @DisplayName("true pour PAYOUT_FAILED") - void testPayoutFailed() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.PAYOUT_FAILED, "{}"); - assertThat(dto.isEvenementPayout()).isTrue(); - } - - @Test - @DisplayName("false pour CHECKOUT_COMPLETE") - void testCheckout() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); - assertThat(dto.isEvenementPayout()).isFalse(); - } - } - - @Nested - @DisplayName("marquerCommeTraite") - class MarquerCommeTraite { - - @Test - @DisplayName("passe statut à TRAITE et remplit dateTraitement") - void testMarquerCommeTraite() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); - dto.marquerCommeTraite(); - assertThat(dto.getStatutTraitement()).isEqualTo(StatutTraitement.TRAITE); - assertThat(dto.getDateTraitement()).isNotNull(); - } - } - - @Nested - @DisplayName("marquerCommeEchec") - class MarquerCommeEchec { - - @Test - @DisplayName("passe statut à ECHEC et incrémente tentatives") - void testMarquerCommeEchec() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); - dto.marquerCommeEchec("Erreur", "ERR_01"); - assertThat(dto.getStatutTraitement()).isEqualTo(StatutTraitement.ECHEC); - assertThat(dto.getMessageErreurTraitement()).isEqualTo("Erreur"); - assertThat(dto.getCodeErreurTraitement()).isEqualTo("ERR_01"); - assertThat(dto.getNombreTentativesTraitement()).isEqualTo(1); - } - } - - @Nested - @DisplayName("demarrerTraitement") - class DemarrerTraitement { - - @Test - @DisplayName("passe statut à EN_COURS et incrémente tentatives") - void testDemarrerTraitement() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); - dto.demarrerTraitement(); - assertThat(dto.getStatutTraitement()).isEqualTo(StatutTraitement.EN_COURS); - assertThat(dto.getNombreTentativesTraitement()).isEqualTo(1); - } - } - - @Nested - @DisplayName("toString") - class ToString { - - @Test - @DisplayName("contient webhookId et statut") - void testToString() { - WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); - dto.setSessionCheckoutId("sess-1"); - dto.setMontantTransaction(BigDecimal.TEN); - String s = dto.toString(); - assertThat(s).contains("wh-1"); - assertThat(s).contains("RECU"); - assertThat(s).contains("sess-1"); - } - } - - @Nested - @DisplayName("Getters et Setters") - class GettersEtSetters { - - @Test - @DisplayName("tous les getters et setters fonctionnent correctement") - void testTousLesGettersSetters() { - WaveWebhookDTO dto = new WaveWebhookDTO(); - - // Test webhookId - dto.setWebhookId("webhook-test-123"); - assertThat(dto.getWebhookId()).isEqualTo("webhook-test-123"); - - // Test statutTraitement - dto.setStatutTraitement(StatutTraitement.EN_COURS); - assertThat(dto.getStatutTraitement()).isEqualTo(StatutTraitement.EN_COURS); - - // Test payloadJson - dto.setPayloadJson("{\"test\": \"value\"}"); - assertThat(dto.getPayloadJson()).isEqualTo("{\"test\": \"value\"}"); - - // Test headersHttp - dto.setHeadersHttp("Content-Type: application/json"); - assertThat(dto.getHeadersHttp()).isEqualTo("Content-Type: application/json"); - - // Test signatureWave - dto.setSignatureWave("signature-abc123"); - assertThat(dto.getSignatureWave()).isEqualTo("signature-abc123"); - - // Test dateReception - LocalDateTime dateReception = LocalDateTime.of(2026, 3, 13, 10, 30); - dto.setDateReception(dateReception); - assertThat(dto.getDateReception()).isEqualTo(dateReception); - - // Test dateTraitement - LocalDateTime dateTraitement = LocalDateTime.of(2026, 3, 13, 11, 0); - dto.setDateTraitement(dateTraitement); - assertThat(dto.getDateTraitement()).isEqualTo(dateTraitement); - - // Test sessionCheckoutId - dto.setSessionCheckoutId("checkout-session-456"); - assertThat(dto.getSessionCheckoutId()).isEqualTo("checkout-session-456"); - - // Test transactionWaveId - dto.setTransactionWaveId("wave-txn-789"); - assertThat(dto.getTransactionWaveId()).isEqualTo("wave-txn-789"); - - // Test montantTransaction - BigDecimal montant = new BigDecimal("1500.50"); - dto.setMontantTransaction(montant); - assertThat(dto.getMontantTransaction()).isEqualTo(montant); - - // Test deviseTransaction - dto.setDeviseTransaction("XOF"); - assertThat(dto.getDeviseTransaction()).isEqualTo("XOF"); - - // Test statutTransactionWave - dto.setStatutTransactionWave("COMPLETED"); - assertThat(dto.getStatutTransactionWave()).isEqualTo("COMPLETED"); - - // Test organisationId - UUID orgId = UUID.randomUUID(); - dto.setOrganisationId(orgId); - assertThat(dto.getOrganisationId()).isEqualTo(orgId); - - // Test membreId - UUID membreId = UUID.randomUUID(); - dto.setMembreId(membreId); - assertThat(dto.getMembreId()).isEqualTo(membreId); - - // Test referenceUnionFlow - dto.setReferenceUnionFlow("REF-UF-2026-001"); - assertThat(dto.getReferenceUnionFlow()).isEqualTo("REF-UF-2026-001"); - - // Test typePaiementUnionFlow - dto.setTypePaiementUnionFlow("COTISATION"); - assertThat(dto.getTypePaiementUnionFlow()).isEqualTo("COTISATION"); - - // Test adresseIpSource - dto.setAdresseIpSource("192.168.1.100"); - assertThat(dto.getAdresseIpSource()).isEqualTo("192.168.1.100"); - - // Test userAgentSource - dto.setUserAgentSource("Mozilla/5.0"); - assertThat(dto.getUserAgentSource()).isEqualTo("Mozilla/5.0"); - - // Test nombreTentativesTraitement - dto.setNombreTentativesTraitement(3); - assertThat(dto.getNombreTentativesTraitement()).isEqualTo(3); - - // Test messageErreurTraitement - dto.setMessageErreurTraitement("Erreur de connexion"); - assertThat(dto.getMessageErreurTraitement()).isEqualTo("Erreur de connexion"); - - // Test codeErreurTraitement - dto.setCodeErreurTraitement("ERR_TIMEOUT"); - assertThat(dto.getCodeErreurTraitement()).isEqualTo("ERR_TIMEOUT"); - - // Test stackTraceErreur - dto.setStackTraceErreur("java.lang.Exception: Test\n\tat Class.method(...)"); - assertThat(dto.getStackTraceErreur()).isEqualTo("java.lang.Exception: Test\n\tat Class.method(...)"); - - // Test traitementAutomatique - dto.setTraitementAutomatique(false); - assertThat(dto.getTraitementAutomatique()).isFalse(); - - // Test interventionManuelleRequise - dto.setInterventionManuelleRequise(true); - assertThat(dto.getInterventionManuelleRequise()).isTrue(); - - // Test notesTraitementManuel - dto.setNotesTraitementManuel("Traité manuellement après erreur"); - assertThat(dto.getNotesTraitementManuel()).isEqualTo("Traité manuellement après erreur"); - - // Test utilisateurTraitementManuel - dto.setUtilisateurTraitementManuel("admin@unionflow.com"); - assertThat(dto.getUtilisateurTraitementManuel()).isEqualTo("admin@unionflow.com"); - - // Test dateTraitementManuel - LocalDateTime dateManuel = LocalDateTime.of(2026, 3, 13, 15, 0); - dto.setDateTraitementManuel(dateManuel); - assertThat(dto.getDateTraitementManuel()).isEqualTo(dateManuel); - } - } -} +package dev.lions.unionflow.server.api.dto.paiement; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.math.BigDecimal; +import java.time.LocalDateTime; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import dev.lions.unionflow.server.api.enums.paiement.StatutTraitement; +import dev.lions.unionflow.server.api.enums.paiement.TypeEvenement; + +/** + * Tests unitaires pour WaveWebhookDTO. + * Couvre toutes les branches : setTypeEvenement/setCodeEvenement, isEvenementCheckout, + * isEvenementPayout, marquerCommeTraite, marquerCommeEchec, demarrerTraitement. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests WaveWebhookDTO") +class WaveWebhookDTOTest { + + @Nested + @DisplayName("Constructeurs") + class Constructeurs { + + @Test + @DisplayName("constructeur par défaut initialise statut et date") + void testConstructeurVide() { + WaveWebhookDTO dto = new WaveWebhookDTO(); + assertThat(dto.getStatutTraitement()).isEqualTo(StatutTraitement.RECU); + assertThat(dto.getDateReception()).isNotNull(); + assertThat(dto.getNombreTentativesTraitement()).isEqualTo(0); + assertThat(dto.getTraitementAutomatique()).isTrue(); + } + + @Test + @DisplayName("constructeur avec paramètres remplit type et code") + void testConstructeurAvecParams() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); + assertThat(dto.getWebhookId()).isEqualTo("wh-1"); + assertThat(dto.getTypeEvenement()).isEqualTo(TypeEvenement.CHECKOUT_COMPLETE); + assertThat(dto.getCodeEvenement()).isEqualTo("checkout.complete"); + assertThat(dto.getPayloadJson()).isEqualTo("{}"); + } + } + + @Nested + @DisplayName("setTypeEvenement") + class SetTypeEvenement { + + @Test + @DisplayName("met à jour codeEvenement quand type non null") + void testTypeNonNull() { + WaveWebhookDTO dto = new WaveWebhookDTO(); + dto.setTypeEvenement(TypeEvenement.PAYOUT_COMPLETE); + assertThat(dto.getTypeEvenement()).isEqualTo(TypeEvenement.PAYOUT_COMPLETE); + assertThat(dto.getCodeEvenement()).isEqualTo("payout.complete"); + } + + @Test + @DisplayName("ne modifie pas codeEvenement quand type null") + void testTypeNull() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); + dto.setCodeEvenement("custom.code"); + dto.setTypeEvenement(null); + assertThat(dto.getCodeEvenement()).isEqualTo("custom.code"); + } + } + + @Nested + @DisplayName("setCodeEvenement") + class SetCodeEvenement { + + @Test + @DisplayName("définit typeEvenement via fromCode") + void testFromCode() { + WaveWebhookDTO dto = new WaveWebhookDTO(); + dto.setCodeEvenement("checkout.cancelled"); + assertThat(dto.getTypeEvenement()).isEqualTo(TypeEvenement.CHECKOUT_CANCELLED); + assertThat(dto.getCodeEvenement()).isEqualTo("checkout.cancelled"); + } + + @Test + @DisplayName("code inconnu met typeEvenement à null") + void testCodeInconnu() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); + dto.setCodeEvenement("unknown.event"); + assertThat(dto.getTypeEvenement()).isNull(); + } + } + + @Nested + @DisplayName("isEvenementCheckout") + class IsEvenementCheckout { + + @Test + @DisplayName("true pour CHECKOUT_COMPLETE") + void testCheckoutComplete() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); + assertThat(dto.isEvenementCheckout()).isTrue(); + } + + @Test + @DisplayName("true pour CHECKOUT_CANCELLED") + void testCheckoutCancelled() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_CANCELLED, "{}"); + assertThat(dto.isEvenementCheckout()).isTrue(); + } + + @Test + @DisplayName("true pour CHECKOUT_EXPIRED") + void testCheckoutExpired() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_EXPIRED, "{}"); + assertThat(dto.isEvenementCheckout()).isTrue(); + } + + @Test + @DisplayName("false pour PAYOUT_COMPLETE") + void testPayout() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.PAYOUT_COMPLETE, "{}"); + assertThat(dto.isEvenementCheckout()).isFalse(); + } + } + + @Nested + @DisplayName("isEvenementPayout") + class IsEvenementPayout { + + @Test + @DisplayName("true pour PAYOUT_COMPLETE") + void testPayoutComplete() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.PAYOUT_COMPLETE, "{}"); + assertThat(dto.isEvenementPayout()).isTrue(); + } + + @Test + @DisplayName("true pour PAYOUT_FAILED") + void testPayoutFailed() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.PAYOUT_FAILED, "{}"); + assertThat(dto.isEvenementPayout()).isTrue(); + } + + @Test + @DisplayName("false pour CHECKOUT_COMPLETE") + void testCheckout() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); + assertThat(dto.isEvenementPayout()).isFalse(); + } + } + + @Nested + @DisplayName("marquerCommeTraite") + class MarquerCommeTraite { + + @Test + @DisplayName("passe statut à TRAITE et remplit dateTraitement") + void testMarquerCommeTraite() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); + dto.marquerCommeTraite(); + assertThat(dto.getStatutTraitement()).isEqualTo(StatutTraitement.TRAITE); + assertThat(dto.getDateTraitement()).isNotNull(); + } + } + + @Nested + @DisplayName("marquerCommeEchec") + class MarquerCommeEchec { + + @Test + @DisplayName("passe statut à ECHEC et incrémente tentatives") + void testMarquerCommeEchec() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); + dto.marquerCommeEchec("Erreur", "ERR_01"); + assertThat(dto.getStatutTraitement()).isEqualTo(StatutTraitement.ECHEC); + assertThat(dto.getMessageErreurTraitement()).isEqualTo("Erreur"); + assertThat(dto.getCodeErreurTraitement()).isEqualTo("ERR_01"); + assertThat(dto.getNombreTentativesTraitement()).isEqualTo(1); + } + } + + @Nested + @DisplayName("demarrerTraitement") + class DemarrerTraitement { + + @Test + @DisplayName("passe statut à EN_COURS et incrémente tentatives") + void testDemarrerTraitement() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); + dto.demarrerTraitement(); + assertThat(dto.getStatutTraitement()).isEqualTo(StatutTraitement.EN_COURS); + assertThat(dto.getNombreTentativesTraitement()).isEqualTo(1); + } + } + + @Nested + @DisplayName("toString") + class ToString { + + @Test + @DisplayName("contient webhookId et statut") + void testToString() { + WaveWebhookDTO dto = new WaveWebhookDTO("wh-1", TypeEvenement.CHECKOUT_COMPLETE, "{}"); + dto.setSessionCheckoutId("sess-1"); + dto.setMontantTransaction(BigDecimal.TEN); + String s = dto.toString(); + assertThat(s).contains("wh-1"); + assertThat(s).contains("RECU"); + assertThat(s).contains("sess-1"); + } + } + + @Nested + @DisplayName("Getters et Setters") + class GettersEtSetters { + + @Test + @DisplayName("tous les getters et setters fonctionnent correctement") + void testTousLesGettersSetters() { + WaveWebhookDTO dto = new WaveWebhookDTO(); + + // Test webhookId + dto.setWebhookId("webhook-test-123"); + assertThat(dto.getWebhookId()).isEqualTo("webhook-test-123"); + + // Test statutTraitement + dto.setStatutTraitement(StatutTraitement.EN_COURS); + assertThat(dto.getStatutTraitement()).isEqualTo(StatutTraitement.EN_COURS); + + // Test payloadJson + dto.setPayloadJson("{\"test\": \"value\"}"); + assertThat(dto.getPayloadJson()).isEqualTo("{\"test\": \"value\"}"); + + // Test headersHttp + dto.setHeadersHttp("Content-Type: application/json"); + assertThat(dto.getHeadersHttp()).isEqualTo("Content-Type: application/json"); + + // Test signatureWave + dto.setSignatureWave("signature-abc123"); + assertThat(dto.getSignatureWave()).isEqualTo("signature-abc123"); + + // Test dateReception + LocalDateTime dateReception = LocalDateTime.of(2026, 3, 13, 10, 30); + dto.setDateReception(dateReception); + assertThat(dto.getDateReception()).isEqualTo(dateReception); + + // Test dateTraitement + LocalDateTime dateTraitement = LocalDateTime.of(2026, 3, 13, 11, 0); + dto.setDateTraitement(dateTraitement); + assertThat(dto.getDateTraitement()).isEqualTo(dateTraitement); + + // Test sessionCheckoutId + dto.setSessionCheckoutId("checkout-session-456"); + assertThat(dto.getSessionCheckoutId()).isEqualTo("checkout-session-456"); + + // Test transactionWaveId + dto.setTransactionWaveId("wave-txn-789"); + assertThat(dto.getTransactionWaveId()).isEqualTo("wave-txn-789"); + + // Test montantTransaction + BigDecimal montant = new BigDecimal("1500.50"); + dto.setMontantTransaction(montant); + assertThat(dto.getMontantTransaction()).isEqualTo(montant); + + // Test deviseTransaction + dto.setDeviseTransaction("XOF"); + assertThat(dto.getDeviseTransaction()).isEqualTo("XOF"); + + // Test statutTransactionWave + dto.setStatutTransactionWave("COMPLETED"); + assertThat(dto.getStatutTransactionWave()).isEqualTo("COMPLETED"); + + // Test organisationId + UUID orgId = UUID.randomUUID(); + dto.setOrganisationId(orgId); + assertThat(dto.getOrganisationId()).isEqualTo(orgId); + + // Test membreId + UUID membreId = UUID.randomUUID(); + dto.setMembreId(membreId); + assertThat(dto.getMembreId()).isEqualTo(membreId); + + // Test referenceUnionFlow + dto.setReferenceUnionFlow("REF-UF-2026-001"); + assertThat(dto.getReferenceUnionFlow()).isEqualTo("REF-UF-2026-001"); + + // Test typePaiementUnionFlow + dto.setTypePaiementUnionFlow("COTISATION"); + assertThat(dto.getTypePaiementUnionFlow()).isEqualTo("COTISATION"); + + // Test adresseIpSource + dto.setAdresseIpSource("192.168.1.100"); + assertThat(dto.getAdresseIpSource()).isEqualTo("192.168.1.100"); + + // Test userAgentSource + dto.setUserAgentSource("Mozilla/5.0"); + assertThat(dto.getUserAgentSource()).isEqualTo("Mozilla/5.0"); + + // Test nombreTentativesTraitement + dto.setNombreTentativesTraitement(3); + assertThat(dto.getNombreTentativesTraitement()).isEqualTo(3); + + // Test messageErreurTraitement + dto.setMessageErreurTraitement("Erreur de connexion"); + assertThat(dto.getMessageErreurTraitement()).isEqualTo("Erreur de connexion"); + + // Test codeErreurTraitement + dto.setCodeErreurTraitement("ERR_TIMEOUT"); + assertThat(dto.getCodeErreurTraitement()).isEqualTo("ERR_TIMEOUT"); + + // Test stackTraceErreur + dto.setStackTraceErreur("java.lang.Exception: Test\n\tat Class.method(...)"); + assertThat(dto.getStackTraceErreur()).isEqualTo("java.lang.Exception: Test\n\tat Class.method(...)"); + + // Test traitementAutomatique + dto.setTraitementAutomatique(false); + assertThat(dto.getTraitementAutomatique()).isFalse(); + + // Test interventionManuelleRequise + dto.setInterventionManuelleRequise(true); + assertThat(dto.getInterventionManuelleRequise()).isTrue(); + + // Test notesTraitementManuel + dto.setNotesTraitementManuel("Traité manuellement après erreur"); + assertThat(dto.getNotesTraitementManuel()).isEqualTo("Traité manuellement après erreur"); + + // Test utilisateurTraitementManuel + dto.setUtilisateurTraitementManuel("admin@unionflow.com"); + assertThat(dto.getUtilisateurTraitementManuel()).isEqualTo("admin@unionflow.com"); + + // Test dateTraitementManuel + LocalDateTime dateManuel = LocalDateTime.of(2026, 3, 13, 15, 0); + dto.setDateTraitementManuel(dateManuel); + assertThat(dto.getDateTraitementManuel()).isEqualTo(dateManuel); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/reference/request/CreateTypeReferenceRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/reference/request/CreateTypeReferenceRequestTest.java index ca557c7..bd94c68 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/reference/request/CreateTypeReferenceRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/reference/request/CreateTypeReferenceRequestTest.java @@ -1,173 +1,173 @@ -package dev.lions.unionflow.server.api.dto.reference.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateTypeReferenceRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID organisationId = UUID.randomUUID(); - - CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder() - .domaine("STATUT_ORGANISATION") - .code("ACTIF") - .libelle("Organisation Active") - .description("Organisation en activité") - .icone("pi-check") - .couleur("#22C55E") - .severity("success") - .ordreAffichage(1) - .estDefaut(true) - .estSysteme(true) - .organisationId(organisationId) - .categorie("FINANCIER_SOLIDAIRE") - .modulesRequis("MEMBRES,COTISATIONS,TONTINE,FINANCE") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.domaine()).isEqualTo("STATUT_ORGANISATION"); - assertThat(request.code()).isEqualTo("ACTIF"); - assertThat(request.libelle()).isEqualTo("Organisation Active"); - assertThat(request.description()).isEqualTo("Organisation en activité"); - assertThat(request.icone()).isEqualTo("pi-check"); - assertThat(request.couleur()).isEqualTo("#22C55E"); - assertThat(request.severity()).isEqualTo("success"); - assertThat(request.ordreAffichage()).isEqualTo(1); - assertThat(request.estDefaut()).isTrue(); - assertThat(request.estSysteme()).isTrue(); - assertThat(request.organisationId()).isEqualTo(organisationId); - assertThat(request.categorie()).isEqualTo("FINANCIER_SOLIDAIRE"); - assertThat(request.modulesRequis()).isEqualTo("MEMBRES,COTISATIONS,TONTINE,FINANCE"); - } - - @Test - void testBuilder_MinimalFields() { - CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder() - .domaine("DOMAINE_TEST") - .code("CODE_TEST") - .libelle("Libellé Test") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.domaine()).isEqualTo("DOMAINE_TEST"); - assertThat(request.code()).isEqualTo("CODE_TEST"); - assertThat(request.libelle()).isEqualTo("Libellé Test"); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("domaine")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); - } - - @Test - void testValidation_DomaineTooLong() { - String longDomaine = "A".repeat(51); - CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder() - .domaine(longDomaine) - .code("CODE") - .libelle("Libellé") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("domaine")); - } - - @Test - void testValidation_CodeTooLong() { - String longCode = "A".repeat(51); - CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder() - .domaine("DOMAINE") - .code(longCode) - .libelle("Libellé") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - } - - @Test - void testValidation_ValidFields() { - CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder() - .domaine("STATUT_MEMBRE") - .code("ACTIF") - .libelle("Membre Actif") - .description("Membre en activité") - .icone("pi-user") - .couleur("#22C55E") - .severity("success") - .ordreAffichage(1) - .estDefaut(false) - .estSysteme(false) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID orgId = UUID.randomUUID(); - - CreateTypeReferenceRequest request1 = CreateTypeReferenceRequest.builder() - .domaine("DOMAINE") - .code("CODE") - .libelle("Libellé") - .organisationId(orgId) - .build(); - - CreateTypeReferenceRequest request2 = CreateTypeReferenceRequest.builder() - .domaine("DOMAINE") - .code("CODE") - .libelle("Libellé") - .organisationId(orgId) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder() - .domaine("STATUT_ORGANISATION") - .code("ACTIF") - .libelle("Organisation Active") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateTypeReferenceRequest"); - assertThat(toString).contains("STATUT_ORGANISATION"); - assertThat(toString).contains("ACTIF"); - } -} +package dev.lions.unionflow.server.api.dto.reference.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateTypeReferenceRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID organisationId = UUID.randomUUID(); + + CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder() + .domaine("STATUT_ORGANISATION") + .code("ACTIF") + .libelle("Organisation Active") + .description("Organisation en activité") + .icone("pi-check") + .couleur("#22C55E") + .severity("success") + .ordreAffichage(1) + .estDefaut(true) + .estSysteme(true) + .organisationId(organisationId) + .categorie("FINANCIER_SOLIDAIRE") + .modulesRequis("MEMBRES,COTISATIONS,TONTINE,FINANCE") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.domaine()).isEqualTo("STATUT_ORGANISATION"); + assertThat(request.code()).isEqualTo("ACTIF"); + assertThat(request.libelle()).isEqualTo("Organisation Active"); + assertThat(request.description()).isEqualTo("Organisation en activité"); + assertThat(request.icone()).isEqualTo("pi-check"); + assertThat(request.couleur()).isEqualTo("#22C55E"); + assertThat(request.severity()).isEqualTo("success"); + assertThat(request.ordreAffichage()).isEqualTo(1); + assertThat(request.estDefaut()).isTrue(); + assertThat(request.estSysteme()).isTrue(); + assertThat(request.organisationId()).isEqualTo(organisationId); + assertThat(request.categorie()).isEqualTo("FINANCIER_SOLIDAIRE"); + assertThat(request.modulesRequis()).isEqualTo("MEMBRES,COTISATIONS,TONTINE,FINANCE"); + } + + @Test + void testBuilder_MinimalFields() { + CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder() + .domaine("DOMAINE_TEST") + .code("CODE_TEST") + .libelle("Libellé Test") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.domaine()).isEqualTo("DOMAINE_TEST"); + assertThat(request.code()).isEqualTo("CODE_TEST"); + assertThat(request.libelle()).isEqualTo("Libellé Test"); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("domaine")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); + } + + @Test + void testValidation_DomaineTooLong() { + String longDomaine = "A".repeat(51); + CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder() + .domaine(longDomaine) + .code("CODE") + .libelle("Libellé") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("domaine")); + } + + @Test + void testValidation_CodeTooLong() { + String longCode = "A".repeat(51); + CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder() + .domaine("DOMAINE") + .code(longCode) + .libelle("Libellé") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + } + + @Test + void testValidation_ValidFields() { + CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder() + .domaine("STATUT_MEMBRE") + .code("ACTIF") + .libelle("Membre Actif") + .description("Membre en activité") + .icone("pi-user") + .couleur("#22C55E") + .severity("success") + .ordreAffichage(1) + .estDefaut(false) + .estSysteme(false) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID orgId = UUID.randomUUID(); + + CreateTypeReferenceRequest request1 = CreateTypeReferenceRequest.builder() + .domaine("DOMAINE") + .code("CODE") + .libelle("Libellé") + .organisationId(orgId) + .build(); + + CreateTypeReferenceRequest request2 = CreateTypeReferenceRequest.builder() + .domaine("DOMAINE") + .code("CODE") + .libelle("Libellé") + .organisationId(orgId) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateTypeReferenceRequest request = CreateTypeReferenceRequest.builder() + .domaine("STATUT_ORGANISATION") + .code("ACTIF") + .libelle("Organisation Active") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateTypeReferenceRequest"); + assertThat(toString).contains("STATUT_ORGANISATION"); + assertThat(toString).contains("ACTIF"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/role/request/CreateRoleRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/role/request/CreateRoleRequestTest.java index 63de0a7..24a06b6 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/role/request/CreateRoleRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/role/request/CreateRoleRequestTest.java @@ -1,162 +1,162 @@ -package dev.lions.unionflow.server.api.dto.role.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateRoleRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID organisationId = UUID.randomUUID(); - - CreateRoleRequest request = CreateRoleRequest.builder() - .code("ROLE_ADMIN") - .libelle("Administrateur") - .description("Rôle administrateur avec tous les privilèges") - .typeRole("SYSTEM") - .niveauHierarchique(1) - .organisationId(organisationId) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.code()).isEqualTo("ROLE_ADMIN"); - assertThat(request.libelle()).isEqualTo("Administrateur"); - assertThat(request.description()).isEqualTo("Rôle administrateur avec tous les privilèges"); - assertThat(request.typeRole()).isEqualTo("SYSTEM"); - assertThat(request.niveauHierarchique()).isEqualTo(1); - assertThat(request.organisationId()).isEqualTo(organisationId); - } - - @Test - void testBuilder_MinimalFields() { - CreateRoleRequest request = CreateRoleRequest.builder() - .code("ROLE_USER") - .libelle("Utilisateur") - .typeRole("CUSTOM") - .niveauHierarchique(5) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.code()).isEqualTo("ROLE_USER"); - assertThat(request.libelle()).isEqualTo("Utilisateur"); - assertThat(request.typeRole()).isEqualTo("CUSTOM"); - assertThat(request.niveauHierarchique()).isEqualTo(5); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateRoleRequest request = CreateRoleRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeRole")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("niveauHierarchique")); - } - - @Test - void testValidation_CodeTooLong() { - String longCode = "A".repeat(51); - CreateRoleRequest request = CreateRoleRequest.builder() - .code(longCode) - .libelle("Libellé") - .typeRole("SYSTEM") - .niveauHierarchique(1) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); - } - - @Test - void testValidation_LibelleTooLong() { - String longLibelle = "A".repeat(101); - CreateRoleRequest request = CreateRoleRequest.builder() - .code("CODE") - .libelle(longLibelle) - .typeRole("SYSTEM") - .niveauHierarchique(1) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); - } - - @Test - void testValidation_ValidFields() { - CreateRoleRequest request = CreateRoleRequest.builder() - .code("ROLE_MODERATOR") - .libelle("Modérateur") - .description("Rôle de modération") - .typeRole("CUSTOM") - .niveauHierarchique(3) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID orgId = UUID.randomUUID(); - - CreateRoleRequest request1 = CreateRoleRequest.builder() - .code("ROLE_TEST") - .libelle("Test") - .typeRole("SYSTEM") - .niveauHierarchique(2) - .organisationId(orgId) - .build(); - - CreateRoleRequest request2 = CreateRoleRequest.builder() - .code("ROLE_TEST") - .libelle("Test") - .typeRole("SYSTEM") - .niveauHierarchique(2) - .organisationId(orgId) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateRoleRequest request = CreateRoleRequest.builder() - .code("ROLE_ADMIN") - .libelle("Administrateur") - .typeRole("SYSTEM") - .niveauHierarchique(1) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateRoleRequest"); - assertThat(toString).contains("ROLE_ADMIN"); - assertThat(toString).contains("Administrateur"); - } -} +package dev.lions.unionflow.server.api.dto.role.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateRoleRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID organisationId = UUID.randomUUID(); + + CreateRoleRequest request = CreateRoleRequest.builder() + .code("ROLE_ADMIN") + .libelle("Administrateur") + .description("Rôle administrateur avec tous les privilèges") + .typeRole("SYSTEM") + .niveauHierarchique(1) + .organisationId(organisationId) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.code()).isEqualTo("ROLE_ADMIN"); + assertThat(request.libelle()).isEqualTo("Administrateur"); + assertThat(request.description()).isEqualTo("Rôle administrateur avec tous les privilèges"); + assertThat(request.typeRole()).isEqualTo("SYSTEM"); + assertThat(request.niveauHierarchique()).isEqualTo(1); + assertThat(request.organisationId()).isEqualTo(organisationId); + } + + @Test + void testBuilder_MinimalFields() { + CreateRoleRequest request = CreateRoleRequest.builder() + .code("ROLE_USER") + .libelle("Utilisateur") + .typeRole("CUSTOM") + .niveauHierarchique(5) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.code()).isEqualTo("ROLE_USER"); + assertThat(request.libelle()).isEqualTo("Utilisateur"); + assertThat(request.typeRole()).isEqualTo("CUSTOM"); + assertThat(request.niveauHierarchique()).isEqualTo(5); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateRoleRequest request = CreateRoleRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeRole")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("niveauHierarchique")); + } + + @Test + void testValidation_CodeTooLong() { + String longCode = "A".repeat(51); + CreateRoleRequest request = CreateRoleRequest.builder() + .code(longCode) + .libelle("Libellé") + .typeRole("SYSTEM") + .niveauHierarchique(1) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("code")); + } + + @Test + void testValidation_LibelleTooLong() { + String longLibelle = "A".repeat(101); + CreateRoleRequest request = CreateRoleRequest.builder() + .code("CODE") + .libelle(longLibelle) + .typeRole("SYSTEM") + .niveauHierarchique(1) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); + } + + @Test + void testValidation_ValidFields() { + CreateRoleRequest request = CreateRoleRequest.builder() + .code("ROLE_MODERATOR") + .libelle("Modérateur") + .description("Rôle de modération") + .typeRole("CUSTOM") + .niveauHierarchique(3) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID orgId = UUID.randomUUID(); + + CreateRoleRequest request1 = CreateRoleRequest.builder() + .code("ROLE_TEST") + .libelle("Test") + .typeRole("SYSTEM") + .niveauHierarchique(2) + .organisationId(orgId) + .build(); + + CreateRoleRequest request2 = CreateRoleRequest.builder() + .code("ROLE_TEST") + .libelle("Test") + .typeRole("SYSTEM") + .niveauHierarchique(2) + .organisationId(orgId) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateRoleRequest request = CreateRoleRequest.builder() + .code("ROLE_ADMIN") + .libelle("Administrateur") + .typeRole("SYSTEM") + .niveauHierarchique(1) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateRoleRequest"); + assertThat(toString).contains("ROLE_ADMIN"); + assertThat(toString).contains("Administrateur"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/role/request/UpdateRoleRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/role/request/UpdateRoleRequestTest.java index f3c40b1..5ae0757 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/role/request/UpdateRoleRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/role/request/UpdateRoleRequestTest.java @@ -1,122 +1,122 @@ -package dev.lions.unionflow.server.api.dto.role.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateRoleRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UpdateRoleRequest request = UpdateRoleRequest.builder() - .libelle("Libellé mis à jour") - .description("Description mise à jour") - .niveauHierarchique(2) - .actif(true) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.libelle()).isEqualTo("Libellé mis à jour"); - assertThat(request.description()).isEqualTo("Description mise à jour"); - assertThat(request.niveauHierarchique()).isEqualTo(2); - assertThat(request.actif()).isTrue(); - } - - @Test - void testBuilder_MinimalFields() { - UpdateRoleRequest request = UpdateRoleRequest.builder() - .libelle("Nouveau libellé") - .niveauHierarchique(3) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.libelle()).isEqualTo("Nouveau libellé"); - assertThat(request.niveauHierarchique()).isEqualTo(3); - } - - @Test - void testValidation_MissingRequiredFields() { - UpdateRoleRequest request = UpdateRoleRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("niveauHierarchique")); - } - - @Test - void testValidation_LibelleTooLong() { - String longLibelle = "A".repeat(101); - UpdateRoleRequest request = UpdateRoleRequest.builder() - .libelle(longLibelle) - .niveauHierarchique(1) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); - } - - @Test - void testValidation_ValidFields() { - UpdateRoleRequest request = UpdateRoleRequest.builder() - .libelle("Rôle modifié") - .description("Description modifiée") - .niveauHierarchique(2) - .actif(false) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UpdateRoleRequest request1 = UpdateRoleRequest.builder() - .libelle("Test") - .niveauHierarchique(2) - .actif(true) - .build(); - - UpdateRoleRequest request2 = UpdateRoleRequest.builder() - .libelle("Test") - .niveauHierarchique(2) - .actif(true) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateRoleRequest request = UpdateRoleRequest.builder() - .libelle("Updated Role") - .niveauHierarchique(3) - .actif(true) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateRoleRequest"); - assertThat(toString).contains("Updated Role"); - } -} +package dev.lions.unionflow.server.api.dto.role.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateRoleRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UpdateRoleRequest request = UpdateRoleRequest.builder() + .libelle("Libellé mis à jour") + .description("Description mise à jour") + .niveauHierarchique(2) + .actif(true) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.libelle()).isEqualTo("Libellé mis à jour"); + assertThat(request.description()).isEqualTo("Description mise à jour"); + assertThat(request.niveauHierarchique()).isEqualTo(2); + assertThat(request.actif()).isTrue(); + } + + @Test + void testBuilder_MinimalFields() { + UpdateRoleRequest request = UpdateRoleRequest.builder() + .libelle("Nouveau libellé") + .niveauHierarchique(3) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.libelle()).isEqualTo("Nouveau libellé"); + assertThat(request.niveauHierarchique()).isEqualTo(3); + } + + @Test + void testValidation_MissingRequiredFields() { + UpdateRoleRequest request = UpdateRoleRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("niveauHierarchique")); + } + + @Test + void testValidation_LibelleTooLong() { + String longLibelle = "A".repeat(101); + UpdateRoleRequest request = UpdateRoleRequest.builder() + .libelle(longLibelle) + .niveauHierarchique(1) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("libelle")); + } + + @Test + void testValidation_ValidFields() { + UpdateRoleRequest request = UpdateRoleRequest.builder() + .libelle("Rôle modifié") + .description("Description modifiée") + .niveauHierarchique(2) + .actif(false) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UpdateRoleRequest request1 = UpdateRoleRequest.builder() + .libelle("Test") + .niveauHierarchique(2) + .actif(true) + .build(); + + UpdateRoleRequest request2 = UpdateRoleRequest.builder() + .libelle("Test") + .niveauHierarchique(2) + .actif(true) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateRoleRequest request = UpdateRoleRequest.builder() + .libelle("Updated Role") + .niveauHierarchique(3) + .actif(true) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateRoleRequest"); + assertThat(toString).contains("Updated Role"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/CreneauDisponibiliteDTOTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/CreneauDisponibiliteDTOTest.java index 1de701c..d278785 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/CreneauDisponibiliteDTOTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/CreneauDisponibiliteDTOTest.java @@ -1,310 +1,310 @@ -package dev.lions.unionflow.server.api.dto.solidarite; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.DayOfWeek; -import java.time.LocalDate; -import java.time.LocalTime; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -/** - * Tests unitaires pour CreneauDisponibiliteDTO. - * Couvre isValide, getDureeMinutes, isDisponibleLe (tous types), contientHeure, getLibelle, - * et l'enum TypeCreneau. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests CreneauDisponibiliteDTO") -class CreneauDisponibiliteDTOTest { - - @Nested - @DisplayName("isValide") - class IsValide { - - @Test - @DisplayName("retourne false quand heureDebut est null") - void testHeureDebutNull() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureFin(LocalTime.of(18, 0)).build(); - assertThat(dto.isValide()).isFalse(); - } - - @Test - @DisplayName("retourne false quand heureFin est null") - void testHeureFinNull() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)).build(); - assertThat(dto.isValide()).isFalse(); - } - - @Test - @DisplayName("retourne false quand heureFin avant heureDebut") - void testHeureFinAvantDebut() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(18, 0)) - .heureFin(LocalTime.of(9, 0)).build(); - assertThat(dto.isValide()).isFalse(); - } - - @Test - @DisplayName("retourne false quand heureFin égale heureDebut") - void testHeuresEgales() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(9, 0)).build(); - assertThat(dto.isValide()).isFalse(); - } - - @Test - @DisplayName("retourne true quand heureFin après heureDebut") - void testValide() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 0)).build(); - assertThat(dto.isValide()).isTrue(); - } - } - - @Nested - @DisplayName("getDureeMinutes") - class GetDureeMinutes { - - @Test - @DisplayName("retourne 0 quand créneau invalide") - void testInvalide() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(18, 0)) - .heureFin(LocalTime.of(9, 0)).build(); - assertThat(dto.getDureeMinutes()).isEqualTo(0); - } - - @Test - @DisplayName("retourne la durée en minutes") - void testDuree() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 30)).build(); - assertThat(dto.getDureeMinutes()).isEqualTo(210); - } - } - - @Nested - @DisplayName("isDisponibleLe") - class IsDisponibleLe { - - @Test - @DisplayName("retourne false quand estActif est false") - void testNonActif() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 0)) - .estActif(false) - .type(CreneauDisponibiliteDTO.TypeCreneau.RECURRENT) - .jourSemaine(DayOfWeek.MONDAY).build(); - assertThat(dto.isDisponibleLe(LocalDate.of(2026, 2, 2))).isFalse(); - } - - @Test - @DisplayName("PONCTUEL: true seulement si dateSpecifique égale à la date") - void testPonctuel() { - LocalDate date = LocalDate.of(2026, 2, 15); - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 0)) - .estActif(true) - .type(CreneauDisponibiliteDTO.TypeCreneau.PONCTUEL) - .dateSpecifique(date).build(); - assertThat(dto.isDisponibleLe(date)).isTrue(); - assertThat(dto.isDisponibleLe(date.plusDays(1))).isFalse(); - dto.setDateSpecifique(null); - assertThat(dto.isDisponibleLe(date)).isFalse(); - } - - @Test - @DisplayName("RECURRENT: true si jourSemaine correspond") - void testRecurrent() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 0)) - .estActif(true) - .type(CreneauDisponibiliteDTO.TypeCreneau.RECURRENT) - .jourSemaine(DayOfWeek.WEDNESDAY).build(); - LocalDate mercredi = LocalDate.of(2026, 2, 18); - assertThat(dto.isDisponibleLe(mercredi)).isTrue(); - assertThat(dto.isDisponibleLe(mercredi.plusDays(1))).isFalse(); - dto.setJourSemaine(null); - assertThat(dto.isDisponibleLe(mercredi)).isFalse(); - } - - @Test - @DisplayName("URGENCE et FLEXIBLE: toujours true si actif") - void testUrgenceFlexible() { - CreneauDisponibiliteDTO urg = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 0)) - .estActif(true) - .type(CreneauDisponibiliteDTO.TypeCreneau.URGENCE).build(); - CreneauDisponibiliteDTO flex = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 0)) - .estActif(true) - .type(CreneauDisponibiliteDTO.TypeCreneau.FLEXIBLE).build(); - LocalDate any = LocalDate.of(2026, 2, 20); - assertThat(urg.isDisponibleLe(any)).isTrue(); - assertThat(flex.isDisponibleLe(any)).isTrue(); - } - } - - @Nested - @DisplayName("contientHeure") - class ContientHeure { - - @Test - @DisplayName("retourne false quand créneau invalide") - void testInvalide() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(18, 0)) - .heureFin(LocalTime.of(9, 0)).build(); - assertThat(dto.contientHeure(LocalTime.of(12, 0))).isFalse(); - } - - @Test - @DisplayName("retourne true quand heure dans le créneau") - void testDedans() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 0)).build(); - assertThat(dto.contientHeure(LocalTime.of(10, 30))).isTrue(); - assertThat(dto.contientHeure(LocalTime.of(9, 0))).isTrue(); - assertThat(dto.contientHeure(LocalTime.of(12, 0))).isTrue(); - } - - @Test - @DisplayName("retourne false quand heure en dehors") - void testDehors() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 0)).build(); - assertThat(dto.contientHeure(LocalTime.of(8, 59))).isFalse(); - assertThat(dto.contientHeure(LocalTime.of(12, 1))).isFalse(); - } - } - - @Nested - @DisplayName("getLibelle") - class GetLibelle { - - @Test - @DisplayName("RECURRENT avec jourSemaine inclut le jour") - void testRecurrent() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 0)) - .type(CreneauDisponibiliteDTO.TypeCreneau.RECURRENT) - .jourSemaine(DayOfWeek.MONDAY).build(); - assertThat(dto.getLibelle()).startsWith("MONDAY "); - assertThat(dto.getLibelle()).endsWith("09:00 - 12:00"); - } - - @Test - @DisplayName("RECURRENT sans jourSemaine: seulement heures") - void testRecurrentSansJourSemaine() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 0)) - .type(CreneauDisponibiliteDTO.TypeCreneau.RECURRENT) - .jourSemaine(null).build(); - assertThat(dto.getLibelle()).isEqualTo("09:00 - 12:00"); - } - - @Test - @DisplayName("PONCTUEL avec dateSpecifique inclut la date") - void testPonctuel() { - LocalDate date = LocalDate.of(2026, 2, 15); - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 0)) - .type(CreneauDisponibiliteDTO.TypeCreneau.PONCTUEL) - .dateSpecifique(date).build(); - assertThat(dto.getLibelle()).startsWith("2026-02-15 "); - assertThat(dto.getLibelle()).endsWith("09:00 - 12:00"); - } - - @Test - @DisplayName("PONCTUEL sans dateSpecifique: seulement heures") - void testPonctuelSansDate() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 0)) - .type(CreneauDisponibiliteDTO.TypeCreneau.PONCTUEL) - .dateSpecifique(null).build(); - assertThat(dto.getLibelle()).isEqualTo("09:00 - 12:00"); - } - - @Test - @DisplayName("autre type: seulement heures (URGENCE)") - void testAutre() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(9, 0)) - .heureFin(LocalTime.of(12, 0)) - .type(CreneauDisponibiliteDTO.TypeCreneau.URGENCE).build(); - assertThat(dto.getLibelle()).isEqualTo("09:00 - 12:00"); - } - - @Test - @DisplayName("FLEXIBLE: seulement heures (pas RECURRENT ni PONCTUEL)") - void testFlexible() { - CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() - .heureDebut(LocalTime.of(14, 0)) - .heureFin(LocalTime.of(17, 0)) - .type(CreneauDisponibiliteDTO.TypeCreneau.FLEXIBLE).build(); - assertThat(dto.getLibelle()).isEqualTo("14:00 - 17:00"); - } - } - - @Nested - @DisplayName("TypeCreneau enum") - class TypeCreneauEnum { - - @Test - @DisplayName("values contient RECURRENT, PONCTUEL, URGENCE, FLEXIBLE") - void testValues() { - CreneauDisponibiliteDTO.TypeCreneau[] values = CreneauDisponibiliteDTO.TypeCreneau.values(); - assertThat(values).hasSize(4); - assertThat(values).contains( - CreneauDisponibiliteDTO.TypeCreneau.RECURRENT, - CreneauDisponibiliteDTO.TypeCreneau.PONCTUEL, - CreneauDisponibiliteDTO.TypeCreneau.URGENCE, - CreneauDisponibiliteDTO.TypeCreneau.FLEXIBLE); - } - - @ParameterizedTest - @EnumSource(CreneauDisponibiliteDTO.TypeCreneau.class) - @DisplayName("getLibelle non vide pour chaque type") - void testGetLibelle(CreneauDisponibiliteDTO.TypeCreneau type) { - assertThat(type.getLibelle()).isNotBlank(); - } - - @Test - @DisplayName("valueOf pour chaque constante") - void testValueOf() { - assertThat(CreneauDisponibiliteDTO.TypeCreneau.valueOf("RECURRENT")).isEqualTo(CreneauDisponibiliteDTO.TypeCreneau.RECURRENT); - assertThat(CreneauDisponibiliteDTO.TypeCreneau.valueOf("PONCTUEL")).isEqualTo(CreneauDisponibiliteDTO.TypeCreneau.PONCTUEL); - assertThat(CreneauDisponibiliteDTO.TypeCreneau.valueOf("URGENCE")).isEqualTo(CreneauDisponibiliteDTO.TypeCreneau.URGENCE); - assertThat(CreneauDisponibiliteDTO.TypeCreneau.valueOf("FLEXIBLE")).isEqualTo(CreneauDisponibiliteDTO.TypeCreneau.FLEXIBLE); - } - - @Test - @DisplayName("valueOf INEXISTANT lance IllegalArgumentException") - void testValueOfInexistant() { - assertThat(org.junit.jupiter.api.Assertions.assertThrows(IllegalArgumentException.class, - () -> CreneauDisponibiliteDTO.TypeCreneau.valueOf("INEXISTANT"))).isNotNull(); - } - } -} +package dev.lions.unionflow.server.api.dto.solidarite; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.DayOfWeek; +import java.time.LocalDate; +import java.time.LocalTime; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +/** + * Tests unitaires pour CreneauDisponibiliteDTO. + * Couvre isValide, getDureeMinutes, isDisponibleLe (tous types), contientHeure, getLibelle, + * et l'enum TypeCreneau. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests CreneauDisponibiliteDTO") +class CreneauDisponibiliteDTOTest { + + @Nested + @DisplayName("isValide") + class IsValide { + + @Test + @DisplayName("retourne false quand heureDebut est null") + void testHeureDebutNull() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureFin(LocalTime.of(18, 0)).build(); + assertThat(dto.isValide()).isFalse(); + } + + @Test + @DisplayName("retourne false quand heureFin est null") + void testHeureFinNull() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)).build(); + assertThat(dto.isValide()).isFalse(); + } + + @Test + @DisplayName("retourne false quand heureFin avant heureDebut") + void testHeureFinAvantDebut() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(18, 0)) + .heureFin(LocalTime.of(9, 0)).build(); + assertThat(dto.isValide()).isFalse(); + } + + @Test + @DisplayName("retourne false quand heureFin égale heureDebut") + void testHeuresEgales() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(9, 0)).build(); + assertThat(dto.isValide()).isFalse(); + } + + @Test + @DisplayName("retourne true quand heureFin après heureDebut") + void testValide() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 0)).build(); + assertThat(dto.isValide()).isTrue(); + } + } + + @Nested + @DisplayName("getDureeMinutes") + class GetDureeMinutes { + + @Test + @DisplayName("retourne 0 quand créneau invalide") + void testInvalide() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(18, 0)) + .heureFin(LocalTime.of(9, 0)).build(); + assertThat(dto.getDureeMinutes()).isEqualTo(0); + } + + @Test + @DisplayName("retourne la durée en minutes") + void testDuree() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 30)).build(); + assertThat(dto.getDureeMinutes()).isEqualTo(210); + } + } + + @Nested + @DisplayName("isDisponibleLe") + class IsDisponibleLe { + + @Test + @DisplayName("retourne false quand estActif est false") + void testNonActif() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 0)) + .estActif(false) + .type(CreneauDisponibiliteDTO.TypeCreneau.RECURRENT) + .jourSemaine(DayOfWeek.MONDAY).build(); + assertThat(dto.isDisponibleLe(LocalDate.of(2026, 2, 2))).isFalse(); + } + + @Test + @DisplayName("PONCTUEL: true seulement si dateSpecifique égale à la date") + void testPonctuel() { + LocalDate date = LocalDate.of(2026, 2, 15); + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 0)) + .estActif(true) + .type(CreneauDisponibiliteDTO.TypeCreneau.PONCTUEL) + .dateSpecifique(date).build(); + assertThat(dto.isDisponibleLe(date)).isTrue(); + assertThat(dto.isDisponibleLe(date.plusDays(1))).isFalse(); + dto.setDateSpecifique(null); + assertThat(dto.isDisponibleLe(date)).isFalse(); + } + + @Test + @DisplayName("RECURRENT: true si jourSemaine correspond") + void testRecurrent() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 0)) + .estActif(true) + .type(CreneauDisponibiliteDTO.TypeCreneau.RECURRENT) + .jourSemaine(DayOfWeek.WEDNESDAY).build(); + LocalDate mercredi = LocalDate.of(2026, 2, 18); + assertThat(dto.isDisponibleLe(mercredi)).isTrue(); + assertThat(dto.isDisponibleLe(mercredi.plusDays(1))).isFalse(); + dto.setJourSemaine(null); + assertThat(dto.isDisponibleLe(mercredi)).isFalse(); + } + + @Test + @DisplayName("URGENCE et FLEXIBLE: toujours true si actif") + void testUrgenceFlexible() { + CreneauDisponibiliteDTO urg = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 0)) + .estActif(true) + .type(CreneauDisponibiliteDTO.TypeCreneau.URGENCE).build(); + CreneauDisponibiliteDTO flex = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 0)) + .estActif(true) + .type(CreneauDisponibiliteDTO.TypeCreneau.FLEXIBLE).build(); + LocalDate any = LocalDate.of(2026, 2, 20); + assertThat(urg.isDisponibleLe(any)).isTrue(); + assertThat(flex.isDisponibleLe(any)).isTrue(); + } + } + + @Nested + @DisplayName("contientHeure") + class ContientHeure { + + @Test + @DisplayName("retourne false quand créneau invalide") + void testInvalide() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(18, 0)) + .heureFin(LocalTime.of(9, 0)).build(); + assertThat(dto.contientHeure(LocalTime.of(12, 0))).isFalse(); + } + + @Test + @DisplayName("retourne true quand heure dans le créneau") + void testDedans() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 0)).build(); + assertThat(dto.contientHeure(LocalTime.of(10, 30))).isTrue(); + assertThat(dto.contientHeure(LocalTime.of(9, 0))).isTrue(); + assertThat(dto.contientHeure(LocalTime.of(12, 0))).isTrue(); + } + + @Test + @DisplayName("retourne false quand heure en dehors") + void testDehors() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 0)).build(); + assertThat(dto.contientHeure(LocalTime.of(8, 59))).isFalse(); + assertThat(dto.contientHeure(LocalTime.of(12, 1))).isFalse(); + } + } + + @Nested + @DisplayName("getLibelle") + class GetLibelle { + + @Test + @DisplayName("RECURRENT avec jourSemaine inclut le jour") + void testRecurrent() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 0)) + .type(CreneauDisponibiliteDTO.TypeCreneau.RECURRENT) + .jourSemaine(DayOfWeek.MONDAY).build(); + assertThat(dto.getLibelle()).startsWith("MONDAY "); + assertThat(dto.getLibelle()).endsWith("09:00 - 12:00"); + } + + @Test + @DisplayName("RECURRENT sans jourSemaine: seulement heures") + void testRecurrentSansJourSemaine() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 0)) + .type(CreneauDisponibiliteDTO.TypeCreneau.RECURRENT) + .jourSemaine(null).build(); + assertThat(dto.getLibelle()).isEqualTo("09:00 - 12:00"); + } + + @Test + @DisplayName("PONCTUEL avec dateSpecifique inclut la date") + void testPonctuel() { + LocalDate date = LocalDate.of(2026, 2, 15); + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 0)) + .type(CreneauDisponibiliteDTO.TypeCreneau.PONCTUEL) + .dateSpecifique(date).build(); + assertThat(dto.getLibelle()).startsWith("2026-02-15 "); + assertThat(dto.getLibelle()).endsWith("09:00 - 12:00"); + } + + @Test + @DisplayName("PONCTUEL sans dateSpecifique: seulement heures") + void testPonctuelSansDate() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 0)) + .type(CreneauDisponibiliteDTO.TypeCreneau.PONCTUEL) + .dateSpecifique(null).build(); + assertThat(dto.getLibelle()).isEqualTo("09:00 - 12:00"); + } + + @Test + @DisplayName("autre type: seulement heures (URGENCE)") + void testAutre() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(9, 0)) + .heureFin(LocalTime.of(12, 0)) + .type(CreneauDisponibiliteDTO.TypeCreneau.URGENCE).build(); + assertThat(dto.getLibelle()).isEqualTo("09:00 - 12:00"); + } + + @Test + @DisplayName("FLEXIBLE: seulement heures (pas RECURRENT ni PONCTUEL)") + void testFlexible() { + CreneauDisponibiliteDTO dto = CreneauDisponibiliteDTO.builder() + .heureDebut(LocalTime.of(14, 0)) + .heureFin(LocalTime.of(17, 0)) + .type(CreneauDisponibiliteDTO.TypeCreneau.FLEXIBLE).build(); + assertThat(dto.getLibelle()).isEqualTo("14:00 - 17:00"); + } + } + + @Nested + @DisplayName("TypeCreneau enum") + class TypeCreneauEnum { + + @Test + @DisplayName("values contient RECURRENT, PONCTUEL, URGENCE, FLEXIBLE") + void testValues() { + CreneauDisponibiliteDTO.TypeCreneau[] values = CreneauDisponibiliteDTO.TypeCreneau.values(); + assertThat(values).hasSize(4); + assertThat(values).contains( + CreneauDisponibiliteDTO.TypeCreneau.RECURRENT, + CreneauDisponibiliteDTO.TypeCreneau.PONCTUEL, + CreneauDisponibiliteDTO.TypeCreneau.URGENCE, + CreneauDisponibiliteDTO.TypeCreneau.FLEXIBLE); + } + + @ParameterizedTest + @EnumSource(CreneauDisponibiliteDTO.TypeCreneau.class) + @DisplayName("getLibelle non vide pour chaque type") + void testGetLibelle(CreneauDisponibiliteDTO.TypeCreneau type) { + assertThat(type.getLibelle()).isNotBlank(); + } + + @Test + @DisplayName("valueOf pour chaque constante") + void testValueOf() { + assertThat(CreneauDisponibiliteDTO.TypeCreneau.valueOf("RECURRENT")).isEqualTo(CreneauDisponibiliteDTO.TypeCreneau.RECURRENT); + assertThat(CreneauDisponibiliteDTO.TypeCreneau.valueOf("PONCTUEL")).isEqualTo(CreneauDisponibiliteDTO.TypeCreneau.PONCTUEL); + assertThat(CreneauDisponibiliteDTO.TypeCreneau.valueOf("URGENCE")).isEqualTo(CreneauDisponibiliteDTO.TypeCreneau.URGENCE); + assertThat(CreneauDisponibiliteDTO.TypeCreneau.valueOf("FLEXIBLE")).isEqualTo(CreneauDisponibiliteDTO.TypeCreneau.FLEXIBLE); + } + + @Test + @DisplayName("valueOf INEXISTANT lance IllegalArgumentException") + void testValueOfInexistant() { + assertThat(org.junit.jupiter.api.Assertions.assertThrows(IllegalArgumentException.class, + () -> CreneauDisponibiliteDTO.TypeCreneau.valueOf("INEXISTANT"))).isNotNull(); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateCommentaireAideRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateCommentaireAideRequestTest.java index 839446a..03fd040 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateCommentaireAideRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateCommentaireAideRequestTest.java @@ -1,155 +1,155 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.List; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateCommentaireAideRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID auteurId = UUID.randomUUID(); - UUID parentId = UUID.randomUUID(); - List mentions = List.of("user1", "user2"); - - CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder() - .contenu("Ceci est un commentaire de test valide") - .typeCommentaire("QUESTION") - .auteurId(auteurId) - .estPrive(true) - .estImportant(true) - .commentaireParentId(parentId) - .mentionsUtilisateurs(mentions) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.contenu()).isEqualTo("Ceci est un commentaire de test valide"); - assertThat(request.typeCommentaire()).isEqualTo("QUESTION"); - assertThat(request.auteurId()).isEqualTo(auteurId); - assertThat(request.estPrive()).isTrue(); - assertThat(request.estImportant()).isTrue(); - assertThat(request.commentaireParentId()).isEqualTo(parentId); - assertThat(request.mentionsUtilisateurs()).isEqualTo(mentions); - } - - @Test - void testBuilder_MinimalFields() { - UUID auteurId = UUID.randomUUID(); - - CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder() - .contenu("Commentaire minimal") - .typeCommentaire("GENERAL") - .auteurId(auteurId) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.contenu()).isEqualTo("Commentaire minimal"); - assertThat(request.typeCommentaire()).isEqualTo("GENERAL"); - assertThat(request.auteurId()).isEqualTo(auteurId); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("contenu")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeCommentaire")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("auteurId")); - } - - @Test - void testValidation_ContenuTooShort() { - CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder() - .contenu("abc") - .typeCommentaire("GENERAL") - .auteurId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("contenu")); - } - - @Test - void testValidation_ContenuTooLong() { - String longContenu = "A".repeat(2001); - CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder() - .contenu(longContenu) - .typeCommentaire("GENERAL") - .auteurId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("contenu")); - } - - @Test - void testValidation_ValidFields() { - CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder() - .contenu("Commentaire valide avec au moins 5 caractères") - .typeCommentaire("GENERAL") - .auteurId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID auteurId = UUID.randomUUID(); - - CreateCommentaireAideRequest request1 = CreateCommentaireAideRequest.builder() - .contenu("Commentaire test") - .typeCommentaire("GENERAL") - .auteurId(auteurId) - .build(); - - CreateCommentaireAideRequest request2 = CreateCommentaireAideRequest.builder() - .contenu("Commentaire test") - .typeCommentaire("GENERAL") - .auteurId(auteurId) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder() - .contenu("Commentaire test") - .typeCommentaire("GENERAL") - .auteurId(UUID.randomUUID()) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateCommentaireAideRequest"); - assertThat(toString).contains("Commentaire test"); - } -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.List; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateCommentaireAideRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID auteurId = UUID.randomUUID(); + UUID parentId = UUID.randomUUID(); + List mentions = List.of("user1", "user2"); + + CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder() + .contenu("Ceci est un commentaire de test valide") + .typeCommentaire("QUESTION") + .auteurId(auteurId) + .estPrive(true) + .estImportant(true) + .commentaireParentId(parentId) + .mentionsUtilisateurs(mentions) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.contenu()).isEqualTo("Ceci est un commentaire de test valide"); + assertThat(request.typeCommentaire()).isEqualTo("QUESTION"); + assertThat(request.auteurId()).isEqualTo(auteurId); + assertThat(request.estPrive()).isTrue(); + assertThat(request.estImportant()).isTrue(); + assertThat(request.commentaireParentId()).isEqualTo(parentId); + assertThat(request.mentionsUtilisateurs()).isEqualTo(mentions); + } + + @Test + void testBuilder_MinimalFields() { + UUID auteurId = UUID.randomUUID(); + + CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder() + .contenu("Commentaire minimal") + .typeCommentaire("GENERAL") + .auteurId(auteurId) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.contenu()).isEqualTo("Commentaire minimal"); + assertThat(request.typeCommentaire()).isEqualTo("GENERAL"); + assertThat(request.auteurId()).isEqualTo(auteurId); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("contenu")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeCommentaire")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("auteurId")); + } + + @Test + void testValidation_ContenuTooShort() { + CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder() + .contenu("abc") + .typeCommentaire("GENERAL") + .auteurId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("contenu")); + } + + @Test + void testValidation_ContenuTooLong() { + String longContenu = "A".repeat(2001); + CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder() + .contenu(longContenu) + .typeCommentaire("GENERAL") + .auteurId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("contenu")); + } + + @Test + void testValidation_ValidFields() { + CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder() + .contenu("Commentaire valide avec au moins 5 caractères") + .typeCommentaire("GENERAL") + .auteurId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID auteurId = UUID.randomUUID(); + + CreateCommentaireAideRequest request1 = CreateCommentaireAideRequest.builder() + .contenu("Commentaire test") + .typeCommentaire("GENERAL") + .auteurId(auteurId) + .build(); + + CreateCommentaireAideRequest request2 = CreateCommentaireAideRequest.builder() + .contenu("Commentaire test") + .typeCommentaire("GENERAL") + .auteurId(auteurId) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateCommentaireAideRequest request = CreateCommentaireAideRequest.builder() + .contenu("Commentaire test") + .typeCommentaire("GENERAL") + .auteurId(UUID.randomUUID()) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateCommentaireAideRequest"); + assertThat(toString).contains("Commentaire test"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateDemandeAideRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateDemandeAideRequestTest.java index 1ca4a9e..cb6f71e 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateDemandeAideRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateDemandeAideRequestTest.java @@ -1,268 +1,268 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.dto.solidarite.BeneficiaireAideDTO; -import dev.lions.unionflow.server.api.dto.solidarite.ContactUrgenceDTO; -import dev.lions.unionflow.server.api.dto.solidarite.LocalisationDTO; -import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; -import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; -import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.util.List; -import java.util.Map; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateDemandeAideRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID membreId = UUID.randomUUID(); - UUID assocId = UUID.randomUUID(); - LocalDate dateLimite = LocalDate.now().plusDays(30); - List pieces = List.of(); - List beneficiaires = List.of(); - Map donnees = Map.of("key", "value"); - List tags = List.of("urgent", "medical"); - LocalisationDTO localisation = LocalisationDTO.builder().build(); - ContactUrgenceDTO contact = ContactUrgenceDTO.builder().build(); - - CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Aide médicale") - .description("Aide pour frais hospitaliers") - .justification("Hospitalisation urgente") - .montantDemande(new BigDecimal("5000.00")) - .devise("XOF") - .membreDemandeurId(membreId) - .associationId(assocId) - .priorite(PrioriteAide.ELEVEE) - .piecesJustificatives(pieces) - .beneficiaires(beneficiaires) - .donneesPersonnalisees(donnees) - .tags(tags) - .estConfidentielle(true) - .localisation(localisation) - .contactUrgence(contact) - .dateLimite(dateLimite) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.typeAide()).isEqualTo(TypeAide.AIDE_FINANCIERE_URGENTE); - assertThat(request.titre()).isEqualTo("Aide médicale"); - assertThat(request.description()).isEqualTo("Aide pour frais hospitaliers"); - assertThat(request.justification()).isEqualTo("Hospitalisation urgente"); - assertThat(request.montantDemande()).isEqualByComparingTo(new BigDecimal("5000.00")); - assertThat(request.devise()).isEqualTo("XOF"); - assertThat(request.membreDemandeurId()).isEqualTo(membreId); - assertThat(request.associationId()).isEqualTo(assocId); - assertThat(request.priorite()).isEqualTo(PrioriteAide.ELEVEE); - assertThat(request.piecesJustificatives()).isEqualTo(pieces); - assertThat(request.beneficiaires()).isEqualTo(beneficiaires); - assertThat(request.donneesPersonnalisees()).isEqualTo(donnees); - assertThat(request.tags()).isEqualTo(tags); - assertThat(request.estConfidentielle()).isTrue(); - assertThat(request.localisation()).isEqualTo(localisation); - assertThat(request.contactUrgence()).isEqualTo(contact); - assertThat(request.dateLimite()).isEqualTo(dateLimite); - } - - @Test - void testBuilder_MinimalFields() { - UUID membreId = UUID.randomUUID(); - UUID assocId = UUID.randomUUID(); - - CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() - .typeAide(TypeAide.DON_MATERIEL) - .titre("Aide") - .description("Description") - .membreDemandeurId(membreId) - .associationId(assocId) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.typeAide()).isEqualTo(TypeAide.DON_MATERIEL); - assertThat(request.titre()).isEqualTo("Aide"); - assertThat(request.description()).isEqualTo("Description"); - assertThat(request.membreDemandeurId()).isEqualTo(membreId); - assertThat(request.associationId()).isEqualTo(assocId); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateDemandeAideRequest request = CreateDemandeAideRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeAide")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("titre")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("membreDemandeurId")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("associationId")); - } - - @Test - void testValidation_TitreTooLong() { - String longTitre = "A".repeat(201); - CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre(longTitre) - .description("Description") - .membreDemandeurId(UUID.randomUUID()) - .associationId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("titre")); - } - - @Test - void testValidation_DescriptionTooLong() { - String longDesc = "A".repeat(2001); - CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Titre") - .description(longDesc) - .membreDemandeurId(UUID.randomUUID()) - .associationId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); - } - - @Test - void testValidation_JustificationTooLong() { - String longJustif = "A".repeat(1001); - CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Titre") - .description("Description") - .justification(longJustif) - .membreDemandeurId(UUID.randomUUID()) - .associationId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("justification")); - } - - @Test - void testValidation_MontantNegatif() { - CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Titre") - .description("Description") - .montantDemande(new BigDecimal("-100")) - .membreDemandeurId(UUID.randomUUID()) - .associationId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDemande")); - } - - @Test - void testValidation_DeviseInvalide() { - CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Titre") - .description("Description") - .devise("INVALID") - .membreDemandeurId(UUID.randomUUID()) - .associationId(UUID.randomUUID()) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); - } - - @Test - void testValidation_ValidFields() { - CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Aide médicale") - .description("Aide pour frais hospitaliers") - .justification("Urgence médicale") - .montantDemande(new BigDecimal("5000.00")) - .devise("XOF") - .membreDemandeurId(UUID.randomUUID()) - .associationId(UUID.randomUUID()) - .priorite(PrioriteAide.ELEVEE) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID membreId = UUID.randomUUID(); - UUID assocId = UUID.randomUUID(); - - CreateDemandeAideRequest request1 = CreateDemandeAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Aide") - .description("Description") - .membreDemandeurId(membreId) - .associationId(assocId) - .build(); - - CreateDemandeAideRequest request2 = CreateDemandeAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Aide") - .description("Description") - .membreDemandeurId(membreId) - .associationId(assocId) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Aide") - .description("Description") - .membreDemandeurId(UUID.randomUUID()) - .associationId(UUID.randomUUID()) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateDemandeAideRequest"); - assertThat(toString).contains("AIDE_FINANCIERE_URGENTE"); - assertThat(toString).contains("Aide"); - } -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.dto.solidarite.BeneficiaireAideDTO; +import dev.lions.unionflow.server.api.dto.solidarite.ContactUrgenceDTO; +import dev.lions.unionflow.server.api.dto.solidarite.LocalisationDTO; +import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; +import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; +import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.util.List; +import java.util.Map; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateDemandeAideRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID membreId = UUID.randomUUID(); + UUID assocId = UUID.randomUUID(); + LocalDate dateLimite = LocalDate.now().plusDays(30); + List pieces = List.of(); + List beneficiaires = List.of(); + Map donnees = Map.of("key", "value"); + List tags = List.of("urgent", "medical"); + LocalisationDTO localisation = LocalisationDTO.builder().build(); + ContactUrgenceDTO contact = ContactUrgenceDTO.builder().build(); + + CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Aide médicale") + .description("Aide pour frais hospitaliers") + .justification("Hospitalisation urgente") + .montantDemande(new BigDecimal("5000.00")) + .devise("XOF") + .membreDemandeurId(membreId) + .associationId(assocId) + .priorite(PrioriteAide.ELEVEE) + .piecesJustificatives(pieces) + .beneficiaires(beneficiaires) + .donneesPersonnalisees(donnees) + .tags(tags) + .estConfidentielle(true) + .localisation(localisation) + .contactUrgence(contact) + .dateLimite(dateLimite) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.typeAide()).isEqualTo(TypeAide.AIDE_FINANCIERE_URGENTE); + assertThat(request.titre()).isEqualTo("Aide médicale"); + assertThat(request.description()).isEqualTo("Aide pour frais hospitaliers"); + assertThat(request.justification()).isEqualTo("Hospitalisation urgente"); + assertThat(request.montantDemande()).isEqualByComparingTo(new BigDecimal("5000.00")); + assertThat(request.devise()).isEqualTo("XOF"); + assertThat(request.membreDemandeurId()).isEqualTo(membreId); + assertThat(request.associationId()).isEqualTo(assocId); + assertThat(request.priorite()).isEqualTo(PrioriteAide.ELEVEE); + assertThat(request.piecesJustificatives()).isEqualTo(pieces); + assertThat(request.beneficiaires()).isEqualTo(beneficiaires); + assertThat(request.donneesPersonnalisees()).isEqualTo(donnees); + assertThat(request.tags()).isEqualTo(tags); + assertThat(request.estConfidentielle()).isTrue(); + assertThat(request.localisation()).isEqualTo(localisation); + assertThat(request.contactUrgence()).isEqualTo(contact); + assertThat(request.dateLimite()).isEqualTo(dateLimite); + } + + @Test + void testBuilder_MinimalFields() { + UUID membreId = UUID.randomUUID(); + UUID assocId = UUID.randomUUID(); + + CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() + .typeAide(TypeAide.DON_MATERIEL) + .titre("Aide") + .description("Description") + .membreDemandeurId(membreId) + .associationId(assocId) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.typeAide()).isEqualTo(TypeAide.DON_MATERIEL); + assertThat(request.titre()).isEqualTo("Aide"); + assertThat(request.description()).isEqualTo("Description"); + assertThat(request.membreDemandeurId()).isEqualTo(membreId); + assertThat(request.associationId()).isEqualTo(assocId); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateDemandeAideRequest request = CreateDemandeAideRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeAide")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("titre")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("membreDemandeurId")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("associationId")); + } + + @Test + void testValidation_TitreTooLong() { + String longTitre = "A".repeat(201); + CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre(longTitre) + .description("Description") + .membreDemandeurId(UUID.randomUUID()) + .associationId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("titre")); + } + + @Test + void testValidation_DescriptionTooLong() { + String longDesc = "A".repeat(2001); + CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Titre") + .description(longDesc) + .membreDemandeurId(UUID.randomUUID()) + .associationId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); + } + + @Test + void testValidation_JustificationTooLong() { + String longJustif = "A".repeat(1001); + CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Titre") + .description("Description") + .justification(longJustif) + .membreDemandeurId(UUID.randomUUID()) + .associationId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("justification")); + } + + @Test + void testValidation_MontantNegatif() { + CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Titre") + .description("Description") + .montantDemande(new BigDecimal("-100")) + .membreDemandeurId(UUID.randomUUID()) + .associationId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montantDemande")); + } + + @Test + void testValidation_DeviseInvalide() { + CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Titre") + .description("Description") + .devise("INVALID") + .membreDemandeurId(UUID.randomUUID()) + .associationId(UUID.randomUUID()) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("devise")); + } + + @Test + void testValidation_ValidFields() { + CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Aide médicale") + .description("Aide pour frais hospitaliers") + .justification("Urgence médicale") + .montantDemande(new BigDecimal("5000.00")) + .devise("XOF") + .membreDemandeurId(UUID.randomUUID()) + .associationId(UUID.randomUUID()) + .priorite(PrioriteAide.ELEVEE) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID membreId = UUID.randomUUID(); + UUID assocId = UUID.randomUUID(); + + CreateDemandeAideRequest request1 = CreateDemandeAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Aide") + .description("Description") + .membreDemandeurId(membreId) + .associationId(assocId) + .build(); + + CreateDemandeAideRequest request2 = CreateDemandeAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Aide") + .description("Description") + .membreDemandeurId(membreId) + .associationId(assocId) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateDemandeAideRequest request = CreateDemandeAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Aide") + .description("Description") + .membreDemandeurId(UUID.randomUUID()) + .associationId(UUID.randomUUID()) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateDemandeAideRequest"); + assertThat(toString).contains("AIDE_FINANCIERE_URGENTE"); + assertThat(toString).contains("Aide"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateEvaluationAideRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateEvaluationAideRequestTest.java index cdd47ce..3c4fec0 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateEvaluationAideRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreateEvaluationAideRequestTest.java @@ -1,240 +1,240 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.solidarite.TypeEvaluation; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Map; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateEvaluationAideRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID demandeId = UUID.randomUUID(); - UUID propositionId = UUID.randomUUID(); - UUID evaluateurId = UUID.randomUUID(); - Map notesDetaillees = Map.of("critere1", 4.5, "critere2", 4.0); - - CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() - .demandeAideId(demandeId) - .propositionAideId(propositionId) - .evaluateurId(evaluateurId) - .roleEvaluateur("beneficiaire") - .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) - .noteGlobale(4.5) - .notesDetaillees(notesDetaillees) - .commentairePrincipal("Très satisfait de l'aide reçue, processus rapide et efficace") - .pointsPositifs("Réactivité excellente") - .pointsAmelioration("Communication à améliorer") - .recommandations("Maintenir le niveau de service") - .recommande(true) - .aideUtile(true) - .problemeResolu(true) - .noteDelaiReponse(4.5) - .noteCommunication(4.0) - .noteProfessionnalisme(5.0) - .noteRespectEngagements(4.5) - .estAnonyme(false) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.demandeAideId()).isEqualTo(demandeId); - assertThat(request.propositionAideId()).isEqualTo(propositionId); - assertThat(request.evaluateurId()).isEqualTo(evaluateurId); - assertThat(request.roleEvaluateur()).isEqualTo("beneficiaire"); - assertThat(request.typeEvaluation()).isEqualTo(TypeEvaluation.SATISFACTION_BENEFICIAIRE); - assertThat(request.noteGlobale()).isEqualTo(4.5); - assertThat(request.notesDetaillees()).isEqualTo(notesDetaillees); - assertThat(request.commentairePrincipal()).isEqualTo("Très satisfait de l'aide reçue, processus rapide et efficace"); - assertThat(request.pointsPositifs()).isEqualTo("Réactivité excellente"); - assertThat(request.pointsAmelioration()).isEqualTo("Communication à améliorer"); - assertThat(request.recommandations()).isEqualTo("Maintenir le niveau de service"); - assertThat(request.recommande()).isTrue(); - assertThat(request.aideUtile()).isTrue(); - assertThat(request.problemeResolu()).isTrue(); - assertThat(request.noteDelaiReponse()).isEqualTo(4.5); - assertThat(request.noteCommunication()).isEqualTo(4.0); - assertThat(request.noteProfessionnalisme()).isEqualTo(5.0); - assertThat(request.noteRespectEngagements()).isEqualTo(4.5); - assertThat(request.estAnonyme()).isFalse(); - } - - @Test - void testBuilder_MinimalFields() { - UUID demandeId = UUID.randomUUID(); - UUID evaluateurId = UUID.randomUUID(); - - CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() - .demandeAideId(demandeId) - .evaluateurId(evaluateurId) - .roleEvaluateur("beneficiaire") - .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) - .noteGlobale(4.0) - .commentairePrincipal("Commentaire valide de test avec plus de 10 caractères") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.demandeAideId()).isEqualTo(demandeId); - assertThat(request.evaluateurId()).isEqualTo(evaluateurId); - assertThat(request.noteGlobale()).isEqualTo(4.0); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("demandeAideId")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("evaluateurId")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("roleEvaluateur")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeEvaluation")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("noteGlobale")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("commentairePrincipal")); - } - - @Test - void testValidation_NoteGlobaleTooLow() { - CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() - .demandeAideId(UUID.randomUUID()) - .evaluateurId(UUID.randomUUID()) - .roleEvaluateur("beneficiaire") - .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) - .noteGlobale(0.5) - .commentairePrincipal("Commentaire valide avec minimum 10 caractères") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("noteGlobale")); - } - - @Test - void testValidation_NoteGlobaleTooHigh() { - CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() - .demandeAideId(UUID.randomUUID()) - .evaluateurId(UUID.randomUUID()) - .roleEvaluateur("beneficiaire") - .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) - .noteGlobale(5.5) - .commentairePrincipal("Commentaire valide avec minimum 10 caractères") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("noteGlobale")); - } - - @Test - void testValidation_CommentaireTooShort() { - CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() - .demandeAideId(UUID.randomUUID()) - .evaluateurId(UUID.randomUUID()) - .roleEvaluateur("beneficiaire") - .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) - .noteGlobale(4.0) - .commentairePrincipal("Court") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("commentairePrincipal")); - } - - @Test - void testValidation_CommentaireTooLong() { - String longComment = "A".repeat(1001); - CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() - .demandeAideId(UUID.randomUUID()) - .evaluateurId(UUID.randomUUID()) - .roleEvaluateur("beneficiaire") - .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) - .noteGlobale(4.0) - .commentairePrincipal(longComment) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("commentairePrincipal")); - } - - @Test - void testValidation_ValidFields() { - CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() - .demandeAideId(UUID.randomUUID()) - .evaluateurId(UUID.randomUUID()) - .roleEvaluateur("beneficiaire") - .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) - .noteGlobale(4.5) - .commentairePrincipal("Commentaire valide avec au moins 10 caractères requis") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID demandeId = UUID.randomUUID(); - UUID evaluateurId = UUID.randomUUID(); - - CreateEvaluationAideRequest request1 = CreateEvaluationAideRequest.builder() - .demandeAideId(demandeId) - .evaluateurId(evaluateurId) - .roleEvaluateur("beneficiaire") - .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) - .noteGlobale(4.0) - .commentairePrincipal("Commentaire identique pour test égalité") - .build(); - - CreateEvaluationAideRequest request2 = CreateEvaluationAideRequest.builder() - .demandeAideId(demandeId) - .evaluateurId(evaluateurId) - .roleEvaluateur("beneficiaire") - .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) - .noteGlobale(4.0) - .commentairePrincipal("Commentaire identique pour test égalité") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() - .demandeAideId(UUID.randomUUID()) - .evaluateurId(UUID.randomUUID()) - .roleEvaluateur("beneficiaire") - .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) - .noteGlobale(4.5) - .commentairePrincipal("Commentaire pour test toString") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateEvaluationAideRequest"); - } -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.solidarite.TypeEvaluation; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Map; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateEvaluationAideRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID demandeId = UUID.randomUUID(); + UUID propositionId = UUID.randomUUID(); + UUID evaluateurId = UUID.randomUUID(); + Map notesDetaillees = Map.of("critere1", 4.5, "critere2", 4.0); + + CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() + .demandeAideId(demandeId) + .propositionAideId(propositionId) + .evaluateurId(evaluateurId) + .roleEvaluateur("beneficiaire") + .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) + .noteGlobale(4.5) + .notesDetaillees(notesDetaillees) + .commentairePrincipal("Très satisfait de l'aide reçue, processus rapide et efficace") + .pointsPositifs("Réactivité excellente") + .pointsAmelioration("Communication à améliorer") + .recommandations("Maintenir le niveau de service") + .recommande(true) + .aideUtile(true) + .problemeResolu(true) + .noteDelaiReponse(4.5) + .noteCommunication(4.0) + .noteProfessionnalisme(5.0) + .noteRespectEngagements(4.5) + .estAnonyme(false) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.demandeAideId()).isEqualTo(demandeId); + assertThat(request.propositionAideId()).isEqualTo(propositionId); + assertThat(request.evaluateurId()).isEqualTo(evaluateurId); + assertThat(request.roleEvaluateur()).isEqualTo("beneficiaire"); + assertThat(request.typeEvaluation()).isEqualTo(TypeEvaluation.SATISFACTION_BENEFICIAIRE); + assertThat(request.noteGlobale()).isEqualTo(4.5); + assertThat(request.notesDetaillees()).isEqualTo(notesDetaillees); + assertThat(request.commentairePrincipal()).isEqualTo("Très satisfait de l'aide reçue, processus rapide et efficace"); + assertThat(request.pointsPositifs()).isEqualTo("Réactivité excellente"); + assertThat(request.pointsAmelioration()).isEqualTo("Communication à améliorer"); + assertThat(request.recommandations()).isEqualTo("Maintenir le niveau de service"); + assertThat(request.recommande()).isTrue(); + assertThat(request.aideUtile()).isTrue(); + assertThat(request.problemeResolu()).isTrue(); + assertThat(request.noteDelaiReponse()).isEqualTo(4.5); + assertThat(request.noteCommunication()).isEqualTo(4.0); + assertThat(request.noteProfessionnalisme()).isEqualTo(5.0); + assertThat(request.noteRespectEngagements()).isEqualTo(4.5); + assertThat(request.estAnonyme()).isFalse(); + } + + @Test + void testBuilder_MinimalFields() { + UUID demandeId = UUID.randomUUID(); + UUID evaluateurId = UUID.randomUUID(); + + CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() + .demandeAideId(demandeId) + .evaluateurId(evaluateurId) + .roleEvaluateur("beneficiaire") + .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) + .noteGlobale(4.0) + .commentairePrincipal("Commentaire valide de test avec plus de 10 caractères") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.demandeAideId()).isEqualTo(demandeId); + assertThat(request.evaluateurId()).isEqualTo(evaluateurId); + assertThat(request.noteGlobale()).isEqualTo(4.0); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("demandeAideId")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("evaluateurId")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("roleEvaluateur")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeEvaluation")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("noteGlobale")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("commentairePrincipal")); + } + + @Test + void testValidation_NoteGlobaleTooLow() { + CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() + .demandeAideId(UUID.randomUUID()) + .evaluateurId(UUID.randomUUID()) + .roleEvaluateur("beneficiaire") + .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) + .noteGlobale(0.5) + .commentairePrincipal("Commentaire valide avec minimum 10 caractères") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("noteGlobale")); + } + + @Test + void testValidation_NoteGlobaleTooHigh() { + CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() + .demandeAideId(UUID.randomUUID()) + .evaluateurId(UUID.randomUUID()) + .roleEvaluateur("beneficiaire") + .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) + .noteGlobale(5.5) + .commentairePrincipal("Commentaire valide avec minimum 10 caractères") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("noteGlobale")); + } + + @Test + void testValidation_CommentaireTooShort() { + CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() + .demandeAideId(UUID.randomUUID()) + .evaluateurId(UUID.randomUUID()) + .roleEvaluateur("beneficiaire") + .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) + .noteGlobale(4.0) + .commentairePrincipal("Court") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("commentairePrincipal")); + } + + @Test + void testValidation_CommentaireTooLong() { + String longComment = "A".repeat(1001); + CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() + .demandeAideId(UUID.randomUUID()) + .evaluateurId(UUID.randomUUID()) + .roleEvaluateur("beneficiaire") + .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) + .noteGlobale(4.0) + .commentairePrincipal(longComment) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("commentairePrincipal")); + } + + @Test + void testValidation_ValidFields() { + CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() + .demandeAideId(UUID.randomUUID()) + .evaluateurId(UUID.randomUUID()) + .roleEvaluateur("beneficiaire") + .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) + .noteGlobale(4.5) + .commentairePrincipal("Commentaire valide avec au moins 10 caractères requis") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID demandeId = UUID.randomUUID(); + UUID evaluateurId = UUID.randomUUID(); + + CreateEvaluationAideRequest request1 = CreateEvaluationAideRequest.builder() + .demandeAideId(demandeId) + .evaluateurId(evaluateurId) + .roleEvaluateur("beneficiaire") + .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) + .noteGlobale(4.0) + .commentairePrincipal("Commentaire identique pour test égalité") + .build(); + + CreateEvaluationAideRequest request2 = CreateEvaluationAideRequest.builder() + .demandeAideId(demandeId) + .evaluateurId(evaluateurId) + .roleEvaluateur("beneficiaire") + .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) + .noteGlobale(4.0) + .commentairePrincipal("Commentaire identique pour test égalité") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateEvaluationAideRequest request = CreateEvaluationAideRequest.builder() + .demandeAideId(UUID.randomUUID()) + .evaluateurId(UUID.randomUUID()) + .roleEvaluateur("beneficiaire") + .typeEvaluation(TypeEvaluation.SATISFACTION_BENEFICIAIRE) + .noteGlobale(4.5) + .commentairePrincipal("Commentaire pour test toString") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateEvaluationAideRequest"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreatePropositionAideRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreatePropositionAideRequestTest.java index 24c3c77..3fa8553 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreatePropositionAideRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/CreatePropositionAideRequestTest.java @@ -1,98 +1,98 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; -import java.math.BigDecimal; -import java.time.LocalDateTime; -import org.junit.jupiter.api.Test; - -class CreatePropositionAideRequestTest { - - @Test - void testBuilder_AllFields() { - LocalDateTime expiration = LocalDateTime.now().plusDays(30); - - CreatePropositionAideRequest request = CreatePropositionAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Proposition d'aide") - .description("Description de la proposition") - .conditions("Conditions d'éligibilité") - .montantMaximum(new BigDecimal("10000.00")) - .nombreMaxBeneficiaires(5) - .devise("XOF") - .proposantId("proposant-123") - .organisationId("org-456") - .demandeAideId("demande-789") - .dateExpiration(expiration) - .delaiReponseHeures(48) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.typeAide()).isEqualTo(TypeAide.AIDE_FINANCIERE_URGENTE); - assertThat(request.titre()).isEqualTo("Proposition d'aide"); - assertThat(request.description()).isEqualTo("Description de la proposition"); - assertThat(request.conditions()).isEqualTo("Conditions d'éligibilité"); - assertThat(request.montantMaximum()).isEqualByComparingTo(new BigDecimal("10000.00")); - assertThat(request.nombreMaxBeneficiaires()).isEqualTo(5); - assertThat(request.devise()).isEqualTo("XOF"); - assertThat(request.proposantId()).isEqualTo("proposant-123"); - assertThat(request.organisationId()).isEqualTo("org-456"); - assertThat(request.demandeAideId()).isEqualTo("demande-789"); - assertThat(request.dateExpiration()).isEqualTo(expiration); - assertThat(request.delaiReponseHeures()).isEqualTo(48); - } - - @Test - void testBuilder_MinimalFields() { - CreatePropositionAideRequest request = CreatePropositionAideRequest.builder() - .typeAide(TypeAide.DON_MATERIEL) - .titre("Proposition") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.typeAide()).isEqualTo(TypeAide.DON_MATERIEL); - assertThat(request.titre()).isEqualTo("Proposition"); - } - - @Test - void testBuilder_NullFields() { - CreatePropositionAideRequest request = CreatePropositionAideRequest.builder().build(); - - assertThat(request).isNotNull(); - assertThat(request.typeAide()).isNull(); - assertThat(request.titre()).isNull(); - assertThat(request.description()).isNull(); - } - - @Test - void testEquals() { - CreatePropositionAideRequest request1 = CreatePropositionAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Proposition") - .proposantId("proposant-123") - .build(); - - CreatePropositionAideRequest request2 = CreatePropositionAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Proposition") - .proposantId("proposant-123") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreatePropositionAideRequest request = CreatePropositionAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Proposition") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreatePropositionAideRequest"); - } -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; +import java.math.BigDecimal; +import java.time.LocalDateTime; +import org.junit.jupiter.api.Test; + +class CreatePropositionAideRequestTest { + + @Test + void testBuilder_AllFields() { + LocalDateTime expiration = LocalDateTime.now().plusDays(30); + + CreatePropositionAideRequest request = CreatePropositionAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Proposition d'aide") + .description("Description de la proposition") + .conditions("Conditions d'éligibilité") + .montantMaximum(new BigDecimal("10000.00")) + .nombreMaxBeneficiaires(5) + .devise("XOF") + .proposantId("proposant-123") + .organisationId("org-456") + .demandeAideId("demande-789") + .dateExpiration(expiration) + .delaiReponseHeures(48) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.typeAide()).isEqualTo(TypeAide.AIDE_FINANCIERE_URGENTE); + assertThat(request.titre()).isEqualTo("Proposition d'aide"); + assertThat(request.description()).isEqualTo("Description de la proposition"); + assertThat(request.conditions()).isEqualTo("Conditions d'éligibilité"); + assertThat(request.montantMaximum()).isEqualByComparingTo(new BigDecimal("10000.00")); + assertThat(request.nombreMaxBeneficiaires()).isEqualTo(5); + assertThat(request.devise()).isEqualTo("XOF"); + assertThat(request.proposantId()).isEqualTo("proposant-123"); + assertThat(request.organisationId()).isEqualTo("org-456"); + assertThat(request.demandeAideId()).isEqualTo("demande-789"); + assertThat(request.dateExpiration()).isEqualTo(expiration); + assertThat(request.delaiReponseHeures()).isEqualTo(48); + } + + @Test + void testBuilder_MinimalFields() { + CreatePropositionAideRequest request = CreatePropositionAideRequest.builder() + .typeAide(TypeAide.DON_MATERIEL) + .titre("Proposition") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.typeAide()).isEqualTo(TypeAide.DON_MATERIEL); + assertThat(request.titre()).isEqualTo("Proposition"); + } + + @Test + void testBuilder_NullFields() { + CreatePropositionAideRequest request = CreatePropositionAideRequest.builder().build(); + + assertThat(request).isNotNull(); + assertThat(request.typeAide()).isNull(); + assertThat(request.titre()).isNull(); + assertThat(request.description()).isNull(); + } + + @Test + void testEquals() { + CreatePropositionAideRequest request1 = CreatePropositionAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Proposition") + .proposantId("proposant-123") + .build(); + + CreatePropositionAideRequest request2 = CreatePropositionAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Proposition") + .proposantId("proposant-123") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreatePropositionAideRequest request = CreatePropositionAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Proposition") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreatePropositionAideRequest"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateCommentaireAideRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateCommentaireAideRequestTest.java index c08884e..35fc86e 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateCommentaireAideRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateCommentaireAideRequestTest.java @@ -1,131 +1,131 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateCommentaireAideRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID resoluteurId = UUID.randomUUID(); - - UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder() - .contenu("Commentaire mis à jour avec succès") - .estPrive(false) - .estImportant(true) - .estResolu(true) - .resoluteurId(resoluteurId) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.contenu()).isEqualTo("Commentaire mis à jour avec succès"); - assertThat(request.estPrive()).isFalse(); - assertThat(request.estImportant()).isTrue(); - assertThat(request.estResolu()).isTrue(); - assertThat(request.resoluteurId()).isEqualTo(resoluteurId); - } - - @Test - void testBuilder_MinimalFields() { - UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder() - .contenu("Nouveau contenu") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.contenu()).isEqualTo("Nouveau contenu"); - } - - @Test - void testBuilder_NullFields() { - UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder().build(); - - assertThat(request).isNotNull(); - assertThat(request.contenu()).isNull(); - assertThat(request.estPrive()).isNull(); - } - - @Test - void testValidation_ContenuTooShort() { - UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder() - .contenu("abc") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("contenu")); - } - - @Test - void testValidation_ContenuTooLong() { - String longContenu = "A".repeat(2001); - UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder() - .contenu(longContenu) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("contenu")); - } - - @Test - void testValidation_ValidContenu() { - UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder() - .contenu("Contenu valide avec au moins 5 caractères") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID resoluteurId = UUID.randomUUID(); - - UpdateCommentaireAideRequest request1 = UpdateCommentaireAideRequest.builder() - .contenu("Commentaire") - .estResolu(true) - .resoluteurId(resoluteurId) - .build(); - - UpdateCommentaireAideRequest request2 = UpdateCommentaireAideRequest.builder() - .contenu("Commentaire") - .estResolu(true) - .resoluteurId(resoluteurId) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder() - .contenu("Commentaire") - .estImportant(true) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateCommentaireAideRequest"); - } -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateCommentaireAideRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID resoluteurId = UUID.randomUUID(); + + UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder() + .contenu("Commentaire mis à jour avec succès") + .estPrive(false) + .estImportant(true) + .estResolu(true) + .resoluteurId(resoluteurId) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.contenu()).isEqualTo("Commentaire mis à jour avec succès"); + assertThat(request.estPrive()).isFalse(); + assertThat(request.estImportant()).isTrue(); + assertThat(request.estResolu()).isTrue(); + assertThat(request.resoluteurId()).isEqualTo(resoluteurId); + } + + @Test + void testBuilder_MinimalFields() { + UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder() + .contenu("Nouveau contenu") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.contenu()).isEqualTo("Nouveau contenu"); + } + + @Test + void testBuilder_NullFields() { + UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder().build(); + + assertThat(request).isNotNull(); + assertThat(request.contenu()).isNull(); + assertThat(request.estPrive()).isNull(); + } + + @Test + void testValidation_ContenuTooShort() { + UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder() + .contenu("abc") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("contenu")); + } + + @Test + void testValidation_ContenuTooLong() { + String longContenu = "A".repeat(2001); + UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder() + .contenu(longContenu) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("contenu")); + } + + @Test + void testValidation_ValidContenu() { + UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder() + .contenu("Contenu valide avec au moins 5 caractères") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID resoluteurId = UUID.randomUUID(); + + UpdateCommentaireAideRequest request1 = UpdateCommentaireAideRequest.builder() + .contenu("Commentaire") + .estResolu(true) + .resoluteurId(resoluteurId) + .build(); + + UpdateCommentaireAideRequest request2 = UpdateCommentaireAideRequest.builder() + .contenu("Commentaire") + .estResolu(true) + .resoluteurId(resoluteurId) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateCommentaireAideRequest request = UpdateCommentaireAideRequest.builder() + .contenu("Commentaire") + .estImportant(true) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateCommentaireAideRequest"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateDemandeAideRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateDemandeAideRequestTest.java index d4a4294..f77f49f 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateDemandeAideRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateDemandeAideRequestTest.java @@ -1,152 +1,152 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.dto.solidarite.BeneficiaireAideDTO; -import dev.lions.unionflow.server.api.dto.solidarite.ContactUrgenceDTO; -import dev.lions.unionflow.server.api.dto.solidarite.LocalisationDTO; -import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; -import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; -import dev.lions.unionflow.server.api.enums.solidarite.StatutAide; -import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDate; -import java.time.LocalDateTime; -import java.util.List; -import java.util.Map; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateDemandeAideRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - LocalDate dateLimite = LocalDate.now().plusDays(30); - LocalDateTime dateSoumission = LocalDateTime.now().minusDays(5); - LocalDateTime dateEvaluation = LocalDateTime.now().minusDays(2); - LocalDateTime dateVersement = LocalDateTime.now().minusDays(1); - - UpdateDemandeAideRequest request = UpdateDemandeAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Aide médicale") - .description("Aide pour frais hospitaliers") - .justification("Hospitalisation urgente") - .montantDemande(new BigDecimal("5000.00")) - .devise("XOF") - .priorite(PrioriteAide.ELEVEE) - .piecesJustificatives(List.of()) - .beneficiaires(List.of()) - .donneesPersonnalisees(Map.of("key", "value")) - .tags(List.of("urgent")) - .estConfidentielle(true) - .necessiteSuivi(true) - .localisation(LocalisationDTO.builder().build()) - .contactUrgence(ContactUrgenceDTO.builder().build()) - .dateLimite(dateLimite) - .statut(StatutAide.EN_ATTENTE) - .montantApprouve(new BigDecimal("4500.00")) - .commentairesEvaluateur("Approuvé avec réduction") - .documentsJoints("doc1.pdf,doc2.pdf") - .dateSoumission(dateSoumission) - .dateEvaluation(dateEvaluation) - .dateVersement(dateVersement) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.typeAide()).isEqualTo(TypeAide.AIDE_FINANCIERE_URGENTE); - assertThat(request.titre()).isEqualTo("Aide médicale"); - assertThat(request.statut()).isEqualTo(StatutAide.EN_ATTENTE); - assertThat(request.montantApprouve()).isEqualByComparingTo(new BigDecimal("4500.00")); - } - - @Test - void testBuilder_MinimalFields() { - UpdateDemandeAideRequest request = UpdateDemandeAideRequest.builder() - .titre("Nouveau titre") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.titre()).isEqualTo("Nouveau titre"); - } - - @Test - void testValidation_TitreTooLong() { - String longTitre = "A".repeat(201); - UpdateDemandeAideRequest request = UpdateDemandeAideRequest.builder() - .titre(longTitre) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("titre")); - } - - @Test - void testValidation_DescriptionTooLong() { - String longDesc = "A".repeat(2001); - UpdateDemandeAideRequest request = UpdateDemandeAideRequest.builder() - .description(longDesc) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); - } - - @Test - void testValidation_JustificationTooLong() { - String longJustif = "A".repeat(1001); - UpdateDemandeAideRequest request = UpdateDemandeAideRequest.builder() - .justification(longJustif) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("justification")); - } - - @Test - void testEquals() { - UpdateDemandeAideRequest request1 = UpdateDemandeAideRequest.builder() - .titre("Aide") - .description("Description") - .build(); - - UpdateDemandeAideRequest request2 = UpdateDemandeAideRequest.builder() - .titre("Aide") - .description("Description") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateDemandeAideRequest request = UpdateDemandeAideRequest.builder() - .titre("Aide") - .typeAide(TypeAide.DON_MATERIEL) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateDemandeAideRequest"); - } -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.dto.solidarite.BeneficiaireAideDTO; +import dev.lions.unionflow.server.api.dto.solidarite.ContactUrgenceDTO; +import dev.lions.unionflow.server.api.dto.solidarite.LocalisationDTO; +import dev.lions.unionflow.server.api.dto.solidarite.PieceJustificativeDTO; +import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; +import dev.lions.unionflow.server.api.enums.solidarite.StatutAide; +import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.util.List; +import java.util.Map; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateDemandeAideRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + LocalDate dateLimite = LocalDate.now().plusDays(30); + LocalDateTime dateSoumission = LocalDateTime.now().minusDays(5); + LocalDateTime dateEvaluation = LocalDateTime.now().minusDays(2); + LocalDateTime dateVersement = LocalDateTime.now().minusDays(1); + + UpdateDemandeAideRequest request = UpdateDemandeAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Aide médicale") + .description("Aide pour frais hospitaliers") + .justification("Hospitalisation urgente") + .montantDemande(new BigDecimal("5000.00")) + .devise("XOF") + .priorite(PrioriteAide.ELEVEE) + .piecesJustificatives(List.of()) + .beneficiaires(List.of()) + .donneesPersonnalisees(Map.of("key", "value")) + .tags(List.of("urgent")) + .estConfidentielle(true) + .necessiteSuivi(true) + .localisation(LocalisationDTO.builder().build()) + .contactUrgence(ContactUrgenceDTO.builder().build()) + .dateLimite(dateLimite) + .statut(StatutAide.EN_ATTENTE) + .montantApprouve(new BigDecimal("4500.00")) + .commentairesEvaluateur("Approuvé avec réduction") + .documentsJoints("doc1.pdf,doc2.pdf") + .dateSoumission(dateSoumission) + .dateEvaluation(dateEvaluation) + .dateVersement(dateVersement) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.typeAide()).isEqualTo(TypeAide.AIDE_FINANCIERE_URGENTE); + assertThat(request.titre()).isEqualTo("Aide médicale"); + assertThat(request.statut()).isEqualTo(StatutAide.EN_ATTENTE); + assertThat(request.montantApprouve()).isEqualByComparingTo(new BigDecimal("4500.00")); + } + + @Test + void testBuilder_MinimalFields() { + UpdateDemandeAideRequest request = UpdateDemandeAideRequest.builder() + .titre("Nouveau titre") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.titre()).isEqualTo("Nouveau titre"); + } + + @Test + void testValidation_TitreTooLong() { + String longTitre = "A".repeat(201); + UpdateDemandeAideRequest request = UpdateDemandeAideRequest.builder() + .titre(longTitre) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("titre")); + } + + @Test + void testValidation_DescriptionTooLong() { + String longDesc = "A".repeat(2001); + UpdateDemandeAideRequest request = UpdateDemandeAideRequest.builder() + .description(longDesc) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); + } + + @Test + void testValidation_JustificationTooLong() { + String longJustif = "A".repeat(1001); + UpdateDemandeAideRequest request = UpdateDemandeAideRequest.builder() + .justification(longJustif) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("justification")); + } + + @Test + void testEquals() { + UpdateDemandeAideRequest request1 = UpdateDemandeAideRequest.builder() + .titre("Aide") + .description("Description") + .build(); + + UpdateDemandeAideRequest request2 = UpdateDemandeAideRequest.builder() + .titre("Aide") + .description("Description") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateDemandeAideRequest request = UpdateDemandeAideRequest.builder() + .titre("Aide") + .typeAide(TypeAide.DON_MATERIEL) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateDemandeAideRequest"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateEvaluationAideRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateEvaluationAideRequestTest.java index 86e7770..e67c750 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateEvaluationAideRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdateEvaluationAideRequestTest.java @@ -1,188 +1,188 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.solidarite.StatutEvaluation; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.Map; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateEvaluationAideRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - Map notesDetaillees = Map.of("critere1", 5.0, "critere2", 4.5); - - UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() - .noteGlobale(4.8) - .notesDetaillees(notesDetaillees) - .commentairePrincipal("Commentaire mis à jour après réévaluation complète") - .pointsPositifs("Excellente qualité de service") - .pointsAmelioration("Délais à respecter") - .recommandations("Poursuivre l'amélioration continue") - .recommande(true) - .aideUtile(true) - .problemeResolu(true) - .noteDelaiReponse(4.5) - .noteCommunication(4.8) - .noteProfessionnalisme(5.0) - .noteRespectEngagements(4.5) - .estPublique(true) - .estAnonyme(false) - .statut(StatutEvaluation.ACTIVE) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.noteGlobale()).isEqualTo(4.8); - assertThat(request.notesDetaillees()).isEqualTo(notesDetaillees); - assertThat(request.commentairePrincipal()).isEqualTo("Commentaire mis à jour après réévaluation complète"); - assertThat(request.pointsPositifs()).isEqualTo("Excellente qualité de service"); - assertThat(request.pointsAmelioration()).isEqualTo("Délais à respecter"); - assertThat(request.recommandations()).isEqualTo("Poursuivre l'amélioration continue"); - assertThat(request.recommande()).isTrue(); - assertThat(request.aideUtile()).isTrue(); - assertThat(request.problemeResolu()).isTrue(); - assertThat(request.noteDelaiReponse()).isEqualTo(4.5); - assertThat(request.noteCommunication()).isEqualTo(4.8); - assertThat(request.noteProfessionnalisme()).isEqualTo(5.0); - assertThat(request.noteRespectEngagements()).isEqualTo(4.5); - assertThat(request.estPublique()).isTrue(); - assertThat(request.estAnonyme()).isFalse(); - assertThat(request.statut()).isEqualTo(StatutEvaluation.ACTIVE); - } - - @Test - void testBuilder_MinimalFields() { - UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() - .noteGlobale(4.0) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.noteGlobale()).isEqualTo(4.0); - } - - @Test - void testBuilder_NullFields() { - UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder().build(); - - assertThat(request).isNotNull(); - assertThat(request.noteGlobale()).isNull(); - assertThat(request.commentairePrincipal()).isNull(); - assertThat(request.statut()).isNull(); - } - - @Test - void testValidation_NoteGlobaleTooLow() { - UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() - .noteGlobale(0.5) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("noteGlobale")); - } - - @Test - void testValidation_NoteGlobaleTooHigh() { - UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() - .noteGlobale(6.0) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("noteGlobale")); - } - - @Test - void testValidation_NoteGlobaleValid() { - UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() - .noteGlobale(4.5) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testValidation_CommentaireTooShort() { - UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() - .commentairePrincipal("Court") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("commentairePrincipal")); - } - - @Test - void testValidation_CommentaireTooLong() { - String longComment = "A".repeat(1001); - UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() - .commentairePrincipal(longComment) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("commentairePrincipal")); - } - - @Test - void testValidation_CommentaireValid() { - UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() - .commentairePrincipal("Commentaire valide avec au moins 10 caractères") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UpdateEvaluationAideRequest request1 = UpdateEvaluationAideRequest.builder() - .noteGlobale(4.5) - .commentairePrincipal("Commentaire identique pour test égalité") - .statut(StatutEvaluation.ACTIVE) - .build(); - - UpdateEvaluationAideRequest request2 = UpdateEvaluationAideRequest.builder() - .noteGlobale(4.5) - .commentairePrincipal("Commentaire identique pour test égalité") - .statut(StatutEvaluation.ACTIVE) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() - .noteGlobale(4.5) - .statut(StatutEvaluation.ACTIVE) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateEvaluationAideRequest"); - } -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.solidarite.StatutEvaluation; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.Map; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateEvaluationAideRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + Map notesDetaillees = Map.of("critere1", 5.0, "critere2", 4.5); + + UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() + .noteGlobale(4.8) + .notesDetaillees(notesDetaillees) + .commentairePrincipal("Commentaire mis à jour après réévaluation complète") + .pointsPositifs("Excellente qualité de service") + .pointsAmelioration("Délais à respecter") + .recommandations("Poursuivre l'amélioration continue") + .recommande(true) + .aideUtile(true) + .problemeResolu(true) + .noteDelaiReponse(4.5) + .noteCommunication(4.8) + .noteProfessionnalisme(5.0) + .noteRespectEngagements(4.5) + .estPublique(true) + .estAnonyme(false) + .statut(StatutEvaluation.ACTIVE) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.noteGlobale()).isEqualTo(4.8); + assertThat(request.notesDetaillees()).isEqualTo(notesDetaillees); + assertThat(request.commentairePrincipal()).isEqualTo("Commentaire mis à jour après réévaluation complète"); + assertThat(request.pointsPositifs()).isEqualTo("Excellente qualité de service"); + assertThat(request.pointsAmelioration()).isEqualTo("Délais à respecter"); + assertThat(request.recommandations()).isEqualTo("Poursuivre l'amélioration continue"); + assertThat(request.recommande()).isTrue(); + assertThat(request.aideUtile()).isTrue(); + assertThat(request.problemeResolu()).isTrue(); + assertThat(request.noteDelaiReponse()).isEqualTo(4.5); + assertThat(request.noteCommunication()).isEqualTo(4.8); + assertThat(request.noteProfessionnalisme()).isEqualTo(5.0); + assertThat(request.noteRespectEngagements()).isEqualTo(4.5); + assertThat(request.estPublique()).isTrue(); + assertThat(request.estAnonyme()).isFalse(); + assertThat(request.statut()).isEqualTo(StatutEvaluation.ACTIVE); + } + + @Test + void testBuilder_MinimalFields() { + UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() + .noteGlobale(4.0) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.noteGlobale()).isEqualTo(4.0); + } + + @Test + void testBuilder_NullFields() { + UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder().build(); + + assertThat(request).isNotNull(); + assertThat(request.noteGlobale()).isNull(); + assertThat(request.commentairePrincipal()).isNull(); + assertThat(request.statut()).isNull(); + } + + @Test + void testValidation_NoteGlobaleTooLow() { + UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() + .noteGlobale(0.5) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("noteGlobale")); + } + + @Test + void testValidation_NoteGlobaleTooHigh() { + UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() + .noteGlobale(6.0) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("noteGlobale")); + } + + @Test + void testValidation_NoteGlobaleValid() { + UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() + .noteGlobale(4.5) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testValidation_CommentaireTooShort() { + UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() + .commentairePrincipal("Court") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("commentairePrincipal")); + } + + @Test + void testValidation_CommentaireTooLong() { + String longComment = "A".repeat(1001); + UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() + .commentairePrincipal(longComment) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("commentairePrincipal")); + } + + @Test + void testValidation_CommentaireValid() { + UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() + .commentairePrincipal("Commentaire valide avec au moins 10 caractères") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UpdateEvaluationAideRequest request1 = UpdateEvaluationAideRequest.builder() + .noteGlobale(4.5) + .commentairePrincipal("Commentaire identique pour test égalité") + .statut(StatutEvaluation.ACTIVE) + .build(); + + UpdateEvaluationAideRequest request2 = UpdateEvaluationAideRequest.builder() + .noteGlobale(4.5) + .commentairePrincipal("Commentaire identique pour test égalité") + .statut(StatutEvaluation.ACTIVE) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateEvaluationAideRequest request = UpdateEvaluationAideRequest.builder() + .noteGlobale(4.5) + .statut(StatutEvaluation.ACTIVE) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateEvaluationAideRequest"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdatePropositionAideRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdatePropositionAideRequestTest.java index 1c0d03c..d7b4a28 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdatePropositionAideRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/request/UpdatePropositionAideRequestTest.java @@ -1,99 +1,99 @@ -package dev.lions.unionflow.server.api.dto.solidarite.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.solidarite.StatutProposition; -import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; -import java.math.BigDecimal; -import java.time.LocalDateTime; -import org.junit.jupiter.api.Test; - -class UpdatePropositionAideRequestTest { - - @Test - void testBuilder_AllFields() { - LocalDateTime expiration = LocalDateTime.now().plusDays(30); - - UpdatePropositionAideRequest request = UpdatePropositionAideRequest.builder() - .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) - .titre("Proposition modifiée") - .description("Description mise à jour") - .conditions("Nouvelles conditions") - .montantMaximum(new BigDecimal("12000.00")) - .nombreMaxBeneficiaires(10) - .devise("EUR") - .statut(StatutProposition.ACTIVE) - .estDisponible(true) - .estRecurrente(true) - .frequenceRecurrence("MENSUELLE") - .dateExpiration(expiration) - .delaiReponseHeures(72) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.typeAide()).isEqualTo(TypeAide.AIDE_FINANCIERE_URGENTE); - assertThat(request.titre()).isEqualTo("Proposition modifiée"); - assertThat(request.description()).isEqualTo("Description mise à jour"); - assertThat(request.conditions()).isEqualTo("Nouvelles conditions"); - assertThat(request.montantMaximum()).isEqualByComparingTo(new BigDecimal("12000.00")); - assertThat(request.nombreMaxBeneficiaires()).isEqualTo(10); - assertThat(request.devise()).isEqualTo("EUR"); - assertThat(request.statut()).isEqualTo(StatutProposition.ACTIVE); - assertThat(request.estDisponible()).isTrue(); - assertThat(request.estRecurrente()).isTrue(); - assertThat(request.frequenceRecurrence()).isEqualTo("MENSUELLE"); - assertThat(request.dateExpiration()).isEqualTo(expiration); - assertThat(request.delaiReponseHeures()).isEqualTo(72); - } - - @Test - void testBuilder_MinimalFields() { - UpdatePropositionAideRequest request = UpdatePropositionAideRequest.builder() - .titre("Titre mis à jour") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.titre()).isEqualTo("Titre mis à jour"); - } - - @Test - void testBuilder_NullFields() { - UpdatePropositionAideRequest request = UpdatePropositionAideRequest.builder().build(); - - assertThat(request).isNotNull(); - assertThat(request.typeAide()).isNull(); - assertThat(request.titre()).isNull(); - assertThat(request.statut()).isNull(); - } - - @Test - void testEquals() { - UpdatePropositionAideRequest request1 = UpdatePropositionAideRequest.builder() - .typeAide(TypeAide.DON_MATERIEL) - .titre("Proposition") - .statut(StatutProposition.ACTIVE) - .build(); - - UpdatePropositionAideRequest request2 = UpdatePropositionAideRequest.builder() - .typeAide(TypeAide.DON_MATERIEL) - .titre("Proposition") - .statut(StatutProposition.ACTIVE) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdatePropositionAideRequest request = UpdatePropositionAideRequest.builder() - .titre("Proposition") - .statut(StatutProposition.ACTIVE) - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdatePropositionAideRequest"); - } -} +package dev.lions.unionflow.server.api.dto.solidarite.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.solidarite.StatutProposition; +import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; +import java.math.BigDecimal; +import java.time.LocalDateTime; +import org.junit.jupiter.api.Test; + +class UpdatePropositionAideRequestTest { + + @Test + void testBuilder_AllFields() { + LocalDateTime expiration = LocalDateTime.now().plusDays(30); + + UpdatePropositionAideRequest request = UpdatePropositionAideRequest.builder() + .typeAide(TypeAide.AIDE_FINANCIERE_URGENTE) + .titre("Proposition modifiée") + .description("Description mise à jour") + .conditions("Nouvelles conditions") + .montantMaximum(new BigDecimal("12000.00")) + .nombreMaxBeneficiaires(10) + .devise("EUR") + .statut(StatutProposition.ACTIVE) + .estDisponible(true) + .estRecurrente(true) + .frequenceRecurrence("MENSUELLE") + .dateExpiration(expiration) + .delaiReponseHeures(72) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.typeAide()).isEqualTo(TypeAide.AIDE_FINANCIERE_URGENTE); + assertThat(request.titre()).isEqualTo("Proposition modifiée"); + assertThat(request.description()).isEqualTo("Description mise à jour"); + assertThat(request.conditions()).isEqualTo("Nouvelles conditions"); + assertThat(request.montantMaximum()).isEqualByComparingTo(new BigDecimal("12000.00")); + assertThat(request.nombreMaxBeneficiaires()).isEqualTo(10); + assertThat(request.devise()).isEqualTo("EUR"); + assertThat(request.statut()).isEqualTo(StatutProposition.ACTIVE); + assertThat(request.estDisponible()).isTrue(); + assertThat(request.estRecurrente()).isTrue(); + assertThat(request.frequenceRecurrence()).isEqualTo("MENSUELLE"); + assertThat(request.dateExpiration()).isEqualTo(expiration); + assertThat(request.delaiReponseHeures()).isEqualTo(72); + } + + @Test + void testBuilder_MinimalFields() { + UpdatePropositionAideRequest request = UpdatePropositionAideRequest.builder() + .titre("Titre mis à jour") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.titre()).isEqualTo("Titre mis à jour"); + } + + @Test + void testBuilder_NullFields() { + UpdatePropositionAideRequest request = UpdatePropositionAideRequest.builder().build(); + + assertThat(request).isNotNull(); + assertThat(request.typeAide()).isNull(); + assertThat(request.titre()).isNull(); + assertThat(request.statut()).isNull(); + } + + @Test + void testEquals() { + UpdatePropositionAideRequest request1 = UpdatePropositionAideRequest.builder() + .typeAide(TypeAide.DON_MATERIEL) + .titre("Proposition") + .statut(StatutProposition.ACTIVE) + .build(); + + UpdatePropositionAideRequest request2 = UpdatePropositionAideRequest.builder() + .typeAide(TypeAide.DON_MATERIEL) + .titre("Proposition") + .statut(StatutProposition.ACTIVE) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdatePropositionAideRequest request = UpdatePropositionAideRequest.builder() + .titre("Proposition") + .statut(StatutProposition.ACTIVE) + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdatePropositionAideRequest"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/CommentaireAideResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/CommentaireAideResponseTest.java index d1b9865..1cb1739 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/CommentaireAideResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/CommentaireAideResponseTest.java @@ -1,81 +1,81 @@ -package dev.lions.unionflow.server.api.dto.solidarite.response; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour CommentaireAideResponse. - * Couvre builder, getters/setters et equals/hashCode (héritage BaseResponse). - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests CommentaireAideResponse") -class CommentaireAideResponseTest { - - @Nested - @DisplayName("Builder et getters") - class BuilderEtGetters { - - @Test - @DisplayName("builder remplit tous les champs") - void testBuilder() { - UUID id = UUID.randomUUID(); - UUID auteurId = UUID.randomUUID(); - CommentaireAideResponse r = CommentaireAideResponse.builder() - .contenu("Contenu") - .typeCommentaire("public") - .auteurId(auteurId) - .auteurNom("Dupont") - .auteurRole("Membre") - .estPrive(false) - .estImportant(true) - .estModifie(false) - .nombreReactions(5) - .estResolu(false) - .build(); - r.setId(id); - assertThat(r.getId()).isEqualTo(id); - assertThat(r.getContenu()).isEqualTo("Contenu"); - assertThat(r.getTypeCommentaire()).isEqualTo("public"); - assertThat(r.getAuteurId()).isEqualTo(auteurId); - assertThat(r.getAuteurNom()).isEqualTo("Dupont"); - assertThat(r.getAuteurRole()).isEqualTo("Membre"); - assertThat(r.getEstPrive()).isFalse(); - assertThat(r.getEstImportant()).isTrue(); - assertThat(r.getEstModifie()).isFalse(); - assertThat(r.getNombreReactions()).isEqualTo(5); - assertThat(r.getEstResolu()).isFalse(); - } - - @Test - @DisplayName("constructeur par défaut puis setters") - void testSetters() { - CommentaireAideResponse r = new CommentaireAideResponse(); - r.setContenu("c"); - r.setCommentaireParentId(UUID.randomUUID()); - assertThat(r.getContenu()).isEqualTo("c"); - assertThat(r.getCommentaireParentId()).isNotNull(); - } - - @Test - @DisplayName("equals et hashCode avec même contenu et même id") - void testEqualsHashCode() { - UUID id = UUID.randomUUID(); - CommentaireAideResponse a = CommentaireAideResponse.builder().contenu("x").build(); - a.setId(id); - CommentaireAideResponse b = CommentaireAideResponse.builder().contenu("x").build(); - b.setId(id); - assertThat(a).isEqualTo(a); - assertThat(a.hashCode()).isEqualTo(a.hashCode()); - CommentaireAideResponse autreId = CommentaireAideResponse.builder().contenu("x").build(); - autreId.setId(UUID.randomUUID()); - assertThat(a).isNotEqualTo(autreId); - } - } -} +package dev.lions.unionflow.server.api.dto.solidarite.response; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour CommentaireAideResponse. + * Couvre builder, getters/setters et equals/hashCode (héritage BaseResponse). + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests CommentaireAideResponse") +class CommentaireAideResponseTest { + + @Nested + @DisplayName("Builder et getters") + class BuilderEtGetters { + + @Test + @DisplayName("builder remplit tous les champs") + void testBuilder() { + UUID id = UUID.randomUUID(); + UUID auteurId = UUID.randomUUID(); + CommentaireAideResponse r = CommentaireAideResponse.builder() + .contenu("Contenu") + .typeCommentaire("public") + .auteurId(auteurId) + .auteurNom("Dupont") + .auteurRole("Membre") + .estPrive(false) + .estImportant(true) + .estModifie(false) + .nombreReactions(5) + .estResolu(false) + .build(); + r.setId(id); + assertThat(r.getId()).isEqualTo(id); + assertThat(r.getContenu()).isEqualTo("Contenu"); + assertThat(r.getTypeCommentaire()).isEqualTo("public"); + assertThat(r.getAuteurId()).isEqualTo(auteurId); + assertThat(r.getAuteurNom()).isEqualTo("Dupont"); + assertThat(r.getAuteurRole()).isEqualTo("Membre"); + assertThat(r.getEstPrive()).isFalse(); + assertThat(r.getEstImportant()).isTrue(); + assertThat(r.getEstModifie()).isFalse(); + assertThat(r.getNombreReactions()).isEqualTo(5); + assertThat(r.getEstResolu()).isFalse(); + } + + @Test + @DisplayName("constructeur par défaut puis setters") + void testSetters() { + CommentaireAideResponse r = new CommentaireAideResponse(); + r.setContenu("c"); + r.setCommentaireParentId(UUID.randomUUID()); + assertThat(r.getContenu()).isEqualTo("c"); + assertThat(r.getCommentaireParentId()).isNotNull(); + } + + @Test + @DisplayName("equals et hashCode avec même contenu et même id") + void testEqualsHashCode() { + UUID id = UUID.randomUUID(); + CommentaireAideResponse a = CommentaireAideResponse.builder().contenu("x").build(); + a.setId(id); + CommentaireAideResponse b = CommentaireAideResponse.builder().contenu("x").build(); + b.setId(id); + assertThat(a).isEqualTo(a); + assertThat(a.hashCode()).isEqualTo(a.hashCode()); + CommentaireAideResponse autreId = CommentaireAideResponse.builder().contenu("x").build(); + autreId.setId(UUID.randomUUID()); + assertThat(a).isNotEqualTo(autreId); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/DemandeAideResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/DemandeAideResponseTest.java index ef7c09a..adcbd6a 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/DemandeAideResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/DemandeAideResponseTest.java @@ -1,404 +1,404 @@ -package dev.lions.unionflow.server.api.dto.solidarite.response; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalDateTime; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; -import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; -import dev.lions.unionflow.server.api.enums.solidarite.StatutAide; - -/** - * Tests unitaires pour DemandeAideResponse. - * Couvre estModifiable, peutEtreAnnulee, estUrgente, estTerminee, estEnSucces, - * getPourcentageAvancement (tous statuts), getDelaiRestantHeures, estDelaiDepasse, - * getStatutLibelle, getPrioriteLibelle. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests DemandeAideResponse") -class DemandeAideResponseTest { - - @Nested - @DisplayName("estModifiable") - class EstModifiable { - - @Test - @DisplayName("retourne false quand statut null") - void testStatutNull() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(null).build(); - assertThat(r.estModifiable()).isFalse(); - } - - @Test - @DisplayName("retourne true pour BROUILLON") - void testBrouillon() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.BROUILLON).build(); - assertThat(r.estModifiable()).isTrue(); - } - - @Test - @DisplayName("retourne true pour INFORMATIONS_REQUISES") - void testInformationsRequises() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.INFORMATIONS_REQUISES).build(); - assertThat(r.estModifiable()).isTrue(); - } - - @Test - @DisplayName("retourne false pour SOUMISE") - void testSoumise() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.SOUMISE).build(); - assertThat(r.estModifiable()).isFalse(); - } - } - - @Nested - @DisplayName("peutEtreAnnulee") - class PeutEtreAnnulee { - - @Test - @DisplayName("retourne false quand statut null") - void testStatutNull() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(null).build(); - assertThat(r.peutEtreAnnulee()).isFalse(); - } - - @Test - @DisplayName("retourne true pour BROUILLON") - void testBrouillon() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.BROUILLON).build(); - assertThat(r.peutEtreAnnulee()).isTrue(); - } - - @Test - @DisplayName("retourne false pour VERSEE (final)") - void testFinal() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.VERSEE).build(); - assertThat(r.peutEtreAnnulee()).isFalse(); - } - - @Test - @DisplayName("retourne false pour ANNULEE") - void testAnnulee() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.ANNULEE).build(); - assertThat(r.peutEtreAnnulee()).isFalse(); - } - } - - @Nested - @DisplayName("estUrgente") - class EstUrgente { - - @Test - @DisplayName("retourne false quand priorite null") - void testPrioriteNull() { - DemandeAideResponse r = DemandeAideResponse.builder().priorite(null).build(); - assertThat(r.estUrgente()).isFalse(); - } - - @Test - @DisplayName("retourne true pour CRITIQUE") - void testCritique() { - DemandeAideResponse r = DemandeAideResponse.builder().priorite(PrioriteAide.CRITIQUE).build(); - assertThat(r.estUrgente()).isTrue(); - } - - @Test - @DisplayName("retourne true pour URGENTE") - void testUrgente() { - DemandeAideResponse r = DemandeAideResponse.builder().priorite(PrioriteAide.URGENTE).build(); - assertThat(r.estUrgente()).isTrue(); - } - - @Test - @DisplayName("retourne false pour NORMALE") - void testNormale() { - DemandeAideResponse r = DemandeAideResponse.builder().priorite(PrioriteAide.NORMALE).build(); - assertThat(r.estUrgente()).isFalse(); - } - } - - @Nested - @DisplayName("estTerminee") - class EstTerminee { - - @Test - @DisplayName("retourne false quand statut null") - void testStatutNull() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(null).build(); - assertThat(r.estTerminee()).isFalse(); - } - - @Test - @DisplayName("retourne true pour VERSEE") - void testTerminee() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.VERSEE).build(); - assertThat(r.estTerminee()).isTrue(); - } - - @Test - @DisplayName("retourne false pour EN_ATTENTE") - void testEnCours() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.EN_ATTENTE).build(); - assertThat(r.estTerminee()).isFalse(); - } - } - - @Nested - @DisplayName("estEnSucces") - class EstEnSucces { - - @Test - @DisplayName("retourne false quand statut null") - void testStatutNull() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(null).build(); - assertThat(r.estEnSucces()).isFalse(); - } - - @Test - @DisplayName("retourne true pour VERSEE") - void testVersee() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.VERSEE).build(); - assertThat(r.estEnSucces()).isTrue(); - } - - @Test - @DisplayName("retourne false pour REJETEE") - void testRejetee() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.REJETEE).build(); - assertThat(r.estEnSucces()).isFalse(); - } - } - - @Nested - @DisplayName("getPourcentageAvancement") - class GetPourcentageAvancement { - - @Test - @DisplayName("retourne 0 quand statut null") - void testStatutNull() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(null).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(0.0); - } - - @ParameterizedTest - @EnumSource(value = StatutAide.class, names = {"BROUILLON"}) - @DisplayName("BROUILLON -> 5.0") - void testBrouillon(StatutAide statut) { - DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(5.0); - } - - @ParameterizedTest - @EnumSource(value = StatutAide.class, names = {"SOUMISE"}) - @DisplayName("SOUMISE -> 10.0") - void testSoumise(StatutAide statut) { - DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(10.0); - } - - @ParameterizedTest - @EnumSource(value = StatutAide.class, names = {"EN_ATTENTE"}) - @DisplayName("EN_ATTENTE -> 20.0") - void testEnAttente(StatutAide statut) { - DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(20.0); - } - - @ParameterizedTest - @EnumSource(value = StatutAide.class, names = {"EN_COURS_EVALUATION"}) - @DisplayName("EN_COURS_EVALUATION -> 40.0") - void testEnCoursEvaluation(StatutAide statut) { - DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(40.0); - } - - @ParameterizedTest - @EnumSource(value = StatutAide.class, names = {"INFORMATIONS_REQUISES"}) - @DisplayName("INFORMATIONS_REQUISES -> 35.0") - void testInformationsRequises(StatutAide statut) { - DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(35.0); - } - - @ParameterizedTest - @EnumSource(value = StatutAide.class, names = {"APPROUVEE", "APPROUVEE_PARTIELLEMENT"}) - @DisplayName("APPROUVEE/APPROUVEE_PARTIELLEMENT -> 60.0") - void testApprouvee(StatutAide statut) { - DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(60.0); - } - - @ParameterizedTest - @EnumSource(value = StatutAide.class, names = {"EN_COURS_TRAITEMENT"}) - @DisplayName("EN_COURS_TRAITEMENT -> 70.0") - void testEnCoursTraitement(StatutAide statut) { - DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(70.0); - } - - @ParameterizedTest - @EnumSource(value = StatutAide.class, names = {"EN_COURS_VERSEMENT"}) - @DisplayName("EN_COURS_VERSEMENT -> 85.0") - void testEnCoursVersement(StatutAide statut) { - DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(85.0); - } - - @ParameterizedTest - @EnumSource(value = StatutAide.class, names = {"VERSEE", "LIVREE", "TERMINEE"}) - @DisplayName("VERSEE/LIVREE/TERMINEE -> 100.0") - void testFinauxSucces(StatutAide statut) { - DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(100.0); - } - - @ParameterizedTest - @EnumSource(value = StatutAide.class, names = {"REJETEE", "ANNULEE", "EXPIREE"}) - @DisplayName("REJETEE/ANNULEE/EXPIREE -> 100.0") - void testFinauxEchec(StatutAide statut) { - DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(100.0); - } - - @ParameterizedTest - @EnumSource(value = StatutAide.class, names = {"SUSPENDUE"}) - @DisplayName("SUSPENDUE -> 50.0") - void testSuspendue(StatutAide statut) { - DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(50.0); - } - - @ParameterizedTest - @EnumSource(value = StatutAide.class, names = {"EN_SUIVI"}) - @DisplayName("EN_SUIVI -> 95.0") - void testEnSuivi(StatutAide statut) { - DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(95.0); - } - - @ParameterizedTest - @EnumSource(value = StatutAide.class, names = {"CLOTUREE"}) - @DisplayName("CLOTUREE -> 100.0") - void testCloturee(StatutAide statut) { - DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); - assertThat(r.getPourcentageAvancement()).isEqualTo(100.0); - } - } - - @Nested - @DisplayName("getDelaiRestantHeures") - class GetDelaiRestantHeures { - - @Test - @DisplayName("retourne -1 quand dateLimiteTraitement null") - void testNull() { - DemandeAideResponse r = DemandeAideResponse.builder().dateLimiteTraitement(null).build(); - assertThat(r.getDelaiRestantHeures()).isEqualTo(-1); - } - - @Test - @DisplayName("retourne 0 quand date limite dépassée") - void testDepasse() { - LocalDateTime hier = LocalDateTime.now().minusHours(1); - DemandeAideResponse r = DemandeAideResponse.builder().dateLimiteTraitement(hier).build(); - assertThat(r.getDelaiRestantHeures()).isEqualTo(0); - } - - @Test - @DisplayName("retourne heures restantes quand date limite future") - void testRestant() { - LocalDateTime demain = LocalDateTime.now().plusHours(24); - DemandeAideResponse r = DemandeAideResponse.builder().dateLimiteTraitement(demain).build(); - assertThat(r.getDelaiRestantHeures()).isGreaterThanOrEqualTo(23); - } - } - - @Nested - @DisplayName("estDelaiDepasse") - class EstDelaiDepasse { - - @Test - @DisplayName("retourne true quand delai restant 0") - void testDepasse() { - LocalDateTime hier = LocalDateTime.now().minusHours(1); - DemandeAideResponse r = DemandeAideResponse.builder().dateLimiteTraitement(hier).build(); - assertThat(r.estDelaiDepasse()).isTrue(); - } - - @Test - @DisplayName("retourne false quand delai restant > 0") - void testNonDepasse() { - LocalDateTime demain = LocalDateTime.now().plusHours(24); - DemandeAideResponse r = DemandeAideResponse.builder().dateLimiteTraitement(demain).build(); - assertThat(r.estDelaiDepasse()).isFalse(); - } - } - - @Nested - @DisplayName("getStatutLibelle") - class GetStatutLibelle { - - @Test - @DisplayName("retourne Non défini quand statut null") - void testNull() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(null).build(); - assertThat(r.getStatutLibelle()).isEqualTo("Non défini"); - } - - @Test - @DisplayName("retourne libellé du statut") - void testLibelle() { - DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.BROUILLON).build(); - assertThat(r.getStatutLibelle()).isEqualTo("Brouillon"); - } - } - - @Nested - @DisplayName("getPrioriteLibelle") - class GetPrioriteLibelle { - - @Test - @DisplayName("retourne Normale quand priorite null") - void testNull() { - DemandeAideResponse r = DemandeAideResponse.builder().priorite(null).build(); - assertThat(r.getPrioriteLibelle()).isEqualTo("Normale"); - } - - @Test - @DisplayName("retourne libellé de la priorité") - void testLibelle() { - DemandeAideResponse r = DemandeAideResponse.builder().priorite(PrioriteAide.URGENTE).build(); - assertThat(r.getPrioriteLibelle()).isEqualTo("Urgente"); - } - } - - @Nested - @DisplayName("Builder et getters") - class BuilderEtGetters { - - @Test - @DisplayName("builder remplit les champs") - void testBuilder() { - UUID id = UUID.randomUUID(); - DemandeAideResponse r = DemandeAideResponse.builder() - .numeroReference("REF-001") - .titre("Titre") - .statut(StatutAide.SOUMISE) - .priorite(PrioriteAide.NORMALE) - .build(); - r.setId(id); - assertThat(r.getId()).isEqualTo(id); - assertThat(r.getNumeroReference()).isEqualTo("REF-001"); - assertThat(r.getTitre()).isEqualTo("Titre"); - assertThat(r.getStatut()).isEqualTo(StatutAide.SOUMISE); - assertThat(r.getPriorite()).isEqualTo(PrioriteAide.NORMALE); - } - } -} +package dev.lions.unionflow.server.api.dto.solidarite.response; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalDateTime; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; +import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; +import dev.lions.unionflow.server.api.enums.solidarite.StatutAide; + +/** + * Tests unitaires pour DemandeAideResponse. + * Couvre estModifiable, peutEtreAnnulee, estUrgente, estTerminee, estEnSucces, + * getPourcentageAvancement (tous statuts), getDelaiRestantHeures, estDelaiDepasse, + * getStatutLibelle, getPrioriteLibelle. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests DemandeAideResponse") +class DemandeAideResponseTest { + + @Nested + @DisplayName("estModifiable") + class EstModifiable { + + @Test + @DisplayName("retourne false quand statut null") + void testStatutNull() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(null).build(); + assertThat(r.estModifiable()).isFalse(); + } + + @Test + @DisplayName("retourne true pour BROUILLON") + void testBrouillon() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.BROUILLON).build(); + assertThat(r.estModifiable()).isTrue(); + } + + @Test + @DisplayName("retourne true pour INFORMATIONS_REQUISES") + void testInformationsRequises() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.INFORMATIONS_REQUISES).build(); + assertThat(r.estModifiable()).isTrue(); + } + + @Test + @DisplayName("retourne false pour SOUMISE") + void testSoumise() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.SOUMISE).build(); + assertThat(r.estModifiable()).isFalse(); + } + } + + @Nested + @DisplayName("peutEtreAnnulee") + class PeutEtreAnnulee { + + @Test + @DisplayName("retourne false quand statut null") + void testStatutNull() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(null).build(); + assertThat(r.peutEtreAnnulee()).isFalse(); + } + + @Test + @DisplayName("retourne true pour BROUILLON") + void testBrouillon() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.BROUILLON).build(); + assertThat(r.peutEtreAnnulee()).isTrue(); + } + + @Test + @DisplayName("retourne false pour VERSEE (final)") + void testFinal() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.VERSEE).build(); + assertThat(r.peutEtreAnnulee()).isFalse(); + } + + @Test + @DisplayName("retourne false pour ANNULEE") + void testAnnulee() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.ANNULEE).build(); + assertThat(r.peutEtreAnnulee()).isFalse(); + } + } + + @Nested + @DisplayName("estUrgente") + class EstUrgente { + + @Test + @DisplayName("retourne false quand priorite null") + void testPrioriteNull() { + DemandeAideResponse r = DemandeAideResponse.builder().priorite(null).build(); + assertThat(r.estUrgente()).isFalse(); + } + + @Test + @DisplayName("retourne true pour CRITIQUE") + void testCritique() { + DemandeAideResponse r = DemandeAideResponse.builder().priorite(PrioriteAide.CRITIQUE).build(); + assertThat(r.estUrgente()).isTrue(); + } + + @Test + @DisplayName("retourne true pour URGENTE") + void testUrgente() { + DemandeAideResponse r = DemandeAideResponse.builder().priorite(PrioriteAide.URGENTE).build(); + assertThat(r.estUrgente()).isTrue(); + } + + @Test + @DisplayName("retourne false pour NORMALE") + void testNormale() { + DemandeAideResponse r = DemandeAideResponse.builder().priorite(PrioriteAide.NORMALE).build(); + assertThat(r.estUrgente()).isFalse(); + } + } + + @Nested + @DisplayName("estTerminee") + class EstTerminee { + + @Test + @DisplayName("retourne false quand statut null") + void testStatutNull() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(null).build(); + assertThat(r.estTerminee()).isFalse(); + } + + @Test + @DisplayName("retourne true pour VERSEE") + void testTerminee() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.VERSEE).build(); + assertThat(r.estTerminee()).isTrue(); + } + + @Test + @DisplayName("retourne false pour EN_ATTENTE") + void testEnCours() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.EN_ATTENTE).build(); + assertThat(r.estTerminee()).isFalse(); + } + } + + @Nested + @DisplayName("estEnSucces") + class EstEnSucces { + + @Test + @DisplayName("retourne false quand statut null") + void testStatutNull() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(null).build(); + assertThat(r.estEnSucces()).isFalse(); + } + + @Test + @DisplayName("retourne true pour VERSEE") + void testVersee() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.VERSEE).build(); + assertThat(r.estEnSucces()).isTrue(); + } + + @Test + @DisplayName("retourne false pour REJETEE") + void testRejetee() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.REJETEE).build(); + assertThat(r.estEnSucces()).isFalse(); + } + } + + @Nested + @DisplayName("getPourcentageAvancement") + class GetPourcentageAvancement { + + @Test + @DisplayName("retourne 0 quand statut null") + void testStatutNull() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(null).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(0.0); + } + + @ParameterizedTest + @EnumSource(value = StatutAide.class, names = {"BROUILLON"}) + @DisplayName("BROUILLON -> 5.0") + void testBrouillon(StatutAide statut) { + DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(5.0); + } + + @ParameterizedTest + @EnumSource(value = StatutAide.class, names = {"SOUMISE"}) + @DisplayName("SOUMISE -> 10.0") + void testSoumise(StatutAide statut) { + DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(10.0); + } + + @ParameterizedTest + @EnumSource(value = StatutAide.class, names = {"EN_ATTENTE"}) + @DisplayName("EN_ATTENTE -> 20.0") + void testEnAttente(StatutAide statut) { + DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(20.0); + } + + @ParameterizedTest + @EnumSource(value = StatutAide.class, names = {"EN_COURS_EVALUATION"}) + @DisplayName("EN_COURS_EVALUATION -> 40.0") + void testEnCoursEvaluation(StatutAide statut) { + DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(40.0); + } + + @ParameterizedTest + @EnumSource(value = StatutAide.class, names = {"INFORMATIONS_REQUISES"}) + @DisplayName("INFORMATIONS_REQUISES -> 35.0") + void testInformationsRequises(StatutAide statut) { + DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(35.0); + } + + @ParameterizedTest + @EnumSource(value = StatutAide.class, names = {"APPROUVEE", "APPROUVEE_PARTIELLEMENT"}) + @DisplayName("APPROUVEE/APPROUVEE_PARTIELLEMENT -> 60.0") + void testApprouvee(StatutAide statut) { + DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(60.0); + } + + @ParameterizedTest + @EnumSource(value = StatutAide.class, names = {"EN_COURS_TRAITEMENT"}) + @DisplayName("EN_COURS_TRAITEMENT -> 70.0") + void testEnCoursTraitement(StatutAide statut) { + DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(70.0); + } + + @ParameterizedTest + @EnumSource(value = StatutAide.class, names = {"EN_COURS_VERSEMENT"}) + @DisplayName("EN_COURS_VERSEMENT -> 85.0") + void testEnCoursVersement(StatutAide statut) { + DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(85.0); + } + + @ParameterizedTest + @EnumSource(value = StatutAide.class, names = {"VERSEE", "LIVREE", "TERMINEE"}) + @DisplayName("VERSEE/LIVREE/TERMINEE -> 100.0") + void testFinauxSucces(StatutAide statut) { + DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(100.0); + } + + @ParameterizedTest + @EnumSource(value = StatutAide.class, names = {"REJETEE", "ANNULEE", "EXPIREE"}) + @DisplayName("REJETEE/ANNULEE/EXPIREE -> 100.0") + void testFinauxEchec(StatutAide statut) { + DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(100.0); + } + + @ParameterizedTest + @EnumSource(value = StatutAide.class, names = {"SUSPENDUE"}) + @DisplayName("SUSPENDUE -> 50.0") + void testSuspendue(StatutAide statut) { + DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(50.0); + } + + @ParameterizedTest + @EnumSource(value = StatutAide.class, names = {"EN_SUIVI"}) + @DisplayName("EN_SUIVI -> 95.0") + void testEnSuivi(StatutAide statut) { + DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(95.0); + } + + @ParameterizedTest + @EnumSource(value = StatutAide.class, names = {"CLOTUREE"}) + @DisplayName("CLOTUREE -> 100.0") + void testCloturee(StatutAide statut) { + DemandeAideResponse r = DemandeAideResponse.builder().statut(statut).build(); + assertThat(r.getPourcentageAvancement()).isEqualTo(100.0); + } + } + + @Nested + @DisplayName("getDelaiRestantHeures") + class GetDelaiRestantHeures { + + @Test + @DisplayName("retourne -1 quand dateLimiteTraitement null") + void testNull() { + DemandeAideResponse r = DemandeAideResponse.builder().dateLimiteTraitement(null).build(); + assertThat(r.getDelaiRestantHeures()).isEqualTo(-1); + } + + @Test + @DisplayName("retourne 0 quand date limite dépassée") + void testDepasse() { + LocalDateTime hier = LocalDateTime.now().minusHours(1); + DemandeAideResponse r = DemandeAideResponse.builder().dateLimiteTraitement(hier).build(); + assertThat(r.getDelaiRestantHeures()).isEqualTo(0); + } + + @Test + @DisplayName("retourne heures restantes quand date limite future") + void testRestant() { + LocalDateTime demain = LocalDateTime.now().plusHours(24); + DemandeAideResponse r = DemandeAideResponse.builder().dateLimiteTraitement(demain).build(); + assertThat(r.getDelaiRestantHeures()).isGreaterThanOrEqualTo(23); + } + } + + @Nested + @DisplayName("estDelaiDepasse") + class EstDelaiDepasse { + + @Test + @DisplayName("retourne true quand delai restant 0") + void testDepasse() { + LocalDateTime hier = LocalDateTime.now().minusHours(1); + DemandeAideResponse r = DemandeAideResponse.builder().dateLimiteTraitement(hier).build(); + assertThat(r.estDelaiDepasse()).isTrue(); + } + + @Test + @DisplayName("retourne false quand delai restant > 0") + void testNonDepasse() { + LocalDateTime demain = LocalDateTime.now().plusHours(24); + DemandeAideResponse r = DemandeAideResponse.builder().dateLimiteTraitement(demain).build(); + assertThat(r.estDelaiDepasse()).isFalse(); + } + } + + @Nested + @DisplayName("getStatutLibelle") + class GetStatutLibelle { + + @Test + @DisplayName("retourne Non défini quand statut null") + void testNull() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(null).build(); + assertThat(r.getStatutLibelle()).isEqualTo("Non défini"); + } + + @Test + @DisplayName("retourne libellé du statut") + void testLibelle() { + DemandeAideResponse r = DemandeAideResponse.builder().statut(StatutAide.BROUILLON).build(); + assertThat(r.getStatutLibelle()).isEqualTo("Brouillon"); + } + } + + @Nested + @DisplayName("getPrioriteLibelle") + class GetPrioriteLibelle { + + @Test + @DisplayName("retourne Normale quand priorite null") + void testNull() { + DemandeAideResponse r = DemandeAideResponse.builder().priorite(null).build(); + assertThat(r.getPrioriteLibelle()).isEqualTo("Normale"); + } + + @Test + @DisplayName("retourne libellé de la priorité") + void testLibelle() { + DemandeAideResponse r = DemandeAideResponse.builder().priorite(PrioriteAide.URGENTE).build(); + assertThat(r.getPrioriteLibelle()).isEqualTo("Urgente"); + } + } + + @Nested + @DisplayName("Builder et getters") + class BuilderEtGetters { + + @Test + @DisplayName("builder remplit les champs") + void testBuilder() { + UUID id = UUID.randomUUID(); + DemandeAideResponse r = DemandeAideResponse.builder() + .numeroReference("REF-001") + .titre("Titre") + .statut(StatutAide.SOUMISE) + .priorite(PrioriteAide.NORMALE) + .build(); + r.setId(id); + assertThat(r.getId()).isEqualTo(id); + assertThat(r.getNumeroReference()).isEqualTo("REF-001"); + assertThat(r.getTitre()).isEqualTo("Titre"); + assertThat(r.getStatut()).isEqualTo(StatutAide.SOUMISE); + assertThat(r.getPriorite()).isEqualTo(PrioriteAide.NORMALE); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/EvaluationAideResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/EvaluationAideResponseTest.java index 4f1ff4b..5203f25 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/EvaluationAideResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/EvaluationAideResponseTest.java @@ -1,385 +1,385 @@ -package dev.lions.unionflow.server.api.dto.solidarite.response; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.util.Map; -import java.util.UUID; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour EvaluationAideResponse. - * Couvre getNoteMoyenneDetaillees, isPositive, isNegative, getScoreQualite, - * isComplete, getNiveauSatisfaction (tous cas du switch). - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests EvaluationAideResponse") -class EvaluationAideResponseTest { - - @Nested - @DisplayName("getNoteMoyenneDetaillees") - class GetNoteMoyenneDetaillees { - - @Test - @DisplayName("retourne noteGlobale quand notesDetaillees null") - void testNotesNull() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(4.0) - .notesDetaillees(null) - .build(); - assertThat(r.getNoteMoyenneDetaillees()).isEqualTo(4.0); - } - - @Test - @DisplayName("retourne noteGlobale quand notesDetaillees vide") - void testNotesVide() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(3.5) - .notesDetaillees(Map.of()) - .build(); - assertThat(r.getNoteMoyenneDetaillees()).isEqualTo(3.5); - } - - @Test - @DisplayName("retourne moyenne des notes détaillées") - void testMoyenne() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(5.0) - .notesDetaillees(Map.of("a", 3.0, "b", 5.0)) - .build(); - assertThat(r.getNoteMoyenneDetaillees()).isEqualTo(4.0); - } - - @Test - @DisplayName("retourne noteGlobale quand notesDetaillees non vide mais noteGlobale null (fallback 0)") - void testNoteGlobaleNullAvecNotes() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(null) - .notesDetaillees(Map.of("a", 2.0)) - .build(); - assertThat(r.getNoteMoyenneDetaillees()).isEqualTo(2.0); - } - } - - @Nested - @DisplayName("isPositive") - class IsPositive { - - @Test - @DisplayName("retourne false quand noteGlobale null") - void testNull() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(null).build(); - assertThat(r.isPositive()).isFalse(); - } - - @Test - @DisplayName("retourne true quand noteGlobale >= 4") - void testPositive() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(4.0).build(); - assertThat(r.isPositive()).isTrue(); - r.setNoteGlobale(5.0); - assertThat(r.isPositive()).isTrue(); - } - - @Test - @DisplayName("retourne false quand noteGlobale < 4") - void testNonPositive() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(3.9).build(); - assertThat(r.isPositive()).isFalse(); - } - } - - @Nested - @DisplayName("isNegative") - class IsNegative { - - @Test - @DisplayName("retourne false quand noteGlobale null") - void testNull() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(null).build(); - assertThat(r.isNegative()).isFalse(); - } - - @Test - @DisplayName("retourne true quand noteGlobale <= 2") - void testNegative() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(2.0).build(); - assertThat(r.isNegative()).isTrue(); - r.setNoteGlobale(1.0); - assertThat(r.isNegative()).isTrue(); - } - - @Test - @DisplayName("retourne false quand noteGlobale > 2") - void testNonNegative() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(2.1).build(); - assertThat(r.isNegative()).isFalse(); - } - } - - @Nested - @DisplayName("getScoreQualite") - class GetScoreQualite { - - @Test - @DisplayName("retourne 0 quand noteGlobale null et pas d'autres notes") - void testNoteGlobaleNull() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(null).build(); - assertThat(r.getScoreQualite()).isEqualTo(0.0); - } - - @Test - @DisplayName("inclut noteGlobale et bonus recommande + problemeResolu") - void testAvecRecommandeEtResolu() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(4.0) - .recommande(true) - .problemeResolu(true) - .build(); - double score = r.getScoreQualite(); - assertThat(score).isGreaterThanOrEqualTo(4.0); - assertThat(score).isLessThanOrEqualTo(5.0); - } - - @Test - @DisplayName("inclut notes détaillées (delai, communication, etc.)") - void testAvecNotesDetaillees() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(4.0) - .noteDelaiReponse(5.0) - .noteCommunication(4.0) - .noteProfessionnalisme(5.0) - .noteRespectEngagements(4.0) - .build(); - double score = r.getScoreQualite(); - assertThat(score).isGreaterThan(4.0); - assertThat(score).isLessThanOrEqualTo(5.0); - } - - @Test - @DisplayName("décrémente avec nombreSignalements") - void testAvecSignalements() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(4.0) - .nombreSignalements(2) - .build(); - double score = r.getScoreQualite(); - assertThat(score).isLessThan(4.0); - } - - @Test - @DisplayName("score borné entre 0 et 5") - void testBorne() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(5.0) - .noteDelaiReponse(5.0) - .noteCommunication(5.0) - .noteProfessionnalisme(5.0) - .noteRespectEngagements(5.0) - .recommande(true) - .problemeResolu(true) - .build(); - assertThat(r.getScoreQualite()).isLessThanOrEqualTo(5.0); - } - - @Test - @DisplayName("ne donne pas de bonus quand recommande false") - void testRecommandeFalse() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(4.0) - .recommande(false) - .build(); - assertThat(r.getScoreQualite()).isEqualTo(4.0); - } - - @Test - @DisplayName("ne donne pas de bonus quand problemeResolu false") - void testProblemeResoluFalse() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(4.0) - .problemeResolu(false) - .build(); - assertThat(r.getScoreQualite()).isEqualTo(4.0); - } - - @Test - @DisplayName("ne décrémente pas quand nombreSignalements 0") - void testNombreSignalementsZero() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(4.0) - .nombreSignalements(0) - .build(); - assertThat(r.getScoreQualite()).isEqualTo(4.0); - } - } - - @Nested - @DisplayName("isComplete") - class IsComplete { - - @Test - @DisplayName("retourne false quand noteGlobale null") - void testNoteNull() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .commentairePrincipal("x") - .recommande(true) - .aideUtile(true) - .problemeResolu(true) - .build(); - assertThat(r.isComplete()).isFalse(); - } - - @Test - @DisplayName("retourne false quand commentairePrincipal null") - void testCommentaireNull() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(4.0) - .recommande(true) - .aideUtile(true) - .problemeResolu(true) - .build(); - assertThat(r.isComplete()).isFalse(); - } - - @Test - @DisplayName("retourne false quand commentairePrincipal vide (trim)") - void testCommentaireVide() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(4.0) - .commentairePrincipal(" ") - .recommande(true) - .aideUtile(true) - .problemeResolu(true) - .build(); - assertThat(r.isComplete()).isFalse(); - } - - @Test - @DisplayName("retourne false quand recommande null") - void testRecommandeNull() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(4.0) - .commentairePrincipal("OK") - .aideUtile(true) - .problemeResolu(true) - .build(); - assertThat(r.isComplete()).isFalse(); - } - - @Test - @DisplayName("retourne false quand aideUtile null") - void testAideUtileNull() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(4.0) - .commentairePrincipal("OK") - .recommande(true) - .problemeResolu(true) - .build(); - assertThat(r.isComplete()).isFalse(); - } - - @Test - @DisplayName("retourne false quand problemeResolu null") - void testProblemeResoluNull() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(4.0) - .commentairePrincipal("OK") - .recommande(true) - .aideUtile(true) - .build(); - assertThat(r.isComplete()).isFalse(); - } - - @Test - @DisplayName("retourne true quand tous les champs requis remplis") - void testComplete() { - EvaluationAideResponse r = EvaluationAideResponse.builder() - .noteGlobale(4.0) - .commentairePrincipal("Très bien") - .recommande(true) - .aideUtile(true) - .problemeResolu(true) - .build(); - assertThat(r.isComplete()).isTrue(); - } - } - - @Nested - @DisplayName("getNiveauSatisfaction") - class GetNiveauSatisfaction { - - @Test - @DisplayName("retourne Non évalué quand noteGlobale null") - void testNull() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(null).build(); - assertThat(r.getNiveauSatisfaction()).isEqualTo("Non évalué"); - } - - @Test - @DisplayName("note 5 -> Excellent") - void test5() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(5.0).build(); - assertThat(r.getNiveauSatisfaction()).isEqualTo("Excellent"); - } - - @Test - @DisplayName("note 4 -> Très bien") - void test4() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(4.0).build(); - assertThat(r.getNiveauSatisfaction()).isEqualTo("Très bien"); - } - - @Test - @DisplayName("note 3 -> Bien") - void test3() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(3.0).build(); - assertThat(r.getNiveauSatisfaction()).isEqualTo("Bien"); - } - - @Test - @DisplayName("note 2 -> Passable") - void test2() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(2.0).build(); - assertThat(r.getNiveauSatisfaction()).isEqualTo("Passable"); - } - - @Test - @DisplayName("note 1 -> Insuffisant") - void test1() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(1.0).build(); - assertThat(r.getNiveauSatisfaction()).isEqualTo("Insuffisant"); - } - - @Test - @DisplayName("autre valeur -> Non évalué") - void testDefault() { - EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(0.5).build(); - assertThat(r.getNiveauSatisfaction()).isEqualTo("Non évalué"); - } - } - - @Nested - @DisplayName("Builder et getters") - class BuilderEtGetters { - - @Test - @DisplayName("builder remplit les champs") - void testBuilder() { - UUID id = UUID.randomUUID(); - EvaluationAideResponse r = EvaluationAideResponse.builder() - .demandeAideId(id) - .noteGlobale(4.5) - .commentairePrincipal("Bien") - .build(); - r.setId(id); - assertThat(r.getId()).isEqualTo(id); - assertThat(r.getDemandeAideId()).isEqualTo(id); - assertThat(r.getNoteGlobale()).isEqualTo(4.5); - assertThat(r.getCommentairePrincipal()).isEqualTo("Bien"); - } - } -} +package dev.lions.unionflow.server.api.dto.solidarite.response; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.Map; +import java.util.UUID; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour EvaluationAideResponse. + * Couvre getNoteMoyenneDetaillees, isPositive, isNegative, getScoreQualite, + * isComplete, getNiveauSatisfaction (tous cas du switch). + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests EvaluationAideResponse") +class EvaluationAideResponseTest { + + @Nested + @DisplayName("getNoteMoyenneDetaillees") + class GetNoteMoyenneDetaillees { + + @Test + @DisplayName("retourne noteGlobale quand notesDetaillees null") + void testNotesNull() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(4.0) + .notesDetaillees(null) + .build(); + assertThat(r.getNoteMoyenneDetaillees()).isEqualTo(4.0); + } + + @Test + @DisplayName("retourne noteGlobale quand notesDetaillees vide") + void testNotesVide() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(3.5) + .notesDetaillees(Map.of()) + .build(); + assertThat(r.getNoteMoyenneDetaillees()).isEqualTo(3.5); + } + + @Test + @DisplayName("retourne moyenne des notes détaillées") + void testMoyenne() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(5.0) + .notesDetaillees(Map.of("a", 3.0, "b", 5.0)) + .build(); + assertThat(r.getNoteMoyenneDetaillees()).isEqualTo(4.0); + } + + @Test + @DisplayName("retourne noteGlobale quand notesDetaillees non vide mais noteGlobale null (fallback 0)") + void testNoteGlobaleNullAvecNotes() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(null) + .notesDetaillees(Map.of("a", 2.0)) + .build(); + assertThat(r.getNoteMoyenneDetaillees()).isEqualTo(2.0); + } + } + + @Nested + @DisplayName("isPositive") + class IsPositive { + + @Test + @DisplayName("retourne false quand noteGlobale null") + void testNull() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(null).build(); + assertThat(r.isPositive()).isFalse(); + } + + @Test + @DisplayName("retourne true quand noteGlobale >= 4") + void testPositive() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(4.0).build(); + assertThat(r.isPositive()).isTrue(); + r.setNoteGlobale(5.0); + assertThat(r.isPositive()).isTrue(); + } + + @Test + @DisplayName("retourne false quand noteGlobale < 4") + void testNonPositive() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(3.9).build(); + assertThat(r.isPositive()).isFalse(); + } + } + + @Nested + @DisplayName("isNegative") + class IsNegative { + + @Test + @DisplayName("retourne false quand noteGlobale null") + void testNull() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(null).build(); + assertThat(r.isNegative()).isFalse(); + } + + @Test + @DisplayName("retourne true quand noteGlobale <= 2") + void testNegative() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(2.0).build(); + assertThat(r.isNegative()).isTrue(); + r.setNoteGlobale(1.0); + assertThat(r.isNegative()).isTrue(); + } + + @Test + @DisplayName("retourne false quand noteGlobale > 2") + void testNonNegative() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(2.1).build(); + assertThat(r.isNegative()).isFalse(); + } + } + + @Nested + @DisplayName("getScoreQualite") + class GetScoreQualite { + + @Test + @DisplayName("retourne 0 quand noteGlobale null et pas d'autres notes") + void testNoteGlobaleNull() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(null).build(); + assertThat(r.getScoreQualite()).isEqualTo(0.0); + } + + @Test + @DisplayName("inclut noteGlobale et bonus recommande + problemeResolu") + void testAvecRecommandeEtResolu() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(4.0) + .recommande(true) + .problemeResolu(true) + .build(); + double score = r.getScoreQualite(); + assertThat(score).isGreaterThanOrEqualTo(4.0); + assertThat(score).isLessThanOrEqualTo(5.0); + } + + @Test + @DisplayName("inclut notes détaillées (delai, communication, etc.)") + void testAvecNotesDetaillees() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(4.0) + .noteDelaiReponse(5.0) + .noteCommunication(4.0) + .noteProfessionnalisme(5.0) + .noteRespectEngagements(4.0) + .build(); + double score = r.getScoreQualite(); + assertThat(score).isGreaterThan(4.0); + assertThat(score).isLessThanOrEqualTo(5.0); + } + + @Test + @DisplayName("décrémente avec nombreSignalements") + void testAvecSignalements() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(4.0) + .nombreSignalements(2) + .build(); + double score = r.getScoreQualite(); + assertThat(score).isLessThan(4.0); + } + + @Test + @DisplayName("score borné entre 0 et 5") + void testBorne() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(5.0) + .noteDelaiReponse(5.0) + .noteCommunication(5.0) + .noteProfessionnalisme(5.0) + .noteRespectEngagements(5.0) + .recommande(true) + .problemeResolu(true) + .build(); + assertThat(r.getScoreQualite()).isLessThanOrEqualTo(5.0); + } + + @Test + @DisplayName("ne donne pas de bonus quand recommande false") + void testRecommandeFalse() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(4.0) + .recommande(false) + .build(); + assertThat(r.getScoreQualite()).isEqualTo(4.0); + } + + @Test + @DisplayName("ne donne pas de bonus quand problemeResolu false") + void testProblemeResoluFalse() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(4.0) + .problemeResolu(false) + .build(); + assertThat(r.getScoreQualite()).isEqualTo(4.0); + } + + @Test + @DisplayName("ne décrémente pas quand nombreSignalements 0") + void testNombreSignalementsZero() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(4.0) + .nombreSignalements(0) + .build(); + assertThat(r.getScoreQualite()).isEqualTo(4.0); + } + } + + @Nested + @DisplayName("isComplete") + class IsComplete { + + @Test + @DisplayName("retourne false quand noteGlobale null") + void testNoteNull() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .commentairePrincipal("x") + .recommande(true) + .aideUtile(true) + .problemeResolu(true) + .build(); + assertThat(r.isComplete()).isFalse(); + } + + @Test + @DisplayName("retourne false quand commentairePrincipal null") + void testCommentaireNull() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(4.0) + .recommande(true) + .aideUtile(true) + .problemeResolu(true) + .build(); + assertThat(r.isComplete()).isFalse(); + } + + @Test + @DisplayName("retourne false quand commentairePrincipal vide (trim)") + void testCommentaireVide() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(4.0) + .commentairePrincipal(" ") + .recommande(true) + .aideUtile(true) + .problemeResolu(true) + .build(); + assertThat(r.isComplete()).isFalse(); + } + + @Test + @DisplayName("retourne false quand recommande null") + void testRecommandeNull() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(4.0) + .commentairePrincipal("OK") + .aideUtile(true) + .problemeResolu(true) + .build(); + assertThat(r.isComplete()).isFalse(); + } + + @Test + @DisplayName("retourne false quand aideUtile null") + void testAideUtileNull() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(4.0) + .commentairePrincipal("OK") + .recommande(true) + .problemeResolu(true) + .build(); + assertThat(r.isComplete()).isFalse(); + } + + @Test + @DisplayName("retourne false quand problemeResolu null") + void testProblemeResoluNull() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(4.0) + .commentairePrincipal("OK") + .recommande(true) + .aideUtile(true) + .build(); + assertThat(r.isComplete()).isFalse(); + } + + @Test + @DisplayName("retourne true quand tous les champs requis remplis") + void testComplete() { + EvaluationAideResponse r = EvaluationAideResponse.builder() + .noteGlobale(4.0) + .commentairePrincipal("Très bien") + .recommande(true) + .aideUtile(true) + .problemeResolu(true) + .build(); + assertThat(r.isComplete()).isTrue(); + } + } + + @Nested + @DisplayName("getNiveauSatisfaction") + class GetNiveauSatisfaction { + + @Test + @DisplayName("retourne Non évalué quand noteGlobale null") + void testNull() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(null).build(); + assertThat(r.getNiveauSatisfaction()).isEqualTo("Non évalué"); + } + + @Test + @DisplayName("note 5 -> Excellent") + void test5() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(5.0).build(); + assertThat(r.getNiveauSatisfaction()).isEqualTo("Excellent"); + } + + @Test + @DisplayName("note 4 -> Très bien") + void test4() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(4.0).build(); + assertThat(r.getNiveauSatisfaction()).isEqualTo("Très bien"); + } + + @Test + @DisplayName("note 3 -> Bien") + void test3() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(3.0).build(); + assertThat(r.getNiveauSatisfaction()).isEqualTo("Bien"); + } + + @Test + @DisplayName("note 2 -> Passable") + void test2() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(2.0).build(); + assertThat(r.getNiveauSatisfaction()).isEqualTo("Passable"); + } + + @Test + @DisplayName("note 1 -> Insuffisant") + void test1() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(1.0).build(); + assertThat(r.getNiveauSatisfaction()).isEqualTo("Insuffisant"); + } + + @Test + @DisplayName("autre valeur -> Non évalué") + void testDefault() { + EvaluationAideResponse r = EvaluationAideResponse.builder().noteGlobale(0.5).build(); + assertThat(r.getNiveauSatisfaction()).isEqualTo("Non évalué"); + } + } + + @Nested + @DisplayName("Builder et getters") + class BuilderEtGetters { + + @Test + @DisplayName("builder remplit les champs") + void testBuilder() { + UUID id = UUID.randomUUID(); + EvaluationAideResponse r = EvaluationAideResponse.builder() + .demandeAideId(id) + .noteGlobale(4.5) + .commentairePrincipal("Bien") + .build(); + r.setId(id); + assertThat(r.getId()).isEqualTo(id); + assertThat(r.getDemandeAideId()).isEqualTo(id); + assertThat(r.getNoteGlobale()).isEqualTo(4.5); + assertThat(r.getCommentairePrincipal()).isEqualTo("Bien"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/PropositionAideResponseTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/PropositionAideResponseTest.java index 02e6dc6..1a25d51 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/PropositionAideResponseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/solidarite/response/PropositionAideResponseTest.java @@ -1,248 +1,248 @@ -package dev.lions.unionflow.server.api.dto.solidarite.response; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalDateTime; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import dev.lions.unionflow.server.api.enums.solidarite.StatutProposition; - -/** - * Tests unitaires pour PropositionAideResponse. - * Couvre isActiveEtDisponible, isExpiree, peutAccepterBeneficiaires, - * getPourcentageCapaciteUtilisee, getPlacesRestantes. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-02-21 - */ -@DisplayName("Tests PropositionAideResponse") -class PropositionAideResponseTest { - - @Nested - @DisplayName("isExpiree") - class IsExpiree { - - @Test - @DisplayName("retourne false quand dateExpiration null") - void testNull() { - PropositionAideResponse r = PropositionAideResponse.builder().dateExpiration(null).build(); - assertThat(r.isExpiree()).isFalse(); - } - - @Test - @DisplayName("retourne true quand date expiration passée") - void testExpiree() { - LocalDateTime hier = LocalDateTime.now().minusHours(1); - PropositionAideResponse r = PropositionAideResponse.builder().dateExpiration(hier).build(); - assertThat(r.isExpiree()).isTrue(); - } - - @Test - @DisplayName("retourne false quand date expiration future") - void testNonExpiree() { - LocalDateTime demain = LocalDateTime.now().plusDays(1); - PropositionAideResponse r = PropositionAideResponse.builder().dateExpiration(demain).build(); - assertThat(r.isExpiree()).isFalse(); - } - } - - @Nested - @DisplayName("isActiveEtDisponible") - class IsActiveEtDisponible { - - @Test - @DisplayName("retourne false quand statut pas ACTIVE") - void testStatutNonActive() { - LocalDateTime demain = LocalDateTime.now().plusDays(1); - PropositionAideResponse r = PropositionAideResponse.builder() - .statut(StatutProposition.BROUILLON) - .estDisponible(true) - .dateExpiration(demain) - .build(); - assertThat(r.isActiveEtDisponible()).isFalse(); - } - - @Test - @DisplayName("retourne false quand estDisponible false") - void testNonDisponible() { - LocalDateTime demain = LocalDateTime.now().plusDays(1); - PropositionAideResponse r = PropositionAideResponse.builder() - .statut(StatutProposition.ACTIVE) - .estDisponible(false) - .dateExpiration(demain) - .build(); - assertThat(r.isActiveEtDisponible()).isFalse(); - } - - @Test - @DisplayName("retourne false quand expirée") - void testExpiree() { - LocalDateTime hier = LocalDateTime.now().minusHours(1); - PropositionAideResponse r = PropositionAideResponse.builder() - .statut(StatutProposition.ACTIVE) - .estDisponible(true) - .dateExpiration(hier) - .build(); - assertThat(r.isActiveEtDisponible()).isFalse(); - } - - @Test - @DisplayName("retourne true quand ACTIVE, disponible et non expirée") - void testActiveDisponible() { - LocalDateTime demain = LocalDateTime.now().plusDays(1); - PropositionAideResponse r = PropositionAideResponse.builder() - .statut(StatutProposition.ACTIVE) - .estDisponible(true) - .dateExpiration(demain) - .build(); - assertThat(r.isActiveEtDisponible()).isTrue(); - } - } - - @Nested - @DisplayName("peutAccepterBeneficiaires") - class PeutAccepterBeneficiaires { - - @Test - @DisplayName("retourne false quand pas active et disponible") - void testNonActive() { - PropositionAideResponse r = PropositionAideResponse.builder() - .statut(StatutProposition.SUSPENDUE) - .estDisponible(true) - .dateExpiration(LocalDateTime.now().plusDays(1)) - .nombreMaxBeneficiaires(10) - .nombreBeneficiairesAides(5) - .build(); - assertThat(r.peutAccepterBeneficiaires()).isFalse(); - } - - @Test - @DisplayName("retourne false quand capacité pleine") - void testCapacitePleine() { - LocalDateTime demain = LocalDateTime.now().plusDays(1); - PropositionAideResponse r = PropositionAideResponse.builder() - .statut(StatutProposition.ACTIVE) - .estDisponible(true) - .dateExpiration(demain) - .nombreMaxBeneficiaires(10) - .nombreBeneficiairesAides(10) - .build(); - assertThat(r.peutAccepterBeneficiaires()).isFalse(); - } - - @Test - @DisplayName("retourne true quand active, disponible et places restantes") - void testPeutAccepter() { - LocalDateTime demain = LocalDateTime.now().plusDays(1); - PropositionAideResponse r = PropositionAideResponse.builder() - .statut(StatutProposition.ACTIVE) - .estDisponible(true) - .dateExpiration(demain) - .nombreMaxBeneficiaires(10) - .nombreBeneficiairesAides(3) - .build(); - assertThat(r.peutAccepterBeneficiaires()).isTrue(); - } - } - - @Nested - @DisplayName("getPourcentageCapaciteUtilisee") - class GetPourcentageCapaciteUtilisee { - - @Test - @DisplayName("retourne 100 quand nombreMaxBeneficiaires null") - void testMaxNull() { - PropositionAideResponse r = PropositionAideResponse.builder() - .nombreMaxBeneficiaires(null) - .nombreBeneficiairesAides(5) - .build(); - assertThat(r.getPourcentageCapaciteUtilisee()).isEqualTo(100.0); - } - - @Test - @DisplayName("retourne 100 quand nombreMaxBeneficiaires 0") - void testMaxZero() { - PropositionAideResponse r = PropositionAideResponse.builder() - .nombreMaxBeneficiaires(0) - .nombreBeneficiairesAides(0) - .build(); - assertThat(r.getPourcentageCapaciteUtilisee()).isEqualTo(100.0); - } - - @Test - @DisplayName("retourne pourcentage calculé") - void testCalcul() { - PropositionAideResponse r = PropositionAideResponse.builder() - .nombreMaxBeneficiaires(10) - .nombreBeneficiairesAides(3) - .build(); - assertThat(r.getPourcentageCapaciteUtilisee()).isEqualTo(30.0); - } - } - - @Nested - @DisplayName("getPlacesRestantes") - class GetPlacesRestantes { - - @Test - @DisplayName("retourne 0 quand nombreMaxBeneficiaires null") - void testMaxNull() { - PropositionAideResponse r = PropositionAideResponse.builder() - .nombreMaxBeneficiaires(null) - .build(); - assertThat(r.getPlacesRestantes()).isEqualTo(0); - } - - @Test - @DisplayName("retourne max quand nombreBeneficiairesAides null") - void testAidesNull() { - PropositionAideResponse r = PropositionAideResponse.builder() - .nombreMaxBeneficiaires(10) - .nombreBeneficiairesAides(null) - .build(); - assertThat(r.getPlacesRestantes()).isEqualTo(10); - } - - @Test - @DisplayName("retourne différence positive") - void testDifference() { - PropositionAideResponse r = PropositionAideResponse.builder() - .nombreMaxBeneficiaires(10) - .nombreBeneficiairesAides(4) - .build(); - assertThat(r.getPlacesRestantes()).isEqualTo(6); - } - - @Test - @DisplayName("retourne 0 quand plus de bénéficiaires que max (cap)") - void testCap() { - PropositionAideResponse r = PropositionAideResponse.builder() - .nombreMaxBeneficiaires(10) - .nombreBeneficiairesAides(15) - .build(); - assertThat(r.getPlacesRestantes()).isEqualTo(0); - } - } - - @Nested - @DisplayName("Builder et getters") - class BuilderEtGetters { - - @Test - @DisplayName("builder remplit les champs") - void testBuilder() { - PropositionAideResponse r = PropositionAideResponse.builder() - .numeroReference("PROP-001") - .titre("Titre") - .statut(StatutProposition.ACTIVE) - .estDisponible(true) - .build(); - assertThat(r.getNumeroReference()).isEqualTo("PROP-001"); - assertThat(r.getTitre()).isEqualTo("Titre"); - assertThat(r.getStatut()).isEqualTo(StatutProposition.ACTIVE); - assertThat(r.getEstDisponible()).isTrue(); - } - } -} +package dev.lions.unionflow.server.api.dto.solidarite.response; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalDateTime; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import dev.lions.unionflow.server.api.enums.solidarite.StatutProposition; + +/** + * Tests unitaires pour PropositionAideResponse. + * Couvre isActiveEtDisponible, isExpiree, peutAccepterBeneficiaires, + * getPourcentageCapaciteUtilisee, getPlacesRestantes. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-02-21 + */ +@DisplayName("Tests PropositionAideResponse") +class PropositionAideResponseTest { + + @Nested + @DisplayName("isExpiree") + class IsExpiree { + + @Test + @DisplayName("retourne false quand dateExpiration null") + void testNull() { + PropositionAideResponse r = PropositionAideResponse.builder().dateExpiration(null).build(); + assertThat(r.isExpiree()).isFalse(); + } + + @Test + @DisplayName("retourne true quand date expiration passée") + void testExpiree() { + LocalDateTime hier = LocalDateTime.now().minusHours(1); + PropositionAideResponse r = PropositionAideResponse.builder().dateExpiration(hier).build(); + assertThat(r.isExpiree()).isTrue(); + } + + @Test + @DisplayName("retourne false quand date expiration future") + void testNonExpiree() { + LocalDateTime demain = LocalDateTime.now().plusDays(1); + PropositionAideResponse r = PropositionAideResponse.builder().dateExpiration(demain).build(); + assertThat(r.isExpiree()).isFalse(); + } + } + + @Nested + @DisplayName("isActiveEtDisponible") + class IsActiveEtDisponible { + + @Test + @DisplayName("retourne false quand statut pas ACTIVE") + void testStatutNonActive() { + LocalDateTime demain = LocalDateTime.now().plusDays(1); + PropositionAideResponse r = PropositionAideResponse.builder() + .statut(StatutProposition.BROUILLON) + .estDisponible(true) + .dateExpiration(demain) + .build(); + assertThat(r.isActiveEtDisponible()).isFalse(); + } + + @Test + @DisplayName("retourne false quand estDisponible false") + void testNonDisponible() { + LocalDateTime demain = LocalDateTime.now().plusDays(1); + PropositionAideResponse r = PropositionAideResponse.builder() + .statut(StatutProposition.ACTIVE) + .estDisponible(false) + .dateExpiration(demain) + .build(); + assertThat(r.isActiveEtDisponible()).isFalse(); + } + + @Test + @DisplayName("retourne false quand expirée") + void testExpiree() { + LocalDateTime hier = LocalDateTime.now().minusHours(1); + PropositionAideResponse r = PropositionAideResponse.builder() + .statut(StatutProposition.ACTIVE) + .estDisponible(true) + .dateExpiration(hier) + .build(); + assertThat(r.isActiveEtDisponible()).isFalse(); + } + + @Test + @DisplayName("retourne true quand ACTIVE, disponible et non expirée") + void testActiveDisponible() { + LocalDateTime demain = LocalDateTime.now().plusDays(1); + PropositionAideResponse r = PropositionAideResponse.builder() + .statut(StatutProposition.ACTIVE) + .estDisponible(true) + .dateExpiration(demain) + .build(); + assertThat(r.isActiveEtDisponible()).isTrue(); + } + } + + @Nested + @DisplayName("peutAccepterBeneficiaires") + class PeutAccepterBeneficiaires { + + @Test + @DisplayName("retourne false quand pas active et disponible") + void testNonActive() { + PropositionAideResponse r = PropositionAideResponse.builder() + .statut(StatutProposition.SUSPENDUE) + .estDisponible(true) + .dateExpiration(LocalDateTime.now().plusDays(1)) + .nombreMaxBeneficiaires(10) + .nombreBeneficiairesAides(5) + .build(); + assertThat(r.peutAccepterBeneficiaires()).isFalse(); + } + + @Test + @DisplayName("retourne false quand capacité pleine") + void testCapacitePleine() { + LocalDateTime demain = LocalDateTime.now().plusDays(1); + PropositionAideResponse r = PropositionAideResponse.builder() + .statut(StatutProposition.ACTIVE) + .estDisponible(true) + .dateExpiration(demain) + .nombreMaxBeneficiaires(10) + .nombreBeneficiairesAides(10) + .build(); + assertThat(r.peutAccepterBeneficiaires()).isFalse(); + } + + @Test + @DisplayName("retourne true quand active, disponible et places restantes") + void testPeutAccepter() { + LocalDateTime demain = LocalDateTime.now().plusDays(1); + PropositionAideResponse r = PropositionAideResponse.builder() + .statut(StatutProposition.ACTIVE) + .estDisponible(true) + .dateExpiration(demain) + .nombreMaxBeneficiaires(10) + .nombreBeneficiairesAides(3) + .build(); + assertThat(r.peutAccepterBeneficiaires()).isTrue(); + } + } + + @Nested + @DisplayName("getPourcentageCapaciteUtilisee") + class GetPourcentageCapaciteUtilisee { + + @Test + @DisplayName("retourne 100 quand nombreMaxBeneficiaires null") + void testMaxNull() { + PropositionAideResponse r = PropositionAideResponse.builder() + .nombreMaxBeneficiaires(null) + .nombreBeneficiairesAides(5) + .build(); + assertThat(r.getPourcentageCapaciteUtilisee()).isEqualTo(100.0); + } + + @Test + @DisplayName("retourne 100 quand nombreMaxBeneficiaires 0") + void testMaxZero() { + PropositionAideResponse r = PropositionAideResponse.builder() + .nombreMaxBeneficiaires(0) + .nombreBeneficiairesAides(0) + .build(); + assertThat(r.getPourcentageCapaciteUtilisee()).isEqualTo(100.0); + } + + @Test + @DisplayName("retourne pourcentage calculé") + void testCalcul() { + PropositionAideResponse r = PropositionAideResponse.builder() + .nombreMaxBeneficiaires(10) + .nombreBeneficiairesAides(3) + .build(); + assertThat(r.getPourcentageCapaciteUtilisee()).isEqualTo(30.0); + } + } + + @Nested + @DisplayName("getPlacesRestantes") + class GetPlacesRestantes { + + @Test + @DisplayName("retourne 0 quand nombreMaxBeneficiaires null") + void testMaxNull() { + PropositionAideResponse r = PropositionAideResponse.builder() + .nombreMaxBeneficiaires(null) + .build(); + assertThat(r.getPlacesRestantes()).isEqualTo(0); + } + + @Test + @DisplayName("retourne max quand nombreBeneficiairesAides null") + void testAidesNull() { + PropositionAideResponse r = PropositionAideResponse.builder() + .nombreMaxBeneficiaires(10) + .nombreBeneficiairesAides(null) + .build(); + assertThat(r.getPlacesRestantes()).isEqualTo(10); + } + + @Test + @DisplayName("retourne différence positive") + void testDifference() { + PropositionAideResponse r = PropositionAideResponse.builder() + .nombreMaxBeneficiaires(10) + .nombreBeneficiairesAides(4) + .build(); + assertThat(r.getPlacesRestantes()).isEqualTo(6); + } + + @Test + @DisplayName("retourne 0 quand plus de bénéficiaires que max (cap)") + void testCap() { + PropositionAideResponse r = PropositionAideResponse.builder() + .nombreMaxBeneficiaires(10) + .nombreBeneficiairesAides(15) + .build(); + assertThat(r.getPlacesRestantes()).isEqualTo(0); + } + } + + @Nested + @DisplayName("Builder et getters") + class BuilderEtGetters { + + @Test + @DisplayName("builder remplit les champs") + void testBuilder() { + PropositionAideResponse r = PropositionAideResponse.builder() + .numeroReference("PROP-001") + .titre("Titre") + .statut(StatutProposition.ACTIVE) + .estDisponible(true) + .build(); + assertThat(r.getNumeroReference()).isEqualTo("PROP-001"); + assertThat(r.getTitre()).isEqualTo("Titre"); + assertThat(r.getStatut()).isEqualTo(StatutProposition.ACTIVE); + assertThat(r.getEstDisponible()).isTrue(); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/suggestion/request/CreateSuggestionRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/suggestion/request/CreateSuggestionRequestTest.java index d05df69..92212aa 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/suggestion/request/CreateSuggestionRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/suggestion/request/CreateSuggestionRequestTest.java @@ -1,121 +1,121 @@ -package dev.lions.unionflow.server.api.dto.suggestion.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.List; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateSuggestionRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID utilisateurId = UUID.randomUUID(); - List piecesJointes = List.of("document1.pdf", "document2.pdf"); - - CreateSuggestionRequest request = CreateSuggestionRequest.builder() - .utilisateurId(utilisateurId) - .utilisateurNom("Jean Dupont") - .titre("Amélioration du dashboard") - .description("Ajouter des graphiques interactifs") - .justification("Meilleure visualisation des données") - .categorie("UI/UX") - .prioriteEstimee("HAUTE") - .piecesJointes(piecesJointes) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.utilisateurId()).isEqualTo(utilisateurId); - assertThat(request.utilisateurNom()).isEqualTo("Jean Dupont"); - assertThat(request.titre()).isEqualTo("Amélioration du dashboard"); - assertThat(request.description()).isEqualTo("Ajouter des graphiques interactifs"); - assertThat(request.justification()).isEqualTo("Meilleure visualisation des données"); - assertThat(request.categorie()).isEqualTo("UI/UX"); - assertThat(request.prioriteEstimee()).isEqualTo("HAUTE"); - assertThat(request.piecesJointes()).isEqualTo(piecesJointes); - } - - @Test - void testBuilder_MinimalFields() { - UUID utilisateurId = UUID.randomUUID(); - - CreateSuggestionRequest request = CreateSuggestionRequest.builder() - .utilisateurId(utilisateurId) - .titre("Suggestion simple") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.utilisateurId()).isEqualTo(utilisateurId); - assertThat(request.titre()).isEqualTo("Suggestion simple"); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateSuggestionRequest request = CreateSuggestionRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("utilisateurId")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("titre")); - } - - @Test - void testValidation_ValidFields() { - CreateSuggestionRequest request = CreateSuggestionRequest.builder() - .utilisateurId(UUID.randomUUID()) - .titre("Nouvelle fonctionnalité") - .description("Description détaillée") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID utilisateurId = UUID.randomUUID(); - - CreateSuggestionRequest request1 = CreateSuggestionRequest.builder() - .utilisateurId(utilisateurId) - .titre("Titre") - .build(); - - CreateSuggestionRequest request2 = CreateSuggestionRequest.builder() - .utilisateurId(utilisateurId) - .titre("Titre") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateSuggestionRequest request = CreateSuggestionRequest.builder() - .utilisateurId(UUID.randomUUID()) - .titre("Test Suggestion") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateSuggestionRequest"); - assertThat(toString).contains("Test Suggestion"); - } -} +package dev.lions.unionflow.server.api.dto.suggestion.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.List; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateSuggestionRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID utilisateurId = UUID.randomUUID(); + List piecesJointes = List.of("document1.pdf", "document2.pdf"); + + CreateSuggestionRequest request = CreateSuggestionRequest.builder() + .utilisateurId(utilisateurId) + .utilisateurNom("Jean Dupont") + .titre("Amélioration du dashboard") + .description("Ajouter des graphiques interactifs") + .justification("Meilleure visualisation des données") + .categorie("UI/UX") + .prioriteEstimee("HAUTE") + .piecesJointes(piecesJointes) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.utilisateurId()).isEqualTo(utilisateurId); + assertThat(request.utilisateurNom()).isEqualTo("Jean Dupont"); + assertThat(request.titre()).isEqualTo("Amélioration du dashboard"); + assertThat(request.description()).isEqualTo("Ajouter des graphiques interactifs"); + assertThat(request.justification()).isEqualTo("Meilleure visualisation des données"); + assertThat(request.categorie()).isEqualTo("UI/UX"); + assertThat(request.prioriteEstimee()).isEqualTo("HAUTE"); + assertThat(request.piecesJointes()).isEqualTo(piecesJointes); + } + + @Test + void testBuilder_MinimalFields() { + UUID utilisateurId = UUID.randomUUID(); + + CreateSuggestionRequest request = CreateSuggestionRequest.builder() + .utilisateurId(utilisateurId) + .titre("Suggestion simple") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.utilisateurId()).isEqualTo(utilisateurId); + assertThat(request.titre()).isEqualTo("Suggestion simple"); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateSuggestionRequest request = CreateSuggestionRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("utilisateurId")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("titre")); + } + + @Test + void testValidation_ValidFields() { + CreateSuggestionRequest request = CreateSuggestionRequest.builder() + .utilisateurId(UUID.randomUUID()) + .titre("Nouvelle fonctionnalité") + .description("Description détaillée") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID utilisateurId = UUID.randomUUID(); + + CreateSuggestionRequest request1 = CreateSuggestionRequest.builder() + .utilisateurId(utilisateurId) + .titre("Titre") + .build(); + + CreateSuggestionRequest request2 = CreateSuggestionRequest.builder() + .utilisateurId(utilisateurId) + .titre("Titre") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateSuggestionRequest request = CreateSuggestionRequest.builder() + .utilisateurId(UUID.randomUUID()) + .titre("Test Suggestion") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateSuggestionRequest"); + assertThat(toString).contains("Test Suggestion"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/suggestion/request/UpdateSuggestionRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/suggestion/request/UpdateSuggestionRequestTest.java index 861a5fa..284b523 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/suggestion/request/UpdateSuggestionRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/suggestion/request/UpdateSuggestionRequestTest.java @@ -1,104 +1,104 @@ -package dev.lions.unionflow.server.api.dto.suggestion.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.List; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateSuggestionRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - List piecesJointes = List.of("new_doc1.pdf", "new_doc2.pdf"); - - UpdateSuggestionRequest request = UpdateSuggestionRequest.builder() - .titre("Titre mis à jour") - .description("Description mise à jour") - .justification("Justification mise à jour") - .categorie("Performance") - .prioriteEstimee("MOYENNE") - .statut("EN_COURS") - .versionCiblee("v2.0") - .piecesJointes(piecesJointes) - .miseAJour("Ajout de nouveaux détails") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.titre()).isEqualTo("Titre mis à jour"); - assertThat(request.description()).isEqualTo("Description mise à jour"); - assertThat(request.justification()).isEqualTo("Justification mise à jour"); - assertThat(request.categorie()).isEqualTo("Performance"); - assertThat(request.prioriteEstimee()).isEqualTo("MOYENNE"); - assertThat(request.statut()).isEqualTo("EN_COURS"); - assertThat(request.versionCiblee()).isEqualTo("v2.0"); - assertThat(request.piecesJointes()).isEqualTo(piecesJointes); - assertThat(request.miseAJour()).isEqualTo("Ajout de nouveaux détails"); - } - - @Test - void testBuilder_MinimalFields() { - UpdateSuggestionRequest request = UpdateSuggestionRequest.builder() - .statut("REJETEE") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.statut()).isEqualTo("REJETEE"); - } - - @Test - void testValidation_ValidFields() { - UpdateSuggestionRequest request = UpdateSuggestionRequest.builder() - .titre("Nouveau titre") - .description("Nouvelle description") - .statut("ACCEPTEE") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UpdateSuggestionRequest request1 = UpdateSuggestionRequest.builder() - .titre("Titre") - .statut("EN_COURS") - .build(); - - UpdateSuggestionRequest request2 = UpdateSuggestionRequest.builder() - .titre("Titre") - .statut("EN_COURS") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateSuggestionRequest request = UpdateSuggestionRequest.builder() - .titre("Titre Updated") - .statut("ACCEPTEE") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateSuggestionRequest"); - assertThat(toString).contains("ACCEPTEE"); - } -} +package dev.lions.unionflow.server.api.dto.suggestion.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.List; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateSuggestionRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + List piecesJointes = List.of("new_doc1.pdf", "new_doc2.pdf"); + + UpdateSuggestionRequest request = UpdateSuggestionRequest.builder() + .titre("Titre mis à jour") + .description("Description mise à jour") + .justification("Justification mise à jour") + .categorie("Performance") + .prioriteEstimee("MOYENNE") + .statut("EN_COURS") + .versionCiblee("v2.0") + .piecesJointes(piecesJointes) + .miseAJour("Ajout de nouveaux détails") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.titre()).isEqualTo("Titre mis à jour"); + assertThat(request.description()).isEqualTo("Description mise à jour"); + assertThat(request.justification()).isEqualTo("Justification mise à jour"); + assertThat(request.categorie()).isEqualTo("Performance"); + assertThat(request.prioriteEstimee()).isEqualTo("MOYENNE"); + assertThat(request.statut()).isEqualTo("EN_COURS"); + assertThat(request.versionCiblee()).isEqualTo("v2.0"); + assertThat(request.piecesJointes()).isEqualTo(piecesJointes); + assertThat(request.miseAJour()).isEqualTo("Ajout de nouveaux détails"); + } + + @Test + void testBuilder_MinimalFields() { + UpdateSuggestionRequest request = UpdateSuggestionRequest.builder() + .statut("REJETEE") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.statut()).isEqualTo("REJETEE"); + } + + @Test + void testValidation_ValidFields() { + UpdateSuggestionRequest request = UpdateSuggestionRequest.builder() + .titre("Nouveau titre") + .description("Nouvelle description") + .statut("ACCEPTEE") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UpdateSuggestionRequest request1 = UpdateSuggestionRequest.builder() + .titre("Titre") + .statut("EN_COURS") + .build(); + + UpdateSuggestionRequest request2 = UpdateSuggestionRequest.builder() + .titre("Titre") + .statut("EN_COURS") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateSuggestionRequest request = UpdateSuggestionRequest.builder() + .titre("Titre Updated") + .statut("ACCEPTEE") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateSuggestionRequest"); + assertThat(toString).contains("ACCEPTEE"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/ticket/request/CreateTicketRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/ticket/request/CreateTicketRequestTest.java index 1b53504..a1d1ef2 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/ticket/request/CreateTicketRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/ticket/request/CreateTicketRequestTest.java @@ -1,169 +1,169 @@ -package dev.lions.unionflow.server.api.dto.ticket.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.List; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateTicketRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID utilisateurId = UUID.randomUUID(); - List piecesJointes = List.of("screenshot.png", "logs.txt"); - - CreateTicketRequest request = CreateTicketRequest.builder() - .utilisateurId(utilisateurId) - .sujet("Problème de connexion") - .description("Impossible de se connecter au système depuis ce matin") - .categorie("TECHNIQUE") - .priorite("HAUTE") - .piecesJointes(piecesJointes) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.utilisateurId()).isEqualTo(utilisateurId); - assertThat(request.sujet()).isEqualTo("Problème de connexion"); - assertThat(request.description()).isEqualTo("Impossible de se connecter au système depuis ce matin"); - assertThat(request.categorie()).isEqualTo("TECHNIQUE"); - assertThat(request.priorite()).isEqualTo("HAUTE"); - assertThat(request.piecesJointes()).isEqualTo(piecesJointes); - } - - @Test - void testBuilder_MinimalFields() { - UUID utilisateurId = UUID.randomUUID(); - - CreateTicketRequest request = CreateTicketRequest.builder() - .utilisateurId(utilisateurId) - .sujet("Question simple") - .description("Comment faire ceci?") - .categorie("QUESTION") - .priorite("BASSE") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.utilisateurId()).isEqualTo(utilisateurId); - assertThat(request.sujet()).isEqualTo("Question simple"); - assertThat(request.description()).isEqualTo("Comment faire ceci?"); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateTicketRequest request = CreateTicketRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("utilisateurId")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("sujet")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("categorie")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("priorite")); - } - - @Test - void testValidation_SujetTooLong() { - String longSujet = "A".repeat(201); - CreateTicketRequest request = CreateTicketRequest.builder() - .utilisateurId(UUID.randomUUID()) - .sujet(longSujet) - .description("Description") - .categorie("TECHNIQUE") - .priorite("BASSE") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("sujet")); - } - - @Test - void testValidation_DescriptionTooLong() { - String longDescription = "A".repeat(2001); - CreateTicketRequest request = CreateTicketRequest.builder() - .utilisateurId(UUID.randomUUID()) - .sujet("Sujet") - .description(longDescription) - .categorie("TECHNIQUE") - .priorite("BASSE") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); - } - - @Test - void testValidation_ValidFields() { - CreateTicketRequest request = CreateTicketRequest.builder() - .utilisateurId(UUID.randomUUID()) - .sujet("Ticket valide") - .description("Description valide du problème") - .categorie("SUPPORT") - .priorite("MOYENNE") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID utilisateurId = UUID.randomUUID(); - - CreateTicketRequest request1 = CreateTicketRequest.builder() - .utilisateurId(utilisateurId) - .sujet("Sujet") - .description("Description") - .categorie("TECHNIQUE") - .priorite("HAUTE") - .build(); - - CreateTicketRequest request2 = CreateTicketRequest.builder() - .utilisateurId(utilisateurId) - .sujet("Sujet") - .description("Description") - .categorie("TECHNIQUE") - .priorite("HAUTE") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateTicketRequest request = CreateTicketRequest.builder() - .utilisateurId(UUID.randomUUID()) - .sujet("Test Ticket") - .description("Test Description") - .categorie("TEST") - .priorite("BASSE") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateTicketRequest"); - assertThat(toString).contains("Test Ticket"); - } -} +package dev.lions.unionflow.server.api.dto.ticket.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.List; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateTicketRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID utilisateurId = UUID.randomUUID(); + List piecesJointes = List.of("screenshot.png", "logs.txt"); + + CreateTicketRequest request = CreateTicketRequest.builder() + .utilisateurId(utilisateurId) + .sujet("Problème de connexion") + .description("Impossible de se connecter au système depuis ce matin") + .categorie("TECHNIQUE") + .priorite("HAUTE") + .piecesJointes(piecesJointes) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.utilisateurId()).isEqualTo(utilisateurId); + assertThat(request.sujet()).isEqualTo("Problème de connexion"); + assertThat(request.description()).isEqualTo("Impossible de se connecter au système depuis ce matin"); + assertThat(request.categorie()).isEqualTo("TECHNIQUE"); + assertThat(request.priorite()).isEqualTo("HAUTE"); + assertThat(request.piecesJointes()).isEqualTo(piecesJointes); + } + + @Test + void testBuilder_MinimalFields() { + UUID utilisateurId = UUID.randomUUID(); + + CreateTicketRequest request = CreateTicketRequest.builder() + .utilisateurId(utilisateurId) + .sujet("Question simple") + .description("Comment faire ceci?") + .categorie("QUESTION") + .priorite("BASSE") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.utilisateurId()).isEqualTo(utilisateurId); + assertThat(request.sujet()).isEqualTo("Question simple"); + assertThat(request.description()).isEqualTo("Comment faire ceci?"); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateTicketRequest request = CreateTicketRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("utilisateurId")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("sujet")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("categorie")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("priorite")); + } + + @Test + void testValidation_SujetTooLong() { + String longSujet = "A".repeat(201); + CreateTicketRequest request = CreateTicketRequest.builder() + .utilisateurId(UUID.randomUUID()) + .sujet(longSujet) + .description("Description") + .categorie("TECHNIQUE") + .priorite("BASSE") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("sujet")); + } + + @Test + void testValidation_DescriptionTooLong() { + String longDescription = "A".repeat(2001); + CreateTicketRequest request = CreateTicketRequest.builder() + .utilisateurId(UUID.randomUUID()) + .sujet("Sujet") + .description(longDescription) + .categorie("TECHNIQUE") + .priorite("BASSE") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); + } + + @Test + void testValidation_ValidFields() { + CreateTicketRequest request = CreateTicketRequest.builder() + .utilisateurId(UUID.randomUUID()) + .sujet("Ticket valide") + .description("Description valide du problème") + .categorie("SUPPORT") + .priorite("MOYENNE") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID utilisateurId = UUID.randomUUID(); + + CreateTicketRequest request1 = CreateTicketRequest.builder() + .utilisateurId(utilisateurId) + .sujet("Sujet") + .description("Description") + .categorie("TECHNIQUE") + .priorite("HAUTE") + .build(); + + CreateTicketRequest request2 = CreateTicketRequest.builder() + .utilisateurId(utilisateurId) + .sujet("Sujet") + .description("Description") + .categorie("TECHNIQUE") + .priorite("HAUTE") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateTicketRequest request = CreateTicketRequest.builder() + .utilisateurId(UUID.randomUUID()) + .sujet("Test Ticket") + .description("Test Description") + .categorie("TEST") + .priorite("BASSE") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateTicketRequest"); + assertThat(toString).contains("Test Ticket"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/ticket/request/UpdateTicketRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/ticket/request/UpdateTicketRequestTest.java index 658df74..fbc0525 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/ticket/request/UpdateTicketRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/ticket/request/UpdateTicketRequestTest.java @@ -1,133 +1,133 @@ -package dev.lions.unionflow.server.api.dto.ticket.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.List; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateTicketRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - UUID agentId = UUID.randomUUID(); - List piecesJointes = List.of("solution.pdf", "update.txt"); - - UpdateTicketRequest request = UpdateTicketRequest.builder() - .sujet("Sujet mis à jour") - .description("Description mise à jour") - .categorie("SUPPORT") - .priorite("MOYENNE") - .statut("EN_COURS") - .agentId(agentId) - .resolution("Problème résolu par redémarrage") - .piecesJointes(piecesJointes) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.sujet()).isEqualTo("Sujet mis à jour"); - assertThat(request.description()).isEqualTo("Description mise à jour"); - assertThat(request.categorie()).isEqualTo("SUPPORT"); - assertThat(request.priorite()).isEqualTo("MOYENNE"); - assertThat(request.statut()).isEqualTo("EN_COURS"); - assertThat(request.agentId()).isEqualTo(agentId); - assertThat(request.resolution()).isEqualTo("Problème résolu par redémarrage"); - assertThat(request.piecesJointes()).isEqualTo(piecesJointes); - } - - @Test - void testBuilder_MinimalFields() { - UpdateTicketRequest request = UpdateTicketRequest.builder() - .statut("RESOLU") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.statut()).isEqualTo("RESOLU"); - } - - @Test - void testValidation_SujetTooLong() { - String longSujet = "A".repeat(201); - UpdateTicketRequest request = UpdateTicketRequest.builder() - .sujet(longSujet) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("sujet")); - } - - @Test - void testValidation_DescriptionTooLong() { - String longDescription = "A".repeat(2001); - UpdateTicketRequest request = UpdateTicketRequest.builder() - .description(longDescription) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); - } - - @Test - void testValidation_ValidFields() { - UpdateTicketRequest request = UpdateTicketRequest.builder() - .sujet("Updated Subject") - .description("Updated Description") - .statut("RESOLU") - .resolution("Fixed successfully") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UUID agentId = UUID.randomUUID(); - - UpdateTicketRequest request1 = UpdateTicketRequest.builder() - .statut("EN_COURS") - .agentId(agentId) - .build(); - - UpdateTicketRequest request2 = UpdateTicketRequest.builder() - .statut("EN_COURS") - .agentId(agentId) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateTicketRequest request = UpdateTicketRequest.builder() - .statut("RESOLU") - .resolution("Problem fixed") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateTicketRequest"); - assertThat(toString).contains("RESOLU"); - } -} +package dev.lions.unionflow.server.api.dto.ticket.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.List; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateTicketRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + UUID agentId = UUID.randomUUID(); + List piecesJointes = List.of("solution.pdf", "update.txt"); + + UpdateTicketRequest request = UpdateTicketRequest.builder() + .sujet("Sujet mis à jour") + .description("Description mise à jour") + .categorie("SUPPORT") + .priorite("MOYENNE") + .statut("EN_COURS") + .agentId(agentId) + .resolution("Problème résolu par redémarrage") + .piecesJointes(piecesJointes) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.sujet()).isEqualTo("Sujet mis à jour"); + assertThat(request.description()).isEqualTo("Description mise à jour"); + assertThat(request.categorie()).isEqualTo("SUPPORT"); + assertThat(request.priorite()).isEqualTo("MOYENNE"); + assertThat(request.statut()).isEqualTo("EN_COURS"); + assertThat(request.agentId()).isEqualTo(agentId); + assertThat(request.resolution()).isEqualTo("Problème résolu par redémarrage"); + assertThat(request.piecesJointes()).isEqualTo(piecesJointes); + } + + @Test + void testBuilder_MinimalFields() { + UpdateTicketRequest request = UpdateTicketRequest.builder() + .statut("RESOLU") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.statut()).isEqualTo("RESOLU"); + } + + @Test + void testValidation_SujetTooLong() { + String longSujet = "A".repeat(201); + UpdateTicketRequest request = UpdateTicketRequest.builder() + .sujet(longSujet) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("sujet")); + } + + @Test + void testValidation_DescriptionTooLong() { + String longDescription = "A".repeat(2001); + UpdateTicketRequest request = UpdateTicketRequest.builder() + .description(longDescription) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("description")); + } + + @Test + void testValidation_ValidFields() { + UpdateTicketRequest request = UpdateTicketRequest.builder() + .sujet("Updated Subject") + .description("Updated Description") + .statut("RESOLU") + .resolution("Fixed successfully") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UUID agentId = UUID.randomUUID(); + + UpdateTicketRequest request1 = UpdateTicketRequest.builder() + .statut("EN_COURS") + .agentId(agentId) + .build(); + + UpdateTicketRequest request2 = UpdateTicketRequest.builder() + .statut("EN_COURS") + .agentId(agentId) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateTicketRequest request = UpdateTicketRequest.builder() + .statut("RESOLU") + .resolution("Problem fixed") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateTicketRequest"); + assertThat(toString).contains("RESOLU"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/user/request/CreateUserRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/user/request/CreateUserRequestTest.java index fb1c123..dc53d4e 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/user/request/CreateUserRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/user/request/CreateUserRequestTest.java @@ -1,188 +1,188 @@ -package dev.lions.unionflow.server.api.dto.user.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.List; -import java.util.Map; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CreateUserRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - List roles = List.of("ROLE_USER", "ROLE_ADMIN"); - Map> attributes = Map.of("department", List.of("IT")); - - CreateUserRequest request = CreateUserRequest.builder() - .username("johndoe123") - .prenom("John") - .nom("Doe") - .email("john.doe@example.com") - .password("SecurePassword123!") - .enabled(true) - .emailVerified(true) - .realmRoles(roles) - .attributes(attributes) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.username()).isEqualTo("johndoe123"); - assertThat(request.prenom()).isEqualTo("John"); - assertThat(request.nom()).isEqualTo("Doe"); - assertThat(request.email()).isEqualTo("john.doe@example.com"); - assertThat(request.password()).isEqualTo("SecurePassword123!"); - assertThat(request.enabled()).isTrue(); - assertThat(request.emailVerified()).isTrue(); - assertThat(request.realmRoles()).isEqualTo(roles); - assertThat(request.attributes()).isEqualTo(attributes); - } - - @Test - void testBuilder_MinimalFields() { - CreateUserRequest request = CreateUserRequest.builder() - .username("testuser") - .prenom("Test") - .nom("User") - .email("test@example.com") - .password("password123") - .build(); - - assertThat(request).isNotNull(); - assertThat(request.username()).isEqualTo("testuser"); - assertThat(request.prenom()).isEqualTo("Test"); - assertThat(request.nom()).isEqualTo("User"); - assertThat(request.email()).isEqualTo("test@example.com"); - assertThat(request.password()).isEqualTo("password123"); - } - - @Test - void testValidation_MissingRequiredFields() { - CreateUserRequest request = CreateUserRequest.builder().build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("username")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prenom")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("password")); - } - - @Test - void testValidation_InvalidEmail() { - CreateUserRequest request = CreateUserRequest.builder() - .username("testuser") - .prenom("Test") - .nom("User") - .email("invalid-email") - .password("password123") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); - } - - @Test - void testValidation_UsernameTooShort() { - CreateUserRequest request = CreateUserRequest.builder() - .username("ab") - .prenom("Test") - .nom("User") - .email("test@example.com") - .password("password123") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("username")); - } - - @Test - void testValidation_PasswordTooShort() { - CreateUserRequest request = CreateUserRequest.builder() - .username("testuser") - .prenom("Test") - .nom("User") - .email("test@example.com") - .password("short") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("password")); - } - - @Test - void testValidation_ValidFields() { - CreateUserRequest request = CreateUserRequest.builder() - .username("validuser") - .prenom("Valid") - .nom("User") - .email("valid@example.com") - .password("ValidPassword123!") - .enabled(true) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - CreateUserRequest request1 = CreateUserRequest.builder() - .username("user1") - .prenom("First") - .nom("Last") - .email("user1@example.com") - .password("password123") - .build(); - - CreateUserRequest request2 = CreateUserRequest.builder() - .username("user1") - .prenom("First") - .nom("Last") - .email("user1@example.com") - .password("password123") - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - CreateUserRequest request = CreateUserRequest.builder() - .username("testuser") - .prenom("Test") - .nom("User") - .email("test@example.com") - .password("password123") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("CreateUserRequest"); - assertThat(toString).contains("testuser"); - } -} +package dev.lions.unionflow.server.api.dto.user.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.List; +import java.util.Map; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CreateUserRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + List roles = List.of("ROLE_USER", "ROLE_ADMIN"); + Map> attributes = Map.of("department", List.of("IT")); + + CreateUserRequest request = CreateUserRequest.builder() + .username("johndoe123") + .prenom("John") + .nom("Doe") + .email("john.doe@example.com") + .password("SecurePassword123!") + .enabled(true) + .emailVerified(true) + .realmRoles(roles) + .attributes(attributes) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.username()).isEqualTo("johndoe123"); + assertThat(request.prenom()).isEqualTo("John"); + assertThat(request.nom()).isEqualTo("Doe"); + assertThat(request.email()).isEqualTo("john.doe@example.com"); + assertThat(request.password()).isEqualTo("SecurePassword123!"); + assertThat(request.enabled()).isTrue(); + assertThat(request.emailVerified()).isTrue(); + assertThat(request.realmRoles()).isEqualTo(roles); + assertThat(request.attributes()).isEqualTo(attributes); + } + + @Test + void testBuilder_MinimalFields() { + CreateUserRequest request = CreateUserRequest.builder() + .username("testuser") + .prenom("Test") + .nom("User") + .email("test@example.com") + .password("password123") + .build(); + + assertThat(request).isNotNull(); + assertThat(request.username()).isEqualTo("testuser"); + assertThat(request.prenom()).isEqualTo("Test"); + assertThat(request.nom()).isEqualTo("User"); + assertThat(request.email()).isEqualTo("test@example.com"); + assertThat(request.password()).isEqualTo("password123"); + } + + @Test + void testValidation_MissingRequiredFields() { + CreateUserRequest request = CreateUserRequest.builder().build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("username")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("prenom")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("nom")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("password")); + } + + @Test + void testValidation_InvalidEmail() { + CreateUserRequest request = CreateUserRequest.builder() + .username("testuser") + .prenom("Test") + .nom("User") + .email("invalid-email") + .password("password123") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); + } + + @Test + void testValidation_UsernameTooShort() { + CreateUserRequest request = CreateUserRequest.builder() + .username("ab") + .prenom("Test") + .nom("User") + .email("test@example.com") + .password("password123") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("username")); + } + + @Test + void testValidation_PasswordTooShort() { + CreateUserRequest request = CreateUserRequest.builder() + .username("testuser") + .prenom("Test") + .nom("User") + .email("test@example.com") + .password("short") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("password")); + } + + @Test + void testValidation_ValidFields() { + CreateUserRequest request = CreateUserRequest.builder() + .username("validuser") + .prenom("Valid") + .nom("User") + .email("valid@example.com") + .password("ValidPassword123!") + .enabled(true) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + CreateUserRequest request1 = CreateUserRequest.builder() + .username("user1") + .prenom("First") + .nom("Last") + .email("user1@example.com") + .password("password123") + .build(); + + CreateUserRequest request2 = CreateUserRequest.builder() + .username("user1") + .prenom("First") + .nom("Last") + .email("user1@example.com") + .password("password123") + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + CreateUserRequest request = CreateUserRequest.builder() + .username("testuser") + .prenom("Test") + .nom("User") + .email("test@example.com") + .password("password123") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("CreateUserRequest"); + assertThat(toString).contains("testuser"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/user/request/UpdateUserRequestTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/user/request/UpdateUserRequestTest.java index 58683b6..55e88a9 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/user/request/UpdateUserRequestTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/user/request/UpdateUserRequestTest.java @@ -1,119 +1,119 @@ -package dev.lions.unionflow.server.api.dto.user.request; - -import static org.assertj.core.api.Assertions.assertThat; - -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.util.List; -import java.util.Map; -import java.util.Set; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class UpdateUserRequestTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testBuilder_AllFields() { - List roles = List.of("ROLE_USER", "ROLE_MODERATOR"); - Map> attributes = Map.of("department", List.of("Sales")); - - UpdateUserRequest request = UpdateUserRequest.builder() - .prenom("Jane") - .nom("Smith") - .email("jane.smith@example.com") - .enabled(true) - .emailVerified(true) - .realmRoles(roles) - .attributes(attributes) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.prenom()).isEqualTo("Jane"); - assertThat(request.nom()).isEqualTo("Smith"); - assertThat(request.email()).isEqualTo("jane.smith@example.com"); - assertThat(request.enabled()).isTrue(); - assertThat(request.emailVerified()).isTrue(); - assertThat(request.realmRoles()).isEqualTo(roles); - assertThat(request.attributes()).isEqualTo(attributes); - } - - @Test - void testBuilder_MinimalFields() { - UpdateUserRequest request = UpdateUserRequest.builder() - .enabled(false) - .build(); - - assertThat(request).isNotNull(); - assertThat(request.enabled()).isFalse(); - } - - @Test - void testValidation_InvalidEmail() { - UpdateUserRequest request = UpdateUserRequest.builder() - .email("invalid-email-format") - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); - } - - @Test - void testValidation_ValidFields() { - UpdateUserRequest request = UpdateUserRequest.builder() - .prenom("Updated") - .nom("Name") - .email("updated@example.com") - .enabled(true) - .emailVerified(true) - .build(); - - Set> violations = validator.validate(request); - - assertThat(violations).isEmpty(); - } - - @Test - void testEquals() { - UpdateUserRequest request1 = UpdateUserRequest.builder() - .prenom("Test") - .nom("User") - .enabled(true) - .build(); - - UpdateUserRequest request2 = UpdateUserRequest.builder() - .prenom("Test") - .nom("User") - .enabled(true) - .build(); - - assertThat(request1).isEqualTo(request2); - assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); - } - - @Test - void testToString() { - UpdateUserRequest request = UpdateUserRequest.builder() - .prenom("Test") - .nom("User") - .email("test@example.com") - .build(); - - String toString = request.toString(); - - assertThat(toString).isNotNull(); - assertThat(toString).contains("UpdateUserRequest"); - assertThat(toString).contains("test@example.com"); - } -} +package dev.lions.unionflow.server.api.dto.user.request; + +import static org.assertj.core.api.Assertions.assertThat; + +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.util.List; +import java.util.Map; +import java.util.Set; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class UpdateUserRequestTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testBuilder_AllFields() { + List roles = List.of("ROLE_USER", "ROLE_MODERATOR"); + Map> attributes = Map.of("department", List.of("Sales")); + + UpdateUserRequest request = UpdateUserRequest.builder() + .prenom("Jane") + .nom("Smith") + .email("jane.smith@example.com") + .enabled(true) + .emailVerified(true) + .realmRoles(roles) + .attributes(attributes) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.prenom()).isEqualTo("Jane"); + assertThat(request.nom()).isEqualTo("Smith"); + assertThat(request.email()).isEqualTo("jane.smith@example.com"); + assertThat(request.enabled()).isTrue(); + assertThat(request.emailVerified()).isTrue(); + assertThat(request.realmRoles()).isEqualTo(roles); + assertThat(request.attributes()).isEqualTo(attributes); + } + + @Test + void testBuilder_MinimalFields() { + UpdateUserRequest request = UpdateUserRequest.builder() + .enabled(false) + .build(); + + assertThat(request).isNotNull(); + assertThat(request.enabled()).isFalse(); + } + + @Test + void testValidation_InvalidEmail() { + UpdateUserRequest request = UpdateUserRequest.builder() + .email("invalid-email-format") + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("email")); + } + + @Test + void testValidation_ValidFields() { + UpdateUserRequest request = UpdateUserRequest.builder() + .prenom("Updated") + .nom("Name") + .email("updated@example.com") + .enabled(true) + .emailVerified(true) + .build(); + + Set> violations = validator.validate(request); + + assertThat(violations).isEmpty(); + } + + @Test + void testEquals() { + UpdateUserRequest request1 = UpdateUserRequest.builder() + .prenom("Test") + .nom("User") + .enabled(true) + .build(); + + UpdateUserRequest request2 = UpdateUserRequest.builder() + .prenom("Test") + .nom("User") + .enabled(true) + .build(); + + assertThat(request1).isEqualTo(request2); + assertThat(request1.hashCode()).isEqualTo(request2.hashCode()); + } + + @Test + void testToString() { + UpdateUserRequest request = UpdateUserRequest.builder() + .prenom("Test") + .nom("User") + .email("test@example.com") + .build(); + + String toString = request.toString(); + + assertThat(toString).isNotNull(); + assertThat(toString).contains("UpdateUserRequest"); + assertThat(toString).contains("test@example.com"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/wave/CompteWaveDTOTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/wave/CompteWaveDTOTest.java index 46841b2..5d1c7d1 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/wave/CompteWaveDTOTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/wave/CompteWaveDTOTest.java @@ -1,94 +1,94 @@ -package dev.lions.unionflow.server.api.dto.wave; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.wave.StatutCompteWave; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.time.LocalDateTime; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class CompteWaveDTOTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testGettersSetters_AllFields() { - LocalDateTime now = LocalDateTime.now(); - UUID orgId = UUID.randomUUID(); - UUID membreId = UUID.randomUUID(); - - CompteWaveDTO dto = new CompteWaveDTO(); - dto.setNumeroTelephone("+22501234567"); - dto.setStatutCompte(StatutCompteWave.VERIFIE); - dto.setWaveAccountId("wave-acc-123"); - dto.setEnvironnement("PRODUCTION"); - dto.setDateDerniereVerification(now); - dto.setCommentaire("Test comment"); - dto.setOrganisationId(orgId); - dto.setMembreId(membreId); - - assertThat(dto.getNumeroTelephone()).isEqualTo("+22501234567"); - assertThat(dto.getStatutCompte()).isEqualTo(StatutCompteWave.VERIFIE); - assertThat(dto.getWaveAccountId()).isEqualTo("wave-acc-123"); - assertThat(dto.getEnvironnement()).isEqualTo("PRODUCTION"); - assertThat(dto.getDateDerniereVerification()).isEqualTo(now); - assertThat(dto.getCommentaire()).isEqualTo("Test comment"); - assertThat(dto.getOrganisationId()).isEqualTo(orgId); - assertThat(dto.getMembreId()).isEqualTo(membreId); - } - - @Test - void testValidation_NumeroTelephoneBlank() { - CompteWaveDTO dto = new CompteWaveDTO(); - dto.setNumeroTelephone(""); - - Set> violations = validator.validate(dto); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroTelephone")); - } - - @Test - void testValidation_NumeroTelephoneInvalidFormat() { - CompteWaveDTO dto = new CompteWaveDTO(); - dto.setNumeroTelephone("+221123456789"); - - Set> violations = validator.validate(dto); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroTelephone")); - } - - @Test - void testValidation_NumeroTelephoneTooShort() { - CompteWaveDTO dto = new CompteWaveDTO(); - dto.setNumeroTelephone("+2251234567"); - - Set> violations = validator.validate(dto); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroTelephone")); - } - - @Test - void testValidation_ValidNumeroTelephone() { - CompteWaveDTO dto = new CompteWaveDTO(); - dto.setNumeroTelephone("+22512345678"); - - Set> violations = validator.validate(dto); - - assertThat(violations).isEmpty(); - } -} +package dev.lions.unionflow.server.api.dto.wave; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.wave.StatutCompteWave; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.time.LocalDateTime; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class CompteWaveDTOTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testGettersSetters_AllFields() { + LocalDateTime now = LocalDateTime.now(); + UUID orgId = UUID.randomUUID(); + UUID membreId = UUID.randomUUID(); + + CompteWaveDTO dto = new CompteWaveDTO(); + dto.setNumeroTelephone("+22501234567"); + dto.setStatutCompte(StatutCompteWave.VERIFIE); + dto.setWaveAccountId("wave-acc-123"); + dto.setEnvironnement("PRODUCTION"); + dto.setDateDerniereVerification(now); + dto.setCommentaire("Test comment"); + dto.setOrganisationId(orgId); + dto.setMembreId(membreId); + + assertThat(dto.getNumeroTelephone()).isEqualTo("+22501234567"); + assertThat(dto.getStatutCompte()).isEqualTo(StatutCompteWave.VERIFIE); + assertThat(dto.getWaveAccountId()).isEqualTo("wave-acc-123"); + assertThat(dto.getEnvironnement()).isEqualTo("PRODUCTION"); + assertThat(dto.getDateDerniereVerification()).isEqualTo(now); + assertThat(dto.getCommentaire()).isEqualTo("Test comment"); + assertThat(dto.getOrganisationId()).isEqualTo(orgId); + assertThat(dto.getMembreId()).isEqualTo(membreId); + } + + @Test + void testValidation_NumeroTelephoneBlank() { + CompteWaveDTO dto = new CompteWaveDTO(); + dto.setNumeroTelephone(""); + + Set> violations = validator.validate(dto); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroTelephone")); + } + + @Test + void testValidation_NumeroTelephoneInvalidFormat() { + CompteWaveDTO dto = new CompteWaveDTO(); + dto.setNumeroTelephone("+221123456789"); + + Set> violations = validator.validate(dto); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroTelephone")); + } + + @Test + void testValidation_NumeroTelephoneTooShort() { + CompteWaveDTO dto = new CompteWaveDTO(); + dto.setNumeroTelephone("+2251234567"); + + Set> violations = validator.validate(dto); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("numeroTelephone")); + } + + @Test + void testValidation_ValidNumeroTelephone() { + CompteWaveDTO dto = new CompteWaveDTO(); + dto.setNumeroTelephone("+22512345678"); + + Set> violations = validator.validate(dto); + + assertThat(violations).isEmpty(); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/dto/wave/TransactionWaveDTOTest.java b/src/test/java/dev/lions/unionflow/server/api/dto/wave/TransactionWaveDTOTest.java index 3fadc9d..d245944 100644 --- a/src/test/java/dev/lions/unionflow/server/api/dto/wave/TransactionWaveDTOTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/dto/wave/TransactionWaveDTOTest.java @@ -1,132 +1,132 @@ -package dev.lions.unionflow.server.api.dto.wave; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.wave.StatutTransactionWave; -import dev.lions.unionflow.server.api.enums.wave.TypeTransactionWave; -import jakarta.validation.ConstraintViolation; -import jakarta.validation.Validation; -import jakarta.validation.Validator; -import jakarta.validation.ValidatorFactory; -import java.math.BigDecimal; -import java.time.LocalDateTime; -import java.util.Set; -import java.util.UUID; -import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; - -class TransactionWaveDTOTest { - - private Validator validator; - - @BeforeEach - void setUp() { - ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); - validator = factory.getValidator(); - } - - @Test - void testGettersSetters_AllFields() { - LocalDateTime now = LocalDateTime.now(); - UUID compteId = UUID.randomUUID(); - - TransactionWaveDTO dto = new TransactionWaveDTO(); - dto.setWaveTransactionId("wave-txn-123"); - dto.setWaveRequestId("wave-req-456"); - dto.setWaveReference("wave-ref-789"); - dto.setTypeTransaction(TypeTransactionWave.PAIEMENT); - dto.setStatutTransaction(StatutTransactionWave.REUSSIE); - dto.setMontant(new BigDecimal("1000.00")); - dto.setFrais(new BigDecimal("10.00")); - dto.setMontantNet(new BigDecimal("990.00")); - dto.setCodeDevise("XOF"); - dto.setTelephonePayeur("+22512345678"); - dto.setTelephoneBeneficiaire("+22587654321"); - dto.setMetadonnees("{\"key\":\"value\"}"); - dto.setNombreTentatives(1); - dto.setDateDerniereTentative(now); - dto.setMessageErreur(null); - dto.setCompteWaveId(compteId); - - assertThat(dto.getWaveTransactionId()).isEqualTo("wave-txn-123"); - assertThat(dto.getWaveRequestId()).isEqualTo("wave-req-456"); - assertThat(dto.getWaveReference()).isEqualTo("wave-ref-789"); - assertThat(dto.getTypeTransaction()).isEqualTo(TypeTransactionWave.PAIEMENT); - assertThat(dto.getStatutTransaction()).isEqualTo(StatutTransactionWave.REUSSIE); - assertThat(dto.getMontant()).isEqualByComparingTo(new BigDecimal("1000.00")); - assertThat(dto.getFrais()).isEqualByComparingTo(new BigDecimal("10.00")); - assertThat(dto.getMontantNet()).isEqualByComparingTo(new BigDecimal("990.00")); - assertThat(dto.getCodeDevise()).isEqualTo("XOF"); - assertThat(dto.getTelephonePayeur()).isEqualTo("+22512345678"); - assertThat(dto.getTelephoneBeneficiaire()).isEqualTo("+22587654321"); - assertThat(dto.getMetadonnees()).isEqualTo("{\"key\":\"value\"}"); - assertThat(dto.getNombreTentatives()).isEqualTo(1); - assertThat(dto.getDateDerniereTentative()).isEqualTo(now); - assertThat(dto.getMessageErreur()).isNull(); - assertThat(dto.getCompteWaveId()).isEqualTo(compteId); - } - - @Test - void testValidation_MissingRequiredFields() { - TransactionWaveDTO dto = new TransactionWaveDTO(); - - Set> violations = validator.validate(dto); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("waveTransactionId")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeTransaction")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("statutTransaction")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montant")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codeDevise")); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("compteWaveId")); - } - - @Test - void testValidation_MontantNegatif() { - TransactionWaveDTO dto = new TransactionWaveDTO(); - dto.setWaveTransactionId("wave-txn-123"); - dto.setTypeTransaction(TypeTransactionWave.PAIEMENT); - dto.setStatutTransaction(StatutTransactionWave.EN_ATTENTE); - dto.setMontant(new BigDecimal("-100.00")); - dto.setCodeDevise("XOF"); - dto.setCompteWaveId(UUID.randomUUID()); - - Set> violations = validator.validate(dto); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montant")); - } - - @Test - void testValidation_CodeDeviseInvalide() { - TransactionWaveDTO dto = new TransactionWaveDTO(); - dto.setWaveTransactionId("wave-txn-123"); - dto.setTypeTransaction(TypeTransactionWave.PAIEMENT); - dto.setStatutTransaction(StatutTransactionWave.EN_ATTENTE); - dto.setMontant(new BigDecimal("100.00")); - dto.setCodeDevise("INVALID"); - dto.setCompteWaveId(UUID.randomUUID()); - - Set> violations = validator.validate(dto); - - assertThat(violations).isNotEmpty(); - assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codeDevise")); - } - - @Test - void testValidation_ValidFields() { - TransactionWaveDTO dto = new TransactionWaveDTO(); - dto.setWaveTransactionId("wave-txn-123"); - dto.setTypeTransaction(TypeTransactionWave.PAIEMENT); - dto.setStatutTransaction(StatutTransactionWave.REUSSIE); - dto.setMontant(new BigDecimal("1000.00")); - dto.setFrais(new BigDecimal("10.00")); - dto.setMontantNet(new BigDecimal("990.00")); - dto.setCodeDevise("XOF"); - dto.setCompteWaveId(UUID.randomUUID()); - - Set> violations = validator.validate(dto); - - assertThat(violations).isEmpty(); - } -} +package dev.lions.unionflow.server.api.dto.wave; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.wave.StatutTransactionWave; +import dev.lions.unionflow.server.api.enums.wave.TypeTransactionWave; +import jakarta.validation.ConstraintViolation; +import jakarta.validation.Validation; +import jakarta.validation.Validator; +import jakarta.validation.ValidatorFactory; +import java.math.BigDecimal; +import java.time.LocalDateTime; +import java.util.Set; +import java.util.UUID; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +class TransactionWaveDTOTest { + + private Validator validator; + + @BeforeEach + void setUp() { + ValidatorFactory factory = Validation.buildDefaultValidatorFactory(); + validator = factory.getValidator(); + } + + @Test + void testGettersSetters_AllFields() { + LocalDateTime now = LocalDateTime.now(); + UUID compteId = UUID.randomUUID(); + + TransactionWaveDTO dto = new TransactionWaveDTO(); + dto.setWaveTransactionId("wave-txn-123"); + dto.setWaveRequestId("wave-req-456"); + dto.setWaveReference("wave-ref-789"); + dto.setTypeTransaction(TypeTransactionWave.PAIEMENT); + dto.setStatutTransaction(StatutTransactionWave.REUSSIE); + dto.setMontant(new BigDecimal("1000.00")); + dto.setFrais(new BigDecimal("10.00")); + dto.setMontantNet(new BigDecimal("990.00")); + dto.setCodeDevise("XOF"); + dto.setTelephonePayeur("+22512345678"); + dto.setTelephoneBeneficiaire("+22587654321"); + dto.setMetadonnees("{\"key\":\"value\"}"); + dto.setNombreTentatives(1); + dto.setDateDerniereTentative(now); + dto.setMessageErreur(null); + dto.setCompteWaveId(compteId); + + assertThat(dto.getWaveTransactionId()).isEqualTo("wave-txn-123"); + assertThat(dto.getWaveRequestId()).isEqualTo("wave-req-456"); + assertThat(dto.getWaveReference()).isEqualTo("wave-ref-789"); + assertThat(dto.getTypeTransaction()).isEqualTo(TypeTransactionWave.PAIEMENT); + assertThat(dto.getStatutTransaction()).isEqualTo(StatutTransactionWave.REUSSIE); + assertThat(dto.getMontant()).isEqualByComparingTo(new BigDecimal("1000.00")); + assertThat(dto.getFrais()).isEqualByComparingTo(new BigDecimal("10.00")); + assertThat(dto.getMontantNet()).isEqualByComparingTo(new BigDecimal("990.00")); + assertThat(dto.getCodeDevise()).isEqualTo("XOF"); + assertThat(dto.getTelephonePayeur()).isEqualTo("+22512345678"); + assertThat(dto.getTelephoneBeneficiaire()).isEqualTo("+22587654321"); + assertThat(dto.getMetadonnees()).isEqualTo("{\"key\":\"value\"}"); + assertThat(dto.getNombreTentatives()).isEqualTo(1); + assertThat(dto.getDateDerniereTentative()).isEqualTo(now); + assertThat(dto.getMessageErreur()).isNull(); + assertThat(dto.getCompteWaveId()).isEqualTo(compteId); + } + + @Test + void testValidation_MissingRequiredFields() { + TransactionWaveDTO dto = new TransactionWaveDTO(); + + Set> violations = validator.validate(dto); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("waveTransactionId")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("typeTransaction")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("statutTransaction")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montant")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codeDevise")); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("compteWaveId")); + } + + @Test + void testValidation_MontantNegatif() { + TransactionWaveDTO dto = new TransactionWaveDTO(); + dto.setWaveTransactionId("wave-txn-123"); + dto.setTypeTransaction(TypeTransactionWave.PAIEMENT); + dto.setStatutTransaction(StatutTransactionWave.EN_ATTENTE); + dto.setMontant(new BigDecimal("-100.00")); + dto.setCodeDevise("XOF"); + dto.setCompteWaveId(UUID.randomUUID()); + + Set> violations = validator.validate(dto); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("montant")); + } + + @Test + void testValidation_CodeDeviseInvalide() { + TransactionWaveDTO dto = new TransactionWaveDTO(); + dto.setWaveTransactionId("wave-txn-123"); + dto.setTypeTransaction(TypeTransactionWave.PAIEMENT); + dto.setStatutTransaction(StatutTransactionWave.EN_ATTENTE); + dto.setMontant(new BigDecimal("100.00")); + dto.setCodeDevise("INVALID"); + dto.setCompteWaveId(UUID.randomUUID()); + + Set> violations = validator.validate(dto); + + assertThat(violations).isNotEmpty(); + assertThat(violations).anyMatch(v -> v.getPropertyPath().toString().equals("codeDevise")); + } + + @Test + void testValidation_ValidFields() { + TransactionWaveDTO dto = new TransactionWaveDTO(); + dto.setWaveTransactionId("wave-txn-123"); + dto.setTypeTransaction(TypeTransactionWave.PAIEMENT); + dto.setStatutTransaction(StatutTransactionWave.REUSSIE); + dto.setMontant(new BigDecimal("1000.00")); + dto.setFrais(new BigDecimal("10.00")); + dto.setMontantNet(new BigDecimal("990.00")); + dto.setCodeDevise("XOF"); + dto.setCompteWaveId(UUID.randomUUID()); + + Set> violations = validator.validate(dto); + + assertThat(violations).isEmpty(); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/EnumsRefactoringTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/EnumsRefactoringTest.java index 4b9241d..465cbf6 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/EnumsRefactoringTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/EnumsRefactoringTest.java @@ -1,340 +1,340 @@ -package dev.lions.unionflow.server.api.enums; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; -import dev.lions.unionflow.server.api.enums.abonnement.StatutFormule; -import dev.lions.unionflow.server.api.enums.abonnement.TypeFormule; -import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; -import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; -import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; -import dev.lions.unionflow.server.api.enums.finance.StatutCotisation; -import dev.lions.unionflow.server.api.enums.membre.StatutMembre; -import dev.lions.unionflow.server.api.enums.organisation.StatutOrganisation; -import dev.lions.unionflow.server.api.enums.organisation.TypeOrganisation; -import dev.lions.unionflow.server.api.enums.paiement.StatutSession; -import dev.lions.unionflow.server.api.enums.paiement.StatutTraitement; -import dev.lions.unionflow.server.api.enums.paiement.TypeEvenement; -import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; -import dev.lions.unionflow.server.api.enums.solidarite.StatutAide; -import dev.lions.unionflow.server.api.enums.solidarite.StatutEvaluation; -import dev.lions.unionflow.server.api.enums.solidarite.StatutProposition; -import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; -import dev.lions.unionflow.server.api.enums.solidarite.TypeEvaluation; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests de validation de la refactorisation des énumérations UnionFlow Vérifie - * que toutes les enums - * sont correctement séparées et fonctionnelles - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-01-10 - */ -@DisplayName("Tests de Refactorisation des Énumérations") -class EnumsRefactoringTest { - - @Test - @DisplayName("Test de base - toutes les enums sont accessibles") - void testEnumsAccessibles() { - assertThat(StatutMembre.ACTIF).isNotNull(); - assertThat(TypeOrganisation.LIONS_CLUB).isNotNull(); - } - - @Nested - @DisplayName("Énumérations Organisation") - class OrganisationEnumsTest { - - @Test - @DisplayName("TypeOrganisation - Tous les types disponibles") - void testTypeOrganisationTousLesTypes() { - // Given & When & Then - assertThat(TypeOrganisation.LIONS_CLUB.getLibelle()).isEqualTo("Lions Club"); - assertThat(TypeOrganisation.ASSOCIATION.getLibelle()).isEqualTo("Association"); - assertThat(TypeOrganisation.FEDERATION.getLibelle()).isEqualTo("Fédération / Union d'associations"); - assertThat(TypeOrganisation.ONG.getLibelle()).isEqualTo("ONG / Association humanitaire"); - assertThat(TypeOrganisation.SYNDICAT.getLibelle()).isEqualTo("Syndicat non partisan"); - assertThat(TypeOrganisation.MUTUELLE_SANTE.getLibelle()).isEqualTo("Mutuelle de santé"); - assertThat(TypeOrganisation.MUTUELLE_EPARGNE_CREDIT.getLibelle()).isEqualTo("Mutuelle d'épargne et de crédit"); - assertThat(TypeOrganisation.TONTINE.getLibelle()).isEqualTo("Tontine / épargne rotative"); - } - - @Test - @DisplayName("StatutOrganisation - Tous les statuts disponibles") - void testStatutOrganisationTousLesStatuts() { - // Given & When & Then - assertThat(StatutOrganisation.ACTIVE.getLibelle()).isEqualTo("Active"); - assertThat(StatutOrganisation.INACTIVE.getLibelle()).isEqualTo("Inactive"); - assertThat(StatutOrganisation.SUSPENDUE.getLibelle()).isEqualTo("Suspendue"); - assertThat(StatutOrganisation.EN_CREATION.getLibelle()).isEqualTo("En Création"); - assertThat(StatutOrganisation.DISSOUTE.getLibelle()).isEqualTo("Dissoute"); - } - } - - @Nested - @DisplayName("Énumérations Membre") - class MembreEnumsTest { - - @Test - @DisplayName("StatutMembre - Tous les statuts disponibles") - void testStatutMembreTousLesStatuts() { - // Given & When & Then - assertThat(StatutMembre.ACTIF.getLibelle()).isEqualTo("Actif"); - assertThat(StatutMembre.INACTIF.getLibelle()).contains("Inactif"); - assertThat(StatutMembre.SUSPENDU.getLibelle()).contains("Suspendu"); - assertThat(StatutMembre.RADIE.getLibelle()).contains("Radié"); - assertThat(StatutMembre.DEMISSIONNAIRE.getLibelle()).isNotNull(); - assertThat(StatutMembre.HONORAIRE.getLibelle()).isNotNull(); - assertThat(StatutMembre.DECEDE.getLibelle()).isNotNull(); - } - } - - @Nested - @DisplayName("Énumérations Paiement") - class PaiementEnumsTest { - - @Test - @DisplayName("StatutSession - Tous les statuts disponibles") - void testStatutSessionTousLesStatuts() { - // Given & When & Then - assertThat(StatutSession.PENDING.getLibelle()).isEqualTo("En attente"); - assertThat(StatutSession.COMPLETED.getLibelle()).isEqualTo("Complétée"); - assertThat(StatutSession.CANCELLED.getLibelle()).isEqualTo("Annulée"); - assertThat(StatutSession.EXPIRED.getLibelle()).isEqualTo("Expirée"); - assertThat(StatutSession.FAILED.getLibelle()).isEqualTo("Échouée"); - } - - @Test - @DisplayName("TypeEvenement - Méthode fromCode") - void testTypeEvenementFromCode() { - // Given & When & Then - assertThat(TypeEvenement.fromCode("checkout.complete")) - .isEqualTo(TypeEvenement.CHECKOUT_COMPLETE); - assertThat(TypeEvenement.fromCode("payout.failed")).isEqualTo(TypeEvenement.PAYOUT_FAILED); - assertThat(TypeEvenement.fromCode("balance.updated")) - .isEqualTo(TypeEvenement.BALANCE_UPDATED); - assertThat(TypeEvenement.fromCode("code_inexistant")).isNull(); - } - - @Test - @DisplayName("StatutTraitement - Tous les statuts disponibles") - void testStatutTraitementTousLesStatuts() { - // Given & When & Then - assertThat(StatutTraitement.RECU.getLibelle()).isEqualTo("Reçu"); - assertThat(StatutTraitement.EN_COURS.getLibelle()).isEqualTo("En cours de traitement"); - assertThat(StatutTraitement.TRAITE.getLibelle()).isEqualTo("Traité avec succès"); - assertThat(StatutTraitement.ECHEC.getLibelle()).isEqualTo("Échec de traitement"); - assertThat(StatutTraitement.IGNORE.getLibelle()).isEqualTo("Ignoré"); - } - } - - @Nested - @DisplayName("Énumérations Abonnement") - class AbonnementEnumsTest { - - @Test - @DisplayName("TypeFormule - Tous les types disponibles") - void testTypeFormuleTousLesTypes() { - // Given & When & Then - assertThat(TypeFormule.BASIC.getLibelle()).contains("Basic"); - assertThat(TypeFormule.STANDARD.getLibelle()).contains("Standard"); - assertThat(TypeFormule.PREMIUM.getLibelle()).contains("Premium"); - } - - @Test - @DisplayName("StatutFormule - Tous les statuts disponibles") - void testStatutFormuleTousLesStatuts() { - // Given & When & Then - assertThat(StatutFormule.ACTIVE.getLibelle()).isEqualTo("Active"); - assertThat(StatutFormule.INACTIVE.getLibelle()).isEqualTo("Inactive"); - assertThat(StatutFormule.ARCHIVEE.getLibelle()).isEqualTo("Archivée"); - assertThat(StatutFormule.BIENTOT_DISPONIBLE.getLibelle()).isEqualTo("Bientôt Disponible"); - } - - @Test - @DisplayName("StatutAbonnement - Tous les statuts disponibles") - void testStatutAbonnementTousLesStatuts() { - // Given & When & Then - assertThat(StatutAbonnement.ACTIF.getLibelle()).isEqualTo("Actif"); - assertThat(StatutAbonnement.SUSPENDU.getLibelle()).isEqualTo("Suspendu"); - assertThat(StatutAbonnement.EXPIRE.getLibelle()).isEqualTo("Expiré"); - assertThat(StatutAbonnement.ANNULE.getLibelle()).isEqualTo("Annulé"); - assertThat(StatutAbonnement.EN_ATTENTE_PAIEMENT.getLibelle()) - .isEqualTo("En attente de paiement"); - } - } - - @Nested - @DisplayName("Énumérations Événement") - class EvenementEnumsTest { - - @Test - @DisplayName("TypeEvenementMetier - Tous les types disponibles") - void testTypeEvenementMetierTousLesTypes() { - // Given & When & Then - assertThat(TypeEvenementMetier.ASSEMBLEE_GENERALE.getLibelle()) - .isEqualTo("Assemblée Générale"); - assertThat(TypeEvenementMetier.FORMATION.getLibelle()).isEqualTo("Formation"); - assertThat(TypeEvenementMetier.ACTIVITE_SOCIALE.getLibelle()).isEqualTo("Activité Sociale"); - assertThat(TypeEvenementMetier.ACTION_CARITATIVE.getLibelle()).isEqualTo("Action Caritative"); - assertThat(TypeEvenementMetier.REUNION_BUREAU.getLibelle()).isEqualTo("Réunion de Bureau"); - assertThat(TypeEvenementMetier.CONFERENCE.getLibelle()).isEqualTo("Conférence"); - assertThat(TypeEvenementMetier.ATELIER.getLibelle()).isEqualTo("Atelier"); - assertThat(TypeEvenementMetier.CEREMONIE.getLibelle()).isEqualTo("Cérémonie"); - assertThat(TypeEvenementMetier.AUTRE.getLibelle()).isEqualTo("Autre"); - } - - @Test - @DisplayName("StatutEvenement - Tous les statuts disponibles") - void testStatutEvenementTousLesStatuts() { - // Given & When & Then - assertThat(StatutEvenement.PLANIFIE.getLibelle()).isEqualTo("Planifié"); - assertThat(StatutEvenement.CONFIRME.getLibelle()).isEqualTo("Confirmé"); - assertThat(StatutEvenement.EN_COURS.getLibelle()).isEqualTo("En cours"); - assertThat(StatutEvenement.TERMINE.getLibelle()).isEqualTo("Terminé"); - assertThat(StatutEvenement.ANNULE.getLibelle()).isEqualTo("Annulé"); - assertThat(StatutEvenement.REPORTE.getLibelle()).isEqualTo("Reporté"); - } - - @Test - @DisplayName("PrioriteEvenement - Toutes les priorités disponibles") - void testPrioriteEvenementToutesLesPriorites() { - // Given & When & Then - assertThat(PrioriteEvenement.CRITIQUE.getLibelle()).isEqualTo("Critique"); - assertThat(PrioriteEvenement.HAUTE.getLibelle()).isEqualTo("Haute"); - assertThat(PrioriteEvenement.NORMALE.getLibelle()).isEqualTo("Normale"); - assertThat(PrioriteEvenement.BASSE.getLibelle()).isEqualTo("Basse"); - } - } - - @Nested - @DisplayName("Énumérations Finance") - class FinanceEnumsTest { - - @Test - @DisplayName("StatutCotisation - Tous les statuts disponibles") - void testStatutCotisationTousLesStatuts() { - // Given & When & Then - assertThat(StatutCotisation.EN_ATTENTE.getLibelle()).isEqualTo("En attente"); - assertThat(StatutCotisation.PAYEE.getLibelle()).isEqualTo("Payée"); - assertThat(StatutCotisation.PARTIELLEMENT_PAYEE.getLibelle()) - .isEqualTo("Partiellement payée"); - assertThat(StatutCotisation.EN_RETARD.getLibelle()).isEqualTo("En retard"); - assertThat(StatutCotisation.ANNULEE.getLibelle()).isEqualTo("Annulée"); - assertThat(StatutCotisation.REMBOURSEE.getLibelle()).isEqualTo("Remboursée"); - } - } - - @Nested - @DisplayName("Énumérations Solidarité") - class SolidariteEnumsTest { - - @Test - @DisplayName("TypeAide - Tous les types disponibles") - void testTypeAideTousLesTypes() { - // Given & When & Then - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getLibelle()) - .isEqualTo("Aide financière urgente"); - assertThat(TypeAide.AIDE_FRAIS_MEDICAUX.getLibelle()).isEqualTo("Aide frais médicaux"); - assertThat(TypeAide.AIDE_FRAIS_SCOLARITE.getLibelle()).isEqualTo("Aide frais de scolarité"); - assertThat(TypeAide.HEBERGEMENT_URGENCE.getLibelle()).isEqualTo("Hébergement d'urgence"); - assertThat(TypeAide.AIDE_ALIMENTAIRE.getLibelle()).isEqualTo("Aide alimentaire"); - assertThat(TypeAide.CONSEIL_JURIDIQUE.getLibelle()).isEqualTo("Conseil juridique"); - assertThat(TypeAide.AIDE_RECHERCHE_EMPLOI.getLibelle()).isEqualTo("Aide recherche d'emploi"); - assertThat(TypeAide.SOUTIEN_PSYCHOLOGIQUE.getLibelle()).isEqualTo("Soutien psychologique"); - assertThat(TypeAide.AUTRE.getLibelle()).isEqualTo("Autre"); - } - - @Test - @DisplayName("StatutAide - Tous les statuts disponibles") - void testStatutAideTousLesStatuts() { - // Given & When & Then - assertThat(StatutAide.EN_ATTENTE.getLibelle()).isEqualTo("En attente"); - assertThat(StatutAide.EN_COURS_EVALUATION.getLibelle()).isEqualTo("En cours d'évaluation"); - assertThat(StatutAide.APPROUVEE.getLibelle()).isEqualTo("Approuvée"); - assertThat(StatutAide.REJETEE.getLibelle()).isEqualTo("Rejetée"); - assertThat(StatutAide.EN_COURS_VERSEMENT.getLibelle()).isEqualTo("En cours de versement"); - assertThat(StatutAide.VERSEE.getLibelle()).isEqualTo("Versée"); - assertThat(StatutAide.ANNULEE.getLibelle()).isEqualTo("Annulée"); - assertThat(StatutAide.SUSPENDUE.getLibelle()).isEqualTo("Suspendue"); - } - - @Test - @DisplayName("PrioriteAide - Toutes les priorités disponibles") - void testPrioriteAideToutesLesPriorites() { - // Given & When & Then - assertThat(PrioriteAide.CRITIQUE.getLibelle()).isEqualTo("Critique"); - assertThat(PrioriteAide.URGENTE.getLibelle()).isEqualTo("Urgente"); - assertThat(PrioriteAide.ELEVEE.getLibelle()).isEqualTo("Élevée"); - assertThat(PrioriteAide.NORMALE.getLibelle()).isEqualTo("Normale"); - assertThat(PrioriteAide.FAIBLE.getLibelle()).isEqualTo("Faible"); - } - - @Test - @DisplayName("StatutProposition - Tous les statuts disponibles") - void testStatutPropositionTousLesStatuts() { - assertThat(StatutProposition.BROUILLON.getLibelle()).isEqualTo("Brouillon"); - assertThat(StatutProposition.ACTIVE.getLibelle()).isEqualTo("Active"); - assertThat(StatutProposition.SUSPENDUE.getLibelle()).isEqualTo("Suspendue"); - assertThat(StatutProposition.TERMINEE.getLibelle()).isEqualTo("Terminée"); - assertThat(StatutProposition.ANNULEE.getLibelle()).isEqualTo("Annulée"); - } - - @Test - @DisplayName("StatutEvaluation - Tous les statuts disponibles") - void testStatutEvaluationTousLesStatuts() { - assertThat(StatutEvaluation.BROUILLON.getLibelle()).isEqualTo("Brouillon"); - assertThat(StatutEvaluation.ACTIVE.getLibelle()).isEqualTo("Active"); - assertThat(StatutEvaluation.MASQUEE.getLibelle()).isEqualTo("Masquée"); - } - - @Test - @DisplayName("TypeEvaluation - Tous les types disponibles") - void testTypeEvaluationTousLesTypes() { - assertThat(TypeEvaluation.SATISFACTION_BENEFICIAIRE.getLibelle()).isEqualTo("Satisfaction du bénéficiaire"); - assertThat(TypeEvaluation.EVALUATION_IMPACT.getLibelle()).isEqualTo("Évaluation d'impact"); - } - } - - @Nested - @DisplayName("Tests de Couverture Complète") - class CouvertureCompleteTest { - - @Test - @DisplayName("Vérification que toutes les enums ont des valeurs") - void testToutesLesEnumsOntDesValeurs() { - // Given & When & Then - Organisation - assertThat(TypeOrganisation.values()).isNotEmpty(); - assertThat(StatutOrganisation.values()).isNotEmpty(); - - // Given & When & Then - Membre - assertThat(StatutMembre.values()).isNotEmpty(); - - // Given & When & Then - Paiement - assertThat(StatutSession.values()).isNotEmpty(); - assertThat(TypeEvenement.values()).isNotEmpty(); - assertThat(StatutTraitement.values()).isNotEmpty(); - - // Given & When & Then - Abonnement - assertThat(TypeFormule.values()).isNotEmpty(); - assertThat(StatutFormule.values()).isNotEmpty(); - assertThat(StatutAbonnement.values()).isNotEmpty(); - - // Given & When & Then - Événement - assertThat(TypeEvenementMetier.values()).isNotEmpty(); - - // Given & When & Then - Finance - assertThat(StatutCotisation.values()).isNotEmpty(); - - // Given & When & Then - Solidarité - assertThat(TypeAide.values()).isNotEmpty(); - assertThat(StatutAide.values()).isNotEmpty(); - assertThat(StatutProposition.values()).isNotEmpty(); - assertThat(StatutEvaluation.values()).isNotEmpty(); - assertThat(TypeEvaluation.values()).isNotEmpty(); - } - } -} +package dev.lions.unionflow.server.api.enums; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.enums.abonnement.StatutAbonnement; +import dev.lions.unionflow.server.api.enums.abonnement.StatutFormule; +import dev.lions.unionflow.server.api.enums.abonnement.TypeFormule; +import dev.lions.unionflow.server.api.enums.evenement.PrioriteEvenement; +import dev.lions.unionflow.server.api.enums.evenement.StatutEvenement; +import dev.lions.unionflow.server.api.enums.evenement.TypeEvenementMetier; +import dev.lions.unionflow.server.api.enums.finance.StatutCotisation; +import dev.lions.unionflow.server.api.enums.membre.StatutMembre; +import dev.lions.unionflow.server.api.enums.organisation.StatutOrganisation; +import dev.lions.unionflow.server.api.enums.organisation.TypeOrganisation; +import dev.lions.unionflow.server.api.enums.paiement.StatutSession; +import dev.lions.unionflow.server.api.enums.paiement.StatutTraitement; +import dev.lions.unionflow.server.api.enums.paiement.TypeEvenement; +import dev.lions.unionflow.server.api.enums.solidarite.PrioriteAide; +import dev.lions.unionflow.server.api.enums.solidarite.StatutAide; +import dev.lions.unionflow.server.api.enums.solidarite.StatutEvaluation; +import dev.lions.unionflow.server.api.enums.solidarite.StatutProposition; +import dev.lions.unionflow.server.api.enums.solidarite.TypeAide; +import dev.lions.unionflow.server.api.enums.solidarite.TypeEvaluation; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests de validation de la refactorisation des énumérations UnionFlow Vérifie + * que toutes les enums + * sont correctement séparées et fonctionnelles + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-01-10 + */ +@DisplayName("Tests de Refactorisation des Énumérations") +class EnumsRefactoringTest { + + @Test + @DisplayName("Test de base - toutes les enums sont accessibles") + void testEnumsAccessibles() { + assertThat(StatutMembre.ACTIF).isNotNull(); + assertThat(TypeOrganisation.LIONS_CLUB).isNotNull(); + } + + @Nested + @DisplayName("Énumérations Organisation") + class OrganisationEnumsTest { + + @Test + @DisplayName("TypeOrganisation - Tous les types disponibles") + void testTypeOrganisationTousLesTypes() { + // Given & When & Then + assertThat(TypeOrganisation.LIONS_CLUB.getLibelle()).isEqualTo("Lions Club"); + assertThat(TypeOrganisation.ASSOCIATION.getLibelle()).isEqualTo("Association"); + assertThat(TypeOrganisation.FEDERATION.getLibelle()).isEqualTo("Fédération / Union d'associations"); + assertThat(TypeOrganisation.ONG.getLibelle()).isEqualTo("ONG / Association humanitaire"); + assertThat(TypeOrganisation.SYNDICAT.getLibelle()).isEqualTo("Syndicat non partisan"); + assertThat(TypeOrganisation.MUTUELLE_SANTE.getLibelle()).isEqualTo("Mutuelle de santé"); + assertThat(TypeOrganisation.MUTUELLE_EPARGNE_CREDIT.getLibelle()).isEqualTo("Mutuelle d'épargne et de crédit"); + assertThat(TypeOrganisation.TONTINE.getLibelle()).isEqualTo("Tontine / épargne rotative"); + } + + @Test + @DisplayName("StatutOrganisation - Tous les statuts disponibles") + void testStatutOrganisationTousLesStatuts() { + // Given & When & Then + assertThat(StatutOrganisation.ACTIVE.getLibelle()).isEqualTo("Active"); + assertThat(StatutOrganisation.INACTIVE.getLibelle()).isEqualTo("Inactive"); + assertThat(StatutOrganisation.SUSPENDUE.getLibelle()).isEqualTo("Suspendue"); + assertThat(StatutOrganisation.EN_CREATION.getLibelle()).isEqualTo("En Création"); + assertThat(StatutOrganisation.DISSOUTE.getLibelle()).isEqualTo("Dissoute"); + } + } + + @Nested + @DisplayName("Énumérations Membre") + class MembreEnumsTest { + + @Test + @DisplayName("StatutMembre - Tous les statuts disponibles") + void testStatutMembreTousLesStatuts() { + // Given & When & Then + assertThat(StatutMembre.ACTIF.getLibelle()).isEqualTo("Actif"); + assertThat(StatutMembre.INACTIF.getLibelle()).contains("Inactif"); + assertThat(StatutMembre.SUSPENDU.getLibelle()).contains("Suspendu"); + assertThat(StatutMembre.RADIE.getLibelle()).contains("Radié"); + assertThat(StatutMembre.DEMISSIONNAIRE.getLibelle()).isNotNull(); + assertThat(StatutMembre.HONORAIRE.getLibelle()).isNotNull(); + assertThat(StatutMembre.DECEDE.getLibelle()).isNotNull(); + } + } + + @Nested + @DisplayName("Énumérations Paiement") + class PaiementEnumsTest { + + @Test + @DisplayName("StatutSession - Tous les statuts disponibles") + void testStatutSessionTousLesStatuts() { + // Given & When & Then + assertThat(StatutSession.PENDING.getLibelle()).isEqualTo("En attente"); + assertThat(StatutSession.COMPLETED.getLibelle()).isEqualTo("Complétée"); + assertThat(StatutSession.CANCELLED.getLibelle()).isEqualTo("Annulée"); + assertThat(StatutSession.EXPIRED.getLibelle()).isEqualTo("Expirée"); + assertThat(StatutSession.FAILED.getLibelle()).isEqualTo("Échouée"); + } + + @Test + @DisplayName("TypeEvenement - Méthode fromCode") + void testTypeEvenementFromCode() { + // Given & When & Then + assertThat(TypeEvenement.fromCode("checkout.complete")) + .isEqualTo(TypeEvenement.CHECKOUT_COMPLETE); + assertThat(TypeEvenement.fromCode("payout.failed")).isEqualTo(TypeEvenement.PAYOUT_FAILED); + assertThat(TypeEvenement.fromCode("balance.updated")) + .isEqualTo(TypeEvenement.BALANCE_UPDATED); + assertThat(TypeEvenement.fromCode("code_inexistant")).isNull(); + } + + @Test + @DisplayName("StatutTraitement - Tous les statuts disponibles") + void testStatutTraitementTousLesStatuts() { + // Given & When & Then + assertThat(StatutTraitement.RECU.getLibelle()).isEqualTo("Reçu"); + assertThat(StatutTraitement.EN_COURS.getLibelle()).isEqualTo("En cours de traitement"); + assertThat(StatutTraitement.TRAITE.getLibelle()).isEqualTo("Traité avec succès"); + assertThat(StatutTraitement.ECHEC.getLibelle()).isEqualTo("Échec de traitement"); + assertThat(StatutTraitement.IGNORE.getLibelle()).isEqualTo("Ignoré"); + } + } + + @Nested + @DisplayName("Énumérations Abonnement") + class AbonnementEnumsTest { + + @Test + @DisplayName("TypeFormule - Tous les types disponibles") + void testTypeFormuleTousLesTypes() { + // Given & When & Then + assertThat(TypeFormule.BASIC.getLibelle()).contains("Basic"); + assertThat(TypeFormule.STANDARD.getLibelle()).contains("Standard"); + assertThat(TypeFormule.PREMIUM.getLibelle()).contains("Premium"); + } + + @Test + @DisplayName("StatutFormule - Tous les statuts disponibles") + void testStatutFormuleTousLesStatuts() { + // Given & When & Then + assertThat(StatutFormule.ACTIVE.getLibelle()).isEqualTo("Active"); + assertThat(StatutFormule.INACTIVE.getLibelle()).isEqualTo("Inactive"); + assertThat(StatutFormule.ARCHIVEE.getLibelle()).isEqualTo("Archivée"); + assertThat(StatutFormule.BIENTOT_DISPONIBLE.getLibelle()).isEqualTo("Bientôt Disponible"); + } + + @Test + @DisplayName("StatutAbonnement - Tous les statuts disponibles") + void testStatutAbonnementTousLesStatuts() { + // Given & When & Then + assertThat(StatutAbonnement.ACTIF.getLibelle()).isEqualTo("Actif"); + assertThat(StatutAbonnement.SUSPENDU.getLibelle()).isEqualTo("Suspendu"); + assertThat(StatutAbonnement.EXPIRE.getLibelle()).isEqualTo("Expiré"); + assertThat(StatutAbonnement.ANNULE.getLibelle()).isEqualTo("Annulé"); + assertThat(StatutAbonnement.EN_ATTENTE_PAIEMENT.getLibelle()) + .isEqualTo("En attente de paiement"); + } + } + + @Nested + @DisplayName("Énumérations Événement") + class EvenementEnumsTest { + + @Test + @DisplayName("TypeEvenementMetier - Tous les types disponibles") + void testTypeEvenementMetierTousLesTypes() { + // Given & When & Then + assertThat(TypeEvenementMetier.ASSEMBLEE_GENERALE.getLibelle()) + .isEqualTo("Assemblée Générale"); + assertThat(TypeEvenementMetier.FORMATION.getLibelle()).isEqualTo("Formation"); + assertThat(TypeEvenementMetier.ACTIVITE_SOCIALE.getLibelle()).isEqualTo("Activité Sociale"); + assertThat(TypeEvenementMetier.ACTION_CARITATIVE.getLibelle()).isEqualTo("Action Caritative"); + assertThat(TypeEvenementMetier.REUNION_BUREAU.getLibelle()).isEqualTo("Réunion de Bureau"); + assertThat(TypeEvenementMetier.CONFERENCE.getLibelle()).isEqualTo("Conférence"); + assertThat(TypeEvenementMetier.ATELIER.getLibelle()).isEqualTo("Atelier"); + assertThat(TypeEvenementMetier.CEREMONIE.getLibelle()).isEqualTo("Cérémonie"); + assertThat(TypeEvenementMetier.AUTRE.getLibelle()).isEqualTo("Autre"); + } + + @Test + @DisplayName("StatutEvenement - Tous les statuts disponibles") + void testStatutEvenementTousLesStatuts() { + // Given & When & Then + assertThat(StatutEvenement.PLANIFIE.getLibelle()).isEqualTo("Planifié"); + assertThat(StatutEvenement.CONFIRME.getLibelle()).isEqualTo("Confirmé"); + assertThat(StatutEvenement.EN_COURS.getLibelle()).isEqualTo("En cours"); + assertThat(StatutEvenement.TERMINE.getLibelle()).isEqualTo("Terminé"); + assertThat(StatutEvenement.ANNULE.getLibelle()).isEqualTo("Annulé"); + assertThat(StatutEvenement.REPORTE.getLibelle()).isEqualTo("Reporté"); + } + + @Test + @DisplayName("PrioriteEvenement - Toutes les priorités disponibles") + void testPrioriteEvenementToutesLesPriorites() { + // Given & When & Then + assertThat(PrioriteEvenement.CRITIQUE.getLibelle()).isEqualTo("Critique"); + assertThat(PrioriteEvenement.HAUTE.getLibelle()).isEqualTo("Haute"); + assertThat(PrioriteEvenement.NORMALE.getLibelle()).isEqualTo("Normale"); + assertThat(PrioriteEvenement.BASSE.getLibelle()).isEqualTo("Basse"); + } + } + + @Nested + @DisplayName("Énumérations Finance") + class FinanceEnumsTest { + + @Test + @DisplayName("StatutCotisation - Tous les statuts disponibles") + void testStatutCotisationTousLesStatuts() { + // Given & When & Then + assertThat(StatutCotisation.EN_ATTENTE.getLibelle()).isEqualTo("En attente"); + assertThat(StatutCotisation.PAYEE.getLibelle()).isEqualTo("Payée"); + assertThat(StatutCotisation.PARTIELLEMENT_PAYEE.getLibelle()) + .isEqualTo("Partiellement payée"); + assertThat(StatutCotisation.EN_RETARD.getLibelle()).isEqualTo("En retard"); + assertThat(StatutCotisation.ANNULEE.getLibelle()).isEqualTo("Annulée"); + assertThat(StatutCotisation.REMBOURSEE.getLibelle()).isEqualTo("Remboursée"); + } + } + + @Nested + @DisplayName("Énumérations Solidarité") + class SolidariteEnumsTest { + + @Test + @DisplayName("TypeAide - Tous les types disponibles") + void testTypeAideTousLesTypes() { + // Given & When & Then + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getLibelle()) + .isEqualTo("Aide financière urgente"); + assertThat(TypeAide.AIDE_FRAIS_MEDICAUX.getLibelle()).isEqualTo("Aide frais médicaux"); + assertThat(TypeAide.AIDE_FRAIS_SCOLARITE.getLibelle()).isEqualTo("Aide frais de scolarité"); + assertThat(TypeAide.HEBERGEMENT_URGENCE.getLibelle()).isEqualTo("Hébergement d'urgence"); + assertThat(TypeAide.AIDE_ALIMENTAIRE.getLibelle()).isEqualTo("Aide alimentaire"); + assertThat(TypeAide.CONSEIL_JURIDIQUE.getLibelle()).isEqualTo("Conseil juridique"); + assertThat(TypeAide.AIDE_RECHERCHE_EMPLOI.getLibelle()).isEqualTo("Aide recherche d'emploi"); + assertThat(TypeAide.SOUTIEN_PSYCHOLOGIQUE.getLibelle()).isEqualTo("Soutien psychologique"); + assertThat(TypeAide.AUTRE.getLibelle()).isEqualTo("Autre"); + } + + @Test + @DisplayName("StatutAide - Tous les statuts disponibles") + void testStatutAideTousLesStatuts() { + // Given & When & Then + assertThat(StatutAide.EN_ATTENTE.getLibelle()).isEqualTo("En attente"); + assertThat(StatutAide.EN_COURS_EVALUATION.getLibelle()).isEqualTo("En cours d'évaluation"); + assertThat(StatutAide.APPROUVEE.getLibelle()).isEqualTo("Approuvée"); + assertThat(StatutAide.REJETEE.getLibelle()).isEqualTo("Rejetée"); + assertThat(StatutAide.EN_COURS_VERSEMENT.getLibelle()).isEqualTo("En cours de versement"); + assertThat(StatutAide.VERSEE.getLibelle()).isEqualTo("Versée"); + assertThat(StatutAide.ANNULEE.getLibelle()).isEqualTo("Annulée"); + assertThat(StatutAide.SUSPENDUE.getLibelle()).isEqualTo("Suspendue"); + } + + @Test + @DisplayName("PrioriteAide - Toutes les priorités disponibles") + void testPrioriteAideToutesLesPriorites() { + // Given & When & Then + assertThat(PrioriteAide.CRITIQUE.getLibelle()).isEqualTo("Critique"); + assertThat(PrioriteAide.URGENTE.getLibelle()).isEqualTo("Urgente"); + assertThat(PrioriteAide.ELEVEE.getLibelle()).isEqualTo("Élevée"); + assertThat(PrioriteAide.NORMALE.getLibelle()).isEqualTo("Normale"); + assertThat(PrioriteAide.FAIBLE.getLibelle()).isEqualTo("Faible"); + } + + @Test + @DisplayName("StatutProposition - Tous les statuts disponibles") + void testStatutPropositionTousLesStatuts() { + assertThat(StatutProposition.BROUILLON.getLibelle()).isEqualTo("Brouillon"); + assertThat(StatutProposition.ACTIVE.getLibelle()).isEqualTo("Active"); + assertThat(StatutProposition.SUSPENDUE.getLibelle()).isEqualTo("Suspendue"); + assertThat(StatutProposition.TERMINEE.getLibelle()).isEqualTo("Terminée"); + assertThat(StatutProposition.ANNULEE.getLibelle()).isEqualTo("Annulée"); + } + + @Test + @DisplayName("StatutEvaluation - Tous les statuts disponibles") + void testStatutEvaluationTousLesStatuts() { + assertThat(StatutEvaluation.BROUILLON.getLibelle()).isEqualTo("Brouillon"); + assertThat(StatutEvaluation.ACTIVE.getLibelle()).isEqualTo("Active"); + assertThat(StatutEvaluation.MASQUEE.getLibelle()).isEqualTo("Masquée"); + } + + @Test + @DisplayName("TypeEvaluation - Tous les types disponibles") + void testTypeEvaluationTousLesTypes() { + assertThat(TypeEvaluation.SATISFACTION_BENEFICIAIRE.getLibelle()).isEqualTo("Satisfaction du bénéficiaire"); + assertThat(TypeEvaluation.EVALUATION_IMPACT.getLibelle()).isEqualTo("Évaluation d'impact"); + } + } + + @Nested + @DisplayName("Tests de Couverture Complète") + class CouvertureCompleteTest { + + @Test + @DisplayName("Vérification que toutes les enums ont des valeurs") + void testToutesLesEnumsOntDesValeurs() { + // Given & When & Then - Organisation + assertThat(TypeOrganisation.values()).isNotEmpty(); + assertThat(StatutOrganisation.values()).isNotEmpty(); + + // Given & When & Then - Membre + assertThat(StatutMembre.values()).isNotEmpty(); + + // Given & When & Then - Paiement + assertThat(StatutSession.values()).isNotEmpty(); + assertThat(TypeEvenement.values()).isNotEmpty(); + assertThat(StatutTraitement.values()).isNotEmpty(); + + // Given & When & Then - Abonnement + assertThat(TypeFormule.values()).isNotEmpty(); + assertThat(StatutFormule.values()).isNotEmpty(); + assertThat(StatutAbonnement.values()).isNotEmpty(); + + // Given & When & Then - Événement + assertThat(TypeEvenementMetier.values()).isNotEmpty(); + + // Given & When & Then - Finance + assertThat(StatutCotisation.values()).isNotEmpty(); + + // Given & When & Then - Solidarité + assertThat(TypeAide.values()).isNotEmpty(); + assertThat(StatutAide.values()).isNotEmpty(); + assertThat(StatutProposition.values()).isNotEmpty(); + assertThat(StatutEvaluation.values()).isNotEmpty(); + assertThat(TypeEvaluation.values()).isNotEmpty(); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/StatutAbonnementTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/StatutAbonnementTest.java index ea0f4ba..3038239 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/StatutAbonnementTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/StatutAbonnementTest.java @@ -1,73 +1,73 @@ -package dev.lions.unionflow.server.api.enums.abonnement; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutAbonnement") -class StatutAbonnementTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutAbonnement.ACTIF).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutAbonnement[] values = StatutAbonnement.values(); - assertThat(values).hasSize(5); - assertThat(values).containsExactly( - StatutAbonnement.ACTIF, - StatutAbonnement.SUSPENDU, - StatutAbonnement.EXPIRE, - StatutAbonnement.ANNULE, - StatutAbonnement.EN_ATTENTE_PAIEMENT); - } - - @Test - @DisplayName("Test valueOf") - void testValueOf() { - assertThat(StatutAbonnement.valueOf("ACTIF")).isEqualTo(StatutAbonnement.ACTIF); - assertThat(StatutAbonnement.valueOf("SUSPENDU")).isEqualTo(StatutAbonnement.SUSPENDU); - assertThat(StatutAbonnement.valueOf("EXPIRE")).isEqualTo(StatutAbonnement.EXPIRE); - assertThat(StatutAbonnement.valueOf("ANNULE")).isEqualTo(StatutAbonnement.ANNULE); - assertThat(StatutAbonnement.valueOf("EN_ATTENTE_PAIEMENT")).isEqualTo(StatutAbonnement.EN_ATTENTE_PAIEMENT); - - assertThatThrownBy(() -> StatutAbonnement.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutAbonnement.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutAbonnement statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @ParameterizedTest - @CsvSource({ - "ACTIF, Actif", - "SUSPENDU, Suspendu", - "EXPIRE, Expiré", - "ANNULE, Annulé", - "EN_ATTENTE_PAIEMENT, En attente de paiement" - }) - @DisplayName("Test getLibelle avec valeurs exactes") - void testGetLibelleValeursExactes(StatutAbonnement statut, String expectedLibelle) { - assertThat(statut.getLibelle()).isEqualTo(expectedLibelle); - } - } -} - +package dev.lions.unionflow.server.api.enums.abonnement; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutAbonnement") +class StatutAbonnementTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutAbonnement.ACTIF).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutAbonnement[] values = StatutAbonnement.values(); + assertThat(values).hasSize(5); + assertThat(values).containsExactly( + StatutAbonnement.ACTIF, + StatutAbonnement.SUSPENDU, + StatutAbonnement.EXPIRE, + StatutAbonnement.ANNULE, + StatutAbonnement.EN_ATTENTE_PAIEMENT); + } + + @Test + @DisplayName("Test valueOf") + void testValueOf() { + assertThat(StatutAbonnement.valueOf("ACTIF")).isEqualTo(StatutAbonnement.ACTIF); + assertThat(StatutAbonnement.valueOf("SUSPENDU")).isEqualTo(StatutAbonnement.SUSPENDU); + assertThat(StatutAbonnement.valueOf("EXPIRE")).isEqualTo(StatutAbonnement.EXPIRE); + assertThat(StatutAbonnement.valueOf("ANNULE")).isEqualTo(StatutAbonnement.ANNULE); + assertThat(StatutAbonnement.valueOf("EN_ATTENTE_PAIEMENT")).isEqualTo(StatutAbonnement.EN_ATTENTE_PAIEMENT); + + assertThatThrownBy(() -> StatutAbonnement.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutAbonnement.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutAbonnement statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @ParameterizedTest + @CsvSource({ + "ACTIF, Actif", + "SUSPENDU, Suspendu", + "EXPIRE, Expiré", + "ANNULE, Annulé", + "EN_ATTENTE_PAIEMENT, En attente de paiement" + }) + @DisplayName("Test getLibelle avec valeurs exactes") + void testGetLibelleValeursExactes(StatutAbonnement statut, String expectedLibelle) { + assertThat(statut.getLibelle()).isEqualTo(expectedLibelle); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/StatutFormuleTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/StatutFormuleTest.java index 6f77fdc..873299c 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/StatutFormuleTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/StatutFormuleTest.java @@ -1,70 +1,70 @@ -package dev.lions.unionflow.server.api.enums.abonnement; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutFormule") -class StatutFormuleTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutFormule.ACTIVE).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutFormule[] values = StatutFormule.values(); - assertThat(values).hasSize(4); - assertThat(values).containsExactly( - StatutFormule.ACTIVE, - StatutFormule.INACTIVE, - StatutFormule.ARCHIVEE, - StatutFormule.BIENTOT_DISPONIBLE); - } - - @Test - @DisplayName("Test valueOf") - void testValueOf() { - assertThat(StatutFormule.valueOf("ACTIVE")).isEqualTo(StatutFormule.ACTIVE); - assertThat(StatutFormule.valueOf("INACTIVE")).isEqualTo(StatutFormule.INACTIVE); - assertThat(StatutFormule.valueOf("ARCHIVEE")).isEqualTo(StatutFormule.ARCHIVEE); - assertThat(StatutFormule.valueOf("BIENTOT_DISPONIBLE")).isEqualTo(StatutFormule.BIENTOT_DISPONIBLE); - - assertThatThrownBy(() -> StatutFormule.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutFormule.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutFormule statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @ParameterizedTest - @CsvSource({ - "ACTIVE, Active", - "INACTIVE, Inactive", - "ARCHIVEE, Archivée", - "BIENTOT_DISPONIBLE, Bientôt Disponible" - }) - @DisplayName("Test getLibelle avec valeurs exactes") - void testGetLibelleValeursExactes(StatutFormule statut, String expectedLibelle) { - assertThat(statut.getLibelle()).isEqualTo(expectedLibelle); - } - } -} - +package dev.lions.unionflow.server.api.enums.abonnement; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutFormule") +class StatutFormuleTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutFormule.ACTIVE).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutFormule[] values = StatutFormule.values(); + assertThat(values).hasSize(4); + assertThat(values).containsExactly( + StatutFormule.ACTIVE, + StatutFormule.INACTIVE, + StatutFormule.ARCHIVEE, + StatutFormule.BIENTOT_DISPONIBLE); + } + + @Test + @DisplayName("Test valueOf") + void testValueOf() { + assertThat(StatutFormule.valueOf("ACTIVE")).isEqualTo(StatutFormule.ACTIVE); + assertThat(StatutFormule.valueOf("INACTIVE")).isEqualTo(StatutFormule.INACTIVE); + assertThat(StatutFormule.valueOf("ARCHIVEE")).isEqualTo(StatutFormule.ARCHIVEE); + assertThat(StatutFormule.valueOf("BIENTOT_DISPONIBLE")).isEqualTo(StatutFormule.BIENTOT_DISPONIBLE); + + assertThatThrownBy(() -> StatutFormule.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutFormule.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutFormule statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @ParameterizedTest + @CsvSource({ + "ACTIVE, Active", + "INACTIVE, Inactive", + "ARCHIVEE, Archivée", + "BIENTOT_DISPONIBLE, Bientôt Disponible" + }) + @DisplayName("Test getLibelle avec valeurs exactes") + void testGetLibelleValeursExactes(StatutFormule statut, String expectedLibelle) { + assertThat(statut.getLibelle()).isEqualTo(expectedLibelle); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/StatutSouscriptionTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/StatutSouscriptionTest.java index 40c8e57..82a0cc8 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/StatutSouscriptionTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/StatutSouscriptionTest.java @@ -1,75 +1,75 @@ -package dev.lions.unionflow.server.api.enums.abonnement; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutSouscription") -class StatutSouscriptionTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutSouscription.ACTIVE).isNotNull(); - assertThat(StatutSouscription.RESILIEE).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutSouscription[] values = StatutSouscription.values(); - assertThat(values).hasSize(5); - assertThat(values).containsExactly( - StatutSouscription.EN_ATTENTE, - StatutSouscription.ACTIVE, - StatutSouscription.EXPIREE, - StatutSouscription.SUSPENDUE, - StatutSouscription.RESILIEE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(StatutSouscription.valueOf("EN_ATTENTE")).isEqualTo(StatutSouscription.EN_ATTENTE); - assertThat(StatutSouscription.valueOf("ACTIVE")).isEqualTo(StatutSouscription.ACTIVE); - assertThat(StatutSouscription.valueOf("EXPIREE")).isEqualTo(StatutSouscription.EXPIREE); - assertThat(StatutSouscription.valueOf("SUSPENDUE")).isEqualTo(StatutSouscription.SUSPENDUE); - assertThat(StatutSouscription.valueOf("RESILIEE")).isEqualTo(StatutSouscription.RESILIEE); - - assertThatThrownBy(() -> StatutSouscription.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutSouscription.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutSouscription statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(StatutSouscription.ACTIVE.getLibelle()).isEqualTo("Active"); - assertThat(StatutSouscription.EXPIREE.getLibelle()).isEqualTo("Expirée"); - assertThat(StatutSouscription.SUSPENDUE.getLibelle()).contains("Suspendue"); - assertThat(StatutSouscription.RESILIEE.getLibelle()).isEqualTo("Résiliée"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(StatutSouscription.ACTIVE.name()).isEqualTo("ACTIVE"); - assertThat(StatutSouscription.RESILIEE.name()).isEqualTo("RESILIEE"); - } - } -} +package dev.lions.unionflow.server.api.enums.abonnement; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutSouscription") +class StatutSouscriptionTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutSouscription.ACTIVE).isNotNull(); + assertThat(StatutSouscription.RESILIEE).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutSouscription[] values = StatutSouscription.values(); + assertThat(values).hasSize(5); + assertThat(values).containsExactly( + StatutSouscription.EN_ATTENTE, + StatutSouscription.ACTIVE, + StatutSouscription.EXPIREE, + StatutSouscription.SUSPENDUE, + StatutSouscription.RESILIEE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(StatutSouscription.valueOf("EN_ATTENTE")).isEqualTo(StatutSouscription.EN_ATTENTE); + assertThat(StatutSouscription.valueOf("ACTIVE")).isEqualTo(StatutSouscription.ACTIVE); + assertThat(StatutSouscription.valueOf("EXPIREE")).isEqualTo(StatutSouscription.EXPIREE); + assertThat(StatutSouscription.valueOf("SUSPENDUE")).isEqualTo(StatutSouscription.SUSPENDUE); + assertThat(StatutSouscription.valueOf("RESILIEE")).isEqualTo(StatutSouscription.RESILIEE); + + assertThatThrownBy(() -> StatutSouscription.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutSouscription.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutSouscription statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(StatutSouscription.ACTIVE.getLibelle()).isEqualTo("Active"); + assertThat(StatutSouscription.EXPIREE.getLibelle()).isEqualTo("Expirée"); + assertThat(StatutSouscription.SUSPENDUE.getLibelle()).contains("Suspendue"); + assertThat(StatutSouscription.RESILIEE.getLibelle()).isEqualTo("Résiliée"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(StatutSouscription.ACTIVE.name()).isEqualTo("ACTIVE"); + assertThat(StatutSouscription.RESILIEE.name()).isEqualTo("RESILIEE"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/TypePeriodeAbonnementTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/TypePeriodeAbonnementTest.java index 9fd22f0..8434336 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/TypePeriodeAbonnementTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/abonnement/TypePeriodeAbonnementTest.java @@ -1,93 +1,93 @@ -package dev.lions.unionflow.server.api.enums.abonnement; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour TypePeriodeAbonnement") -class TypePeriodeAbonnementTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(TypePeriodeAbonnement.MENSUEL).isNotNull(); - assertThat(TypePeriodeAbonnement.ANNUEL).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - TypePeriodeAbonnement[] values = TypePeriodeAbonnement.values(); - assertThat(values).hasSize(4); - assertThat(values).containsExactly( - TypePeriodeAbonnement.MENSUEL, - TypePeriodeAbonnement.TRIMESTRIEL, - TypePeriodeAbonnement.SEMESTRIEL, - TypePeriodeAbonnement.ANNUEL); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(TypePeriodeAbonnement.valueOf("MENSUEL")).isEqualTo(TypePeriodeAbonnement.MENSUEL); - assertThat(TypePeriodeAbonnement.valueOf("TRIMESTRIEL")).isEqualTo(TypePeriodeAbonnement.TRIMESTRIEL); - assertThat(TypePeriodeAbonnement.valueOf("SEMESTRIEL")).isEqualTo(TypePeriodeAbonnement.SEMESTRIEL); - assertThat(TypePeriodeAbonnement.valueOf("ANNUEL")).isEqualTo(TypePeriodeAbonnement.ANNUEL); - - assertThatThrownBy(() -> TypePeriodeAbonnement.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(TypePeriodeAbonnement.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(TypePeriodeAbonnement type) { - assertThat(type.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(TypePeriodeAbonnement.MENSUEL.getLibelle()).isEqualTo("Mensuel"); - assertThat(TypePeriodeAbonnement.TRIMESTRIEL.getLibelle()).contains("Trimestriel"); - assertThat(TypePeriodeAbonnement.SEMESTRIEL.getLibelle()).contains("Semestriel"); - assertThat(TypePeriodeAbonnement.ANNUEL.getLibelle()).contains("Annuel"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(TypePeriodeAbonnement.MENSUEL.name()).isEqualTo("MENSUEL"); - assertThat(TypePeriodeAbonnement.TRIMESTRIEL.name()).isEqualTo("TRIMESTRIEL"); - assertThat(TypePeriodeAbonnement.SEMESTRIEL.name()).isEqualTo("SEMESTRIEL"); - assertThat(TypePeriodeAbonnement.ANNUEL.name()).isEqualTo("ANNUEL"); - } - - @Test - @DisplayName("Test getNombreMois - durée en mois de chaque période") - void testGetNombreMois() { - assertThat(TypePeriodeAbonnement.MENSUEL.getNombreMois()).isEqualTo(1); - assertThat(TypePeriodeAbonnement.TRIMESTRIEL.getNombreMois()).isEqualTo(3); - assertThat(TypePeriodeAbonnement.SEMESTRIEL.getNombreMois()).isEqualTo(6); - assertThat(TypePeriodeAbonnement.ANNUEL.getNombreMois()).isEqualTo(12); - } - - @Test - @DisplayName("Test getCoefficient - remise appliquée par période") - void testGetCoefficient() { - assertThat(TypePeriodeAbonnement.MENSUEL.getCoefficient()).isEqualByComparingTo("1.00"); - assertThat(TypePeriodeAbonnement.TRIMESTRIEL.getCoefficient()).isEqualByComparingTo("0.95"); - assertThat(TypePeriodeAbonnement.SEMESTRIEL.getCoefficient()).isEqualByComparingTo("0.90"); - assertThat(TypePeriodeAbonnement.ANNUEL.getCoefficient()).isEqualByComparingTo("0.80"); - } - } -} +package dev.lions.unionflow.server.api.enums.abonnement; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour TypePeriodeAbonnement") +class TypePeriodeAbonnementTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(TypePeriodeAbonnement.MENSUEL).isNotNull(); + assertThat(TypePeriodeAbonnement.ANNUEL).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + TypePeriodeAbonnement[] values = TypePeriodeAbonnement.values(); + assertThat(values).hasSize(4); + assertThat(values).containsExactly( + TypePeriodeAbonnement.MENSUEL, + TypePeriodeAbonnement.TRIMESTRIEL, + TypePeriodeAbonnement.SEMESTRIEL, + TypePeriodeAbonnement.ANNUEL); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(TypePeriodeAbonnement.valueOf("MENSUEL")).isEqualTo(TypePeriodeAbonnement.MENSUEL); + assertThat(TypePeriodeAbonnement.valueOf("TRIMESTRIEL")).isEqualTo(TypePeriodeAbonnement.TRIMESTRIEL); + assertThat(TypePeriodeAbonnement.valueOf("SEMESTRIEL")).isEqualTo(TypePeriodeAbonnement.SEMESTRIEL); + assertThat(TypePeriodeAbonnement.valueOf("ANNUEL")).isEqualTo(TypePeriodeAbonnement.ANNUEL); + + assertThatThrownBy(() -> TypePeriodeAbonnement.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(TypePeriodeAbonnement.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(TypePeriodeAbonnement type) { + assertThat(type.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(TypePeriodeAbonnement.MENSUEL.getLibelle()).isEqualTo("Mensuel"); + assertThat(TypePeriodeAbonnement.TRIMESTRIEL.getLibelle()).contains("Trimestriel"); + assertThat(TypePeriodeAbonnement.SEMESTRIEL.getLibelle()).contains("Semestriel"); + assertThat(TypePeriodeAbonnement.ANNUEL.getLibelle()).contains("Annuel"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(TypePeriodeAbonnement.MENSUEL.name()).isEqualTo("MENSUEL"); + assertThat(TypePeriodeAbonnement.TRIMESTRIEL.name()).isEqualTo("TRIMESTRIEL"); + assertThat(TypePeriodeAbonnement.SEMESTRIEL.name()).isEqualTo("SEMESTRIEL"); + assertThat(TypePeriodeAbonnement.ANNUEL.name()).isEqualTo("ANNUEL"); + } + + @Test + @DisplayName("Test getNombreMois - durée en mois de chaque période") + void testGetNombreMois() { + assertThat(TypePeriodeAbonnement.MENSUEL.getNombreMois()).isEqualTo(1); + assertThat(TypePeriodeAbonnement.TRIMESTRIEL.getNombreMois()).isEqualTo(3); + assertThat(TypePeriodeAbonnement.SEMESTRIEL.getNombreMois()).isEqualTo(6); + assertThat(TypePeriodeAbonnement.ANNUEL.getNombreMois()).isEqualTo(12); + } + + @Test + @DisplayName("Test getCoefficient - remise appliquée par période") + void testGetCoefficient() { + assertThat(TypePeriodeAbonnement.MENSUEL.getCoefficient()).isEqualByComparingTo("1.00"); + assertThat(TypePeriodeAbonnement.TRIMESTRIEL.getCoefficient()).isEqualByComparingTo("0.95"); + assertThat(TypePeriodeAbonnement.SEMESTRIEL.getCoefficient()).isEqualByComparingTo("0.90"); + assertThat(TypePeriodeAbonnement.ANNUEL.getCoefficient()).isEqualByComparingTo("0.80"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/agricole/StatutCampagneAgricoleTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/agricole/StatutCampagneAgricoleTest.java index 8b450ea..bf40501 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/agricole/StatutCampagneAgricoleTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/agricole/StatutCampagneAgricoleTest.java @@ -1,79 +1,79 @@ -package dev.lions.unionflow.server.api.enums.agricole; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutCampagneAgricole") -class StatutCampagneAgricoleTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutCampagneAgricole.PREPARATION).isNotNull(); - assertThat(StatutCampagneAgricole.RECOLTE).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutCampagneAgricole[] values = StatutCampagneAgricole.values(); - assertThat(values).hasSize(6); - assertThat(values).containsExactly( - StatutCampagneAgricole.PREPARATION, - StatutCampagneAgricole.LABOUR_SEMIS, - StatutCampagneAgricole.ENTRETIEN, - StatutCampagneAgricole.RECOLTE, - StatutCampagneAgricole.COMMERCIALISATION, - StatutCampagneAgricole.CLOTUREE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(StatutCampagneAgricole.valueOf("PREPARATION")).isEqualTo(StatutCampagneAgricole.PREPARATION); - assertThat(StatutCampagneAgricole.valueOf("LABOUR_SEMIS")).isEqualTo(StatutCampagneAgricole.LABOUR_SEMIS); - assertThat(StatutCampagneAgricole.valueOf("ENTRETIEN")).isEqualTo(StatutCampagneAgricole.ENTRETIEN); - assertThat(StatutCampagneAgricole.valueOf("RECOLTE")).isEqualTo(StatutCampagneAgricole.RECOLTE); - assertThat(StatutCampagneAgricole.valueOf("COMMERCIALISATION")).isEqualTo(StatutCampagneAgricole.COMMERCIALISATION); - assertThat(StatutCampagneAgricole.valueOf("CLOTUREE")).isEqualTo(StatutCampagneAgricole.CLOTUREE); - - assertThatThrownBy(() -> StatutCampagneAgricole.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutCampagneAgricole.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutCampagneAgricole statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(StatutCampagneAgricole.PREPARATION.getLibelle()).isEqualTo("Distribution des intrants et semences"); - assertThat(StatutCampagneAgricole.LABOUR_SEMIS.getLibelle()).isEqualTo("Saison des semis et du labour"); - assertThat(StatutCampagneAgricole.ENTRETIEN.getLibelle()).isEqualTo("Croissance et traitement phytosanitaire"); - assertThat(StatutCampagneAgricole.RECOLTE.getLibelle()).isEqualTo("Saison des récoltes"); - assertThat(StatutCampagneAgricole.COMMERCIALISATION.getLibelle()).isEqualTo("Stockage et vente des coopérateurs"); - assertThat(StatutCampagneAgricole.CLOTUREE.getLibelle()).isEqualTo("Campagne soldée"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(StatutCampagneAgricole.PREPARATION.name()).isEqualTo("PREPARATION"); - assertThat(StatutCampagneAgricole.LABOUR_SEMIS.name()).isEqualTo("LABOUR_SEMIS"); - } - } -} +package dev.lions.unionflow.server.api.enums.agricole; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutCampagneAgricole") +class StatutCampagneAgricoleTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutCampagneAgricole.PREPARATION).isNotNull(); + assertThat(StatutCampagneAgricole.RECOLTE).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutCampagneAgricole[] values = StatutCampagneAgricole.values(); + assertThat(values).hasSize(6); + assertThat(values).containsExactly( + StatutCampagneAgricole.PREPARATION, + StatutCampagneAgricole.LABOUR_SEMIS, + StatutCampagneAgricole.ENTRETIEN, + StatutCampagneAgricole.RECOLTE, + StatutCampagneAgricole.COMMERCIALISATION, + StatutCampagneAgricole.CLOTUREE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(StatutCampagneAgricole.valueOf("PREPARATION")).isEqualTo(StatutCampagneAgricole.PREPARATION); + assertThat(StatutCampagneAgricole.valueOf("LABOUR_SEMIS")).isEqualTo(StatutCampagneAgricole.LABOUR_SEMIS); + assertThat(StatutCampagneAgricole.valueOf("ENTRETIEN")).isEqualTo(StatutCampagneAgricole.ENTRETIEN); + assertThat(StatutCampagneAgricole.valueOf("RECOLTE")).isEqualTo(StatutCampagneAgricole.RECOLTE); + assertThat(StatutCampagneAgricole.valueOf("COMMERCIALISATION")).isEqualTo(StatutCampagneAgricole.COMMERCIALISATION); + assertThat(StatutCampagneAgricole.valueOf("CLOTUREE")).isEqualTo(StatutCampagneAgricole.CLOTUREE); + + assertThatThrownBy(() -> StatutCampagneAgricole.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutCampagneAgricole.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutCampagneAgricole statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(StatutCampagneAgricole.PREPARATION.getLibelle()).isEqualTo("Distribution des intrants et semences"); + assertThat(StatutCampagneAgricole.LABOUR_SEMIS.getLibelle()).isEqualTo("Saison des semis et du labour"); + assertThat(StatutCampagneAgricole.ENTRETIEN.getLibelle()).isEqualTo("Croissance et traitement phytosanitaire"); + assertThat(StatutCampagneAgricole.RECOLTE.getLibelle()).isEqualTo("Saison des récoltes"); + assertThat(StatutCampagneAgricole.COMMERCIALISATION.getLibelle()).isEqualTo("Stockage et vente des coopérateurs"); + assertThat(StatutCampagneAgricole.CLOTUREE.getLibelle()).isEqualTo("Campagne soldée"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(StatutCampagneAgricole.PREPARATION.name()).isEqualTo("PREPARATION"); + assertThat(StatutCampagneAgricole.LABOUR_SEMIS.name()).isEqualTo("LABOUR_SEMIS"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/analytics/FormatExportTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/analytics/FormatExportTest.java index 8522cd7..9418f85 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/analytics/FormatExportTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/analytics/FormatExportTest.java @@ -1,277 +1,277 @@ -package dev.lions.unionflow.server.api.enums.analytics; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour FormatExport") -class FormatExportTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(FormatExport.PDF).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - FormatExport[] values = FormatExport.values(); - assertThat(values).hasSize(11); - } - - @ParameterizedTest - @EnumSource(FormatExport.class) - @DisplayName("Test getters de base pour toutes les valeurs") - void testGettersBase(FormatExport format) { - assertThat(format.getLibelle()).isNotNull().isNotEmpty(); - assertThat(format.getExtension()).isNotNull().isNotEmpty(); - assertThat(format.getMimeType()).isNotNull().isNotEmpty(); - assertThat(format.getDescription()).isNotNull().isNotEmpty(); - } - } - - @Nested - @DisplayName("Tests supporteGraphiques") - class SupporteGraphiquesTests { - - @ParameterizedTest - @CsvSource({ - "PDF, true", - "WORD, true", - "EXCEL, true", - "CSV, false", - "JSON, false", - "XML, false", - "PNG, true", - "JPEG, true", - "SVG, true" - }) - @DisplayName("supporteGraphiques - valeurs exactes") - void testSupporteGraphiques(FormatExport format, Boolean expected) { - assertThat(format.supporteGraphiques()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests supporteGrandesQuantitesDonnees") - class SupporteGrandesQuantitesDonneesTests { - - @ParameterizedTest - @CsvSource({ - "PDF, true", - "WORD, false", - "EXCEL, true", - "CSV, true", - "JSON, true", - "XML, false", - "PNG, false", - "JPEG, false" - }) - @DisplayName("supporteGrandesQuantitesDonnees - valeurs exactes") - void testSupporteGrandesQuantitesDonnees(FormatExport format, Boolean expected) { - assertThat(format.supporteGrandesQuantitesDonnees()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isFormatExecutif") - class IsFormatExecutifTests { - - @ParameterizedTest - @CsvSource({ - "PDF, true", - "POWERPOINT, true", - "WORD, true", - "EXCEL, false", - "CSV, false", - "JSON, false" - }) - @DisplayName("isFormatExecutif - formats exécutifs") - void testIsFormatExecutif(FormatExport format, Boolean expected) { - assertThat(format.isFormatExecutif()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isFormatAnalyse") - class IsFormatAnalyseTests { - - @ParameterizedTest - @CsvSource({ - "EXCEL, true", - "CSV, true", - "JSON, true", - "PDF, false", - "WORD, false", - "XML, false" - }) - @DisplayName("isFormatAnalyse - formats d'analyse") - void testIsFormatAnalyse(FormatExport format, Boolean expected) { - assertThat(format.isFormatAnalyse()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isFormatWeb") - class IsFormatWebTests { - - @ParameterizedTest - @CsvSource({ - "HTML, true", - "PNG, true", - "SVG, true", - "JSON, true", - "PDF, false", - "EXCEL, false", - "WORD, false" - }) - @DisplayName("isFormatWeb - formats web") - void testIsFormatWeb(FormatExport format, Boolean expected) { - assertThat(format.isFormatWeb()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests getIcone") - class GetIconeTests { - - @ParameterizedTest - @CsvSource({ - "PDF, picture_as_pdf", - "WORD, description", - "EXCEL, table_chart", - "CSV, grid_on", - "JSON, code", - "XML, code", - "PNG, image", - "JPEG, image", - "SVG, vector_image", - "POWERPOINT, slideshow", - "HTML, web" - }) - @DisplayName("getIcone - toutes les icônes") - void testGetIcone(FormatExport format, String expectedIcone) { - assertThat(format.getIcone()).isEqualTo(expectedIcone); - } - } - - @Nested - @DisplayName("Tests getCouleur") - class GetCouleurTests { - - @ParameterizedTest - @EnumSource(FormatExport.class) - @DisplayName("getCouleur - toutes les couleurs sont valides") - void testGetCouleur(FormatExport format) { - assertThat(format.getCouleur()).isNotNull().matches("#[0-9A-Fa-f]{6}"); - } - } - - @Nested - @DisplayName("Tests genererNomFichier") - class GenererNomFichierTests { - - @Test - @DisplayName("genererNomFichier - ajoute l'extension") - void testGenererNomFichier() { - assertThat(FormatExport.PDF.genererNomFichier("rapport")).isEqualTo("rapport.pdf"); - assertThat(FormatExport.EXCEL.genererNomFichier("donnees")).isEqualTo("donnees.xlsx"); - assertThat(FormatExport.CSV.genererNomFichier("export")).isEqualTo("export.csv"); - } - } - - @Nested - @DisplayName("Tests getTailleMaximaleRecommandee") - class GetTailleMaximaleRecommandeeTests { - - @ParameterizedTest - @CsvSource({ - "PDF, 50", - "WORD, 50", - "POWERPOINT, 50", - "EXCEL, 100", - "CSV, 200", - "JSON, 200", - "XML, 200", - "PNG, 10", - "JPEG, 10", - "SVG, 5", - "HTML, 5" - }) - @DisplayName("getTailleMaximaleRecommandee - toutes les tailles") - void testGetTailleMaximaleRecommandee(FormatExport format, int expectedMB) { - assertThat(format.getTailleMaximaleRecommandee()).isEqualTo(expectedMB); - } - } - - @Nested - @DisplayName("Tests necessiteTraitementSpecial") - class NecessiteTraitementSpecialTests { - - @ParameterizedTest - @CsvSource({ - "PDF, true", - "EXCEL, true", - "POWERPOINT, true", - "WORD, true", - "CSV, false", - "JSON, false", - "PNG, false" - }) - @DisplayName("necessiteTraitementSpecial - formats spéciaux") - void testNecessiteTraitementSpecial(FormatExport format, Boolean expected) { - assertThat(format.necessiteTraitementSpecial()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests getFormatsRecommandes") - class GetFormatsRecommandesTests { - - @Test - @DisplayName("getFormatsRecommandes - executif") - void testGetFormatsRecommandesExecutif() { - FormatExport[] formats = FormatExport.getFormatsRecommandes("executif"); - assertThat(formats).containsExactly(FormatExport.PDF, FormatExport.POWERPOINT, FormatExport.WORD); - } - - @Test - @DisplayName("getFormatsRecommandes - analytique") - void testGetFormatsRecommandesAnalytique() { - FormatExport[] formats = FormatExport.getFormatsRecommandes("analytique"); - assertThat(formats).containsExactly(FormatExport.EXCEL, FormatExport.CSV, FormatExport.JSON, FormatExport.PDF); - } - - @Test - @DisplayName("getFormatsRecommandes - technique") - void testGetFormatsRecommandesTechnique() { - FormatExport[] formats = FormatExport.getFormatsRecommandes("technique"); - assertThat(formats).containsExactly(FormatExport.JSON, FormatExport.XML, FormatExport.CSV, FormatExport.HTML); - } - - @Test - @DisplayName("getFormatsRecommandes - partage") - void testGetFormatsRecommandesPartage() { - FormatExport[] formats = FormatExport.getFormatsRecommandes("partage"); - assertThat(formats).containsExactly(FormatExport.PDF, FormatExport.PNG, FormatExport.HTML); - } - - @Test - @DisplayName("getFormatsRecommandes - type inconnu") - void testGetFormatsRecommandesInconnu() { - FormatExport[] formats = FormatExport.getFormatsRecommandes("inconnu"); - assertThat(formats).containsExactly(FormatExport.PDF, FormatExport.EXCEL, FormatExport.CSV); - } - } -} - +package dev.lions.unionflow.server.api.enums.analytics; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour FormatExport") +class FormatExportTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(FormatExport.PDF).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + FormatExport[] values = FormatExport.values(); + assertThat(values).hasSize(11); + } + + @ParameterizedTest + @EnumSource(FormatExport.class) + @DisplayName("Test getters de base pour toutes les valeurs") + void testGettersBase(FormatExport format) { + assertThat(format.getLibelle()).isNotNull().isNotEmpty(); + assertThat(format.getExtension()).isNotNull().isNotEmpty(); + assertThat(format.getMimeType()).isNotNull().isNotEmpty(); + assertThat(format.getDescription()).isNotNull().isNotEmpty(); + } + } + + @Nested + @DisplayName("Tests supporteGraphiques") + class SupporteGraphiquesTests { + + @ParameterizedTest + @CsvSource({ + "PDF, true", + "WORD, true", + "EXCEL, true", + "CSV, false", + "JSON, false", + "XML, false", + "PNG, true", + "JPEG, true", + "SVG, true" + }) + @DisplayName("supporteGraphiques - valeurs exactes") + void testSupporteGraphiques(FormatExport format, Boolean expected) { + assertThat(format.supporteGraphiques()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests supporteGrandesQuantitesDonnees") + class SupporteGrandesQuantitesDonneesTests { + + @ParameterizedTest + @CsvSource({ + "PDF, true", + "WORD, false", + "EXCEL, true", + "CSV, true", + "JSON, true", + "XML, false", + "PNG, false", + "JPEG, false" + }) + @DisplayName("supporteGrandesQuantitesDonnees - valeurs exactes") + void testSupporteGrandesQuantitesDonnees(FormatExport format, Boolean expected) { + assertThat(format.supporteGrandesQuantitesDonnees()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isFormatExecutif") + class IsFormatExecutifTests { + + @ParameterizedTest + @CsvSource({ + "PDF, true", + "POWERPOINT, true", + "WORD, true", + "EXCEL, false", + "CSV, false", + "JSON, false" + }) + @DisplayName("isFormatExecutif - formats exécutifs") + void testIsFormatExecutif(FormatExport format, Boolean expected) { + assertThat(format.isFormatExecutif()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isFormatAnalyse") + class IsFormatAnalyseTests { + + @ParameterizedTest + @CsvSource({ + "EXCEL, true", + "CSV, true", + "JSON, true", + "PDF, false", + "WORD, false", + "XML, false" + }) + @DisplayName("isFormatAnalyse - formats d'analyse") + void testIsFormatAnalyse(FormatExport format, Boolean expected) { + assertThat(format.isFormatAnalyse()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isFormatWeb") + class IsFormatWebTests { + + @ParameterizedTest + @CsvSource({ + "HTML, true", + "PNG, true", + "SVG, true", + "JSON, true", + "PDF, false", + "EXCEL, false", + "WORD, false" + }) + @DisplayName("isFormatWeb - formats web") + void testIsFormatWeb(FormatExport format, Boolean expected) { + assertThat(format.isFormatWeb()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests getIcone") + class GetIconeTests { + + @ParameterizedTest + @CsvSource({ + "PDF, picture_as_pdf", + "WORD, description", + "EXCEL, table_chart", + "CSV, grid_on", + "JSON, code", + "XML, code", + "PNG, image", + "JPEG, image", + "SVG, vector_image", + "POWERPOINT, slideshow", + "HTML, web" + }) + @DisplayName("getIcone - toutes les icônes") + void testGetIcone(FormatExport format, String expectedIcone) { + assertThat(format.getIcone()).isEqualTo(expectedIcone); + } + } + + @Nested + @DisplayName("Tests getCouleur") + class GetCouleurTests { + + @ParameterizedTest + @EnumSource(FormatExport.class) + @DisplayName("getCouleur - toutes les couleurs sont valides") + void testGetCouleur(FormatExport format) { + assertThat(format.getCouleur()).isNotNull().matches("#[0-9A-Fa-f]{6}"); + } + } + + @Nested + @DisplayName("Tests genererNomFichier") + class GenererNomFichierTests { + + @Test + @DisplayName("genererNomFichier - ajoute l'extension") + void testGenererNomFichier() { + assertThat(FormatExport.PDF.genererNomFichier("rapport")).isEqualTo("rapport.pdf"); + assertThat(FormatExport.EXCEL.genererNomFichier("donnees")).isEqualTo("donnees.xlsx"); + assertThat(FormatExport.CSV.genererNomFichier("export")).isEqualTo("export.csv"); + } + } + + @Nested + @DisplayName("Tests getTailleMaximaleRecommandee") + class GetTailleMaximaleRecommandeeTests { + + @ParameterizedTest + @CsvSource({ + "PDF, 50", + "WORD, 50", + "POWERPOINT, 50", + "EXCEL, 100", + "CSV, 200", + "JSON, 200", + "XML, 200", + "PNG, 10", + "JPEG, 10", + "SVG, 5", + "HTML, 5" + }) + @DisplayName("getTailleMaximaleRecommandee - toutes les tailles") + void testGetTailleMaximaleRecommandee(FormatExport format, int expectedMB) { + assertThat(format.getTailleMaximaleRecommandee()).isEqualTo(expectedMB); + } + } + + @Nested + @DisplayName("Tests necessiteTraitementSpecial") + class NecessiteTraitementSpecialTests { + + @ParameterizedTest + @CsvSource({ + "PDF, true", + "EXCEL, true", + "POWERPOINT, true", + "WORD, true", + "CSV, false", + "JSON, false", + "PNG, false" + }) + @DisplayName("necessiteTraitementSpecial - formats spéciaux") + void testNecessiteTraitementSpecial(FormatExport format, Boolean expected) { + assertThat(format.necessiteTraitementSpecial()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests getFormatsRecommandes") + class GetFormatsRecommandesTests { + + @Test + @DisplayName("getFormatsRecommandes - executif") + void testGetFormatsRecommandesExecutif() { + FormatExport[] formats = FormatExport.getFormatsRecommandes("executif"); + assertThat(formats).containsExactly(FormatExport.PDF, FormatExport.POWERPOINT, FormatExport.WORD); + } + + @Test + @DisplayName("getFormatsRecommandes - analytique") + void testGetFormatsRecommandesAnalytique() { + FormatExport[] formats = FormatExport.getFormatsRecommandes("analytique"); + assertThat(formats).containsExactly(FormatExport.EXCEL, FormatExport.CSV, FormatExport.JSON, FormatExport.PDF); + } + + @Test + @DisplayName("getFormatsRecommandes - technique") + void testGetFormatsRecommandesTechnique() { + FormatExport[] formats = FormatExport.getFormatsRecommandes("technique"); + assertThat(formats).containsExactly(FormatExport.JSON, FormatExport.XML, FormatExport.CSV, FormatExport.HTML); + } + + @Test + @DisplayName("getFormatsRecommandes - partage") + void testGetFormatsRecommandesPartage() { + FormatExport[] formats = FormatExport.getFormatsRecommandes("partage"); + assertThat(formats).containsExactly(FormatExport.PDF, FormatExport.PNG, FormatExport.HTML); + } + + @Test + @DisplayName("getFormatsRecommandes - type inconnu") + void testGetFormatsRecommandesInconnu() { + FormatExport[] formats = FormatExport.getFormatsRecommandes("inconnu"); + assertThat(formats).containsExactly(FormatExport.PDF, FormatExport.EXCEL, FormatExport.CSV); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/analytics/PeriodeAnalyseTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/analytics/PeriodeAnalyseTest.java index 7aef60c..e3f39ea 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/analytics/PeriodeAnalyseTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/analytics/PeriodeAnalyseTest.java @@ -1,481 +1,481 @@ -package dev.lions.unionflow.server.api.enums.analytics; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalDateTime; -import java.time.temporal.ChronoUnit; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour PeriodeAnalyse") -class PeriodeAnalyseTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(PeriodeAnalyse.AUJOURD_HUI).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - PeriodeAnalyse[] values = PeriodeAnalyse.values(); - assertThat(values).hasSize(16); - } - - @ParameterizedTest - @EnumSource(PeriodeAnalyse.class) - @DisplayName("Test getters de base pour toutes les valeurs") - void testGettersBase(PeriodeAnalyse periode) { - assertThat(periode.getLibelle()).isNotNull().isNotEmpty(); - assertThat(periode.getCode()).isNotNull().isNotEmpty(); - assertThat(periode.getDuree()).isGreaterThanOrEqualTo(0); - assertThat(periode.getUnite()).isNotNull(); - } - } - - @Nested - @DisplayName("Tests getDateDebut") - class GetDateDebutTests { - - @Test - @DisplayName("getDateDebut - AUJOURD_HUI") - void testGetDateDebutAujourdHui() { - LocalDateTime debut = PeriodeAnalyse.AUJOURD_HUI.getDateDebut(); - assertThat(debut).isNotNull(); - assertThat(debut.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); - assertThat(debut.getHour()).isEqualTo(0); - assertThat(debut.getMinute()).isEqualTo(0); - } - - @Test - @DisplayName("getDateDebut - HIER") - void testGetDateDebutHier() { - LocalDateTime debut = PeriodeAnalyse.HIER.getDateDebut(); - assertThat(debut).isNotNull(); - assertThat(debut.toLocalDate()).isEqualTo(LocalDateTime.now().minusDays(1).toLocalDate()); - } - - @Test - @DisplayName("getDateDebut - CETTE_SEMAINE") - void testGetDateDebutCetteSemaine() { - LocalDateTime debut = PeriodeAnalyse.CETTE_SEMAINE.getDateDebut(); - assertThat(debut).isNotNull(); - // Doit être le lundi de cette semaine - assertThat(debut.getDayOfWeek().getValue()).isEqualTo(1); // Lundi - } - - @Test - @DisplayName("getDateDebut - SEMAINE_DERNIERE") - void testGetDateDebutSemaineDerniere() { - LocalDateTime debut = PeriodeAnalyse.SEMAINE_DERNIERE.getDateDebut(); - assertThat(debut).isNotNull(); - // Doit être le lundi de la semaine dernière - assertThat(debut.getDayOfWeek().getValue()).isEqualTo(1); // Lundi - } - - @Test - @DisplayName("getDateDebut - CE_MOIS") - void testGetDateDebutCeMois() { - LocalDateTime debut = PeriodeAnalyse.CE_MOIS.getDateDebut(); - assertThat(debut).isNotNull(); - assertThat(debut.getDayOfMonth()).isEqualTo(1); - assertThat(debut.getMonth()).isEqualTo(LocalDateTime.now().getMonth()); - } - - @Test - @DisplayName("getDateDebut - MOIS_DERNIER") - void testGetDateDebutMoisDernier() { - LocalDateTime debut = PeriodeAnalyse.MOIS_DERNIER.getDateDebut(); - assertThat(debut).isNotNull(); - assertThat(debut.getDayOfMonth()).isEqualTo(1); - assertThat(debut.getMonth()).isEqualTo(LocalDateTime.now().minusMonths(1).getMonth()); - } - - @Test - @DisplayName("getDateDebut - CETTE_ANNEE") - void testGetDateDebutCetteAnnee() { - LocalDateTime debut = PeriodeAnalyse.CETTE_ANNEE.getDateDebut(); - assertThat(debut).isNotNull(); - assertThat(debut.getDayOfYear()).isEqualTo(1); - assertThat(debut.getYear()).isEqualTo(LocalDateTime.now().getYear()); - } - - @Test - @DisplayName("getDateDebut - ANNEE_DERNIERE") - void testGetDateDebutAnneeDerniere() { - LocalDateTime debut = PeriodeAnalyse.ANNEE_DERNIERE.getDateDebut(); - assertThat(debut).isNotNull(); - assertThat(debut.getDayOfYear()).isEqualTo(1); - assertThat(debut.getYear()).isEqualTo(LocalDateTime.now().getYear() - 1); - } - - @Test - @DisplayName("getDateDebut - DEPUIS_CREATION") - void testGetDateDebutDepuisCreation() { - LocalDateTime debut = PeriodeAnalyse.DEPUIS_CREATION.getDateDebut(); - assertThat(debut).isEqualTo(LocalDateTime.of(2020, 1, 1, 0, 0)); - } - - @Test - @DisplayName("getDateDebut - PERIODE_PERSONNALISEE") - void testGetDateDebutPeriodePersonnalisee() { - LocalDateTime avant = LocalDateTime.now(); - LocalDateTime debut = PeriodeAnalyse.PERIODE_PERSONNALISEE.getDateDebut(); - LocalDateTime apres = LocalDateTime.now(); - assertThat(debut).isBetween(avant.minusSeconds(1), apres.plusSeconds(1)); - } - - @ParameterizedTest - @CsvSource({ - "TROIS_DERNIERS_MOIS", - "SIX_DERNIERS_MOIS", - "SEPT_DERNIERS_JOURS", - "TRENTE_DERNIERS_JOURS", - "QUATRE_VINGT_DIX_DERNIERS_JOURS", - "DEUX_DERNIERES_ANNEES" - }) - @DisplayName("getDateDebut - périodes avec default") - void testGetDateDebutDefault(PeriodeAnalyse periode) { - LocalDateTime debut = periode.getDateDebut(); - assertThat(debut).isNotNull(); - // Vérifie que la date est dans le passé - assertThat(debut).isBefore(LocalDateTime.now()); - } - } - - @Nested - @DisplayName("Tests getDateFin") - class GetDateFinTests { - - @Test - @DisplayName("getDateFin - AUJOURD_HUI") - void testGetDateFinAujourdHui() { - LocalDateTime fin = PeriodeAnalyse.AUJOURD_HUI.getDateFin(); - assertThat(fin).isNotNull(); - assertThat(fin.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); - assertThat(fin.getHour()).isEqualTo(23); - assertThat(fin.getMinute()).isEqualTo(59); - } - - @Test - @DisplayName("getDateFin - HIER") - void testGetDateFinHier() { - LocalDateTime fin = PeriodeAnalyse.HIER.getDateFin(); - assertThat(fin).isNotNull(); - assertThat(fin.toLocalDate()).isEqualTo(LocalDateTime.now().minusDays(1).toLocalDate()); - assertThat(fin.getHour()).isEqualTo(23); - } - - @Test - @DisplayName("getDateFin - CETTE_SEMAINE") - void testGetDateFinCetteSemaine() { - LocalDateTime fin = PeriodeAnalyse.CETTE_SEMAINE.getDateFin(); - assertThat(fin).isNotNull(); - assertThat(fin.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); - } - - @Test - @DisplayName("getDateFin - SEMAINE_DERNIERE") - void testGetDateFinSemaineDerniere() { - LocalDateTime fin = PeriodeAnalyse.SEMAINE_DERNIERE.getDateFin(); - assertThat(fin).isNotNull(); - // Doit être le dimanche de la semaine dernière - assertThat(fin.getDayOfWeek().getValue()).isEqualTo(7); // Dimanche - } - - @Test - @DisplayName("getDateFin - CE_MOIS") - void testGetDateFinCeMois() { - LocalDateTime fin = PeriodeAnalyse.CE_MOIS.getDateFin(); - assertThat(fin).isNotNull(); - assertThat(fin.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); - } - - @Test - @DisplayName("getDateFin - MOIS_DERNIER") - void testGetDateFinMoisDernier() { - LocalDateTime fin = PeriodeAnalyse.MOIS_DERNIER.getDateFin(); - assertThat(fin).isNotNull(); - // Doit être le dernier jour du mois dernier - assertThat(fin.getMonth()).isEqualTo(LocalDateTime.now().minusMonths(1).getMonth()); - } - - @Test - @DisplayName("getDateFin - CETTE_ANNEE") - void testGetDateFinCetteAnnee() { - LocalDateTime fin = PeriodeAnalyse.CETTE_ANNEE.getDateFin(); - assertThat(fin).isNotNull(); - assertThat(fin.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); - } - - @Test - @DisplayName("getDateFin - ANNEE_DERNIERE") - void testGetDateFinAnneeDerniere() { - LocalDateTime fin = PeriodeAnalyse.ANNEE_DERNIERE.getDateFin(); - assertThat(fin).isNotNull(); - // Doit être le dernier jour de l'année dernière - assertThat(fin.getYear()).isEqualTo(LocalDateTime.now().getYear() - 1); - assertThat(fin.getMonthValue()).isEqualTo(12); - assertThat(fin.getDayOfMonth()).isEqualTo(31); - } - - @Test - @DisplayName("getDateFin - DEPUIS_CREATION") - void testGetDateFinDepuisCreation() { - LocalDateTime avant = LocalDateTime.now(); - LocalDateTime fin = PeriodeAnalyse.DEPUIS_CREATION.getDateFin(); - LocalDateTime apres = LocalDateTime.now(); - assertThat(fin).isBetween(avant.minusSeconds(1), apres.plusSeconds(1)); - } - - @Test - @DisplayName("getDateFin - PERIODE_PERSONNALISEE") - void testGetDateFinPeriodePersonnalisee() { - LocalDateTime avant = LocalDateTime.now(); - LocalDateTime fin = PeriodeAnalyse.PERIODE_PERSONNALISEE.getDateFin(); - LocalDateTime apres = LocalDateTime.now(); - assertThat(fin).isBetween(avant.minusSeconds(1), apres.plusSeconds(1)); - } - - @ParameterizedTest - @CsvSource({ - "TROIS_DERNIERS_MOIS", - "SIX_DERNIERS_MOIS", - "SEPT_DERNIERS_JOURS", - "TRENTE_DERNIERS_JOURS", - "QUATRE_VINGT_DIX_DERNIERS_JOURS", - "DEUX_DERNIERES_ANNEES" - }) - @DisplayName("getDateFin - périodes avec default") - void testGetDateFinDefault(PeriodeAnalyse periode) { - LocalDateTime fin = periode.getDateFin(); - assertThat(fin).isNotNull(); - assertThat(fin.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); - assertThat(fin.getHour()).isEqualTo(23); - assertThat(fin.getMinute()).isEqualTo(59); - } - } - - @Nested - @DisplayName("Tests isPeriodeCourte") - class IsPeriodeCourteTests { - - @ParameterizedTest - @CsvSource({ - "AUJOURD_HUI, true", - "HIER, true", - "CETTE_SEMAINE, true", - "SEMAINE_DERNIERE, true", - "SEPT_DERNIERS_JOURS, true", - "CE_MOIS, false", - "MOIS_DERNIER, false", - "CETTE_ANNEE, false", - "DEPUIS_CREATION, false" - }) - @DisplayName("isPeriodeCourte - toutes les périodes") - void testIsPeriodeCourte(PeriodeAnalyse periode, boolean expected) { - assertThat(periode.isPeriodeCourte()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isPeriodeLongue") - class IsPeriodeLongueTests { - - @ParameterizedTest - @CsvSource({ - "CETTE_ANNEE, true", - "ANNEE_DERNIERE, true", - "DEUX_DERNIERES_ANNEES, true", - "DEPUIS_CREATION, true", - "AUJOURD_HUI, false", - "CE_MOIS, false", - "CETTE_SEMAINE, false" - }) - @DisplayName("isPeriodeLongue - toutes les périodes") - void testIsPeriodeLongue(PeriodeAnalyse periode, boolean expected) { - assertThat(periode.isPeriodeLongue()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isPersonnalisable") - class IsPersonnalisableTests { - - @Test - @DisplayName("isPersonnalisable - PERIODE_PERSONNALISEE") - void testIsPersonnalisableTrue() { - assertThat(PeriodeAnalyse.PERIODE_PERSONNALISEE.isPersonnalisable()).isTrue(); - } - - @ParameterizedTest - @CsvSource({ - "AUJOURD_HUI", - "CE_MOIS", - "CETTE_ANNEE", - "DEPUIS_CREATION" - }) - @DisplayName("isPersonnalisable - autres périodes") - void testIsPersonnalisableFalse(PeriodeAnalyse periode) { - assertThat(periode.isPersonnalisable()).isFalse(); - } - } - - @Nested - @DisplayName("Tests getIntervalleRegroupement") - class GetIntervalleRegroupementTests { - - @ParameterizedTest - @CsvSource({ - "AUJOURD_HUI, heure", - "HIER, heure", - "CETTE_SEMAINE, jour", - "SEMAINE_DERNIERE, jour", - "SEPT_DERNIERS_JOURS, jour", - "CE_MOIS, jour", - "MOIS_DERNIER, jour", - "TRENTE_DERNIERS_JOURS, jour", - "TROIS_DERNIERS_MOIS, semaine", - "SIX_DERNIERS_MOIS, semaine", - "QUATRE_VINGT_DIX_DERNIERS_JOURS, semaine", - "CETTE_ANNEE, mois", - "ANNEE_DERNIERE, mois", - "DEUX_DERNIERES_ANNEES, mois", - "DEPUIS_CREATION, annee", - "PERIODE_PERSONNALISEE, jour" - }) - @DisplayName("getIntervalleRegroupement - toutes les périodes") - void testGetIntervalleRegroupement(PeriodeAnalyse periode, String expected) { - assertThat(periode.getIntervalleRegroupement()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests getFormatDate") - class GetFormatDateTests { - - @ParameterizedTest - @CsvSource({ - "AUJOURD_HUI, HH:mm", - "HIER, HH:mm", - "CETTE_SEMAINE, dd/MM", - "SEMAINE_DERNIERE, dd/MM", - "SEPT_DERNIERS_JOURS, dd/MM", - "CE_MOIS, dd/MM", - "MOIS_DERNIER, dd/MM", - "TRENTE_DERNIERS_JOURS, dd/MM", - "TROIS_DERNIERS_MOIS, dd/MM", - "SIX_DERNIERS_MOIS, dd/MM", - "QUATRE_VINGT_DIX_DERNIERS_JOURS, dd/MM", - "CETTE_ANNEE, MM/yyyy", - "ANNEE_DERNIERE, MM/yyyy", - "DEUX_DERNIERES_ANNEES, yyyy", - "DEPUIS_CREATION, yyyy", - "PERIODE_PERSONNALISEE, dd/MM/yyyy" - }) - @DisplayName("getFormatDate - toutes les périodes") - void testGetFormatDate(PeriodeAnalyse periode, String expected) { - assertThat(periode.getFormatDate()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests valeurs spécifiques") - class ValeursSpecifiquesTests { - - @Test - @DisplayName("Test duree et unite pour toutes les périodes") - void testDureeEtUnite() { - assertThat(PeriodeAnalyse.AUJOURD_HUI.getDuree()).isEqualTo(1); - assertThat(PeriodeAnalyse.AUJOURD_HUI.getUnite()).isEqualTo(ChronoUnit.DAYS); - - assertThat(PeriodeAnalyse.CE_MOIS.getDuree()).isEqualTo(1); - assertThat(PeriodeAnalyse.CE_MOIS.getUnite()).isEqualTo(ChronoUnit.MONTHS); - - assertThat(PeriodeAnalyse.CETTE_ANNEE.getDuree()).isEqualTo(1); - assertThat(PeriodeAnalyse.CETTE_ANNEE.getUnite()).isEqualTo(ChronoUnit.YEARS); - - assertThat(PeriodeAnalyse.DEPUIS_CREATION.getDuree()).isEqualTo(0); - assertThat(PeriodeAnalyse.DEPUIS_CREATION.getUnite()).isEqualTo(ChronoUnit.FOREVER); - - assertThat(PeriodeAnalyse.PERIODE_PERSONNALISEE.getDuree()).isEqualTo(0); - assertThat(PeriodeAnalyse.PERIODE_PERSONNALISEE.getUnite()).isEqualTo(ChronoUnit.DAYS); - } - - @Test - @DisplayName("Test code pour toutes les périodes") - void testCode() { - assertThat(PeriodeAnalyse.AUJOURD_HUI.getCode()).isEqualTo("today"); - assertThat(PeriodeAnalyse.HIER.getCode()).isEqualTo("yesterday"); - assertThat(PeriodeAnalyse.CE_MOIS.getCode()).isEqualTo("this_month"); - assertThat(PeriodeAnalyse.DEPUIS_CREATION.getCode()).isEqualTo("since_creation"); - assertThat(PeriodeAnalyse.PERIODE_PERSONNALISEE.getCode()).isEqualTo("custom"); - } - - @Test - @DisplayName("Test toutes les périodes - couverture complète") - void testToutesLesPeriodes() { - // Test toutes les périodes pour s'assurer qu'elles sont toutes couvertes - for (PeriodeAnalyse periode : PeriodeAnalyse.values()) { - assertThat(periode.getDateDebut()).isNotNull(); - assertThat(periode.getDateFin()).isNotNull(); - assertThat(periode.getIntervalleRegroupement()).isNotNull().isNotEmpty(); - assertThat(periode.getFormatDate()).isNotNull().isNotEmpty(); - } - } - - @Test - @DisplayName("Test getDateDebut - cas default avec différentes unités") - void testGetDateDebutDefault() { - // Test que le default fonctionne pour toutes les périodes qui l'utilisent - LocalDateTime debutTroisMois = PeriodeAnalyse.TROIS_DERNIERS_MOIS.getDateDebut(); - LocalDateTime debutSixMois = PeriodeAnalyse.SIX_DERNIERS_MOIS.getDateDebut(); - LocalDateTime debutSeptJours = PeriodeAnalyse.SEPT_DERNIERS_JOURS.getDateDebut(); - LocalDateTime debutTrenteJours = PeriodeAnalyse.TRENTE_DERNIERS_JOURS.getDateDebut(); - LocalDateTime debutQuatreVingtDixJours = PeriodeAnalyse.QUATRE_VINGT_DIX_DERNIERS_JOURS.getDateDebut(); - LocalDateTime debutDeuxAnnees = PeriodeAnalyse.DEUX_DERNIERES_ANNEES.getDateDebut(); - - assertThat(debutTroisMois).isBefore(LocalDateTime.now()); - assertThat(debutSixMois).isBefore(LocalDateTime.now()); - assertThat(debutSeptJours).isBefore(LocalDateTime.now()); - assertThat(debutTrenteJours).isBefore(LocalDateTime.now()); - assertThat(debutQuatreVingtDixJours).isBefore(LocalDateTime.now()); - assertThat(debutDeuxAnnees).isBefore(LocalDateTime.now()); - - // Vérifie que les dates sont cohérentes avec les durées - // Plus la durée est grande, plus la date de début est dans le passé - assertThat(debutSixMois).isBefore(debutTroisMois); - assertThat(debutTrenteJours).isBefore(debutSeptJours); - } - - @Test - @DisplayName("Test getDateFin - cas default") - void testGetDateFinDefault() { - // Test que le default fonctionne pour toutes les périodes qui l'utilisent - LocalDateTime finTroisMois = PeriodeAnalyse.TROIS_DERNIERS_MOIS.getDateFin(); - LocalDateTime finSixMois = PeriodeAnalyse.SIX_DERNIERS_MOIS.getDateFin(); - LocalDateTime finSeptJours = PeriodeAnalyse.SEPT_DERNIERS_JOURS.getDateFin(); - LocalDateTime finTrenteJours = PeriodeAnalyse.TRENTE_DERNIERS_JOURS.getDateFin(); - LocalDateTime finQuatreVingtDixJours = PeriodeAnalyse.QUATRE_VINGT_DIX_DERNIERS_JOURS.getDateFin(); - LocalDateTime finDeuxAnnees = PeriodeAnalyse.DEUX_DERNIERES_ANNEES.getDateFin(); - - assertThat(finTroisMois.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); - assertThat(finTroisMois.getHour()).isEqualTo(23); - assertThat(finTroisMois.getMinute()).isEqualTo(59); - assertThat(finSixMois.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); - assertThat(finSeptJours.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); - assertThat(finTrenteJours.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); - assertThat(finQuatreVingtDixJours.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); - assertThat(finDeuxAnnees.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); - } - } -} +package dev.lions.unionflow.server.api.enums.analytics; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalDateTime; +import java.time.temporal.ChronoUnit; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour PeriodeAnalyse") +class PeriodeAnalyseTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(PeriodeAnalyse.AUJOURD_HUI).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + PeriodeAnalyse[] values = PeriodeAnalyse.values(); + assertThat(values).hasSize(16); + } + + @ParameterizedTest + @EnumSource(PeriodeAnalyse.class) + @DisplayName("Test getters de base pour toutes les valeurs") + void testGettersBase(PeriodeAnalyse periode) { + assertThat(periode.getLibelle()).isNotNull().isNotEmpty(); + assertThat(periode.getCode()).isNotNull().isNotEmpty(); + assertThat(periode.getDuree()).isGreaterThanOrEqualTo(0); + assertThat(periode.getUnite()).isNotNull(); + } + } + + @Nested + @DisplayName("Tests getDateDebut") + class GetDateDebutTests { + + @Test + @DisplayName("getDateDebut - AUJOURD_HUI") + void testGetDateDebutAujourdHui() { + LocalDateTime debut = PeriodeAnalyse.AUJOURD_HUI.getDateDebut(); + assertThat(debut).isNotNull(); + assertThat(debut.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); + assertThat(debut.getHour()).isEqualTo(0); + assertThat(debut.getMinute()).isEqualTo(0); + } + + @Test + @DisplayName("getDateDebut - HIER") + void testGetDateDebutHier() { + LocalDateTime debut = PeriodeAnalyse.HIER.getDateDebut(); + assertThat(debut).isNotNull(); + assertThat(debut.toLocalDate()).isEqualTo(LocalDateTime.now().minusDays(1).toLocalDate()); + } + + @Test + @DisplayName("getDateDebut - CETTE_SEMAINE") + void testGetDateDebutCetteSemaine() { + LocalDateTime debut = PeriodeAnalyse.CETTE_SEMAINE.getDateDebut(); + assertThat(debut).isNotNull(); + // Doit être le lundi de cette semaine + assertThat(debut.getDayOfWeek().getValue()).isEqualTo(1); // Lundi + } + + @Test + @DisplayName("getDateDebut - SEMAINE_DERNIERE") + void testGetDateDebutSemaineDerniere() { + LocalDateTime debut = PeriodeAnalyse.SEMAINE_DERNIERE.getDateDebut(); + assertThat(debut).isNotNull(); + // Doit être le lundi de la semaine dernière + assertThat(debut.getDayOfWeek().getValue()).isEqualTo(1); // Lundi + } + + @Test + @DisplayName("getDateDebut - CE_MOIS") + void testGetDateDebutCeMois() { + LocalDateTime debut = PeriodeAnalyse.CE_MOIS.getDateDebut(); + assertThat(debut).isNotNull(); + assertThat(debut.getDayOfMonth()).isEqualTo(1); + assertThat(debut.getMonth()).isEqualTo(LocalDateTime.now().getMonth()); + } + + @Test + @DisplayName("getDateDebut - MOIS_DERNIER") + void testGetDateDebutMoisDernier() { + LocalDateTime debut = PeriodeAnalyse.MOIS_DERNIER.getDateDebut(); + assertThat(debut).isNotNull(); + assertThat(debut.getDayOfMonth()).isEqualTo(1); + assertThat(debut.getMonth()).isEqualTo(LocalDateTime.now().minusMonths(1).getMonth()); + } + + @Test + @DisplayName("getDateDebut - CETTE_ANNEE") + void testGetDateDebutCetteAnnee() { + LocalDateTime debut = PeriodeAnalyse.CETTE_ANNEE.getDateDebut(); + assertThat(debut).isNotNull(); + assertThat(debut.getDayOfYear()).isEqualTo(1); + assertThat(debut.getYear()).isEqualTo(LocalDateTime.now().getYear()); + } + + @Test + @DisplayName("getDateDebut - ANNEE_DERNIERE") + void testGetDateDebutAnneeDerniere() { + LocalDateTime debut = PeriodeAnalyse.ANNEE_DERNIERE.getDateDebut(); + assertThat(debut).isNotNull(); + assertThat(debut.getDayOfYear()).isEqualTo(1); + assertThat(debut.getYear()).isEqualTo(LocalDateTime.now().getYear() - 1); + } + + @Test + @DisplayName("getDateDebut - DEPUIS_CREATION") + void testGetDateDebutDepuisCreation() { + LocalDateTime debut = PeriodeAnalyse.DEPUIS_CREATION.getDateDebut(); + assertThat(debut).isEqualTo(LocalDateTime.of(2020, 1, 1, 0, 0)); + } + + @Test + @DisplayName("getDateDebut - PERIODE_PERSONNALISEE") + void testGetDateDebutPeriodePersonnalisee() { + LocalDateTime avant = LocalDateTime.now(); + LocalDateTime debut = PeriodeAnalyse.PERIODE_PERSONNALISEE.getDateDebut(); + LocalDateTime apres = LocalDateTime.now(); + assertThat(debut).isBetween(avant.minusSeconds(1), apres.plusSeconds(1)); + } + + @ParameterizedTest + @CsvSource({ + "TROIS_DERNIERS_MOIS", + "SIX_DERNIERS_MOIS", + "SEPT_DERNIERS_JOURS", + "TRENTE_DERNIERS_JOURS", + "QUATRE_VINGT_DIX_DERNIERS_JOURS", + "DEUX_DERNIERES_ANNEES" + }) + @DisplayName("getDateDebut - périodes avec default") + void testGetDateDebutDefault(PeriodeAnalyse periode) { + LocalDateTime debut = periode.getDateDebut(); + assertThat(debut).isNotNull(); + // Vérifie que la date est dans le passé + assertThat(debut).isBefore(LocalDateTime.now()); + } + } + + @Nested + @DisplayName("Tests getDateFin") + class GetDateFinTests { + + @Test + @DisplayName("getDateFin - AUJOURD_HUI") + void testGetDateFinAujourdHui() { + LocalDateTime fin = PeriodeAnalyse.AUJOURD_HUI.getDateFin(); + assertThat(fin).isNotNull(); + assertThat(fin.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); + assertThat(fin.getHour()).isEqualTo(23); + assertThat(fin.getMinute()).isEqualTo(59); + } + + @Test + @DisplayName("getDateFin - HIER") + void testGetDateFinHier() { + LocalDateTime fin = PeriodeAnalyse.HIER.getDateFin(); + assertThat(fin).isNotNull(); + assertThat(fin.toLocalDate()).isEqualTo(LocalDateTime.now().minusDays(1).toLocalDate()); + assertThat(fin.getHour()).isEqualTo(23); + } + + @Test + @DisplayName("getDateFin - CETTE_SEMAINE") + void testGetDateFinCetteSemaine() { + LocalDateTime fin = PeriodeAnalyse.CETTE_SEMAINE.getDateFin(); + assertThat(fin).isNotNull(); + assertThat(fin.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); + } + + @Test + @DisplayName("getDateFin - SEMAINE_DERNIERE") + void testGetDateFinSemaineDerniere() { + LocalDateTime fin = PeriodeAnalyse.SEMAINE_DERNIERE.getDateFin(); + assertThat(fin).isNotNull(); + // Doit être le dimanche de la semaine dernière + assertThat(fin.getDayOfWeek().getValue()).isEqualTo(7); // Dimanche + } + + @Test + @DisplayName("getDateFin - CE_MOIS") + void testGetDateFinCeMois() { + LocalDateTime fin = PeriodeAnalyse.CE_MOIS.getDateFin(); + assertThat(fin).isNotNull(); + assertThat(fin.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); + } + + @Test + @DisplayName("getDateFin - MOIS_DERNIER") + void testGetDateFinMoisDernier() { + LocalDateTime fin = PeriodeAnalyse.MOIS_DERNIER.getDateFin(); + assertThat(fin).isNotNull(); + // Doit être le dernier jour du mois dernier + assertThat(fin.getMonth()).isEqualTo(LocalDateTime.now().minusMonths(1).getMonth()); + } + + @Test + @DisplayName("getDateFin - CETTE_ANNEE") + void testGetDateFinCetteAnnee() { + LocalDateTime fin = PeriodeAnalyse.CETTE_ANNEE.getDateFin(); + assertThat(fin).isNotNull(); + assertThat(fin.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); + } + + @Test + @DisplayName("getDateFin - ANNEE_DERNIERE") + void testGetDateFinAnneeDerniere() { + LocalDateTime fin = PeriodeAnalyse.ANNEE_DERNIERE.getDateFin(); + assertThat(fin).isNotNull(); + // Doit être le dernier jour de l'année dernière + assertThat(fin.getYear()).isEqualTo(LocalDateTime.now().getYear() - 1); + assertThat(fin.getMonthValue()).isEqualTo(12); + assertThat(fin.getDayOfMonth()).isEqualTo(31); + } + + @Test + @DisplayName("getDateFin - DEPUIS_CREATION") + void testGetDateFinDepuisCreation() { + LocalDateTime avant = LocalDateTime.now(); + LocalDateTime fin = PeriodeAnalyse.DEPUIS_CREATION.getDateFin(); + LocalDateTime apres = LocalDateTime.now(); + assertThat(fin).isBetween(avant.minusSeconds(1), apres.plusSeconds(1)); + } + + @Test + @DisplayName("getDateFin - PERIODE_PERSONNALISEE") + void testGetDateFinPeriodePersonnalisee() { + LocalDateTime avant = LocalDateTime.now(); + LocalDateTime fin = PeriodeAnalyse.PERIODE_PERSONNALISEE.getDateFin(); + LocalDateTime apres = LocalDateTime.now(); + assertThat(fin).isBetween(avant.minusSeconds(1), apres.plusSeconds(1)); + } + + @ParameterizedTest + @CsvSource({ + "TROIS_DERNIERS_MOIS", + "SIX_DERNIERS_MOIS", + "SEPT_DERNIERS_JOURS", + "TRENTE_DERNIERS_JOURS", + "QUATRE_VINGT_DIX_DERNIERS_JOURS", + "DEUX_DERNIERES_ANNEES" + }) + @DisplayName("getDateFin - périodes avec default") + void testGetDateFinDefault(PeriodeAnalyse periode) { + LocalDateTime fin = periode.getDateFin(); + assertThat(fin).isNotNull(); + assertThat(fin.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); + assertThat(fin.getHour()).isEqualTo(23); + assertThat(fin.getMinute()).isEqualTo(59); + } + } + + @Nested + @DisplayName("Tests isPeriodeCourte") + class IsPeriodeCourteTests { + + @ParameterizedTest + @CsvSource({ + "AUJOURD_HUI, true", + "HIER, true", + "CETTE_SEMAINE, true", + "SEMAINE_DERNIERE, true", + "SEPT_DERNIERS_JOURS, true", + "CE_MOIS, false", + "MOIS_DERNIER, false", + "CETTE_ANNEE, false", + "DEPUIS_CREATION, false" + }) + @DisplayName("isPeriodeCourte - toutes les périodes") + void testIsPeriodeCourte(PeriodeAnalyse periode, boolean expected) { + assertThat(periode.isPeriodeCourte()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isPeriodeLongue") + class IsPeriodeLongueTests { + + @ParameterizedTest + @CsvSource({ + "CETTE_ANNEE, true", + "ANNEE_DERNIERE, true", + "DEUX_DERNIERES_ANNEES, true", + "DEPUIS_CREATION, true", + "AUJOURD_HUI, false", + "CE_MOIS, false", + "CETTE_SEMAINE, false" + }) + @DisplayName("isPeriodeLongue - toutes les périodes") + void testIsPeriodeLongue(PeriodeAnalyse periode, boolean expected) { + assertThat(periode.isPeriodeLongue()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isPersonnalisable") + class IsPersonnalisableTests { + + @Test + @DisplayName("isPersonnalisable - PERIODE_PERSONNALISEE") + void testIsPersonnalisableTrue() { + assertThat(PeriodeAnalyse.PERIODE_PERSONNALISEE.isPersonnalisable()).isTrue(); + } + + @ParameterizedTest + @CsvSource({ + "AUJOURD_HUI", + "CE_MOIS", + "CETTE_ANNEE", + "DEPUIS_CREATION" + }) + @DisplayName("isPersonnalisable - autres périodes") + void testIsPersonnalisableFalse(PeriodeAnalyse periode) { + assertThat(periode.isPersonnalisable()).isFalse(); + } + } + + @Nested + @DisplayName("Tests getIntervalleRegroupement") + class GetIntervalleRegroupementTests { + + @ParameterizedTest + @CsvSource({ + "AUJOURD_HUI, heure", + "HIER, heure", + "CETTE_SEMAINE, jour", + "SEMAINE_DERNIERE, jour", + "SEPT_DERNIERS_JOURS, jour", + "CE_MOIS, jour", + "MOIS_DERNIER, jour", + "TRENTE_DERNIERS_JOURS, jour", + "TROIS_DERNIERS_MOIS, semaine", + "SIX_DERNIERS_MOIS, semaine", + "QUATRE_VINGT_DIX_DERNIERS_JOURS, semaine", + "CETTE_ANNEE, mois", + "ANNEE_DERNIERE, mois", + "DEUX_DERNIERES_ANNEES, mois", + "DEPUIS_CREATION, annee", + "PERIODE_PERSONNALISEE, jour" + }) + @DisplayName("getIntervalleRegroupement - toutes les périodes") + void testGetIntervalleRegroupement(PeriodeAnalyse periode, String expected) { + assertThat(periode.getIntervalleRegroupement()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests getFormatDate") + class GetFormatDateTests { + + @ParameterizedTest + @CsvSource({ + "AUJOURD_HUI, HH:mm", + "HIER, HH:mm", + "CETTE_SEMAINE, dd/MM", + "SEMAINE_DERNIERE, dd/MM", + "SEPT_DERNIERS_JOURS, dd/MM", + "CE_MOIS, dd/MM", + "MOIS_DERNIER, dd/MM", + "TRENTE_DERNIERS_JOURS, dd/MM", + "TROIS_DERNIERS_MOIS, dd/MM", + "SIX_DERNIERS_MOIS, dd/MM", + "QUATRE_VINGT_DIX_DERNIERS_JOURS, dd/MM", + "CETTE_ANNEE, MM/yyyy", + "ANNEE_DERNIERE, MM/yyyy", + "DEUX_DERNIERES_ANNEES, yyyy", + "DEPUIS_CREATION, yyyy", + "PERIODE_PERSONNALISEE, dd/MM/yyyy" + }) + @DisplayName("getFormatDate - toutes les périodes") + void testGetFormatDate(PeriodeAnalyse periode, String expected) { + assertThat(periode.getFormatDate()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests valeurs spécifiques") + class ValeursSpecifiquesTests { + + @Test + @DisplayName("Test duree et unite pour toutes les périodes") + void testDureeEtUnite() { + assertThat(PeriodeAnalyse.AUJOURD_HUI.getDuree()).isEqualTo(1); + assertThat(PeriodeAnalyse.AUJOURD_HUI.getUnite()).isEqualTo(ChronoUnit.DAYS); + + assertThat(PeriodeAnalyse.CE_MOIS.getDuree()).isEqualTo(1); + assertThat(PeriodeAnalyse.CE_MOIS.getUnite()).isEqualTo(ChronoUnit.MONTHS); + + assertThat(PeriodeAnalyse.CETTE_ANNEE.getDuree()).isEqualTo(1); + assertThat(PeriodeAnalyse.CETTE_ANNEE.getUnite()).isEqualTo(ChronoUnit.YEARS); + + assertThat(PeriodeAnalyse.DEPUIS_CREATION.getDuree()).isEqualTo(0); + assertThat(PeriodeAnalyse.DEPUIS_CREATION.getUnite()).isEqualTo(ChronoUnit.FOREVER); + + assertThat(PeriodeAnalyse.PERIODE_PERSONNALISEE.getDuree()).isEqualTo(0); + assertThat(PeriodeAnalyse.PERIODE_PERSONNALISEE.getUnite()).isEqualTo(ChronoUnit.DAYS); + } + + @Test + @DisplayName("Test code pour toutes les périodes") + void testCode() { + assertThat(PeriodeAnalyse.AUJOURD_HUI.getCode()).isEqualTo("today"); + assertThat(PeriodeAnalyse.HIER.getCode()).isEqualTo("yesterday"); + assertThat(PeriodeAnalyse.CE_MOIS.getCode()).isEqualTo("this_month"); + assertThat(PeriodeAnalyse.DEPUIS_CREATION.getCode()).isEqualTo("since_creation"); + assertThat(PeriodeAnalyse.PERIODE_PERSONNALISEE.getCode()).isEqualTo("custom"); + } + + @Test + @DisplayName("Test toutes les périodes - couverture complète") + void testToutesLesPeriodes() { + // Test toutes les périodes pour s'assurer qu'elles sont toutes couvertes + for (PeriodeAnalyse periode : PeriodeAnalyse.values()) { + assertThat(periode.getDateDebut()).isNotNull(); + assertThat(periode.getDateFin()).isNotNull(); + assertThat(periode.getIntervalleRegroupement()).isNotNull().isNotEmpty(); + assertThat(periode.getFormatDate()).isNotNull().isNotEmpty(); + } + } + + @Test + @DisplayName("Test getDateDebut - cas default avec différentes unités") + void testGetDateDebutDefault() { + // Test que le default fonctionne pour toutes les périodes qui l'utilisent + LocalDateTime debutTroisMois = PeriodeAnalyse.TROIS_DERNIERS_MOIS.getDateDebut(); + LocalDateTime debutSixMois = PeriodeAnalyse.SIX_DERNIERS_MOIS.getDateDebut(); + LocalDateTime debutSeptJours = PeriodeAnalyse.SEPT_DERNIERS_JOURS.getDateDebut(); + LocalDateTime debutTrenteJours = PeriodeAnalyse.TRENTE_DERNIERS_JOURS.getDateDebut(); + LocalDateTime debutQuatreVingtDixJours = PeriodeAnalyse.QUATRE_VINGT_DIX_DERNIERS_JOURS.getDateDebut(); + LocalDateTime debutDeuxAnnees = PeriodeAnalyse.DEUX_DERNIERES_ANNEES.getDateDebut(); + + assertThat(debutTroisMois).isBefore(LocalDateTime.now()); + assertThat(debutSixMois).isBefore(LocalDateTime.now()); + assertThat(debutSeptJours).isBefore(LocalDateTime.now()); + assertThat(debutTrenteJours).isBefore(LocalDateTime.now()); + assertThat(debutQuatreVingtDixJours).isBefore(LocalDateTime.now()); + assertThat(debutDeuxAnnees).isBefore(LocalDateTime.now()); + + // Vérifie que les dates sont cohérentes avec les durées + // Plus la durée est grande, plus la date de début est dans le passé + assertThat(debutSixMois).isBefore(debutTroisMois); + assertThat(debutTrenteJours).isBefore(debutSeptJours); + } + + @Test + @DisplayName("Test getDateFin - cas default") + void testGetDateFinDefault() { + // Test que le default fonctionne pour toutes les périodes qui l'utilisent + LocalDateTime finTroisMois = PeriodeAnalyse.TROIS_DERNIERS_MOIS.getDateFin(); + LocalDateTime finSixMois = PeriodeAnalyse.SIX_DERNIERS_MOIS.getDateFin(); + LocalDateTime finSeptJours = PeriodeAnalyse.SEPT_DERNIERS_JOURS.getDateFin(); + LocalDateTime finTrenteJours = PeriodeAnalyse.TRENTE_DERNIERS_JOURS.getDateFin(); + LocalDateTime finQuatreVingtDixJours = PeriodeAnalyse.QUATRE_VINGT_DIX_DERNIERS_JOURS.getDateFin(); + LocalDateTime finDeuxAnnees = PeriodeAnalyse.DEUX_DERNIERES_ANNEES.getDateFin(); + + assertThat(finTroisMois.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); + assertThat(finTroisMois.getHour()).isEqualTo(23); + assertThat(finTroisMois.getMinute()).isEqualTo(59); + assertThat(finSixMois.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); + assertThat(finSeptJours.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); + assertThat(finTrenteJours.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); + assertThat(finQuatreVingtDixJours.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); + assertThat(finDeuxAnnees.toLocalDate()).isEqualTo(LocalDateTime.now().toLocalDate()); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/analytics/TypeMetriqueTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/analytics/TypeMetriqueTest.java index a97c05f..8c92fe4 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/analytics/TypeMetriqueTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/analytics/TypeMetriqueTest.java @@ -1,246 +1,246 @@ -package dev.lions.unionflow.server.api.enums.analytics; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.lang.reflect.Field; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour TypeMetrique") -class TypeMetriqueTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(TypeMetrique.NOMBRE_MEMBRES_ACTIFS).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - TypeMetrique[] values = TypeMetrique.values(); - assertThat(values).hasSize(35); - } - - @ParameterizedTest - @EnumSource(TypeMetrique.class) - @DisplayName("Test getters de base pour toutes les valeurs") - void testGettersBase(TypeMetrique metrique) { - assertThat(metrique.getLibelle()).isNotNull().isNotEmpty(); - assertThat(metrique.getCategorie()).isNotNull().isNotEmpty(); - assertThat(metrique.getTypeValeur()).isNotNull().isNotEmpty(); - } - } - - @Nested - @DisplayName("Tests isFinanciere") - class IsFinanciereTests { - - @ParameterizedTest - @CsvSource({ - "TOTAL_COTISATIONS_COLLECTEES, true", - "COTISATIONS_EN_ATTENTE, true", - "TAUX_RECOUVREMENT_COTISATIONS, true", - "NOMBRE_MEMBRES_ACTIFS, false", - "NOMBRE_EVENEMENTS_ORGANISES, false" - }) - @DisplayName("isFinanciere - métriques financières") - void testIsFinanciere(TypeMetrique metrique, Boolean expected) { - assertThat(metrique.isFinanciere()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isPourcentage") - class IsPourcentageTests { - - @ParameterizedTest - @CsvSource({ - "TAUX_CROISSANCE_MEMBRES, true", - "TAUX_RECOUVREMENT_COTISATIONS, true", - "TAUX_PARTICIPATION_EVENEMENTS, true", - "NOMBRE_MEMBRES_ACTIFS, false", - "TOTAL_COTISATIONS_COLLECTEES, false" - }) - @DisplayName("isPourcentage - métriques en pourcentage") - void testIsPourcentage(TypeMetrique metrique, Boolean expected) { - assertThat(metrique.isPourcentage()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isCompteur") - class IsCompteurTests { - - @ParameterizedTest - @CsvSource({ - "NOMBRE_MEMBRES_ACTIFS, true", - "NOMBRE_EVENEMENTS_ORGANISES, true", - "NOMBRE_DEMANDES_AIDE, true", - "TAUX_CROISSANCE_MEMBRES, false", - "TOTAL_COTISATIONS_COLLECTEES, false" - }) - @DisplayName("isCompteur - métriques compteurs") - void testIsCompteur(TypeMetrique metrique, Boolean expected) { - assertThat(metrique.isCompteur()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests getUnite") - class GetUniteTests { - - @ParameterizedTest - @CsvSource({ - "TAUX_CROISSANCE_MEMBRES, %", - "TOTAL_COTISATIONS_COLLECTEES, XOF", - "DELAI_TRAITEMENT_DEMANDES, jours", - "UTILISATION_STOCKAGE, MB", - "FREQUENCE_UTILISATION_APP, /jour", - "NPS_SATISFACTION, /10", - "NOMBRE_MEMBRES_ACTIFS," - }) - @DisplayName("getUnite - toutes les unités") - void testGetUnite(TypeMetrique metrique, String expected) { - if (expected == null || expected.isEmpty()) { - assertThat(metrique.getUnite()).isEmpty(); - } else { - assertThat(metrique.getUnite()).isEqualTo(expected); - } - } - } - - @Nested - @DisplayName("Tests getIcone") - class GetIconeTests { - - @ParameterizedTest - @CsvSource({ - "NOMBRE_MEMBRES_ACTIFS, people", - "TOTAL_COTISATIONS_COLLECTEES, attach_money", - "NOMBRE_EVENEMENTS_ORGANISES, event", - "NOMBRE_DEMANDES_AIDE, favorite", - "TAUX_CONNEXION_MOBILE, trending_up", - "NOMBRE_ORGANISATIONS_ACTIVES, business", - "TEMPS_REPONSE_API, settings" - }) - @DisplayName("getIcone - toutes les icônes") - void testGetIcone(TypeMetrique metrique, String expected) { - assertThat(metrique.getIcone()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests getCouleur") - class GetCouleurTests { - - @ParameterizedTest - @CsvSource({ - "NOMBRE_MEMBRES_ACTIFS, #2196F3", - "TOTAL_COTISATIONS_COLLECTEES, #4CAF50", - "NOMBRE_EVENEMENTS_ORGANISES, #FF9800", - "NOMBRE_DEMANDES_AIDE, #E91E63", - "TAUX_CONNEXION_MOBILE, #9C27B0", - "NOMBRE_ORGANISATIONS_ACTIVES, #607D8B", - "TEMPS_REPONSE_API, #795548" - }) - @DisplayName("getCouleur - toutes les couleurs") - void testGetCouleur(TypeMetrique metrique, String expected) { - assertThat(metrique.getCouleur()).isEqualTo(expected); - } - - @Test - @DisplayName("getUnite - cas default (typeValeur non reconnu)") - void testGetUniteDefault() { - // Test les métriques avec typeValeur qui tombent dans le default (count, average, distribution, trend) - assertThat(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getUnite()).isEmpty(); // count -> default - assertThat(TypeMetrique.NOMBRE_MEMBRES_INACTIFS.getUnite()).isEmpty(); // count -> default - assertThat(TypeMetrique.MOYENNE_AGE_MEMBRES.getUnite()).isEmpty(); // average -> default - assertThat(TypeMetrique.MOYENNE_COTISATION_MEMBRE.getUnite()).isEmpty(); // average -> default - assertThat(TypeMetrique.MOYENNE_PARTICIPANTS_EVENEMENT.getUnite()).isEmpty(); // average -> default - assertThat(TypeMetrique.MOYENNE_MEMBRES_PAR_ORGANISATION.getUnite()).isEmpty(); // average -> default - assertThat(TypeMetrique.REPARTITION_GENRE_MEMBRES.getUnite()).isEmpty(); // distribution -> default - assertThat(TypeMetrique.EVOLUTION_REVENUS_MENSUELLE.getUnite()).isEmpty(); // trend -> default - - // Test aussi les autres métriques avec count - assertThat(TypeMetrique.NOMBRE_EVENEMENTS_ORGANISES.getUnite()).isEmpty(); - assertThat(TypeMetrique.EVENEMENTS_ANNULES.getUnite()).isEmpty(); - assertThat(TypeMetrique.NOMBRE_DEMANDES_AIDE.getUnite()).isEmpty(); - assertThat(TypeMetrique.ACTIONS_UTILISATEUR_JOUR.getUnite()).isEmpty(); - assertThat(TypeMetrique.NOMBRE_ORGANISATIONS_ACTIVES.getUnite()).isEmpty(); - assertThat(TypeMetrique.ORGANISATIONS_PREMIUM.getUnite()).isEmpty(); - assertThat(TypeMetrique.NOMBRE_ERREURS_SYSTEME.getUnite()).isEmpty(); - } - - @Test - @DisplayName("Test toutes les métriques - couverture complète") - void testToutesLesMetriques() { - // Test toutes les métriques pour s'assurer qu'elles sont toutes couvertes - for (TypeMetrique metrique : TypeMetrique.values()) { - assertThat(metrique.getLibelle()).isNotNull().isNotEmpty(); - assertThat(metrique.getCategorie()).isNotNull().isNotEmpty(); - assertThat(metrique.getTypeValeur()).isNotNull().isNotEmpty(); - assertThat(metrique.getUnite()).isNotNull(); - assertThat(metrique.getIcone()).isNotNull().isNotEmpty(); - assertThat(metrique.getCouleur()).isNotNull().isNotEmpty(); - } - } - - @Test - @DisplayName("getIcone - cas default (catégorie non reconnue)") - void testGetIconeDefault() throws Exception { - // Utiliser la réflexion pour modifier temporairement la catégorie - // et tester le cas default - TypeMetrique metrique = TypeMetrique.NOMBRE_MEMBRES_ACTIFS; - String categorieOriginale = metrique.getCategorie(); - - try { - // Modifier la catégorie via réflexion pour une catégorie non reconnue - Field categorieField = TypeMetrique.class.getDeclaredField("categorie"); - categorieField.setAccessible(true); - categorieField.set(metrique, "categorie_inconnue"); - - // Tester que le default retourne "analytics" - assertThat(metrique.getIcone()).isEqualTo("analytics"); - } finally { - // Restaurer la valeur originale - Field categorieField = TypeMetrique.class.getDeclaredField("categorie"); - categorieField.setAccessible(true); - categorieField.set(metrique, categorieOriginale); - } - } - - @Test - @DisplayName("getCouleur - cas default (catégorie non reconnue)") - void testGetCouleurDefault() throws Exception { - // Utiliser la réflexion pour modifier temporairement la catégorie - // et tester le cas default - TypeMetrique metrique = TypeMetrique.NOMBRE_MEMBRES_ACTIFS; - String categorieOriginale = metrique.getCategorie(); - - try { - // Modifier la catégorie via réflexion pour une catégorie non reconnue - Field categorieField = TypeMetrique.class.getDeclaredField("categorie"); - categorieField.setAccessible(true); - categorieField.set(metrique, "categorie_inconnue"); - - // Tester que le default retourne "#757575" - assertThat(metrique.getCouleur()).isEqualTo("#757575"); - } finally { - // Restaurer la valeur originale - Field categorieField = TypeMetrique.class.getDeclaredField("categorie"); - categorieField.setAccessible(true); - categorieField.set(metrique, categorieOriginale); - } - } - } -} - +package dev.lions.unionflow.server.api.enums.analytics; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.lang.reflect.Field; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour TypeMetrique") +class TypeMetriqueTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(TypeMetrique.NOMBRE_MEMBRES_ACTIFS).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + TypeMetrique[] values = TypeMetrique.values(); + assertThat(values).hasSize(35); + } + + @ParameterizedTest + @EnumSource(TypeMetrique.class) + @DisplayName("Test getters de base pour toutes les valeurs") + void testGettersBase(TypeMetrique metrique) { + assertThat(metrique.getLibelle()).isNotNull().isNotEmpty(); + assertThat(metrique.getCategorie()).isNotNull().isNotEmpty(); + assertThat(metrique.getTypeValeur()).isNotNull().isNotEmpty(); + } + } + + @Nested + @DisplayName("Tests isFinanciere") + class IsFinanciereTests { + + @ParameterizedTest + @CsvSource({ + "TOTAL_COTISATIONS_COLLECTEES, true", + "COTISATIONS_EN_ATTENTE, true", + "TAUX_RECOUVREMENT_COTISATIONS, true", + "NOMBRE_MEMBRES_ACTIFS, false", + "NOMBRE_EVENEMENTS_ORGANISES, false" + }) + @DisplayName("isFinanciere - métriques financières") + void testIsFinanciere(TypeMetrique metrique, Boolean expected) { + assertThat(metrique.isFinanciere()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isPourcentage") + class IsPourcentageTests { + + @ParameterizedTest + @CsvSource({ + "TAUX_CROISSANCE_MEMBRES, true", + "TAUX_RECOUVREMENT_COTISATIONS, true", + "TAUX_PARTICIPATION_EVENEMENTS, true", + "NOMBRE_MEMBRES_ACTIFS, false", + "TOTAL_COTISATIONS_COLLECTEES, false" + }) + @DisplayName("isPourcentage - métriques en pourcentage") + void testIsPourcentage(TypeMetrique metrique, Boolean expected) { + assertThat(metrique.isPourcentage()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isCompteur") + class IsCompteurTests { + + @ParameterizedTest + @CsvSource({ + "NOMBRE_MEMBRES_ACTIFS, true", + "NOMBRE_EVENEMENTS_ORGANISES, true", + "NOMBRE_DEMANDES_AIDE, true", + "TAUX_CROISSANCE_MEMBRES, false", + "TOTAL_COTISATIONS_COLLECTEES, false" + }) + @DisplayName("isCompteur - métriques compteurs") + void testIsCompteur(TypeMetrique metrique, Boolean expected) { + assertThat(metrique.isCompteur()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests getUnite") + class GetUniteTests { + + @ParameterizedTest + @CsvSource({ + "TAUX_CROISSANCE_MEMBRES, %", + "TOTAL_COTISATIONS_COLLECTEES, XOF", + "DELAI_TRAITEMENT_DEMANDES, jours", + "UTILISATION_STOCKAGE, MB", + "FREQUENCE_UTILISATION_APP, /jour", + "NPS_SATISFACTION, /10", + "NOMBRE_MEMBRES_ACTIFS," + }) + @DisplayName("getUnite - toutes les unités") + void testGetUnite(TypeMetrique metrique, String expected) { + if (expected == null || expected.isEmpty()) { + assertThat(metrique.getUnite()).isEmpty(); + } else { + assertThat(metrique.getUnite()).isEqualTo(expected); + } + } + } + + @Nested + @DisplayName("Tests getIcone") + class GetIconeTests { + + @ParameterizedTest + @CsvSource({ + "NOMBRE_MEMBRES_ACTIFS, people", + "TOTAL_COTISATIONS_COLLECTEES, attach_money", + "NOMBRE_EVENEMENTS_ORGANISES, event", + "NOMBRE_DEMANDES_AIDE, favorite", + "TAUX_CONNEXION_MOBILE, trending_up", + "NOMBRE_ORGANISATIONS_ACTIVES, business", + "TEMPS_REPONSE_API, settings" + }) + @DisplayName("getIcone - toutes les icônes") + void testGetIcone(TypeMetrique metrique, String expected) { + assertThat(metrique.getIcone()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests getCouleur") + class GetCouleurTests { + + @ParameterizedTest + @CsvSource({ + "NOMBRE_MEMBRES_ACTIFS, #2196F3", + "TOTAL_COTISATIONS_COLLECTEES, #4CAF50", + "NOMBRE_EVENEMENTS_ORGANISES, #FF9800", + "NOMBRE_DEMANDES_AIDE, #E91E63", + "TAUX_CONNEXION_MOBILE, #9C27B0", + "NOMBRE_ORGANISATIONS_ACTIVES, #607D8B", + "TEMPS_REPONSE_API, #795548" + }) + @DisplayName("getCouleur - toutes les couleurs") + void testGetCouleur(TypeMetrique metrique, String expected) { + assertThat(metrique.getCouleur()).isEqualTo(expected); + } + + @Test + @DisplayName("getUnite - cas default (typeValeur non reconnu)") + void testGetUniteDefault() { + // Test les métriques avec typeValeur qui tombent dans le default (count, average, distribution, trend) + assertThat(TypeMetrique.NOMBRE_MEMBRES_ACTIFS.getUnite()).isEmpty(); // count -> default + assertThat(TypeMetrique.NOMBRE_MEMBRES_INACTIFS.getUnite()).isEmpty(); // count -> default + assertThat(TypeMetrique.MOYENNE_AGE_MEMBRES.getUnite()).isEmpty(); // average -> default + assertThat(TypeMetrique.MOYENNE_COTISATION_MEMBRE.getUnite()).isEmpty(); // average -> default + assertThat(TypeMetrique.MOYENNE_PARTICIPANTS_EVENEMENT.getUnite()).isEmpty(); // average -> default + assertThat(TypeMetrique.MOYENNE_MEMBRES_PAR_ORGANISATION.getUnite()).isEmpty(); // average -> default + assertThat(TypeMetrique.REPARTITION_GENRE_MEMBRES.getUnite()).isEmpty(); // distribution -> default + assertThat(TypeMetrique.EVOLUTION_REVENUS_MENSUELLE.getUnite()).isEmpty(); // trend -> default + + // Test aussi les autres métriques avec count + assertThat(TypeMetrique.NOMBRE_EVENEMENTS_ORGANISES.getUnite()).isEmpty(); + assertThat(TypeMetrique.EVENEMENTS_ANNULES.getUnite()).isEmpty(); + assertThat(TypeMetrique.NOMBRE_DEMANDES_AIDE.getUnite()).isEmpty(); + assertThat(TypeMetrique.ACTIONS_UTILISATEUR_JOUR.getUnite()).isEmpty(); + assertThat(TypeMetrique.NOMBRE_ORGANISATIONS_ACTIVES.getUnite()).isEmpty(); + assertThat(TypeMetrique.ORGANISATIONS_PREMIUM.getUnite()).isEmpty(); + assertThat(TypeMetrique.NOMBRE_ERREURS_SYSTEME.getUnite()).isEmpty(); + } + + @Test + @DisplayName("Test toutes les métriques - couverture complète") + void testToutesLesMetriques() { + // Test toutes les métriques pour s'assurer qu'elles sont toutes couvertes + for (TypeMetrique metrique : TypeMetrique.values()) { + assertThat(metrique.getLibelle()).isNotNull().isNotEmpty(); + assertThat(metrique.getCategorie()).isNotNull().isNotEmpty(); + assertThat(metrique.getTypeValeur()).isNotNull().isNotEmpty(); + assertThat(metrique.getUnite()).isNotNull(); + assertThat(metrique.getIcone()).isNotNull().isNotEmpty(); + assertThat(metrique.getCouleur()).isNotNull().isNotEmpty(); + } + } + + @Test + @DisplayName("getIcone - cas default (catégorie non reconnue)") + void testGetIconeDefault() throws Exception { + // Utiliser la réflexion pour modifier temporairement la catégorie + // et tester le cas default + TypeMetrique metrique = TypeMetrique.NOMBRE_MEMBRES_ACTIFS; + String categorieOriginale = metrique.getCategorie(); + + try { + // Modifier la catégorie via réflexion pour une catégorie non reconnue + Field categorieField = TypeMetrique.class.getDeclaredField("categorie"); + categorieField.setAccessible(true); + categorieField.set(metrique, "categorie_inconnue"); + + // Tester que le default retourne "analytics" + assertThat(metrique.getIcone()).isEqualTo("analytics"); + } finally { + // Restaurer la valeur originale + Field categorieField = TypeMetrique.class.getDeclaredField("categorie"); + categorieField.setAccessible(true); + categorieField.set(metrique, categorieOriginale); + } + } + + @Test + @DisplayName("getCouleur - cas default (catégorie non reconnue)") + void testGetCouleurDefault() throws Exception { + // Utiliser la réflexion pour modifier temporairement la catégorie + // et tester le cas default + TypeMetrique metrique = TypeMetrique.NOMBRE_MEMBRES_ACTIFS; + String categorieOriginale = metrique.getCategorie(); + + try { + // Modifier la catégorie via réflexion pour une catégorie non reconnue + Field categorieField = TypeMetrique.class.getDeclaredField("categorie"); + categorieField.setAccessible(true); + categorieField.set(metrique, "categorie_inconnue"); + + // Tester que le default retourne "#757575" + assertThat(metrique.getCouleur()).isEqualTo("#757575"); + } finally { + // Restaurer la valeur originale + Field categorieField = TypeMetrique.class.getDeclaredField("categorie"); + categorieField.setAccessible(true); + categorieField.set(metrique, categorieOriginale); + } + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/audit/PorteeAuditTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/audit/PorteeAuditTest.java index 7b00a39..8289ccd 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/audit/PorteeAuditTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/audit/PorteeAuditTest.java @@ -1,67 +1,67 @@ -package dev.lions.unionflow.server.api.enums.audit; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour PorteeAudit") -class PorteeAuditTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(PorteeAudit.ORGANISATION).isNotNull(); - assertThat(PorteeAudit.PLATEFORME).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - PorteeAudit[] values = PorteeAudit.values(); - assertThat(values).hasSize(2); - assertThat(values).containsExactly( - PorteeAudit.ORGANISATION, - PorteeAudit.PLATEFORME); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(PorteeAudit.valueOf("ORGANISATION")).isEqualTo(PorteeAudit.ORGANISATION); - assertThat(PorteeAudit.valueOf("PLATEFORME")).isEqualTo(PorteeAudit.PLATEFORME); - - assertThatThrownBy(() -> PorteeAudit.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(PorteeAudit.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(PorteeAudit portee) { - assertThat(portee.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle contient libellé attendu") - void testGetLibelleContenu() { - assertThat(PorteeAudit.ORGANISATION.getLibelle()).contains("organisation"); - assertThat(PorteeAudit.PLATEFORME.getLibelle()).contains("Super Admin"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(PorteeAudit.ORGANISATION.name()).isEqualTo("ORGANISATION"); - assertThat(PorteeAudit.PLATEFORME.name()).isEqualTo("PLATEFORME"); - } - } -} +package dev.lions.unionflow.server.api.enums.audit; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour PorteeAudit") +class PorteeAuditTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(PorteeAudit.ORGANISATION).isNotNull(); + assertThat(PorteeAudit.PLATEFORME).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + PorteeAudit[] values = PorteeAudit.values(); + assertThat(values).hasSize(2); + assertThat(values).containsExactly( + PorteeAudit.ORGANISATION, + PorteeAudit.PLATEFORME); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(PorteeAudit.valueOf("ORGANISATION")).isEqualTo(PorteeAudit.ORGANISATION); + assertThat(PorteeAudit.valueOf("PLATEFORME")).isEqualTo(PorteeAudit.PLATEFORME); + + assertThatThrownBy(() -> PorteeAudit.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(PorteeAudit.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(PorteeAudit portee) { + assertThat(portee.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle contient libellé attendu") + void testGetLibelleContenu() { + assertThat(PorteeAudit.ORGANISATION.getLibelle()).contains("organisation"); + assertThat(PorteeAudit.PLATEFORME.getLibelle()).contains("Super Admin"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(PorteeAudit.ORGANISATION.name()).isEqualTo("ORGANISATION"); + assertThat(PorteeAudit.PLATEFORME.name()).isEqualTo("PLATEFORME"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/ayantdroit/LienParenteTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/ayantdroit/LienParenteTest.java index 40fd89c..7e40625 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/ayantdroit/LienParenteTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/ayantdroit/LienParenteTest.java @@ -1,43 +1,43 @@ -package dev.lions.unionflow.server.api.enums.ayantdroit; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.Test; - -class LienParenteTest { - - @Test - void testValues() { - LienParente[] values = LienParente.values(); - - assertThat(values).hasSize(6); - assertThat(values).contains( - LienParente.CONJOINT, - LienParente.ENFANT, - LienParente.PARENT, - LienParente.FRATRIE, - LienParente.TUTEUR_LEGAL, - LienParente.AUTRE - ); - } - - @Test - void testValueOf() { - assertThat(LienParente.valueOf("CONJOINT")).isEqualTo(LienParente.CONJOINT); - assertThat(LienParente.valueOf("ENFANT")).isEqualTo(LienParente.ENFANT); - assertThat(LienParente.valueOf("PARENT")).isEqualTo(LienParente.PARENT); - assertThat(LienParente.valueOf("FRATRIE")).isEqualTo(LienParente.FRATRIE); - assertThat(LienParente.valueOf("TUTEUR_LEGAL")).isEqualTo(LienParente.TUTEUR_LEGAL); - assertThat(LienParente.valueOf("AUTRE")).isEqualTo(LienParente.AUTRE); - } - - @Test - void testGetLibelle() { - assertThat(LienParente.CONJOINT.getLibelle()).isEqualTo("Conjoint(e) légal(e)"); - assertThat(LienParente.ENFANT.getLibelle()).isEqualTo("Enfant"); - assertThat(LienParente.PARENT.getLibelle()).isEqualTo("Père ou Mère"); - assertThat(LienParente.FRATRIE.getLibelle()).isEqualTo("Frère ou Sœur"); - assertThat(LienParente.TUTEUR_LEGAL.getLibelle()).isEqualTo("Tuteur ou Tutrice légal(e)"); - assertThat(LienParente.AUTRE.getLibelle()).isEqualTo("Autre bénéficiaire désigné"); - } -} +package dev.lions.unionflow.server.api.enums.ayantdroit; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.Test; + +class LienParenteTest { + + @Test + void testValues() { + LienParente[] values = LienParente.values(); + + assertThat(values).hasSize(6); + assertThat(values).contains( + LienParente.CONJOINT, + LienParente.ENFANT, + LienParente.PARENT, + LienParente.FRATRIE, + LienParente.TUTEUR_LEGAL, + LienParente.AUTRE + ); + } + + @Test + void testValueOf() { + assertThat(LienParente.valueOf("CONJOINT")).isEqualTo(LienParente.CONJOINT); + assertThat(LienParente.valueOf("ENFANT")).isEqualTo(LienParente.ENFANT); + assertThat(LienParente.valueOf("PARENT")).isEqualTo(LienParente.PARENT); + assertThat(LienParente.valueOf("FRATRIE")).isEqualTo(LienParente.FRATRIE); + assertThat(LienParente.valueOf("TUTEUR_LEGAL")).isEqualTo(LienParente.TUTEUR_LEGAL); + assertThat(LienParente.valueOf("AUTRE")).isEqualTo(LienParente.AUTRE); + } + + @Test + void testGetLibelle() { + assertThat(LienParente.CONJOINT.getLibelle()).isEqualTo("Conjoint(e) légal(e)"); + assertThat(LienParente.ENFANT.getLibelle()).isEqualTo("Enfant"); + assertThat(LienParente.PARENT.getLibelle()).isEqualTo("Père ou Mère"); + assertThat(LienParente.FRATRIE.getLibelle()).isEqualTo("Frère ou Sœur"); + assertThat(LienParente.TUTEUR_LEGAL.getLibelle()).isEqualTo("Tuteur ou Tutrice légal(e)"); + assertThat(LienParente.AUTRE.getLibelle()).isEqualTo("Autre bénéficiaire désigné"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/ayantdroit/StatutAyantDroitTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/ayantdroit/StatutAyantDroitTest.java index 9ebcd04..56caa89 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/ayantdroit/StatutAyantDroitTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/ayantdroit/StatutAyantDroitTest.java @@ -1,79 +1,79 @@ -package dev.lions.unionflow.server.api.enums.ayantdroit; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutAyantDroit") -class StatutAyantDroitTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutAyantDroit.EN_ATTENTE).isNotNull(); - assertThat(StatutAyantDroit.ACTIF).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutAyantDroit[] values = StatutAyantDroit.values(); - assertThat(values).hasSize(6); - assertThat(values).containsExactly( - StatutAyantDroit.EN_ATTENTE, - StatutAyantDroit.ACTIF, - StatutAyantDroit.INACTIF, - StatutAyantDroit.REJETE, - StatutAyantDroit.DECEDE, - StatutAyantDroit.MAJORITE_ATTEINTE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(StatutAyantDroit.valueOf("EN_ATTENTE")).isEqualTo(StatutAyantDroit.EN_ATTENTE); - assertThat(StatutAyantDroit.valueOf("ACTIF")).isEqualTo(StatutAyantDroit.ACTIF); - assertThat(StatutAyantDroit.valueOf("INACTIF")).isEqualTo(StatutAyantDroit.INACTIF); - assertThat(StatutAyantDroit.valueOf("REJETE")).isEqualTo(StatutAyantDroit.REJETE); - assertThat(StatutAyantDroit.valueOf("DECEDE")).isEqualTo(StatutAyantDroit.DECEDE); - assertThat(StatutAyantDroit.valueOf("MAJORITE_ATTEINTE")).isEqualTo(StatutAyantDroit.MAJORITE_ATTEINTE); - - assertThatThrownBy(() -> StatutAyantDroit.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutAyantDroit.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutAyantDroit statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(StatutAyantDroit.EN_ATTENTE.getLibelle()).isEqualTo("En attente de validation documentaire"); - assertThat(StatutAyantDroit.ACTIF.getLibelle()).isEqualTo("Actif et couvert"); - assertThat(StatutAyantDroit.INACTIF.getLibelle()).isEqualTo("Inactif (Couverture suspendue)"); - assertThat(StatutAyantDroit.REJETE.getLibelle()).isEqualTo("Dossier rejeté"); - assertThat(StatutAyantDroit.DECEDE.getLibelle()).isEqualTo("Déclaré décédé"); - assertThat(StatutAyantDroit.MAJORITE_ATTEINTE.getLibelle()).isEqualTo("Majorité atteinte (Sortie du statut Enfant)"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(StatutAyantDroit.EN_ATTENTE.name()).isEqualTo("EN_ATTENTE"); - assertThat(StatutAyantDroit.MAJORITE_ATTEINTE.name()).isEqualTo("MAJORITE_ATTEINTE"); - } - } -} +package dev.lions.unionflow.server.api.enums.ayantdroit; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutAyantDroit") +class StatutAyantDroitTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutAyantDroit.EN_ATTENTE).isNotNull(); + assertThat(StatutAyantDroit.ACTIF).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutAyantDroit[] values = StatutAyantDroit.values(); + assertThat(values).hasSize(6); + assertThat(values).containsExactly( + StatutAyantDroit.EN_ATTENTE, + StatutAyantDroit.ACTIF, + StatutAyantDroit.INACTIF, + StatutAyantDroit.REJETE, + StatutAyantDroit.DECEDE, + StatutAyantDroit.MAJORITE_ATTEINTE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(StatutAyantDroit.valueOf("EN_ATTENTE")).isEqualTo(StatutAyantDroit.EN_ATTENTE); + assertThat(StatutAyantDroit.valueOf("ACTIF")).isEqualTo(StatutAyantDroit.ACTIF); + assertThat(StatutAyantDroit.valueOf("INACTIF")).isEqualTo(StatutAyantDroit.INACTIF); + assertThat(StatutAyantDroit.valueOf("REJETE")).isEqualTo(StatutAyantDroit.REJETE); + assertThat(StatutAyantDroit.valueOf("DECEDE")).isEqualTo(StatutAyantDroit.DECEDE); + assertThat(StatutAyantDroit.valueOf("MAJORITE_ATTEINTE")).isEqualTo(StatutAyantDroit.MAJORITE_ATTEINTE); + + assertThatThrownBy(() -> StatutAyantDroit.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutAyantDroit.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutAyantDroit statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(StatutAyantDroit.EN_ATTENTE.getLibelle()).isEqualTo("En attente de validation documentaire"); + assertThat(StatutAyantDroit.ACTIF.getLibelle()).isEqualTo("Actif et couvert"); + assertThat(StatutAyantDroit.INACTIF.getLibelle()).isEqualTo("Inactif (Couverture suspendue)"); + assertThat(StatutAyantDroit.REJETE.getLibelle()).isEqualTo("Dossier rejeté"); + assertThat(StatutAyantDroit.DECEDE.getLibelle()).isEqualTo("Déclaré décédé"); + assertThat(StatutAyantDroit.MAJORITE_ATTEINTE.getLibelle()).isEqualTo("Majorité atteinte (Sortie du statut Enfant)"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(StatutAyantDroit.EN_ATTENTE.name()).isEqualTo("EN_ATTENTE"); + assertThat(StatutAyantDroit.MAJORITE_ATTEINTE.name()).isEqualTo("MAJORITE_ATTEINTE"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/collectefonds/StatutCampagneCollecteTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/collectefonds/StatutCampagneCollecteTest.java index be1edf5..2e96184 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/collectefonds/StatutCampagneCollecteTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/collectefonds/StatutCampagneCollecteTest.java @@ -1,76 +1,76 @@ -package dev.lions.unionflow.server.api.enums.collectefonds; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutCampagneCollecte") -class StatutCampagneCollecteTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutCampagneCollecte.BROUILLON).isNotNull(); - assertThat(StatutCampagneCollecte.EN_COURS).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutCampagneCollecte[] values = StatutCampagneCollecte.values(); - assertThat(values).hasSize(5); - assertThat(values).containsExactly( - StatutCampagneCollecte.BROUILLON, - StatutCampagneCollecte.EN_COURS, - StatutCampagneCollecte.ATTEINTE, - StatutCampagneCollecte.EXPIREE, - StatutCampagneCollecte.SUSPENDUE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(StatutCampagneCollecte.valueOf("BROUILLON")).isEqualTo(StatutCampagneCollecte.BROUILLON); - assertThat(StatutCampagneCollecte.valueOf("EN_COURS")).isEqualTo(StatutCampagneCollecte.EN_COURS); - assertThat(StatutCampagneCollecte.valueOf("ATTEINTE")).isEqualTo(StatutCampagneCollecte.ATTEINTE); - assertThat(StatutCampagneCollecte.valueOf("EXPIREE")).isEqualTo(StatutCampagneCollecte.EXPIREE); - assertThat(StatutCampagneCollecte.valueOf("SUSPENDUE")).isEqualTo(StatutCampagneCollecte.SUSPENDUE); - - assertThatThrownBy(() -> StatutCampagneCollecte.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutCampagneCollecte.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutCampagneCollecte statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(StatutCampagneCollecte.BROUILLON.getLibelle()).isEqualTo("Paramétrage de la page de don en cours"); - assertThat(StatutCampagneCollecte.EN_COURS.getLibelle()).isEqualTo("Active et ouverte aux dons"); - assertThat(StatutCampagneCollecte.ATTEINTE.getLibelle()).isEqualTo("Objectif financier atteint (Optionnel de fermer)"); - assertThat(StatutCampagneCollecte.EXPIREE.getLibelle()).isEqualTo("Date de fin de campagne dépassée"); - assertThat(StatutCampagneCollecte.SUSPENDUE.getLibelle()).isEqualTo("Suspendue temporairement"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(StatutCampagneCollecte.BROUILLON.name()).isEqualTo("BROUILLON"); - assertThat(StatutCampagneCollecte.EN_COURS.name()).isEqualTo("EN_COURS"); - } - } -} +package dev.lions.unionflow.server.api.enums.collectefonds; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutCampagneCollecte") +class StatutCampagneCollecteTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutCampagneCollecte.BROUILLON).isNotNull(); + assertThat(StatutCampagneCollecte.EN_COURS).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutCampagneCollecte[] values = StatutCampagneCollecte.values(); + assertThat(values).hasSize(5); + assertThat(values).containsExactly( + StatutCampagneCollecte.BROUILLON, + StatutCampagneCollecte.EN_COURS, + StatutCampagneCollecte.ATTEINTE, + StatutCampagneCollecte.EXPIREE, + StatutCampagneCollecte.SUSPENDUE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(StatutCampagneCollecte.valueOf("BROUILLON")).isEqualTo(StatutCampagneCollecte.BROUILLON); + assertThat(StatutCampagneCollecte.valueOf("EN_COURS")).isEqualTo(StatutCampagneCollecte.EN_COURS); + assertThat(StatutCampagneCollecte.valueOf("ATTEINTE")).isEqualTo(StatutCampagneCollecte.ATTEINTE); + assertThat(StatutCampagneCollecte.valueOf("EXPIREE")).isEqualTo(StatutCampagneCollecte.EXPIREE); + assertThat(StatutCampagneCollecte.valueOf("SUSPENDUE")).isEqualTo(StatutCampagneCollecte.SUSPENDUE); + + assertThatThrownBy(() -> StatutCampagneCollecte.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutCampagneCollecte.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutCampagneCollecte statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(StatutCampagneCollecte.BROUILLON.getLibelle()).isEqualTo("Paramétrage de la page de don en cours"); + assertThat(StatutCampagneCollecte.EN_COURS.getLibelle()).isEqualTo("Active et ouverte aux dons"); + assertThat(StatutCampagneCollecte.ATTEINTE.getLibelle()).isEqualTo("Objectif financier atteint (Optionnel de fermer)"); + assertThat(StatutCampagneCollecte.EXPIREE.getLibelle()).isEqualTo("Date de fin de campagne dépassée"); + assertThat(StatutCampagneCollecte.SUSPENDUE.getLibelle()).isEqualTo("Suspendue temporairement"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(StatutCampagneCollecte.BROUILLON.name()).isEqualTo("BROUILLON"); + assertThat(StatutCampagneCollecte.EN_COURS.name()).isEqualTo("EN_COURS"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/communication/ConversationTypeTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/communication/ConversationTypeTest.java index 35423b2..1561ad7 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/communication/ConversationTypeTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/communication/ConversationTypeTest.java @@ -1,47 +1,47 @@ -package dev.lions.unionflow.server.api.enums.communication; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour ConversationType. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@DisplayName("Tests ConversationType") -class ConversationTypeTest { - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(ConversationType.values()).hasSize(4); - assertThat(ConversationType.values()) - .containsExactlyInAnyOrder( - ConversationType.INDIVIDUAL, - ConversationType.GROUP, - ConversationType.BROADCAST, - ConversationType.ANNOUNCEMENT); - } - - @Test - @DisplayName("valueOf doit retourner la bonne valeur") - void testValueOf() { - assertThat(ConversationType.valueOf("INDIVIDUAL")).isEqualTo(ConversationType.INDIVIDUAL); - assertThat(ConversationType.valueOf("GROUP")).isEqualTo(ConversationType.GROUP); - assertThat(ConversationType.valueOf("BROADCAST")).isEqualTo(ConversationType.BROADCAST); - assertThat(ConversationType.valueOf("ANNOUNCEMENT")).isEqualTo(ConversationType.ANNOUNCEMENT); - } - - @Test - @DisplayName("Les ordinals doivent être cohérents") - void testOrdinals() { - assertThat(ConversationType.INDIVIDUAL.ordinal()).isEqualTo(0); - assertThat(ConversationType.GROUP.ordinal()).isEqualTo(1); - assertThat(ConversationType.BROADCAST.ordinal()).isEqualTo(2); - assertThat(ConversationType.ANNOUNCEMENT.ordinal()).isEqualTo(3); - } -} +package dev.lions.unionflow.server.api.enums.communication; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour ConversationType. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@DisplayName("Tests ConversationType") +class ConversationTypeTest { + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(ConversationType.values()).hasSize(4); + assertThat(ConversationType.values()) + .containsExactlyInAnyOrder( + ConversationType.INDIVIDUAL, + ConversationType.GROUP, + ConversationType.BROADCAST, + ConversationType.ANNOUNCEMENT); + } + + @Test + @DisplayName("valueOf doit retourner la bonne valeur") + void testValueOf() { + assertThat(ConversationType.valueOf("INDIVIDUAL")).isEqualTo(ConversationType.INDIVIDUAL); + assertThat(ConversationType.valueOf("GROUP")).isEqualTo(ConversationType.GROUP); + assertThat(ConversationType.valueOf("BROADCAST")).isEqualTo(ConversationType.BROADCAST); + assertThat(ConversationType.valueOf("ANNOUNCEMENT")).isEqualTo(ConversationType.ANNOUNCEMENT); + } + + @Test + @DisplayName("Les ordinals doivent être cohérents") + void testOrdinals() { + assertThat(ConversationType.INDIVIDUAL.ordinal()).isEqualTo(0); + assertThat(ConversationType.GROUP.ordinal()).isEqualTo(1); + assertThat(ConversationType.BROADCAST.ordinal()).isEqualTo(2); + assertThat(ConversationType.ANNOUNCEMENT.ordinal()).isEqualTo(3); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/communication/MessagePriorityTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/communication/MessagePriorityTest.java index 5e36a82..ffd8fd6 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/communication/MessagePriorityTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/communication/MessagePriorityTest.java @@ -1,44 +1,44 @@ -package dev.lions.unionflow.server.api.enums.communication; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour MessagePriority. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@DisplayName("Tests MessagePriority") -class MessagePriorityTest { - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(MessagePriority.values()).hasSize(3); - assertThat(MessagePriority.values()) - .containsExactlyInAnyOrder( - MessagePriority.NORMAL, - MessagePriority.HIGH, - MessagePriority.URGENT); - } - - @Test - @DisplayName("valueOf doit retourner la bonne valeur") - void testValueOf() { - assertThat(MessagePriority.valueOf("NORMAL")).isEqualTo(MessagePriority.NORMAL); - assertThat(MessagePriority.valueOf("HIGH")).isEqualTo(MessagePriority.HIGH); - assertThat(MessagePriority.valueOf("URGENT")).isEqualTo(MessagePriority.URGENT); - } - - @Test - @DisplayName("Les ordinals doivent être cohérents") - void testOrdinals() { - assertThat(MessagePriority.NORMAL.ordinal()).isEqualTo(0); - assertThat(MessagePriority.HIGH.ordinal()).isEqualTo(1); - assertThat(MessagePriority.URGENT.ordinal()).isEqualTo(2); - } -} +package dev.lions.unionflow.server.api.enums.communication; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour MessagePriority. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@DisplayName("Tests MessagePriority") +class MessagePriorityTest { + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(MessagePriority.values()).hasSize(3); + assertThat(MessagePriority.values()) + .containsExactlyInAnyOrder( + MessagePriority.NORMAL, + MessagePriority.HIGH, + MessagePriority.URGENT); + } + + @Test + @DisplayName("valueOf doit retourner la bonne valeur") + void testValueOf() { + assertThat(MessagePriority.valueOf("NORMAL")).isEqualTo(MessagePriority.NORMAL); + assertThat(MessagePriority.valueOf("HIGH")).isEqualTo(MessagePriority.HIGH); + assertThat(MessagePriority.valueOf("URGENT")).isEqualTo(MessagePriority.URGENT); + } + + @Test + @DisplayName("Les ordinals doivent être cohérents") + void testOrdinals() { + assertThat(MessagePriority.NORMAL.ordinal()).isEqualTo(0); + assertThat(MessagePriority.HIGH.ordinal()).isEqualTo(1); + assertThat(MessagePriority.URGENT.ordinal()).isEqualTo(2); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/communication/MessageStatusTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/communication/MessageStatusTest.java index 7c0ecdd..18b0e1c 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/communication/MessageStatusTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/communication/MessageStatusTest.java @@ -1,47 +1,47 @@ -package dev.lions.unionflow.server.api.enums.communication; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour MessageStatus. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@DisplayName("Tests MessageStatus") -class MessageStatusTest { - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(MessageStatus.values()).hasSize(4); - assertThat(MessageStatus.values()) - .containsExactlyInAnyOrder( - MessageStatus.SENT, - MessageStatus.DELIVERED, - MessageStatus.READ, - MessageStatus.FAILED); - } - - @Test - @DisplayName("valueOf doit retourner la bonne valeur") - void testValueOf() { - assertThat(MessageStatus.valueOf("SENT")).isEqualTo(MessageStatus.SENT); - assertThat(MessageStatus.valueOf("DELIVERED")).isEqualTo(MessageStatus.DELIVERED); - assertThat(MessageStatus.valueOf("READ")).isEqualTo(MessageStatus.READ); - assertThat(MessageStatus.valueOf("FAILED")).isEqualTo(MessageStatus.FAILED); - } - - @Test - @DisplayName("Les ordinals doivent être cohérents") - void testOrdinals() { - assertThat(MessageStatus.SENT.ordinal()).isEqualTo(0); - assertThat(MessageStatus.DELIVERED.ordinal()).isEqualTo(1); - assertThat(MessageStatus.READ.ordinal()).isEqualTo(2); - assertThat(MessageStatus.FAILED.ordinal()).isEqualTo(3); - } -} +package dev.lions.unionflow.server.api.enums.communication; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour MessageStatus. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@DisplayName("Tests MessageStatus") +class MessageStatusTest { + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(MessageStatus.values()).hasSize(4); + assertThat(MessageStatus.values()) + .containsExactlyInAnyOrder( + MessageStatus.SENT, + MessageStatus.DELIVERED, + MessageStatus.READ, + MessageStatus.FAILED); + } + + @Test + @DisplayName("valueOf doit retourner la bonne valeur") + void testValueOf() { + assertThat(MessageStatus.valueOf("SENT")).isEqualTo(MessageStatus.SENT); + assertThat(MessageStatus.valueOf("DELIVERED")).isEqualTo(MessageStatus.DELIVERED); + assertThat(MessageStatus.valueOf("READ")).isEqualTo(MessageStatus.READ); + assertThat(MessageStatus.valueOf("FAILED")).isEqualTo(MessageStatus.FAILED); + } + + @Test + @DisplayName("Les ordinals doivent être cohérents") + void testOrdinals() { + assertThat(MessageStatus.SENT.ordinal()).isEqualTo(0); + assertThat(MessageStatus.DELIVERED.ordinal()).isEqualTo(1); + assertThat(MessageStatus.READ.ordinal()).isEqualTo(2); + assertThat(MessageStatus.FAILED.ordinal()).isEqualTo(3); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/communication/MessageTypeTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/communication/MessageTypeTest.java index 8a5ea74..905d1bc 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/communication/MessageTypeTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/communication/MessageTypeTest.java @@ -1,47 +1,47 @@ -package dev.lions.unionflow.server.api.enums.communication; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour MessageType. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2026-03-13 - */ -@DisplayName("Tests MessageType") -class MessageTypeTest { - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(MessageType.values()).hasSize(4); - assertThat(MessageType.values()) - .containsExactlyInAnyOrder( - MessageType.INDIVIDUAL, - MessageType.BROADCAST, - MessageType.TARGETED, - MessageType.SYSTEM); - } - - @Test - @DisplayName("valueOf doit retourner la bonne valeur") - void testValueOf() { - assertThat(MessageType.valueOf("INDIVIDUAL")).isEqualTo(MessageType.INDIVIDUAL); - assertThat(MessageType.valueOf("BROADCAST")).isEqualTo(MessageType.BROADCAST); - assertThat(MessageType.valueOf("TARGETED")).isEqualTo(MessageType.TARGETED); - assertThat(MessageType.valueOf("SYSTEM")).isEqualTo(MessageType.SYSTEM); - } - - @Test - @DisplayName("Les ordinals doivent être cohérents") - void testOrdinals() { - assertThat(MessageType.INDIVIDUAL.ordinal()).isEqualTo(0); - assertThat(MessageType.BROADCAST.ordinal()).isEqualTo(1); - assertThat(MessageType.TARGETED.ordinal()).isEqualTo(2); - assertThat(MessageType.SYSTEM.ordinal()).isEqualTo(3); - } -} +package dev.lions.unionflow.server.api.enums.communication; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour MessageType. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2026-03-13 + */ +@DisplayName("Tests MessageType") +class MessageTypeTest { + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(MessageType.values()).hasSize(4); + assertThat(MessageType.values()) + .containsExactlyInAnyOrder( + MessageType.INDIVIDUAL, + MessageType.BROADCAST, + MessageType.TARGETED, + MessageType.SYSTEM); + } + + @Test + @DisplayName("valueOf doit retourner la bonne valeur") + void testValueOf() { + assertThat(MessageType.valueOf("INDIVIDUAL")).isEqualTo(MessageType.INDIVIDUAL); + assertThat(MessageType.valueOf("BROADCAST")).isEqualTo(MessageType.BROADCAST); + assertThat(MessageType.valueOf("TARGETED")).isEqualTo(MessageType.TARGETED); + assertThat(MessageType.valueOf("SYSTEM")).isEqualTo(MessageType.SYSTEM); + } + + @Test + @DisplayName("Les ordinals doivent être cohérents") + void testOrdinals() { + assertThat(MessageType.INDIVIDUAL.ordinal()).isEqualTo(0); + assertThat(MessageType.BROADCAST.ordinal()).isEqualTo(1); + assertThat(MessageType.TARGETED.ordinal()).isEqualTo(2); + assertThat(MessageType.SYSTEM.ordinal()).isEqualTo(3); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeCompteComptableTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeCompteComptableTest.java index 286b3ed..132dce6 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeCompteComptableTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeCompteComptableTest.java @@ -1,36 +1,36 @@ -package dev.lions.unionflow.server.api.enums.comptabilite; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour TypeCompteComptable. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests TypeCompteComptable") -class TypeCompteComptableTest { - - @Test - @DisplayName("Tous les types de compte comptable doivent avoir un libellé") - void testTousLesTypesOntLibelle() { - for (TypeCompteComptable type : TypeCompteComptable.values()) { - assertThat(type.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(TypeCompteComptable.values().length).isGreaterThan(0); - for (TypeCompteComptable type : TypeCompteComptable.values()) { - assertThat(type).isNotNull(); - assertThat(type.name()).isNotBlank(); - } - } -} - +package dev.lions.unionflow.server.api.enums.comptabilite; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour TypeCompteComptable. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests TypeCompteComptable") +class TypeCompteComptableTest { + + @Test + @DisplayName("Tous les types de compte comptable doivent avoir un libellé") + void testTousLesTypesOntLibelle() { + for (TypeCompteComptable type : TypeCompteComptable.values()) { + assertThat(type.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(TypeCompteComptable.values().length).isGreaterThan(0); + for (TypeCompteComptable type : TypeCompteComptable.values()) { + assertThat(type).isNotNull(); + assertThat(type.name()).isNotBlank(); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeJournalComptableTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeJournalComptableTest.java index a7d9dc6..7003b65 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeJournalComptableTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/comptabilite/TypeJournalComptableTest.java @@ -1,36 +1,36 @@ -package dev.lions.unionflow.server.api.enums.comptabilite; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour TypeJournalComptable. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests TypeJournalComptable") -class TypeJournalComptableTest { - - @Test - @DisplayName("Tous les types de journal comptable doivent avoir un libellé") - void testTousLesTypesOntLibelle() { - for (TypeJournalComptable type : TypeJournalComptable.values()) { - assertThat(type.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(TypeJournalComptable.values().length).isGreaterThan(0); - for (TypeJournalComptable type : TypeJournalComptable.values()) { - assertThat(type).isNotNull(); - assertThat(type.name()).isNotBlank(); - } - } -} - +package dev.lions.unionflow.server.api.enums.comptabilite; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour TypeJournalComptable. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests TypeJournalComptable") +class TypeJournalComptableTest { + + @Test + @DisplayName("Tous les types de journal comptable doivent avoir un libellé") + void testTousLesTypesOntLibelle() { + for (TypeJournalComptable type : TypeJournalComptable.values()) { + assertThat(type.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(TypeJournalComptable.values().length).isGreaterThan(0); + for (TypeJournalComptable type : TypeJournalComptable.values()) { + assertThat(type).isNotNull(); + assertThat(type.name()).isNotBlank(); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/culte/TypeDonReligieuxTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/culte/TypeDonReligieuxTest.java index 6a31ba5..4d52234 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/culte/TypeDonReligieuxTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/culte/TypeDonReligieuxTest.java @@ -1,76 +1,76 @@ -package dev.lions.unionflow.server.api.enums.culte; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour TypeDonReligieux") -class TypeDonReligieuxTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(TypeDonReligieux.QUETE_ORDINAIRE).isNotNull(); - assertThat(TypeDonReligieux.DIME).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - TypeDonReligieux[] values = TypeDonReligieux.values(); - assertThat(values).hasSize(5); - assertThat(values).containsExactly( - TypeDonReligieux.QUETE_ORDINAIRE, - TypeDonReligieux.DIME, - TypeDonReligieux.ZAKAT, - TypeDonReligieux.OFFRANDE_SPECIALE, - TypeDonReligieux.INTENTION_PRIERE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(TypeDonReligieux.valueOf("QUETE_ORDINAIRE")).isEqualTo(TypeDonReligieux.QUETE_ORDINAIRE); - assertThat(TypeDonReligieux.valueOf("DIME")).isEqualTo(TypeDonReligieux.DIME); - assertThat(TypeDonReligieux.valueOf("ZAKAT")).isEqualTo(TypeDonReligieux.ZAKAT); - assertThat(TypeDonReligieux.valueOf("OFFRANDE_SPECIALE")).isEqualTo(TypeDonReligieux.OFFRANDE_SPECIALE); - assertThat(TypeDonReligieux.valueOf("INTENTION_PRIERE")).isEqualTo(TypeDonReligieux.INTENTION_PRIERE); - - assertThatThrownBy(() -> TypeDonReligieux.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(TypeDonReligieux.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(TypeDonReligieux type) { - assertThat(type.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(TypeDonReligieux.QUETE_ORDINAIRE.getLibelle()).isEqualTo("Quête ordinaire de l'office religieux"); - assertThat(TypeDonReligieux.DIME.getLibelle()).isEqualTo("Obligation ou Dîme régulière"); - assertThat(TypeDonReligieux.ZAKAT.getLibelle()).isEqualTo("Zakat (Aumône légale)"); - assertThat(TypeDonReligieux.OFFRANDE_SPECIALE.getLibelle()).isEqualTo("Offrande spéciale d'action de grâce"); - assertThat(TypeDonReligieux.INTENTION_PRIERE.getLibelle()).isEqualTo("Participation pour intention de prière"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(TypeDonReligieux.QUETE_ORDINAIRE.name()).isEqualTo("QUETE_ORDINAIRE"); - assertThat(TypeDonReligieux.INTENTION_PRIERE.name()).isEqualTo("INTENTION_PRIERE"); - } - } -} +package dev.lions.unionflow.server.api.enums.culte; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour TypeDonReligieux") +class TypeDonReligieuxTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(TypeDonReligieux.QUETE_ORDINAIRE).isNotNull(); + assertThat(TypeDonReligieux.DIME).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + TypeDonReligieux[] values = TypeDonReligieux.values(); + assertThat(values).hasSize(5); + assertThat(values).containsExactly( + TypeDonReligieux.QUETE_ORDINAIRE, + TypeDonReligieux.DIME, + TypeDonReligieux.ZAKAT, + TypeDonReligieux.OFFRANDE_SPECIALE, + TypeDonReligieux.INTENTION_PRIERE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(TypeDonReligieux.valueOf("QUETE_ORDINAIRE")).isEqualTo(TypeDonReligieux.QUETE_ORDINAIRE); + assertThat(TypeDonReligieux.valueOf("DIME")).isEqualTo(TypeDonReligieux.DIME); + assertThat(TypeDonReligieux.valueOf("ZAKAT")).isEqualTo(TypeDonReligieux.ZAKAT); + assertThat(TypeDonReligieux.valueOf("OFFRANDE_SPECIALE")).isEqualTo(TypeDonReligieux.OFFRANDE_SPECIALE); + assertThat(TypeDonReligieux.valueOf("INTENTION_PRIERE")).isEqualTo(TypeDonReligieux.INTENTION_PRIERE); + + assertThatThrownBy(() -> TypeDonReligieux.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(TypeDonReligieux.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(TypeDonReligieux type) { + assertThat(type.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(TypeDonReligieux.QUETE_ORDINAIRE.getLibelle()).isEqualTo("Quête ordinaire de l'office religieux"); + assertThat(TypeDonReligieux.DIME.getLibelle()).isEqualTo("Obligation ou Dîme régulière"); + assertThat(TypeDonReligieux.ZAKAT.getLibelle()).isEqualTo("Zakat (Aumône légale)"); + assertThat(TypeDonReligieux.OFFRANDE_SPECIALE.getLibelle()).isEqualTo("Offrande spéciale d'action de grâce"); + assertThat(TypeDonReligieux.INTENTION_PRIERE.getLibelle()).isEqualTo("Participation pour intention de prière"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(TypeDonReligieux.QUETE_ORDINAIRE.name()).isEqualTo("QUETE_ORDINAIRE"); + assertThat(TypeDonReligieux.INTENTION_PRIERE.name()).isEqualTo("INTENTION_PRIERE"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/document/TypeDocumentTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/document/TypeDocumentTest.java index 0622c6b..2d0305d 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/document/TypeDocumentTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/document/TypeDocumentTest.java @@ -1,36 +1,36 @@ -package dev.lions.unionflow.server.api.enums.document; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour TypeDocument. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests TypeDocument") -class TypeDocumentTest { - - @Test - @DisplayName("Tous les types de document doivent avoir un libellé") - void testTousLesTypesOntLibelle() { - for (TypeDocument type : TypeDocument.values()) { - assertThat(type.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(TypeDocument.values().length).isGreaterThan(0); - for (TypeDocument type : TypeDocument.values()) { - assertThat(type).isNotNull(); - assertThat(type.name()).isNotBlank(); - } - } -} - +package dev.lions.unionflow.server.api.enums.document; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour TypeDocument. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests TypeDocument") +class TypeDocumentTest { + + @Test + @DisplayName("Tous les types de document doivent avoir un libellé") + void testTousLesTypesOntLibelle() { + for (TypeDocument type : TypeDocument.values()) { + assertThat(type.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(TypeDocument.values().length).isGreaterThan(0); + for (TypeDocument type : TypeDocument.values()) { + assertThat(type).isNotNull(); + assertThat(type.name()).isNotBlank(); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/evenement/PrioriteEvenementTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/evenement/PrioriteEvenementTest.java index 7c6646d..9a7b0cc 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/evenement/PrioriteEvenementTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/evenement/PrioriteEvenementTest.java @@ -1,207 +1,207 @@ -package dev.lions.unionflow.server.api.enums.evenement; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.util.List; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour PrioriteEvenement") -class PrioriteEvenementTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(PrioriteEvenement.CRITIQUE).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - PrioriteEvenement[] values = PrioriteEvenement.values(); - assertThat(values).hasSize(4); - assertThat(values).containsExactly( - PrioriteEvenement.CRITIQUE, - PrioriteEvenement.HAUTE, - PrioriteEvenement.NORMALE, - PrioriteEvenement.BASSE); - } - - @ParameterizedTest - @EnumSource(PrioriteEvenement.class) - @DisplayName("Test getters de base pour toutes les valeurs") - void testGettersBase(PrioriteEvenement priorite) { - assertThat(priorite.getLibelle()).isNotNull().isNotEmpty(); - assertThat(priorite.getCode()).isNotNull().isNotEmpty(); - assertThat(priorite.getNiveau()).isBetween(1, 4); - assertThat(priorite.getDescription()).isNotNull().isNotEmpty(); - assertThat(priorite.getCouleur()).isNotNull().matches("#[0-9A-Fa-f]{6}"); - assertThat(priorite.getIcone()).isNotNull().isNotEmpty(); - } - } - - @Nested - @DisplayName("Tests isElevee") - class IsEleveeTests { - - @ParameterizedTest - @CsvSource({ - "CRITIQUE, true", - "HAUTE, true", - "NORMALE, false", - "BASSE, false" - }) - @DisplayName("isElevee - priorités élevées") - void testIsElevee(PrioriteEvenement priorite, Boolean expected) { - assertThat(priorite.isElevee()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isUrgente") - class IsUrgenteTests { - - @ParameterizedTest - @CsvSource({ - "CRITIQUE, true", - "HAUTE, true", - "NORMALE, false", - "BASSE, false" - }) - @DisplayName("isUrgente - priorités urgentes") - void testIsUrgente(PrioriteEvenement priorite, Boolean expected) { - assertThat(priorite.isUrgente()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isSuperieurA") - class IsSuperieurATests { - - @Test - @DisplayName("isSuperieurA - CRITIQUE supérieur à HAUTE") - void testIsSuperieurACritiqueVersHaute() { - assertThat(PrioriteEvenement.CRITIQUE.isSuperieurA(PrioriteEvenement.HAUTE)).isTrue(); - } - - @Test - @DisplayName("isSuperieurA - HAUTE supérieur à NORMALE") - void testIsSuperieurAHauteVersNormale() { - assertThat(PrioriteEvenement.HAUTE.isSuperieurA(PrioriteEvenement.NORMALE)).isTrue(); - } - - @Test - @DisplayName("isSuperieurA - NORMALE supérieur à BASSE") - void testIsSuperieurANormaleVersBasse() { - assertThat(PrioriteEvenement.NORMALE.isSuperieurA(PrioriteEvenement.BASSE)).isTrue(); - } - - @Test - @DisplayName("isSuperieurA - BASSE n'est pas supérieur à CRITIQUE") - void testIsSuperieurABasseVersCritique() { - assertThat(PrioriteEvenement.BASSE.isSuperieurA(PrioriteEvenement.CRITIQUE)).isFalse(); - } - - @Test - @DisplayName("isSuperieurA - même priorité retourne false") - void testIsSuperieurAMemePriorite() { - assertThat(PrioriteEvenement.CRITIQUE.isSuperieurA(PrioriteEvenement.CRITIQUE)).isFalse(); - assertThat(PrioriteEvenement.HAUTE.isSuperieurA(PrioriteEvenement.HAUTE)).isFalse(); - assertThat(PrioriteEvenement.NORMALE.isSuperieurA(PrioriteEvenement.NORMALE)).isFalse(); - assertThat(PrioriteEvenement.BASSE.isSuperieurA(PrioriteEvenement.BASSE)).isFalse(); - } - - @ParameterizedTest - @CsvSource({ - "CRITIQUE, HAUTE, true", - "CRITIQUE, NORMALE, true", - "CRITIQUE, BASSE, true", - "HAUTE, NORMALE, true", - "HAUTE, BASSE, true", - "NORMALE, BASSE, true", - "HAUTE, CRITIQUE, false", - "NORMALE, CRITIQUE, false", - "NORMALE, HAUTE, false", - "BASSE, CRITIQUE, false", - "BASSE, HAUTE, false", - "BASSE, NORMALE, false" - }) - @DisplayName("isSuperieurA - toutes les combinaisons") - void testIsSuperieurAToutesCombinaisons( - PrioriteEvenement priorite1, PrioriteEvenement priorite2, boolean expected) { - assertThat(priorite1.isSuperieurA(priorite2)).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isNotificationImmediate et isEscaladeAutomatique") - class IsNotificationImmediateEtEscaladeTests { - - @ParameterizedTest - @CsvSource({ - "CRITIQUE, true, true", - "HAUTE, true, false", - "NORMALE, false, false", - "BASSE, false, false" - }) - @DisplayName("isNotificationImmediate et isEscaladeAutomatique - toutes les priorités") - void testIsNotificationImmediateEtEscalade( - PrioriteEvenement priorite, boolean notificationImmediate, boolean escaladeAutomatique) { - assertThat(priorite.isNotificationImmediate()).isEqualTo(notificationImmediate); - assertThat(priorite.isEscaladeAutomatique()).isEqualTo(escaladeAutomatique); - } - } - - @Nested - @DisplayName("Tests méthodes statiques") - class MethodesStatiquesTests { - - @Test - @DisplayName("getPrioritesElevees - retourne les priorités élevées") - void testGetPrioritesElevees() { - List priorites = PrioriteEvenement.getPrioritesElevees(); - assertThat(priorites).hasSize(2); - assertThat(priorites).contains(PrioriteEvenement.CRITIQUE, PrioriteEvenement.HAUTE); - } - - @Test - @DisplayName("getPrioritesUrgentes - retourne les priorités urgentes") - void testGetPrioritesUrgentes() { - List priorites = PrioriteEvenement.getPrioritesUrgentes(); - assertThat(priorites).hasSize(2); - assertThat(priorites).contains(PrioriteEvenement.CRITIQUE, PrioriteEvenement.HAUTE); - } - - @ParameterizedTest - @CsvSource({ - "ASSEMBLEE_GENERALE, HAUTE", - "REUNION_BUREAU, HAUTE", - "ACTION_CARITATIVE, NORMALE", - "FORMATION, NORMALE", - "CONFERENCE, NORMALE", - "CEREMONIE, NORMALE", - "AUTRE, NORMALE", - "ACTIVITE_SOCIALE, BASSE", - "ATELIER, BASSE" - }) - @DisplayName("determinerPriorite - tous les types d'événements") - void testDeterminerPrioriteTousLesTypes( - TypeEvenementMetier type, PrioriteEvenement expected) { - assertThat(PrioriteEvenement.determinerPriorite(type)).isEqualTo(expected); - } - - @Test - @DisplayName("getDefaut - retourne NORMALE") - void testGetDefaut() { - assertThat(PrioriteEvenement.getDefaut()).isEqualTo(PrioriteEvenement.NORMALE); - } - } -} +package dev.lions.unionflow.server.api.enums.evenement; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.List; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour PrioriteEvenement") +class PrioriteEvenementTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(PrioriteEvenement.CRITIQUE).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + PrioriteEvenement[] values = PrioriteEvenement.values(); + assertThat(values).hasSize(4); + assertThat(values).containsExactly( + PrioriteEvenement.CRITIQUE, + PrioriteEvenement.HAUTE, + PrioriteEvenement.NORMALE, + PrioriteEvenement.BASSE); + } + + @ParameterizedTest + @EnumSource(PrioriteEvenement.class) + @DisplayName("Test getters de base pour toutes les valeurs") + void testGettersBase(PrioriteEvenement priorite) { + assertThat(priorite.getLibelle()).isNotNull().isNotEmpty(); + assertThat(priorite.getCode()).isNotNull().isNotEmpty(); + assertThat(priorite.getNiveau()).isBetween(1, 4); + assertThat(priorite.getDescription()).isNotNull().isNotEmpty(); + assertThat(priorite.getCouleur()).isNotNull().matches("#[0-9A-Fa-f]{6}"); + assertThat(priorite.getIcone()).isNotNull().isNotEmpty(); + } + } + + @Nested + @DisplayName("Tests isElevee") + class IsEleveeTests { + + @ParameterizedTest + @CsvSource({ + "CRITIQUE, true", + "HAUTE, true", + "NORMALE, false", + "BASSE, false" + }) + @DisplayName("isElevee - priorités élevées") + void testIsElevee(PrioriteEvenement priorite, Boolean expected) { + assertThat(priorite.isElevee()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isUrgente") + class IsUrgenteTests { + + @ParameterizedTest + @CsvSource({ + "CRITIQUE, true", + "HAUTE, true", + "NORMALE, false", + "BASSE, false" + }) + @DisplayName("isUrgente - priorités urgentes") + void testIsUrgente(PrioriteEvenement priorite, Boolean expected) { + assertThat(priorite.isUrgente()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isSuperieurA") + class IsSuperieurATests { + + @Test + @DisplayName("isSuperieurA - CRITIQUE supérieur à HAUTE") + void testIsSuperieurACritiqueVersHaute() { + assertThat(PrioriteEvenement.CRITIQUE.isSuperieurA(PrioriteEvenement.HAUTE)).isTrue(); + } + + @Test + @DisplayName("isSuperieurA - HAUTE supérieur à NORMALE") + void testIsSuperieurAHauteVersNormale() { + assertThat(PrioriteEvenement.HAUTE.isSuperieurA(PrioriteEvenement.NORMALE)).isTrue(); + } + + @Test + @DisplayName("isSuperieurA - NORMALE supérieur à BASSE") + void testIsSuperieurANormaleVersBasse() { + assertThat(PrioriteEvenement.NORMALE.isSuperieurA(PrioriteEvenement.BASSE)).isTrue(); + } + + @Test + @DisplayName("isSuperieurA - BASSE n'est pas supérieur à CRITIQUE") + void testIsSuperieurABasseVersCritique() { + assertThat(PrioriteEvenement.BASSE.isSuperieurA(PrioriteEvenement.CRITIQUE)).isFalse(); + } + + @Test + @DisplayName("isSuperieurA - même priorité retourne false") + void testIsSuperieurAMemePriorite() { + assertThat(PrioriteEvenement.CRITIQUE.isSuperieurA(PrioriteEvenement.CRITIQUE)).isFalse(); + assertThat(PrioriteEvenement.HAUTE.isSuperieurA(PrioriteEvenement.HAUTE)).isFalse(); + assertThat(PrioriteEvenement.NORMALE.isSuperieurA(PrioriteEvenement.NORMALE)).isFalse(); + assertThat(PrioriteEvenement.BASSE.isSuperieurA(PrioriteEvenement.BASSE)).isFalse(); + } + + @ParameterizedTest + @CsvSource({ + "CRITIQUE, HAUTE, true", + "CRITIQUE, NORMALE, true", + "CRITIQUE, BASSE, true", + "HAUTE, NORMALE, true", + "HAUTE, BASSE, true", + "NORMALE, BASSE, true", + "HAUTE, CRITIQUE, false", + "NORMALE, CRITIQUE, false", + "NORMALE, HAUTE, false", + "BASSE, CRITIQUE, false", + "BASSE, HAUTE, false", + "BASSE, NORMALE, false" + }) + @DisplayName("isSuperieurA - toutes les combinaisons") + void testIsSuperieurAToutesCombinaisons( + PrioriteEvenement priorite1, PrioriteEvenement priorite2, boolean expected) { + assertThat(priorite1.isSuperieurA(priorite2)).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isNotificationImmediate et isEscaladeAutomatique") + class IsNotificationImmediateEtEscaladeTests { + + @ParameterizedTest + @CsvSource({ + "CRITIQUE, true, true", + "HAUTE, true, false", + "NORMALE, false, false", + "BASSE, false, false" + }) + @DisplayName("isNotificationImmediate et isEscaladeAutomatique - toutes les priorités") + void testIsNotificationImmediateEtEscalade( + PrioriteEvenement priorite, boolean notificationImmediate, boolean escaladeAutomatique) { + assertThat(priorite.isNotificationImmediate()).isEqualTo(notificationImmediate); + assertThat(priorite.isEscaladeAutomatique()).isEqualTo(escaladeAutomatique); + } + } + + @Nested + @DisplayName("Tests méthodes statiques") + class MethodesStatiquesTests { + + @Test + @DisplayName("getPrioritesElevees - retourne les priorités élevées") + void testGetPrioritesElevees() { + List priorites = PrioriteEvenement.getPrioritesElevees(); + assertThat(priorites).hasSize(2); + assertThat(priorites).contains(PrioriteEvenement.CRITIQUE, PrioriteEvenement.HAUTE); + } + + @Test + @DisplayName("getPrioritesUrgentes - retourne les priorités urgentes") + void testGetPrioritesUrgentes() { + List priorites = PrioriteEvenement.getPrioritesUrgentes(); + assertThat(priorites).hasSize(2); + assertThat(priorites).contains(PrioriteEvenement.CRITIQUE, PrioriteEvenement.HAUTE); + } + + @ParameterizedTest + @CsvSource({ + "ASSEMBLEE_GENERALE, HAUTE", + "REUNION_BUREAU, HAUTE", + "ACTION_CARITATIVE, NORMALE", + "FORMATION, NORMALE", + "CONFERENCE, NORMALE", + "CEREMONIE, NORMALE", + "AUTRE, NORMALE", + "ACTIVITE_SOCIALE, BASSE", + "ATELIER, BASSE" + }) + @DisplayName("determinerPriorite - tous les types d'événements") + void testDeterminerPrioriteTousLesTypes( + TypeEvenementMetier type, PrioriteEvenement expected) { + assertThat(PrioriteEvenement.determinerPriorite(type)).isEqualTo(expected); + } + + @Test + @DisplayName("getDefaut - retourne NORMALE") + void testGetDefaut() { + assertThat(PrioriteEvenement.getDefaut()).isEqualTo(PrioriteEvenement.NORMALE); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/evenement/StatutEvenementTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/evenement/StatutEvenementTest.java index af525b9..7715720 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/evenement/StatutEvenementTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/evenement/StatutEvenementTest.java @@ -1,419 +1,419 @@ -package dev.lions.unionflow.server.api.enums.evenement; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.util.List; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutEvenement") -class StatutEvenementTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutEvenement.PLANIFIE).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutEvenement[] values = StatutEvenement.values(); - assertThat(values).hasSize(6); - assertThat(values).containsExactly( - StatutEvenement.PLANIFIE, - StatutEvenement.CONFIRME, - StatutEvenement.EN_COURS, - StatutEvenement.TERMINE, - StatutEvenement.ANNULE, - StatutEvenement.REPORTE); - } - - @ParameterizedTest - @EnumSource(StatutEvenement.class) - @DisplayName("Test getters de base pour toutes les valeurs") - void testGettersBase(StatutEvenement statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - assertThat(statut.getCode()).isNotNull().isNotEmpty(); - assertThat(statut.getDescription()).isNotNull().isNotEmpty(); - assertThat(statut.getCouleur()).isNotNull().matches("#[0-9A-Fa-f]{6}"); - assertThat(statut.getIcone()).isNotNull().isNotEmpty(); - } - } - - @Nested - @DisplayName("Tests permetModification") - class PermetModificationTests { - - @ParameterizedTest - @CsvSource({ - "PLANIFIE, true", - "CONFIRME, true", - "REPORTE, true", - "EN_COURS, false", - "TERMINE, false", - "ANNULE, false" - }) - @DisplayName("permetModification - statuts modifiables") - void testPermetModification(StatutEvenement statut, Boolean expected) { - assertThat(statut.permetModification()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests permetAnnulation") - class PermetAnnulationTests { - - @ParameterizedTest - @CsvSource({ - "PLANIFIE, true", - "CONFIRME, true", - "EN_COURS, true", - "REPORTE, true", - "TERMINE, false", - "ANNULE, false" - }) - @DisplayName("permetAnnulation - statuts annulables") - void testPermetAnnulation(StatutEvenement statut, Boolean expected) { - assertThat(statut.permetAnnulation()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isEnCours") - class IsEnCoursTests { - - @ParameterizedTest - @CsvSource({ - "EN_COURS, true", - "PLANIFIE, false", - "TERMINE, false" - }) - @DisplayName("isEnCours - statut en cours") - void testIsEnCours(StatutEvenement statut, Boolean expected) { - assertThat(statut.isEnCours()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isSucces") - class IsSuccesTests { - - @ParameterizedTest - @CsvSource({ - "TERMINE, true", - "PLANIFIE, false", - "ANNULE, false" - }) - @DisplayName("isSucces - statut de succès") - void testIsSucces(StatutEvenement statut, Boolean expected) { - assertThat(statut.isSucces()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests peutTransitionnerVers") - class PeutTransitionnerVersTests { - - @Test - @DisplayName("peutTransitionnerVers - même statut retourne false") - void testPeutTransitionnerVersMemeStatut() { - assertThat(StatutEvenement.PLANIFIE.peutTransitionnerVers(StatutEvenement.PLANIFIE)) - .isFalse(); - } - - @Test - @DisplayName("peutTransitionnerVers - statut final vers autre statut (sauf REPORTE)") - void testPeutTransitionnerVersStatutFinal() { - assertThat(StatutEvenement.TERMINE.peutTransitionnerVers(StatutEvenement.PLANIFIE)) - .isFalse(); - assertThat(StatutEvenement.ANNULE.peutTransitionnerVers(StatutEvenement.PLANIFIE)) - .isFalse(); - } - - @Test - @DisplayName("peutTransitionnerVers - statut final vers REPORTE") - void testPeutTransitionnerVersStatutFinalVersReporte() { - // estFinal && nouveauStatut != REPORTE retourne false - // Mais TERMINE.estFinal = true, donc la condition estFinal && nouveauStatut != REPORTE - // est true && true = true, donc retourne false - assertThat(StatutEvenement.TERMINE.peutTransitionnerVers(StatutEvenement.REPORTE)) - .isFalse(); - assertThat(StatutEvenement.ANNULE.peutTransitionnerVers(StatutEvenement.REPORTE)) - .isFalse(); - - // Test avec nouveauStatut == REPORTE : estFinal && nouveauStatut != REPORTE - // = true && false = false, donc on continue vers le switch - // Mais TERMINE et ANNULE ne sont pas dans le switch, donc default -> false - // Donc le résultat est toujours false - // Mais testons aussi avec un statut non-final vers REPORTE pour couvrir la branche - assertThat(StatutEvenement.PLANIFIE.peutTransitionnerVers(StatutEvenement.REPORTE)) - .isTrue(); - } - - @Test - @DisplayName("peutTransitionnerVers - REPORTE vers CONFIRME (non géré dans switch)") - void testPeutTransitionnerVersReporteVersConfirme() { - // REPORTE -> CONFIRME n'est pas dans le switch, donc retourne false (default) - assertThat(StatutEvenement.REPORTE.peutTransitionnerVers(StatutEvenement.CONFIRME)) - .isFalse(); - assertThat(StatutEvenement.REPORTE.peutTransitionnerVers(StatutEvenement.EN_COURS)) - .isFalse(); - assertThat(StatutEvenement.REPORTE.peutTransitionnerVers(StatutEvenement.TERMINE)) - .isFalse(); - } - - @ParameterizedTest - @CsvSource({ - "PLANIFIE, CONFIRME, true", - "PLANIFIE, ANNULE, true", - "PLANIFIE, REPORTE, true", - "PLANIFIE, EN_COURS, false", - "PLANIFIE, TERMINE, false", - "CONFIRME, EN_COURS, true", - "CONFIRME, ANNULE, true", - "CONFIRME, REPORTE, true", - "CONFIRME, PLANIFIE, false", - "CONFIRME, TERMINE, false", - "EN_COURS, TERMINE, true", - "EN_COURS, ANNULE, true", - "EN_COURS, PLANIFIE, false", - "EN_COURS, CONFIRME, false", - "REPORTE, PLANIFIE, true", - "REPORTE, ANNULE, true", - "REPORTE, CONFIRME, false", - "REPORTE, EN_COURS, false", - "TERMINE, ANNULE, false", - "ANNULE, TERMINE, false" - }) - @DisplayName("peutTransitionnerVers - toutes les transitions") - void testPeutTransitionnerVersToutesTransitions( - StatutEvenement source, StatutEvenement cible, boolean expected) { - assertThat(source.peutTransitionnerVers(cible)).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests getNiveauPriorite") - class GetNiveauPrioriteTests { - - @ParameterizedTest - @CsvSource({ - "EN_COURS, 1", - "CONFIRME, 2", - "PLANIFIE, 3", - "REPORTE, 4", - "TERMINE, 5", - "ANNULE, 6" - }) - @DisplayName("getNiveauPriorite - tous les niveaux") - void testGetNiveauPriorite(StatutEvenement statut, int expected) { - assertThat(statut.getNiveauPriorite()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests méthodes statiques") - class MethodesStatiquesTests { - - @Test - @DisplayName("getStatutsFinaux - retourne les statuts finaux") - void testGetStatutsFinaux() { - List statuts = StatutEvenement.getStatutsFinaux(); - assertThat(statuts).isNotEmpty(); - assertThat(statuts).contains(StatutEvenement.TERMINE, StatutEvenement.ANNULE); - } - - @Test - @DisplayName("getStatutsEchec - retourne les statuts d'échec") - void testGetStatutsEchec() { - List statuts = StatutEvenement.getStatutsEchec(); - assertThat(statuts).isNotEmpty(); - assertThat(statuts).contains(StatutEvenement.ANNULE); - } - - @Test - @DisplayName("getStatutsActifs - retourne les statuts actifs") - void testGetStatutsActifs() { - StatutEvenement[] statuts = StatutEvenement.getStatutsActifs(); - assertThat(statuts).hasSize(4); - assertThat(statuts).contains( - StatutEvenement.PLANIFIE, - StatutEvenement.CONFIRME, - StatutEvenement.EN_COURS, - StatutEvenement.REPORTE); - } - - @Test - @DisplayName("fromCode - trouve le statut par code") - void testFromCode() { - assertThat(StatutEvenement.fromCode("planned")).isEqualTo(StatutEvenement.PLANIFIE); - assertThat(StatutEvenement.fromCode("completed")).isEqualTo(StatutEvenement.TERMINE); - } - - @Test - @DisplayName("fromCode - code inexistant retourne null") - void testFromCodeInexistant() { - assertThat(StatutEvenement.fromCode("inexistant")).isNull(); - } - - @Test - @DisplayName("fromCode - code null retourne null") - void testFromCodeNull() { - assertThat(StatutEvenement.fromCode(null)).isNull(); - } - - @Test - @DisplayName("fromCode - code vide retourne null") - void testFromCodeVide() { - assertThat(StatutEvenement.fromCode("")).isNull(); - } - - @Test - @DisplayName("fromCode - code avec whitespace retourne null") - void testFromCodeWhitespace() { - assertThat(StatutEvenement.fromCode(" ")).isNull(); - } - - @Test - @DisplayName("fromCode - tous les codes") - void testFromCodeTousLesCodes() { - assertThat(StatutEvenement.fromCode("planned")).isEqualTo(StatutEvenement.PLANIFIE); - assertThat(StatutEvenement.fromCode("confirmed")).isEqualTo(StatutEvenement.CONFIRME); - assertThat(StatutEvenement.fromCode("ongoing")).isEqualTo(StatutEvenement.EN_COURS); - assertThat(StatutEvenement.fromCode("completed")).isEqualTo(StatutEvenement.TERMINE); - assertThat(StatutEvenement.fromCode("cancelled")).isEqualTo(StatutEvenement.ANNULE); - assertThat(StatutEvenement.fromCode("postponed")).isEqualTo(StatutEvenement.REPORTE); - } - - @Test - @DisplayName("fromLibelle - trouve le statut par libellé") - void testFromLibelle() { - assertThat(StatutEvenement.fromLibelle("Planifié")).isEqualTo(StatutEvenement.PLANIFIE); - assertThat(StatutEvenement.fromLibelle("Terminé")).isEqualTo(StatutEvenement.TERMINE); - } - - @Test - @DisplayName("fromLibelle - libellé inexistant retourne null") - void testFromLibelleInexistant() { - assertThat(StatutEvenement.fromLibelle("Inexistant")).isNull(); - } - - @Test - @DisplayName("fromLibelle - libellé null retourne null") - void testFromLibelleNull() { - assertThat(StatutEvenement.fromLibelle(null)).isNull(); - } - - @Test - @DisplayName("fromLibelle - libellé vide retourne null") - void testFromLibelleVide() { - assertThat(StatutEvenement.fromLibelle("")).isNull(); - } - - @Test - @DisplayName("fromLibelle - libellé avec whitespace retourne null") - void testFromLibelleWhitespace() { - assertThat(StatutEvenement.fromLibelle(" ")).isNull(); - } - - @Test - @DisplayName("fromLibelle - tous les libellés") - void testFromLibelleTousLesLibelles() { - assertThat(StatutEvenement.fromLibelle("Planifié")).isEqualTo(StatutEvenement.PLANIFIE); - assertThat(StatutEvenement.fromLibelle("Confirmé")).isEqualTo(StatutEvenement.CONFIRME); - assertThat(StatutEvenement.fromLibelle("En cours")).isEqualTo(StatutEvenement.EN_COURS); - assertThat(StatutEvenement.fromLibelle("Terminé")).isEqualTo(StatutEvenement.TERMINE); - assertThat(StatutEvenement.fromLibelle("Annulé")).isEqualTo(StatutEvenement.ANNULE); - assertThat(StatutEvenement.fromLibelle("Reporté")).isEqualTo(StatutEvenement.REPORTE); - } - } - - @Nested - @DisplayName("Tests getTransitionsPossibles") - class GetTransitionsPossiblesTests { - - @Test - @DisplayName("getTransitionsPossibles - PLANIFIE") - void testGetTransitionsPossiblesPlanifie() { - StatutEvenement[] transitions = StatutEvenement.PLANIFIE.getTransitionsPossibles(); - assertThat(transitions).containsExactly( - StatutEvenement.CONFIRME, - StatutEvenement.ANNULE, - StatutEvenement.REPORTE); - } - - @Test - @DisplayName("getTransitionsPossibles - CONFIRME") - void testGetTransitionsPossiblesConfirme() { - StatutEvenement[] transitions = StatutEvenement.CONFIRME.getTransitionsPossibles(); - assertThat(transitions).containsExactly( - StatutEvenement.EN_COURS, - StatutEvenement.ANNULE, - StatutEvenement.REPORTE); - } - - @Test - @DisplayName("getTransitionsPossibles - EN_COURS") - void testGetTransitionsPossiblesEnCours() { - StatutEvenement[] transitions = StatutEvenement.EN_COURS.getTransitionsPossibles(); - assertThat(transitions).containsExactly( - StatutEvenement.TERMINE, - StatutEvenement.ANNULE); - } - - @Test - @DisplayName("getTransitionsPossibles - REPORTE") - void testGetTransitionsPossiblesReporte() { - StatutEvenement[] transitions = StatutEvenement.REPORTE.getTransitionsPossibles(); - // Note: selon le code, REPORTE peut transitionner vers PLANIFIE, CONFIRME ou ANNULE - // Mais peutTransitionnerVers ne permet que PLANIFIE ou ANNULE - assertThat(transitions).containsExactly( - StatutEvenement.PLANIFIE, - StatutEvenement.CONFIRME, - StatutEvenement.ANNULE); - } - - @Test - @DisplayName("getTransitionsPossibles - TERMINE") - void testGetTransitionsPossiblesTermine() { - StatutEvenement[] transitions = StatutEvenement.TERMINE.getTransitionsPossibles(); - assertThat(transitions).isEmpty(); - } - - @Test - @DisplayName("getTransitionsPossibles - ANNULE") - void testGetTransitionsPossiblesAnnule() { - StatutEvenement[] transitions = StatutEvenement.ANNULE.getTransitionsPossibles(); - assertThat(transitions).isEmpty(); - } - } - - @Nested - @DisplayName("Tests isEstFinal et isEstEchec") - class IsEstFinalEtEchecTests { - - @ParameterizedTest - @CsvSource({ - "PLANIFIE, false, false", - "CONFIRME, false, false", - "EN_COURS, false, false", - "TERMINE, true, false", - "ANNULE, true, true", - "REPORTE, false, false" - }) - @DisplayName("isEstFinal et isEstEchec - tous les statuts") - void testIsEstFinalEtEchec(StatutEvenement statut, boolean estFinal, boolean estEchec) { - assertThat(statut.isEstFinal()).isEqualTo(estFinal); - assertThat(statut.isEstEchec()).isEqualTo(estEchec); - } - } -} +package dev.lions.unionflow.server.api.enums.evenement; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.List; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutEvenement") +class StatutEvenementTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutEvenement.PLANIFIE).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutEvenement[] values = StatutEvenement.values(); + assertThat(values).hasSize(6); + assertThat(values).containsExactly( + StatutEvenement.PLANIFIE, + StatutEvenement.CONFIRME, + StatutEvenement.EN_COURS, + StatutEvenement.TERMINE, + StatutEvenement.ANNULE, + StatutEvenement.REPORTE); + } + + @ParameterizedTest + @EnumSource(StatutEvenement.class) + @DisplayName("Test getters de base pour toutes les valeurs") + void testGettersBase(StatutEvenement statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + assertThat(statut.getCode()).isNotNull().isNotEmpty(); + assertThat(statut.getDescription()).isNotNull().isNotEmpty(); + assertThat(statut.getCouleur()).isNotNull().matches("#[0-9A-Fa-f]{6}"); + assertThat(statut.getIcone()).isNotNull().isNotEmpty(); + } + } + + @Nested + @DisplayName("Tests permetModification") + class PermetModificationTests { + + @ParameterizedTest + @CsvSource({ + "PLANIFIE, true", + "CONFIRME, true", + "REPORTE, true", + "EN_COURS, false", + "TERMINE, false", + "ANNULE, false" + }) + @DisplayName("permetModification - statuts modifiables") + void testPermetModification(StatutEvenement statut, Boolean expected) { + assertThat(statut.permetModification()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests permetAnnulation") + class PermetAnnulationTests { + + @ParameterizedTest + @CsvSource({ + "PLANIFIE, true", + "CONFIRME, true", + "EN_COURS, true", + "REPORTE, true", + "TERMINE, false", + "ANNULE, false" + }) + @DisplayName("permetAnnulation - statuts annulables") + void testPermetAnnulation(StatutEvenement statut, Boolean expected) { + assertThat(statut.permetAnnulation()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isEnCours") + class IsEnCoursTests { + + @ParameterizedTest + @CsvSource({ + "EN_COURS, true", + "PLANIFIE, false", + "TERMINE, false" + }) + @DisplayName("isEnCours - statut en cours") + void testIsEnCours(StatutEvenement statut, Boolean expected) { + assertThat(statut.isEnCours()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isSucces") + class IsSuccesTests { + + @ParameterizedTest + @CsvSource({ + "TERMINE, true", + "PLANIFIE, false", + "ANNULE, false" + }) + @DisplayName("isSucces - statut de succès") + void testIsSucces(StatutEvenement statut, Boolean expected) { + assertThat(statut.isSucces()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests peutTransitionnerVers") + class PeutTransitionnerVersTests { + + @Test + @DisplayName("peutTransitionnerVers - même statut retourne false") + void testPeutTransitionnerVersMemeStatut() { + assertThat(StatutEvenement.PLANIFIE.peutTransitionnerVers(StatutEvenement.PLANIFIE)) + .isFalse(); + } + + @Test + @DisplayName("peutTransitionnerVers - statut final vers autre statut (sauf REPORTE)") + void testPeutTransitionnerVersStatutFinal() { + assertThat(StatutEvenement.TERMINE.peutTransitionnerVers(StatutEvenement.PLANIFIE)) + .isFalse(); + assertThat(StatutEvenement.ANNULE.peutTransitionnerVers(StatutEvenement.PLANIFIE)) + .isFalse(); + } + + @Test + @DisplayName("peutTransitionnerVers - statut final vers REPORTE") + void testPeutTransitionnerVersStatutFinalVersReporte() { + // estFinal && nouveauStatut != REPORTE retourne false + // Mais TERMINE.estFinal = true, donc la condition estFinal && nouveauStatut != REPORTE + // est true && true = true, donc retourne false + assertThat(StatutEvenement.TERMINE.peutTransitionnerVers(StatutEvenement.REPORTE)) + .isFalse(); + assertThat(StatutEvenement.ANNULE.peutTransitionnerVers(StatutEvenement.REPORTE)) + .isFalse(); + + // Test avec nouveauStatut == REPORTE : estFinal && nouveauStatut != REPORTE + // = true && false = false, donc on continue vers le switch + // Mais TERMINE et ANNULE ne sont pas dans le switch, donc default -> false + // Donc le résultat est toujours false + // Mais testons aussi avec un statut non-final vers REPORTE pour couvrir la branche + assertThat(StatutEvenement.PLANIFIE.peutTransitionnerVers(StatutEvenement.REPORTE)) + .isTrue(); + } + + @Test + @DisplayName("peutTransitionnerVers - REPORTE vers CONFIRME (non géré dans switch)") + void testPeutTransitionnerVersReporteVersConfirme() { + // REPORTE -> CONFIRME n'est pas dans le switch, donc retourne false (default) + assertThat(StatutEvenement.REPORTE.peutTransitionnerVers(StatutEvenement.CONFIRME)) + .isFalse(); + assertThat(StatutEvenement.REPORTE.peutTransitionnerVers(StatutEvenement.EN_COURS)) + .isFalse(); + assertThat(StatutEvenement.REPORTE.peutTransitionnerVers(StatutEvenement.TERMINE)) + .isFalse(); + } + + @ParameterizedTest + @CsvSource({ + "PLANIFIE, CONFIRME, true", + "PLANIFIE, ANNULE, true", + "PLANIFIE, REPORTE, true", + "PLANIFIE, EN_COURS, false", + "PLANIFIE, TERMINE, false", + "CONFIRME, EN_COURS, true", + "CONFIRME, ANNULE, true", + "CONFIRME, REPORTE, true", + "CONFIRME, PLANIFIE, false", + "CONFIRME, TERMINE, false", + "EN_COURS, TERMINE, true", + "EN_COURS, ANNULE, true", + "EN_COURS, PLANIFIE, false", + "EN_COURS, CONFIRME, false", + "REPORTE, PLANIFIE, true", + "REPORTE, ANNULE, true", + "REPORTE, CONFIRME, false", + "REPORTE, EN_COURS, false", + "TERMINE, ANNULE, false", + "ANNULE, TERMINE, false" + }) + @DisplayName("peutTransitionnerVers - toutes les transitions") + void testPeutTransitionnerVersToutesTransitions( + StatutEvenement source, StatutEvenement cible, boolean expected) { + assertThat(source.peutTransitionnerVers(cible)).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests getNiveauPriorite") + class GetNiveauPrioriteTests { + + @ParameterizedTest + @CsvSource({ + "EN_COURS, 1", + "CONFIRME, 2", + "PLANIFIE, 3", + "REPORTE, 4", + "TERMINE, 5", + "ANNULE, 6" + }) + @DisplayName("getNiveauPriorite - tous les niveaux") + void testGetNiveauPriorite(StatutEvenement statut, int expected) { + assertThat(statut.getNiveauPriorite()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests méthodes statiques") + class MethodesStatiquesTests { + + @Test + @DisplayName("getStatutsFinaux - retourne les statuts finaux") + void testGetStatutsFinaux() { + List statuts = StatutEvenement.getStatutsFinaux(); + assertThat(statuts).isNotEmpty(); + assertThat(statuts).contains(StatutEvenement.TERMINE, StatutEvenement.ANNULE); + } + + @Test + @DisplayName("getStatutsEchec - retourne les statuts d'échec") + void testGetStatutsEchec() { + List statuts = StatutEvenement.getStatutsEchec(); + assertThat(statuts).isNotEmpty(); + assertThat(statuts).contains(StatutEvenement.ANNULE); + } + + @Test + @DisplayName("getStatutsActifs - retourne les statuts actifs") + void testGetStatutsActifs() { + StatutEvenement[] statuts = StatutEvenement.getStatutsActifs(); + assertThat(statuts).hasSize(4); + assertThat(statuts).contains( + StatutEvenement.PLANIFIE, + StatutEvenement.CONFIRME, + StatutEvenement.EN_COURS, + StatutEvenement.REPORTE); + } + + @Test + @DisplayName("fromCode - trouve le statut par code") + void testFromCode() { + assertThat(StatutEvenement.fromCode("planned")).isEqualTo(StatutEvenement.PLANIFIE); + assertThat(StatutEvenement.fromCode("completed")).isEqualTo(StatutEvenement.TERMINE); + } + + @Test + @DisplayName("fromCode - code inexistant retourne null") + void testFromCodeInexistant() { + assertThat(StatutEvenement.fromCode("inexistant")).isNull(); + } + + @Test + @DisplayName("fromCode - code null retourne null") + void testFromCodeNull() { + assertThat(StatutEvenement.fromCode(null)).isNull(); + } + + @Test + @DisplayName("fromCode - code vide retourne null") + void testFromCodeVide() { + assertThat(StatutEvenement.fromCode("")).isNull(); + } + + @Test + @DisplayName("fromCode - code avec whitespace retourne null") + void testFromCodeWhitespace() { + assertThat(StatutEvenement.fromCode(" ")).isNull(); + } + + @Test + @DisplayName("fromCode - tous les codes") + void testFromCodeTousLesCodes() { + assertThat(StatutEvenement.fromCode("planned")).isEqualTo(StatutEvenement.PLANIFIE); + assertThat(StatutEvenement.fromCode("confirmed")).isEqualTo(StatutEvenement.CONFIRME); + assertThat(StatutEvenement.fromCode("ongoing")).isEqualTo(StatutEvenement.EN_COURS); + assertThat(StatutEvenement.fromCode("completed")).isEqualTo(StatutEvenement.TERMINE); + assertThat(StatutEvenement.fromCode("cancelled")).isEqualTo(StatutEvenement.ANNULE); + assertThat(StatutEvenement.fromCode("postponed")).isEqualTo(StatutEvenement.REPORTE); + } + + @Test + @DisplayName("fromLibelle - trouve le statut par libellé") + void testFromLibelle() { + assertThat(StatutEvenement.fromLibelle("Planifié")).isEqualTo(StatutEvenement.PLANIFIE); + assertThat(StatutEvenement.fromLibelle("Terminé")).isEqualTo(StatutEvenement.TERMINE); + } + + @Test + @DisplayName("fromLibelle - libellé inexistant retourne null") + void testFromLibelleInexistant() { + assertThat(StatutEvenement.fromLibelle("Inexistant")).isNull(); + } + + @Test + @DisplayName("fromLibelle - libellé null retourne null") + void testFromLibelleNull() { + assertThat(StatutEvenement.fromLibelle(null)).isNull(); + } + + @Test + @DisplayName("fromLibelle - libellé vide retourne null") + void testFromLibelleVide() { + assertThat(StatutEvenement.fromLibelle("")).isNull(); + } + + @Test + @DisplayName("fromLibelle - libellé avec whitespace retourne null") + void testFromLibelleWhitespace() { + assertThat(StatutEvenement.fromLibelle(" ")).isNull(); + } + + @Test + @DisplayName("fromLibelle - tous les libellés") + void testFromLibelleTousLesLibelles() { + assertThat(StatutEvenement.fromLibelle("Planifié")).isEqualTo(StatutEvenement.PLANIFIE); + assertThat(StatutEvenement.fromLibelle("Confirmé")).isEqualTo(StatutEvenement.CONFIRME); + assertThat(StatutEvenement.fromLibelle("En cours")).isEqualTo(StatutEvenement.EN_COURS); + assertThat(StatutEvenement.fromLibelle("Terminé")).isEqualTo(StatutEvenement.TERMINE); + assertThat(StatutEvenement.fromLibelle("Annulé")).isEqualTo(StatutEvenement.ANNULE); + assertThat(StatutEvenement.fromLibelle("Reporté")).isEqualTo(StatutEvenement.REPORTE); + } + } + + @Nested + @DisplayName("Tests getTransitionsPossibles") + class GetTransitionsPossiblesTests { + + @Test + @DisplayName("getTransitionsPossibles - PLANIFIE") + void testGetTransitionsPossiblesPlanifie() { + StatutEvenement[] transitions = StatutEvenement.PLANIFIE.getTransitionsPossibles(); + assertThat(transitions).containsExactly( + StatutEvenement.CONFIRME, + StatutEvenement.ANNULE, + StatutEvenement.REPORTE); + } + + @Test + @DisplayName("getTransitionsPossibles - CONFIRME") + void testGetTransitionsPossiblesConfirme() { + StatutEvenement[] transitions = StatutEvenement.CONFIRME.getTransitionsPossibles(); + assertThat(transitions).containsExactly( + StatutEvenement.EN_COURS, + StatutEvenement.ANNULE, + StatutEvenement.REPORTE); + } + + @Test + @DisplayName("getTransitionsPossibles - EN_COURS") + void testGetTransitionsPossiblesEnCours() { + StatutEvenement[] transitions = StatutEvenement.EN_COURS.getTransitionsPossibles(); + assertThat(transitions).containsExactly( + StatutEvenement.TERMINE, + StatutEvenement.ANNULE); + } + + @Test + @DisplayName("getTransitionsPossibles - REPORTE") + void testGetTransitionsPossiblesReporte() { + StatutEvenement[] transitions = StatutEvenement.REPORTE.getTransitionsPossibles(); + // Note: selon le code, REPORTE peut transitionner vers PLANIFIE, CONFIRME ou ANNULE + // Mais peutTransitionnerVers ne permet que PLANIFIE ou ANNULE + assertThat(transitions).containsExactly( + StatutEvenement.PLANIFIE, + StatutEvenement.CONFIRME, + StatutEvenement.ANNULE); + } + + @Test + @DisplayName("getTransitionsPossibles - TERMINE") + void testGetTransitionsPossiblesTermine() { + StatutEvenement[] transitions = StatutEvenement.TERMINE.getTransitionsPossibles(); + assertThat(transitions).isEmpty(); + } + + @Test + @DisplayName("getTransitionsPossibles - ANNULE") + void testGetTransitionsPossiblesAnnule() { + StatutEvenement[] transitions = StatutEvenement.ANNULE.getTransitionsPossibles(); + assertThat(transitions).isEmpty(); + } + } + + @Nested + @DisplayName("Tests isEstFinal et isEstEchec") + class IsEstFinalEtEchecTests { + + @ParameterizedTest + @CsvSource({ + "PLANIFIE, false, false", + "CONFIRME, false, false", + "EN_COURS, false, false", + "TERMINE, true, false", + "ANNULE, true, true", + "REPORTE, false, false" + }) + @DisplayName("isEstFinal et isEstEchec - tous les statuts") + void testIsEstFinalEtEchec(StatutEvenement statut, boolean estFinal, boolean estEchec) { + assertThat(statut.isEstFinal()).isEqualTo(estFinal); + assertThat(statut.isEstEchec()).isEqualTo(estEchec); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/evenement/TypeEvenementMetierTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/evenement/TypeEvenementMetierTest.java index ee3cab5..063d7d9 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/evenement/TypeEvenementMetierTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/evenement/TypeEvenementMetierTest.java @@ -1,68 +1,68 @@ -package dev.lions.unionflow.server.api.enums.evenement; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour TypeEvenementMetier") -class TypeEvenementMetierTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(TypeEvenementMetier.ASSEMBLEE_GENERALE).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - TypeEvenementMetier[] values = TypeEvenementMetier.values(); - assertThat(values).hasSize(9); - assertThat(values).containsExactly( - TypeEvenementMetier.ASSEMBLEE_GENERALE, - TypeEvenementMetier.FORMATION, - TypeEvenementMetier.ACTIVITE_SOCIALE, - TypeEvenementMetier.ACTION_CARITATIVE, - TypeEvenementMetier.REUNION_BUREAU, - TypeEvenementMetier.CONFERENCE, - TypeEvenementMetier.ATELIER, - TypeEvenementMetier.CEREMONIE, - TypeEvenementMetier.AUTRE); - } - - @ParameterizedTest - @EnumSource(TypeEvenementMetier.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(TypeEvenementMetier type) { - assertThat(type.getLibelle()).isNotNull().isNotEmpty(); - } - - @ParameterizedTest - @CsvSource({ - "ASSEMBLEE_GENERALE, Assemblée Générale", - "FORMATION, Formation", - "ACTIVITE_SOCIALE, Activité Sociale", - "ACTION_CARITATIVE, Action Caritative", - "REUNION_BUREAU, Réunion de Bureau", - "CONFERENCE, Conférence", - "ATELIER, Atelier", - "CEREMONIE, Cérémonie", - "AUTRE, Autre" - }) - @DisplayName("Test getLibelle avec valeurs exactes") - void testGetLibelleValeursExactes(TypeEvenementMetier type, String expectedLibelle) { - assertThat(type.getLibelle()).isEqualTo(expectedLibelle); - } - } -} - +package dev.lions.unionflow.server.api.enums.evenement; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour TypeEvenementMetier") +class TypeEvenementMetierTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(TypeEvenementMetier.ASSEMBLEE_GENERALE).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + TypeEvenementMetier[] values = TypeEvenementMetier.values(); + assertThat(values).hasSize(9); + assertThat(values).containsExactly( + TypeEvenementMetier.ASSEMBLEE_GENERALE, + TypeEvenementMetier.FORMATION, + TypeEvenementMetier.ACTIVITE_SOCIALE, + TypeEvenementMetier.ACTION_CARITATIVE, + TypeEvenementMetier.REUNION_BUREAU, + TypeEvenementMetier.CONFERENCE, + TypeEvenementMetier.ATELIER, + TypeEvenementMetier.CEREMONIE, + TypeEvenementMetier.AUTRE); + } + + @ParameterizedTest + @EnumSource(TypeEvenementMetier.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(TypeEvenementMetier type) { + assertThat(type.getLibelle()).isNotNull().isNotEmpty(); + } + + @ParameterizedTest + @CsvSource({ + "ASSEMBLEE_GENERALE, Assemblée Générale", + "FORMATION, Formation", + "ACTIVITE_SOCIALE, Activité Sociale", + "ACTION_CARITATIVE, Action Caritative", + "REUNION_BUREAU, Réunion de Bureau", + "CONFERENCE, Conférence", + "ATELIER, Atelier", + "CEREMONIE, Cérémonie", + "AUTRE, Autre" + }) + @DisplayName("Test getLibelle avec valeurs exactes") + void testGetLibelleValeursExactes(TypeEvenementMetier type, String expectedLibelle) { + assertThat(type.getLibelle()).isEqualTo(expectedLibelle); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/finance/StatutCotisationTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/finance/StatutCotisationTest.java index 8894a96..7a41b2a 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/finance/StatutCotisationTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/finance/StatutCotisationTest.java @@ -1,76 +1,76 @@ -package dev.lions.unionflow.server.api.enums.finance; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutCotisation") -class StatutCotisationTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutCotisation.EN_ATTENTE).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutCotisation[] values = StatutCotisation.values(); - assertThat(values).hasSize(6); - assertThat(values).containsExactly( - StatutCotisation.EN_ATTENTE, - StatutCotisation.PAYEE, - StatutCotisation.PARTIELLEMENT_PAYEE, - StatutCotisation.EN_RETARD, - StatutCotisation.ANNULEE, - StatutCotisation.REMBOURSEE); - } - - @Test - @DisplayName("Test valueOf") - void testValueOf() { - assertThat(StatutCotisation.valueOf("EN_ATTENTE")).isEqualTo(StatutCotisation.EN_ATTENTE); - assertThat(StatutCotisation.valueOf("PAYEE")).isEqualTo(StatutCotisation.PAYEE); - assertThat(StatutCotisation.valueOf("PARTIELLEMENT_PAYEE")).isEqualTo(StatutCotisation.PARTIELLEMENT_PAYEE); - assertThat(StatutCotisation.valueOf("EN_RETARD")).isEqualTo(StatutCotisation.EN_RETARD); - assertThat(StatutCotisation.valueOf("ANNULEE")).isEqualTo(StatutCotisation.ANNULEE); - assertThat(StatutCotisation.valueOf("REMBOURSEE")).isEqualTo(StatutCotisation.REMBOURSEE); - - assertThatThrownBy(() -> StatutCotisation.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutCotisation.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutCotisation statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @ParameterizedTest - @CsvSource({ - "EN_ATTENTE, En attente", - "PAYEE, Payée", - "PARTIELLEMENT_PAYEE, Partiellement payée", - "EN_RETARD, En retard", - "ANNULEE, Annulée", - "REMBOURSEE, Remboursée" - }) - @DisplayName("Test getLibelle avec valeurs exactes") - void testGetLibelleValeursExactes(StatutCotisation statut, String expectedLibelle) { - assertThat(statut.getLibelle()).isEqualTo(expectedLibelle); - } - } -} - +package dev.lions.unionflow.server.api.enums.finance; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutCotisation") +class StatutCotisationTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutCotisation.EN_ATTENTE).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutCotisation[] values = StatutCotisation.values(); + assertThat(values).hasSize(6); + assertThat(values).containsExactly( + StatutCotisation.EN_ATTENTE, + StatutCotisation.PAYEE, + StatutCotisation.PARTIELLEMENT_PAYEE, + StatutCotisation.EN_RETARD, + StatutCotisation.ANNULEE, + StatutCotisation.REMBOURSEE); + } + + @Test + @DisplayName("Test valueOf") + void testValueOf() { + assertThat(StatutCotisation.valueOf("EN_ATTENTE")).isEqualTo(StatutCotisation.EN_ATTENTE); + assertThat(StatutCotisation.valueOf("PAYEE")).isEqualTo(StatutCotisation.PAYEE); + assertThat(StatutCotisation.valueOf("PARTIELLEMENT_PAYEE")).isEqualTo(StatutCotisation.PARTIELLEMENT_PAYEE); + assertThat(StatutCotisation.valueOf("EN_RETARD")).isEqualTo(StatutCotisation.EN_RETARD); + assertThat(StatutCotisation.valueOf("ANNULEE")).isEqualTo(StatutCotisation.ANNULEE); + assertThat(StatutCotisation.valueOf("REMBOURSEE")).isEqualTo(StatutCotisation.REMBOURSEE); + + assertThatThrownBy(() -> StatutCotisation.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutCotisation.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutCotisation statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @ParameterizedTest + @CsvSource({ + "EN_ATTENTE, En attente", + "PAYEE, Payée", + "PARTIELLEMENT_PAYEE, Partiellement payée", + "EN_RETARD, En retard", + "ANNULEE, Annulée", + "REMBOURSEE, Remboursée" + }) + @DisplayName("Test getLibelle avec valeurs exactes") + void testGetLibelleValeursExactes(StatutCotisation statut, String expectedLibelle) { + assertThat(statut.getLibelle()).isEqualTo(expectedLibelle); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/formuleabonnement/StatutFormuleTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/formuleabonnement/StatutFormuleTest.java index b0c57de..68ce74b 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/formuleabonnement/StatutFormuleTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/formuleabonnement/StatutFormuleTest.java @@ -1,55 +1,55 @@ -package dev.lions.unionflow.server.api.enums.formuleabonnement; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -import static org.assertj.core.api.Assertions.assertThat; - -/** - * Tests unitaires pour l'enum StatutFormule. - */ -@DisplayName("StatutFormule") -class StatutFormuleTest { - - @Nested - @DisplayName("Tests getters") - class GettersTest { - - @Test - @DisplayName("getLibelle doit retourner le libellé") - void testGetLibelle() { - assertThat(StatutFormule.ACTIVE.getLibelle()).isEqualTo("Active"); - assertThat(StatutFormule.INACTIVE.getLibelle()).isEqualTo("Inactive"); - assertThat(StatutFormule.ARCHIVEE.getLibelle()).isEqualTo("Archivée"); - assertThat(StatutFormule.BIENTOT_DISPONIBLE.getLibelle()).isEqualTo("Bientôt Disponible"); - } - } - - @Nested - @DisplayName("Tests enum") - class EnumTest { - - @Test - @DisplayName("values doit retourner toutes les valeurs") - void testValues() { - StatutFormule[] values = StatutFormule.values(); - assertThat(values).hasSize(4); - assertThat(values).containsExactly( - StatutFormule.ACTIVE, - StatutFormule.INACTIVE, - StatutFormule.ARCHIVEE, - StatutFormule.BIENTOT_DISPONIBLE - ); - } - - @Test - @DisplayName("valueOf doit retourner la bonne valeur") - void testValueOf() { - assertThat(StatutFormule.valueOf("ACTIVE")).isEqualTo(StatutFormule.ACTIVE); - assertThat(StatutFormule.valueOf("INACTIVE")).isEqualTo(StatutFormule.INACTIVE); - assertThat(StatutFormule.valueOf("ARCHIVEE")).isEqualTo(StatutFormule.ARCHIVEE); - assertThat(StatutFormule.valueOf("BIENTOT_DISPONIBLE")).isEqualTo(StatutFormule.BIENTOT_DISPONIBLE); - } - } -} +package dev.lions.unionflow.server.api.enums.formuleabonnement; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.Assertions.assertThat; + +/** + * Tests unitaires pour l'enum StatutFormule. + */ +@DisplayName("StatutFormule") +class StatutFormuleTest { + + @Nested + @DisplayName("Tests getters") + class GettersTest { + + @Test + @DisplayName("getLibelle doit retourner le libellé") + void testGetLibelle() { + assertThat(StatutFormule.ACTIVE.getLibelle()).isEqualTo("Active"); + assertThat(StatutFormule.INACTIVE.getLibelle()).isEqualTo("Inactive"); + assertThat(StatutFormule.ARCHIVEE.getLibelle()).isEqualTo("Archivée"); + assertThat(StatutFormule.BIENTOT_DISPONIBLE.getLibelle()).isEqualTo("Bientôt Disponible"); + } + } + + @Nested + @DisplayName("Tests enum") + class EnumTest { + + @Test + @DisplayName("values doit retourner toutes les valeurs") + void testValues() { + StatutFormule[] values = StatutFormule.values(); + assertThat(values).hasSize(4); + assertThat(values).containsExactly( + StatutFormule.ACTIVE, + StatutFormule.INACTIVE, + StatutFormule.ARCHIVEE, + StatutFormule.BIENTOT_DISPONIBLE + ); + } + + @Test + @DisplayName("valueOf doit retourner la bonne valeur") + void testValueOf() { + assertThat(StatutFormule.valueOf("ACTIVE")).isEqualTo(StatutFormule.ACTIVE); + assertThat(StatutFormule.valueOf("INACTIVE")).isEqualTo(StatutFormule.INACTIVE); + assertThat(StatutFormule.valueOf("ARCHIVEE")).isEqualTo(StatutFormule.ARCHIVEE); + assertThat(StatutFormule.valueOf("BIENTOT_DISPONIBLE")).isEqualTo(StatutFormule.BIENTOT_DISPONIBLE); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/formuleabonnement/TypeFormuleTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/formuleabonnement/TypeFormuleTest.java index f69bd85..094851d 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/formuleabonnement/TypeFormuleTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/formuleabonnement/TypeFormuleTest.java @@ -1,55 +1,55 @@ -package dev.lions.unionflow.server.api.enums.formuleabonnement; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -import static org.assertj.core.api.Assertions.assertThat; - -/** - * Tests unitaires pour l'enum TypeFormule. - */ -@DisplayName("TypeFormule") -class TypeFormuleTest { - - @Nested - @DisplayName("Tests getters") - class GettersTest { - - @Test - @DisplayName("getLibelle doit retourner le libellé") - void testGetLibelle() { - assertThat(TypeFormule.BASIC.getLibelle()).isEqualTo("Formule Basique"); - assertThat(TypeFormule.STANDARD.getLibelle()).isEqualTo("Formule Standard"); - assertThat(TypeFormule.PREMIUM.getLibelle()).isEqualTo("Formule Premium"); - assertThat(TypeFormule.ENTERPRISE.getLibelle()).isEqualTo("Formule Entreprise"); - } - } - - @Nested - @DisplayName("Tests enum") - class EnumTest { - - @Test - @DisplayName("values doit retourner toutes les valeurs") - void testValues() { - TypeFormule[] values = TypeFormule.values(); - assertThat(values).hasSize(4); - assertThat(values).containsExactly( - TypeFormule.BASIC, - TypeFormule.STANDARD, - TypeFormule.PREMIUM, - TypeFormule.ENTERPRISE - ); - } - - @Test - @DisplayName("valueOf doit retourner la bonne valeur") - void testValueOf() { - assertThat(TypeFormule.valueOf("BASIC")).isEqualTo(TypeFormule.BASIC); - assertThat(TypeFormule.valueOf("STANDARD")).isEqualTo(TypeFormule.STANDARD); - assertThat(TypeFormule.valueOf("PREMIUM")).isEqualTo(TypeFormule.PREMIUM); - assertThat(TypeFormule.valueOf("ENTERPRISE")).isEqualTo(TypeFormule.ENTERPRISE); - } - } -} +package dev.lions.unionflow.server.api.enums.formuleabonnement; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.Assertions.assertThat; + +/** + * Tests unitaires pour l'enum TypeFormule. + */ +@DisplayName("TypeFormule") +class TypeFormuleTest { + + @Nested + @DisplayName("Tests getters") + class GettersTest { + + @Test + @DisplayName("getLibelle doit retourner le libellé") + void testGetLibelle() { + assertThat(TypeFormule.BASIC.getLibelle()).isEqualTo("Formule Basique"); + assertThat(TypeFormule.STANDARD.getLibelle()).isEqualTo("Formule Standard"); + assertThat(TypeFormule.PREMIUM.getLibelle()).isEqualTo("Formule Premium"); + assertThat(TypeFormule.ENTERPRISE.getLibelle()).isEqualTo("Formule Entreprise"); + } + } + + @Nested + @DisplayName("Tests enum") + class EnumTest { + + @Test + @DisplayName("values doit retourner toutes les valeurs") + void testValues() { + TypeFormule[] values = TypeFormule.values(); + assertThat(values).hasSize(4); + assertThat(values).containsExactly( + TypeFormule.BASIC, + TypeFormule.STANDARD, + TypeFormule.PREMIUM, + TypeFormule.ENTERPRISE + ); + } + + @Test + @DisplayName("valueOf doit retourner la bonne valeur") + void testValueOf() { + assertThat(TypeFormule.valueOf("BASIC")).isEqualTo(TypeFormule.BASIC); + assertThat(TypeFormule.valueOf("STANDARD")).isEqualTo(TypeFormule.STANDARD); + assertThat(TypeFormule.valueOf("PREMIUM")).isEqualTo(TypeFormule.PREMIUM); + assertThat(TypeFormule.valueOf("ENTERPRISE")).isEqualTo(TypeFormule.ENTERPRISE); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/gouvernance/NiveauEchelonTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/gouvernance/NiveauEchelonTest.java index 472c1a6..dd13621 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/gouvernance/NiveauEchelonTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/gouvernance/NiveauEchelonTest.java @@ -1,73 +1,73 @@ -package dev.lions.unionflow.server.api.enums.gouvernance; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour NiveauEchelon") -class NiveauEchelonTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(NiveauEchelon.SIEGE_MONDIAL).isNotNull(); - assertThat(NiveauEchelon.LOCAL).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - NiveauEchelon[] values = NiveauEchelon.values(); - assertThat(values).hasSize(4); - assertThat(values).containsExactly( - NiveauEchelon.SIEGE_MONDIAL, - NiveauEchelon.NATIONAL, - NiveauEchelon.REGIONAL, - NiveauEchelon.LOCAL); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(NiveauEchelon.valueOf("SIEGE_MONDIAL")).isEqualTo(NiveauEchelon.SIEGE_MONDIAL); - assertThat(NiveauEchelon.valueOf("NATIONAL")).isEqualTo(NiveauEchelon.NATIONAL); - assertThat(NiveauEchelon.valueOf("REGIONAL")).isEqualTo(NiveauEchelon.REGIONAL); - assertThat(NiveauEchelon.valueOf("LOCAL")).isEqualTo(NiveauEchelon.LOCAL); - - assertThatThrownBy(() -> NiveauEchelon.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(NiveauEchelon.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(NiveauEchelon niveau) { - assertThat(niveau.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(NiveauEchelon.SIEGE_MONDIAL.getLibelle()).isEqualTo("Siège / Direction Globale"); - assertThat(NiveauEchelon.NATIONAL.getLibelle()).isEqualTo("Fédération ou Bureau National"); - assertThat(NiveauEchelon.REGIONAL.getLibelle()).isEqualTo("Ligue ou Section Régionale/Départementale"); - assertThat(NiveauEchelon.LOCAL.getLibelle()).isEqualTo("Antenne / Cellule de base locale"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(NiveauEchelon.SIEGE_MONDIAL.name()).isEqualTo("SIEGE_MONDIAL"); - assertThat(NiveauEchelon.REGIONAL.name()).isEqualTo("REGIONAL"); - } - } -} +package dev.lions.unionflow.server.api.enums.gouvernance; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour NiveauEchelon") +class NiveauEchelonTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(NiveauEchelon.SIEGE_MONDIAL).isNotNull(); + assertThat(NiveauEchelon.LOCAL).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + NiveauEchelon[] values = NiveauEchelon.values(); + assertThat(values).hasSize(4); + assertThat(values).containsExactly( + NiveauEchelon.SIEGE_MONDIAL, + NiveauEchelon.NATIONAL, + NiveauEchelon.REGIONAL, + NiveauEchelon.LOCAL); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(NiveauEchelon.valueOf("SIEGE_MONDIAL")).isEqualTo(NiveauEchelon.SIEGE_MONDIAL); + assertThat(NiveauEchelon.valueOf("NATIONAL")).isEqualTo(NiveauEchelon.NATIONAL); + assertThat(NiveauEchelon.valueOf("REGIONAL")).isEqualTo(NiveauEchelon.REGIONAL); + assertThat(NiveauEchelon.valueOf("LOCAL")).isEqualTo(NiveauEchelon.LOCAL); + + assertThatThrownBy(() -> NiveauEchelon.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(NiveauEchelon.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(NiveauEchelon niveau) { + assertThat(niveau.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(NiveauEchelon.SIEGE_MONDIAL.getLibelle()).isEqualTo("Siège / Direction Globale"); + assertThat(NiveauEchelon.NATIONAL.getLibelle()).isEqualTo("Fédération ou Bureau National"); + assertThat(NiveauEchelon.REGIONAL.getLibelle()).isEqualTo("Ligue ou Section Régionale/Départementale"); + assertThat(NiveauEchelon.LOCAL.getLibelle()).isEqualTo("Antenne / Cellule de base locale"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(NiveauEchelon.SIEGE_MONDIAL.name()).isEqualTo("SIEGE_MONDIAL"); + assertThat(NiveauEchelon.REGIONAL.name()).isEqualTo("REGIONAL"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/membre/LienParenteTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/membre/LienParenteTest.java index f1f4490..7d64aa7 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/membre/LienParenteTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/membre/LienParenteTest.java @@ -1,73 +1,73 @@ -package dev.lions.unionflow.server.api.enums.membre; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour LienParente") -class LienParenteTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(LienParente.CONJOINT).isNotNull(); - assertThat(LienParente.ENFANT).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - LienParente[] values = LienParente.values(); - assertThat(values).hasSize(4); - assertThat(values).containsExactly( - LienParente.CONJOINT, - LienParente.ENFANT, - LienParente.PARENT, - LienParente.AUTRE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(LienParente.valueOf("CONJOINT")).isEqualTo(LienParente.CONJOINT); - assertThat(LienParente.valueOf("ENFANT")).isEqualTo(LienParente.ENFANT); - assertThat(LienParente.valueOf("PARENT")).isEqualTo(LienParente.PARENT); - assertThat(LienParente.valueOf("AUTRE")).isEqualTo(LienParente.AUTRE); - - assertThatThrownBy(() -> LienParente.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(LienParente.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(LienParente lien) { - assertThat(lien.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(LienParente.CONJOINT.getLibelle()).isEqualTo("Conjoint(e)"); - assertThat(LienParente.ENFANT.getLibelle()).isEqualTo("Enfant"); - assertThat(LienParente.PARENT.getLibelle()).isEqualTo("Parent"); - assertThat(LienParente.AUTRE.getLibelle()).isEqualTo("Autre"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(LienParente.CONJOINT.name()).isEqualTo("CONJOINT"); - assertThat(LienParente.AUTRE.name()).isEqualTo("AUTRE"); - } - } -} +package dev.lions.unionflow.server.api.enums.membre; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour LienParente") +class LienParenteTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(LienParente.CONJOINT).isNotNull(); + assertThat(LienParente.ENFANT).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + LienParente[] values = LienParente.values(); + assertThat(values).hasSize(4); + assertThat(values).containsExactly( + LienParente.CONJOINT, + LienParente.ENFANT, + LienParente.PARENT, + LienParente.AUTRE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(LienParente.valueOf("CONJOINT")).isEqualTo(LienParente.CONJOINT); + assertThat(LienParente.valueOf("ENFANT")).isEqualTo(LienParente.ENFANT); + assertThat(LienParente.valueOf("PARENT")).isEqualTo(LienParente.PARENT); + assertThat(LienParente.valueOf("AUTRE")).isEqualTo(LienParente.AUTRE); + + assertThatThrownBy(() -> LienParente.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(LienParente.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(LienParente lien) { + assertThat(lien.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(LienParente.CONJOINT.getLibelle()).isEqualTo("Conjoint(e)"); + assertThat(LienParente.ENFANT.getLibelle()).isEqualTo("Enfant"); + assertThat(LienParente.PARENT.getLibelle()).isEqualTo("Parent"); + assertThat(LienParente.AUTRE.getLibelle()).isEqualTo("Autre"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(LienParente.CONJOINT.name()).isEqualTo("CONJOINT"); + assertThat(LienParente.AUTRE.name()).isEqualTo("AUTRE"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/membre/NiveauVigilanceKycTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/membre/NiveauVigilanceKycTest.java index e3efa1e..7893918 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/membre/NiveauVigilanceKycTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/membre/NiveauVigilanceKycTest.java @@ -1,31 +1,31 @@ -package dev.lions.unionflow.server.api.enums.membre; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.Test; - -class NiveauVigilanceKycTest { - - @Test - void testValues() { - NiveauVigilanceKyc[] values = NiveauVigilanceKyc.values(); - - assertThat(values).hasSize(2); - assertThat(values).contains( - NiveauVigilanceKyc.SIMPLIFIE, - NiveauVigilanceKyc.RENFORCE - ); - } - - @Test - void testValueOf() { - assertThat(NiveauVigilanceKyc.valueOf("SIMPLIFIE")).isEqualTo(NiveauVigilanceKyc.SIMPLIFIE); - assertThat(NiveauVigilanceKyc.valueOf("RENFORCE")).isEqualTo(NiveauVigilanceKyc.RENFORCE); - } - - @Test - void testGetLibelle() { - assertThat(NiveauVigilanceKyc.SIMPLIFIE.getLibelle()).isEqualTo("Vigilance simplifiée"); - assertThat(NiveauVigilanceKyc.RENFORCE.getLibelle()).isEqualTo("Vigilance renforcée"); - } -} +package dev.lions.unionflow.server.api.enums.membre; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.Test; + +class NiveauVigilanceKycTest { + + @Test + void testValues() { + NiveauVigilanceKyc[] values = NiveauVigilanceKyc.values(); + + assertThat(values).hasSize(2); + assertThat(values).contains( + NiveauVigilanceKyc.SIMPLIFIE, + NiveauVigilanceKyc.RENFORCE + ); + } + + @Test + void testValueOf() { + assertThat(NiveauVigilanceKyc.valueOf("SIMPLIFIE")).isEqualTo(NiveauVigilanceKyc.SIMPLIFIE); + assertThat(NiveauVigilanceKyc.valueOf("RENFORCE")).isEqualTo(NiveauVigilanceKyc.RENFORCE); + } + + @Test + void testGetLibelle() { + assertThat(NiveauVigilanceKyc.SIMPLIFIE.getLibelle()).isEqualTo("Vigilance simplifiée"); + assertThat(NiveauVigilanceKyc.RENFORCE.getLibelle()).isEqualTo("Vigilance renforcée"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/membre/StatutCompteUtilisateurTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/membre/StatutCompteUtilisateurTest.java index 135f3a1..2f88f22 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/membre/StatutCompteUtilisateurTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/membre/StatutCompteUtilisateurTest.java @@ -1,73 +1,73 @@ -package dev.lions.unionflow.server.api.enums.membre; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutCompteUtilisateur") -class StatutCompteUtilisateurTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutCompteUtilisateur.ACTIF).isNotNull(); - assertThat(StatutCompteUtilisateur.EN_ATTENTE_VALIDATION).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutCompteUtilisateur[] values = StatutCompteUtilisateur.values(); - assertThat(values).hasSize(4); - assertThat(values).containsExactly( - StatutCompteUtilisateur.EN_ATTENTE_VALIDATION, - StatutCompteUtilisateur.ACTIF, - StatutCompteUtilisateur.SUSPENDU, - StatutCompteUtilisateur.DESACTIVE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(StatutCompteUtilisateur.valueOf("EN_ATTENTE_VALIDATION")).isEqualTo(StatutCompteUtilisateur.EN_ATTENTE_VALIDATION); - assertThat(StatutCompteUtilisateur.valueOf("ACTIF")).isEqualTo(StatutCompteUtilisateur.ACTIF); - assertThat(StatutCompteUtilisateur.valueOf("SUSPENDU")).isEqualTo(StatutCompteUtilisateur.SUSPENDU); - assertThat(StatutCompteUtilisateur.valueOf("DESACTIVE")).isEqualTo(StatutCompteUtilisateur.DESACTIVE); - - assertThatThrownBy(() -> StatutCompteUtilisateur.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutCompteUtilisateur.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutCompteUtilisateur statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle contient libellé attendu") - void testGetLibelleContenu() { - assertThat(StatutCompteUtilisateur.EN_ATTENTE_VALIDATION.getLibelle()).contains("En attente"); - assertThat(StatutCompteUtilisateur.ACTIF.getLibelle()).contains("Actif"); - assertThat(StatutCompteUtilisateur.SUSPENDU.getLibelle()).contains("Suspendu"); - assertThat(StatutCompteUtilisateur.DESACTIVE.getLibelle()).contains("Désactivé"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(StatutCompteUtilisateur.ACTIF.name()).isEqualTo("ACTIF"); - assertThat(StatutCompteUtilisateur.EN_ATTENTE_VALIDATION.name()).isEqualTo("EN_ATTENTE_VALIDATION"); - } - } -} +package dev.lions.unionflow.server.api.enums.membre; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutCompteUtilisateur") +class StatutCompteUtilisateurTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutCompteUtilisateur.ACTIF).isNotNull(); + assertThat(StatutCompteUtilisateur.EN_ATTENTE_VALIDATION).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutCompteUtilisateur[] values = StatutCompteUtilisateur.values(); + assertThat(values).hasSize(4); + assertThat(values).containsExactly( + StatutCompteUtilisateur.EN_ATTENTE_VALIDATION, + StatutCompteUtilisateur.ACTIF, + StatutCompteUtilisateur.SUSPENDU, + StatutCompteUtilisateur.DESACTIVE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(StatutCompteUtilisateur.valueOf("EN_ATTENTE_VALIDATION")).isEqualTo(StatutCompteUtilisateur.EN_ATTENTE_VALIDATION); + assertThat(StatutCompteUtilisateur.valueOf("ACTIF")).isEqualTo(StatutCompteUtilisateur.ACTIF); + assertThat(StatutCompteUtilisateur.valueOf("SUSPENDU")).isEqualTo(StatutCompteUtilisateur.SUSPENDU); + assertThat(StatutCompteUtilisateur.valueOf("DESACTIVE")).isEqualTo(StatutCompteUtilisateur.DESACTIVE); + + assertThatThrownBy(() -> StatutCompteUtilisateur.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutCompteUtilisateur.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutCompteUtilisateur statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle contient libellé attendu") + void testGetLibelleContenu() { + assertThat(StatutCompteUtilisateur.EN_ATTENTE_VALIDATION.getLibelle()).contains("En attente"); + assertThat(StatutCompteUtilisateur.ACTIF.getLibelle()).contains("Actif"); + assertThat(StatutCompteUtilisateur.SUSPENDU.getLibelle()).contains("Suspendu"); + assertThat(StatutCompteUtilisateur.DESACTIVE.getLibelle()).contains("Désactivé"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(StatutCompteUtilisateur.ACTIF.name()).isEqualTo("ACTIF"); + assertThat(StatutCompteUtilisateur.EN_ATTENTE_VALIDATION.name()).isEqualTo("EN_ATTENTE_VALIDATION"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/membre/StatutKycTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/membre/StatutKycTest.java index 7e0ebe4..c501fb9 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/membre/StatutKycTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/membre/StatutKycTest.java @@ -1,37 +1,37 @@ -package dev.lions.unionflow.server.api.enums.membre; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.Test; - -class StatutKycTest { - - @Test - void testValues() { - StatutKyc[] values = StatutKyc.values(); - - assertThat(values).hasSize(4); - assertThat(values).contains( - StatutKyc.NON_VERIFIE, - StatutKyc.EN_COURS, - StatutKyc.VERIFIE, - StatutKyc.REFUSE - ); - } - - @Test - void testValueOf() { - assertThat(StatutKyc.valueOf("NON_VERIFIE")).isEqualTo(StatutKyc.NON_VERIFIE); - assertThat(StatutKyc.valueOf("EN_COURS")).isEqualTo(StatutKyc.EN_COURS); - assertThat(StatutKyc.valueOf("VERIFIE")).isEqualTo(StatutKyc.VERIFIE); - assertThat(StatutKyc.valueOf("REFUSE")).isEqualTo(StatutKyc.REFUSE); - } - - @Test - void testGetLibelle() { - assertThat(StatutKyc.NON_VERIFIE.getLibelle()).isEqualTo("Non vérifié"); - assertThat(StatutKyc.EN_COURS.getLibelle()).isEqualTo("En cours"); - assertThat(StatutKyc.VERIFIE.getLibelle()).isEqualTo("Vérifié"); - assertThat(StatutKyc.REFUSE.getLibelle()).isEqualTo("Refusé"); - } -} +package dev.lions.unionflow.server.api.enums.membre; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.Test; + +class StatutKycTest { + + @Test + void testValues() { + StatutKyc[] values = StatutKyc.values(); + + assertThat(values).hasSize(4); + assertThat(values).contains( + StatutKyc.NON_VERIFIE, + StatutKyc.EN_COURS, + StatutKyc.VERIFIE, + StatutKyc.REFUSE + ); + } + + @Test + void testValueOf() { + assertThat(StatutKyc.valueOf("NON_VERIFIE")).isEqualTo(StatutKyc.NON_VERIFIE); + assertThat(StatutKyc.valueOf("EN_COURS")).isEqualTo(StatutKyc.EN_COURS); + assertThat(StatutKyc.valueOf("VERIFIE")).isEqualTo(StatutKyc.VERIFIE); + assertThat(StatutKyc.valueOf("REFUSE")).isEqualTo(StatutKyc.REFUSE); + } + + @Test + void testGetLibelle() { + assertThat(StatutKyc.NON_VERIFIE.getLibelle()).isEqualTo("Non vérifié"); + assertThat(StatutKyc.EN_COURS.getLibelle()).isEqualTo("En cours"); + assertThat(StatutKyc.VERIFIE.getLibelle()).isEqualTo("Vérifié"); + assertThat(StatutKyc.REFUSE.getLibelle()).isEqualTo("Refusé"); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/membre/StatutMembreTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/membre/StatutMembreTest.java index 1ef77b0..4dbfbe6 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/membre/StatutMembreTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/membre/StatutMembreTest.java @@ -1,86 +1,86 @@ -package dev.lions.unionflow.server.api.enums.membre; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutMembre") -class StatutMembreTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutMembre.ACTIF).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutMembre[] values = StatutMembre.values(); - assertThat(values).hasSize(10); - assertThat(values).contains( - StatutMembre.INVITE, - StatutMembre.EN_ATTENTE_VALIDATION, - StatutMembre.ACTIF, - StatutMembre.INACTIF, - StatutMembre.SUSPENDU, - StatutMembre.DEMISSIONNAIRE, - StatutMembre.RADIE, - StatutMembre.HONORAIRE, - StatutMembre.DECEDE, - StatutMembre.ARCHIVE); - } - - @Test - @DisplayName("Test valueOf") - void testValueOf() { - assertThat(StatutMembre.valueOf("ACTIF")).isEqualTo(StatutMembre.ACTIF); - assertThat(StatutMembre.valueOf("INACTIF")).isEqualTo(StatutMembre.INACTIF); - assertThat(StatutMembre.valueOf("SUSPENDU")).isEqualTo(StatutMembre.SUSPENDU); - assertThat(StatutMembre.valueOf("RADIE")).isEqualTo(StatutMembre.RADIE); - - assertThatThrownBy(() -> StatutMembre.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutMembre.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutMembre statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle avec valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(StatutMembre.ACTIF.getLibelle()).isEqualTo("Actif"); - assertThat(StatutMembre.INACTIF.getLibelle()).contains("Inactif"); - assertThat(StatutMembre.SUSPENDU.getLibelle()).contains("Suspendu"); - assertThat(StatutMembre.RADIE.getLibelle()).contains("Radié"); - } - - @Test - @DisplayName("Test ordinal et name") - void testOrdinalEtName() { - assertThat(StatutMembre.EN_ATTENTE_VALIDATION.name()).isEqualTo("EN_ATTENTE_VALIDATION"); - assertThat(StatutMembre.ACTIF.name()).isEqualTo("ACTIF"); - assertThat(StatutMembre.INACTIF.name()).isEqualTo("INACTIF"); - assertThat(StatutMembre.SUSPENDU.name()).isEqualTo("SUSPENDU"); - assertThat(StatutMembre.RADIE.name()).isEqualTo("RADIE"); - assertThat(StatutMembre.DEMISSIONNAIRE.name()).isEqualTo("DEMISSIONNAIRE"); - assertThat(StatutMembre.HONORAIRE.name()).isEqualTo("HONORAIRE"); - assertThat(StatutMembre.DECEDE.name()).isEqualTo("DECEDE"); - } - } -} - +package dev.lions.unionflow.server.api.enums.membre; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutMembre") +class StatutMembreTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutMembre.ACTIF).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutMembre[] values = StatutMembre.values(); + assertThat(values).hasSize(10); + assertThat(values).contains( + StatutMembre.INVITE, + StatutMembre.EN_ATTENTE_VALIDATION, + StatutMembre.ACTIF, + StatutMembre.INACTIF, + StatutMembre.SUSPENDU, + StatutMembre.DEMISSIONNAIRE, + StatutMembre.RADIE, + StatutMembre.HONORAIRE, + StatutMembre.DECEDE, + StatutMembre.ARCHIVE); + } + + @Test + @DisplayName("Test valueOf") + void testValueOf() { + assertThat(StatutMembre.valueOf("ACTIF")).isEqualTo(StatutMembre.ACTIF); + assertThat(StatutMembre.valueOf("INACTIF")).isEqualTo(StatutMembre.INACTIF); + assertThat(StatutMembre.valueOf("SUSPENDU")).isEqualTo(StatutMembre.SUSPENDU); + assertThat(StatutMembre.valueOf("RADIE")).isEqualTo(StatutMembre.RADIE); + + assertThatThrownBy(() -> StatutMembre.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutMembre.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutMembre statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle avec valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(StatutMembre.ACTIF.getLibelle()).isEqualTo("Actif"); + assertThat(StatutMembre.INACTIF.getLibelle()).contains("Inactif"); + assertThat(StatutMembre.SUSPENDU.getLibelle()).contains("Suspendu"); + assertThat(StatutMembre.RADIE.getLibelle()).contains("Radié"); + } + + @Test + @DisplayName("Test ordinal et name") + void testOrdinalEtName() { + assertThat(StatutMembre.EN_ATTENTE_VALIDATION.name()).isEqualTo("EN_ATTENTE_VALIDATION"); + assertThat(StatutMembre.ACTIF.name()).isEqualTo("ACTIF"); + assertThat(StatutMembre.INACTIF.name()).isEqualTo("INACTIF"); + assertThat(StatutMembre.SUSPENDU.name()).isEqualTo("SUSPENDU"); + assertThat(StatutMembre.RADIE.name()).isEqualTo("RADIE"); + assertThat(StatutMembre.DEMISSIONNAIRE.name()).isEqualTo("DEMISSIONNAIRE"); + assertThat(StatutMembre.HONORAIRE.name()).isEqualTo("HONORAIRE"); + assertThat(StatutMembre.DECEDE.name()).isEqualTo("DECEDE"); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/module/TypeModuleTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/module/TypeModuleTest.java index 35c8d9b..d25330f 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/module/TypeModuleTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/module/TypeModuleTest.java @@ -1,84 +1,84 @@ -package dev.lions.unionflow.server.api.enums.module; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour TypeModule") -class TypeModuleTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(TypeModule.COTISATIONS).isNotNull(); - assertThat(TypeModule.CULTES_RELIGIEUX).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - TypeModule[] values = TypeModule.values(); - assertThat(values).hasSize(16); - assertThat(values).contains( - TypeModule.COTISATIONS, - TypeModule.EVENEMENTS, - TypeModule.SOLIDARITE, - TypeModule.COMPTABILITE, - TypeModule.DOCUMENTS, - TypeModule.NOTIFICATIONS, - TypeModule.CREDIT_EPARGNE, - TypeModule.AYANTS_DROIT, - TypeModule.TONTINE, - TypeModule.ONG_PROJETS, - TypeModule.COOP_AGRICOLE, - TypeModule.VOTE_INTERNE, - TypeModule.COLLECTE_FONDS, - TypeModule.REGISTRE_PROFESSIONNEL, - TypeModule.CULTES_RELIGIEUX, - TypeModule.GOUVERNANCE_MULTI); - } - - @Test - @DisplayName("Test valueOf - constantes principales") - void testValueOf() { - assertThat(TypeModule.valueOf("COTISATIONS")).isEqualTo(TypeModule.COTISATIONS); - assertThat(TypeModule.valueOf("SOLIDARITE")).isEqualTo(TypeModule.SOLIDARITE); - assertThat(TypeModule.valueOf("CULTES_RELIGIEUX")).isEqualTo(TypeModule.CULTES_RELIGIEUX); - assertThat(TypeModule.valueOf("GOUVERNANCE_MULTI")).isEqualTo(TypeModule.GOUVERNANCE_MULTI); - - assertThatThrownBy(() -> TypeModule.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(TypeModule.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(TypeModule type) { - assertThat(type.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes - échantillon") - void testGetLibelleValeursExactes() { - assertThat(TypeModule.COTISATIONS.getLibelle()).isEqualTo("Gestion des cotisations"); - assertThat(TypeModule.CULTES_RELIGIEUX.getLibelle()).isEqualTo("Gestion cultes et dîmes"); - assertThat(TypeModule.SOLIDARITE.getLibelle()).isEqualTo("Fonds de solidarité"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(TypeModule.COTISATIONS.name()).isEqualTo("COTISATIONS"); - assertThat(TypeModule.CULTES_RELIGIEUX.name()).isEqualTo("CULTES_RELIGIEUX"); - } - } -} +package dev.lions.unionflow.server.api.enums.module; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour TypeModule") +class TypeModuleTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(TypeModule.COTISATIONS).isNotNull(); + assertThat(TypeModule.CULTES_RELIGIEUX).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + TypeModule[] values = TypeModule.values(); + assertThat(values).hasSize(16); + assertThat(values).contains( + TypeModule.COTISATIONS, + TypeModule.EVENEMENTS, + TypeModule.SOLIDARITE, + TypeModule.COMPTABILITE, + TypeModule.DOCUMENTS, + TypeModule.NOTIFICATIONS, + TypeModule.CREDIT_EPARGNE, + TypeModule.AYANTS_DROIT, + TypeModule.TONTINE, + TypeModule.ONG_PROJETS, + TypeModule.COOP_AGRICOLE, + TypeModule.VOTE_INTERNE, + TypeModule.COLLECTE_FONDS, + TypeModule.REGISTRE_PROFESSIONNEL, + TypeModule.CULTES_RELIGIEUX, + TypeModule.GOUVERNANCE_MULTI); + } + + @Test + @DisplayName("Test valueOf - constantes principales") + void testValueOf() { + assertThat(TypeModule.valueOf("COTISATIONS")).isEqualTo(TypeModule.COTISATIONS); + assertThat(TypeModule.valueOf("SOLIDARITE")).isEqualTo(TypeModule.SOLIDARITE); + assertThat(TypeModule.valueOf("CULTES_RELIGIEUX")).isEqualTo(TypeModule.CULTES_RELIGIEUX); + assertThat(TypeModule.valueOf("GOUVERNANCE_MULTI")).isEqualTo(TypeModule.GOUVERNANCE_MULTI); + + assertThatThrownBy(() -> TypeModule.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(TypeModule.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(TypeModule type) { + assertThat(type.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes - échantillon") + void testGetLibelleValeursExactes() { + assertThat(TypeModule.COTISATIONS.getLibelle()).isEqualTo("Gestion des cotisations"); + assertThat(TypeModule.CULTES_RELIGIEUX.getLibelle()).isEqualTo("Gestion cultes et dîmes"); + assertThat(TypeModule.SOLIDARITE.getLibelle()).isEqualTo("Fonds de solidarité"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(TypeModule.COTISATIONS.name()).isEqualTo("COTISATIONS"); + assertThat(TypeModule.CULTES_RELIGIEUX.name()).isEqualTo("CULTES_RELIGIEUX"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutDemandeCreditTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutDemandeCreditTest.java index 45f5d74..d622bc6 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutDemandeCreditTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutDemandeCreditTest.java @@ -1,125 +1,125 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.credit; - -import org.junit.jupiter.api.Test; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.junit.jupiter.api.Assertions.*; - -/** - * Tests unitaires pour l'enum {@link StatutDemandeCredit}. - */ -class StatutDemandeCreditTest { - - @Test - void testValues() { - // Vérifie que l'enum contient exactement 9 valeurs - assertEquals(9, StatutDemandeCredit.values().length); - } - - @Test - void testValueOf() { - // Teste valueOf() pour chaque valeur de l'enum - assertEquals(StatutDemandeCredit.BROUILLON, StatutDemandeCredit.valueOf("BROUILLON")); - assertEquals(StatutDemandeCredit.SOUMISE, StatutDemandeCredit.valueOf("SOUMISE")); - assertEquals(StatutDemandeCredit.EN_EVALUATION, StatutDemandeCredit.valueOf("EN_EVALUATION")); - assertEquals(StatutDemandeCredit.INFORMATIONS_REQUISES, StatutDemandeCredit.valueOf("INFORMATIONS_REQUISES")); - assertEquals(StatutDemandeCredit.APPROUVEE, StatutDemandeCredit.valueOf("APPROUVEE")); - assertEquals(StatutDemandeCredit.REJETEE, StatutDemandeCredit.valueOf("REJETEE")); - assertEquals(StatutDemandeCredit.DECAISSEE, StatutDemandeCredit.valueOf("DECAISSEE")); - assertEquals(StatutDemandeCredit.SOLDEE, StatutDemandeCredit.valueOf("SOLDEE")); - assertEquals(StatutDemandeCredit.EN_CONTENTIEUX, StatutDemandeCredit.valueOf("EN_CONTENTIEUX")); - } - - @Test - void testValueOfWithInvalidValue() { - // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide - assertThrows(IllegalArgumentException.class, () -> StatutDemandeCredit.valueOf("INVALID")); - } - - @Test - void testGetLibelleBrouillon() { - assertThat(StatutDemandeCredit.BROUILLON.getLibelle()) - .isEqualTo("Brouillon / En constitution"); - } - - @Test - void testGetLibelleSoumise() { - assertThat(StatutDemandeCredit.SOUMISE.getLibelle()) - .isEqualTo("Soumise (Attente analyse)"); - } - - @Test - void testGetLibelleEnEvaluation() { - assertThat(StatutDemandeCredit.EN_EVALUATION.getLibelle()) - .isEqualTo("En cours d'étude par le comité"); - } - - @Test - void testGetLibelleInformationsRequises() { - assertThat(StatutDemandeCredit.INFORMATIONS_REQUISES.getLibelle()) - .isEqualTo("Informations complémenaires requises"); - } - - @Test - void testGetLibelleApprouvee() { - assertThat(StatutDemandeCredit.APPROUVEE.getLibelle()) - .isEqualTo("Approuvée (Attente déblocage)"); - } - - @Test - void testGetLibelleRejetee() { - assertThat(StatutDemandeCredit.REJETEE.getLibelle()) - .isEqualTo("Rejetée par le comité"); - } - - @Test - void testGetLibelleDecaissee() { - assertThat(StatutDemandeCredit.DECAISSEE.getLibelle()) - .isEqualTo("Décaissement effectué / En cours de remboursement"); - } - - @Test - void testGetLibelleSoldee() { - assertThat(StatutDemandeCredit.SOLDEE.getLibelle()) - .isEqualTo("Crédit totalement remboursé et soldé"); - } - - @Test - void testGetLibelleEnContentieux() { - assertThat(StatutDemandeCredit.EN_CONTENTIEUX.getLibelle()) - .isEqualTo("En défaut de paiement / Contentieux juridique"); - } - - @Test - void testAllLibellesAreNotNull() { - // Vérifie que tous les libellés sont non-null - for (StatutDemandeCredit statut : StatutDemandeCredit.values()) { - assertThat(statut.getLibelle()) - .isNotNull() - .isNotEmpty(); - } - } - - @Test - void testEnumToString() { - // Vérifie que toString() retourne le nom de la constante - assertThat(StatutDemandeCredit.BROUILLON.toString()).isEqualTo("BROUILLON"); - assertThat(StatutDemandeCredit.SOUMISE.toString()).isEqualTo("SOUMISE"); - assertThat(StatutDemandeCredit.EN_CONTENTIEUX.toString()).isEqualTo("EN_CONTENTIEUX"); - } - - @Test - void testEnumName() { - // Vérifie que name() retourne le nom de la constante - assertThat(StatutDemandeCredit.BROUILLON.name()).isEqualTo("BROUILLON"); - assertThat(StatutDemandeCredit.APPROUVEE.name()).isEqualTo("APPROUVEE"); - } - - @Test - void testEnumOrdinal() { - // Vérifie les positions ordinales - assertThat(StatutDemandeCredit.BROUILLON.ordinal()).isEqualTo(0); - assertThat(StatutDemandeCredit.SOUMISE.ordinal()).isEqualTo(1); - assertThat(StatutDemandeCredit.EN_CONTENTIEUX.ordinal()).isEqualTo(8); - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.credit; + +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.junit.jupiter.api.Assertions.*; + +/** + * Tests unitaires pour l'enum {@link StatutDemandeCredit}. + */ +class StatutDemandeCreditTest { + + @Test + void testValues() { + // Vérifie que l'enum contient exactement 9 valeurs + assertEquals(9, StatutDemandeCredit.values().length); + } + + @Test + void testValueOf() { + // Teste valueOf() pour chaque valeur de l'enum + assertEquals(StatutDemandeCredit.BROUILLON, StatutDemandeCredit.valueOf("BROUILLON")); + assertEquals(StatutDemandeCredit.SOUMISE, StatutDemandeCredit.valueOf("SOUMISE")); + assertEquals(StatutDemandeCredit.EN_EVALUATION, StatutDemandeCredit.valueOf("EN_EVALUATION")); + assertEquals(StatutDemandeCredit.INFORMATIONS_REQUISES, StatutDemandeCredit.valueOf("INFORMATIONS_REQUISES")); + assertEquals(StatutDemandeCredit.APPROUVEE, StatutDemandeCredit.valueOf("APPROUVEE")); + assertEquals(StatutDemandeCredit.REJETEE, StatutDemandeCredit.valueOf("REJETEE")); + assertEquals(StatutDemandeCredit.DECAISSEE, StatutDemandeCredit.valueOf("DECAISSEE")); + assertEquals(StatutDemandeCredit.SOLDEE, StatutDemandeCredit.valueOf("SOLDEE")); + assertEquals(StatutDemandeCredit.EN_CONTENTIEUX, StatutDemandeCredit.valueOf("EN_CONTENTIEUX")); + } + + @Test + void testValueOfWithInvalidValue() { + // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide + assertThrows(IllegalArgumentException.class, () -> StatutDemandeCredit.valueOf("INVALID")); + } + + @Test + void testGetLibelleBrouillon() { + assertThat(StatutDemandeCredit.BROUILLON.getLibelle()) + .isEqualTo("Brouillon / En constitution"); + } + + @Test + void testGetLibelleSoumise() { + assertThat(StatutDemandeCredit.SOUMISE.getLibelle()) + .isEqualTo("Soumise (Attente analyse)"); + } + + @Test + void testGetLibelleEnEvaluation() { + assertThat(StatutDemandeCredit.EN_EVALUATION.getLibelle()) + .isEqualTo("En cours d'étude par le comité"); + } + + @Test + void testGetLibelleInformationsRequises() { + assertThat(StatutDemandeCredit.INFORMATIONS_REQUISES.getLibelle()) + .isEqualTo("Informations complémenaires requises"); + } + + @Test + void testGetLibelleApprouvee() { + assertThat(StatutDemandeCredit.APPROUVEE.getLibelle()) + .isEqualTo("Approuvée (Attente déblocage)"); + } + + @Test + void testGetLibelleRejetee() { + assertThat(StatutDemandeCredit.REJETEE.getLibelle()) + .isEqualTo("Rejetée par le comité"); + } + + @Test + void testGetLibelleDecaissee() { + assertThat(StatutDemandeCredit.DECAISSEE.getLibelle()) + .isEqualTo("Décaissement effectué / En cours de remboursement"); + } + + @Test + void testGetLibelleSoldee() { + assertThat(StatutDemandeCredit.SOLDEE.getLibelle()) + .isEqualTo("Crédit totalement remboursé et soldé"); + } + + @Test + void testGetLibelleEnContentieux() { + assertThat(StatutDemandeCredit.EN_CONTENTIEUX.getLibelle()) + .isEqualTo("En défaut de paiement / Contentieux juridique"); + } + + @Test + void testAllLibellesAreNotNull() { + // Vérifie que tous les libellés sont non-null + for (StatutDemandeCredit statut : StatutDemandeCredit.values()) { + assertThat(statut.getLibelle()) + .isNotNull() + .isNotEmpty(); + } + } + + @Test + void testEnumToString() { + // Vérifie que toString() retourne le nom de la constante + assertThat(StatutDemandeCredit.BROUILLON.toString()).isEqualTo("BROUILLON"); + assertThat(StatutDemandeCredit.SOUMISE.toString()).isEqualTo("SOUMISE"); + assertThat(StatutDemandeCredit.EN_CONTENTIEUX.toString()).isEqualTo("EN_CONTENTIEUX"); + } + + @Test + void testEnumName() { + // Vérifie que name() retourne le nom de la constante + assertThat(StatutDemandeCredit.BROUILLON.name()).isEqualTo("BROUILLON"); + assertThat(StatutDemandeCredit.APPROUVEE.name()).isEqualTo("APPROUVEE"); + } + + @Test + void testEnumOrdinal() { + // Vérifie les positions ordinales + assertThat(StatutDemandeCredit.BROUILLON.ordinal()).isEqualTo(0); + assertThat(StatutDemandeCredit.SOUMISE.ordinal()).isEqualTo(1); + assertThat(StatutDemandeCredit.EN_CONTENTIEUX.ordinal()).isEqualTo(8); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutEcheanceCreditTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutEcheanceCreditTest.java index 8ebac2b..6b46786 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutEcheanceCreditTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/StatutEcheanceCreditTest.java @@ -1,111 +1,111 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.credit; - -import org.junit.jupiter.api.Test; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.junit.jupiter.api.Assertions.*; - -/** - * Tests unitaires pour l'enum {@link StatutEcheanceCredit}. - */ -class StatutEcheanceCreditTest { - - @Test - void testValues() { - // Vérifie que l'enum contient exactement 7 valeurs - assertEquals(7, StatutEcheanceCredit.values().length); - } - - @Test - void testValueOf() { - // Teste valueOf() pour chaque valeur de l'enum - assertEquals(StatutEcheanceCredit.A_VENIR, StatutEcheanceCredit.valueOf("A_VENIR")); - assertEquals(StatutEcheanceCredit.EXIGIBLE, StatutEcheanceCredit.valueOf("EXIGIBLE")); - assertEquals(StatutEcheanceCredit.PAYEE, StatutEcheanceCredit.valueOf("PAYEE")); - assertEquals(StatutEcheanceCredit.PAYEE_PARTIELLEMENT, StatutEcheanceCredit.valueOf("PAYEE_PARTIELLEMENT")); - assertEquals(StatutEcheanceCredit.EN_RETARD, StatutEcheanceCredit.valueOf("EN_RETARD")); - assertEquals(StatutEcheanceCredit.IMPAYEE, StatutEcheanceCredit.valueOf("IMPAYEE")); - assertEquals(StatutEcheanceCredit.RESTRUCTUREE, StatutEcheanceCredit.valueOf("RESTRUCTUREE")); - } - - @Test - void testValueOfWithInvalidValue() { - // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide - assertThrows(IllegalArgumentException.class, () -> StatutEcheanceCredit.valueOf("INVALID")); - } - - @Test - void testGetLibelleAVenir() { - assertThat(StatutEcheanceCredit.A_VENIR.getLibelle()) - .isEqualTo("Échéance à venir"); - } - - @Test - void testGetLibelleExigible() { - assertThat(StatutEcheanceCredit.EXIGIBLE.getLibelle()) - .isEqualTo("Échéance exigible ce jour"); - } - - @Test - void testGetLibellePayee() { - assertThat(StatutEcheanceCredit.PAYEE.getLibelle()) - .isEqualTo("Intégralement payée"); - } - - @Test - void testGetLibellePayeePartiellement() { - assertThat(StatutEcheanceCredit.PAYEE_PARTIELLEMENT.getLibelle()) - .isEqualTo("Partiellement payée"); - } - - @Test - void testGetLibelleEnRetard() { - assertThat(StatutEcheanceCredit.EN_RETARD.getLibelle()) - .isEqualTo("En retard de paiement"); - } - - @Test - void testGetLibelleImpayee() { - assertThat(StatutEcheanceCredit.IMPAYEE.getLibelle()) - .isEqualTo("Déclarée impayée / Recouvrement"); - } - - @Test - void testGetLibelleRestructuree() { - assertThat(StatutEcheanceCredit.RESTRUCTUREE.getLibelle()) - .isEqualTo("Échéance restructurée / reportée"); - } - - @Test - void testAllLibellesAreNotNull() { - // Vérifie que tous les libellés sont non-null - for (StatutEcheanceCredit statut : StatutEcheanceCredit.values()) { - assertThat(statut.getLibelle()) - .isNotNull() - .isNotEmpty(); - } - } - - @Test - void testEnumToString() { - // Vérifie que toString() retourne le nom de la constante - assertThat(StatutEcheanceCredit.A_VENIR.toString()).isEqualTo("A_VENIR"); - assertThat(StatutEcheanceCredit.PAYEE.toString()).isEqualTo("PAYEE"); - assertThat(StatutEcheanceCredit.RESTRUCTUREE.toString()).isEqualTo("RESTRUCTUREE"); - } - - @Test - void testEnumName() { - // Vérifie que name() retourne le nom de la constante - assertThat(StatutEcheanceCredit.EXIGIBLE.name()).isEqualTo("EXIGIBLE"); - assertThat(StatutEcheanceCredit.IMPAYEE.name()).isEqualTo("IMPAYEE"); - } - - @Test - void testEnumOrdinal() { - // Vérifie les positions ordinales - assertThat(StatutEcheanceCredit.A_VENIR.ordinal()).isEqualTo(0); - assertThat(StatutEcheanceCredit.EXIGIBLE.ordinal()).isEqualTo(1); - assertThat(StatutEcheanceCredit.RESTRUCTUREE.ordinal()).isEqualTo(6); - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.credit; + +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.junit.jupiter.api.Assertions.*; + +/** + * Tests unitaires pour l'enum {@link StatutEcheanceCredit}. + */ +class StatutEcheanceCreditTest { + + @Test + void testValues() { + // Vérifie que l'enum contient exactement 7 valeurs + assertEquals(7, StatutEcheanceCredit.values().length); + } + + @Test + void testValueOf() { + // Teste valueOf() pour chaque valeur de l'enum + assertEquals(StatutEcheanceCredit.A_VENIR, StatutEcheanceCredit.valueOf("A_VENIR")); + assertEquals(StatutEcheanceCredit.EXIGIBLE, StatutEcheanceCredit.valueOf("EXIGIBLE")); + assertEquals(StatutEcheanceCredit.PAYEE, StatutEcheanceCredit.valueOf("PAYEE")); + assertEquals(StatutEcheanceCredit.PAYEE_PARTIELLEMENT, StatutEcheanceCredit.valueOf("PAYEE_PARTIELLEMENT")); + assertEquals(StatutEcheanceCredit.EN_RETARD, StatutEcheanceCredit.valueOf("EN_RETARD")); + assertEquals(StatutEcheanceCredit.IMPAYEE, StatutEcheanceCredit.valueOf("IMPAYEE")); + assertEquals(StatutEcheanceCredit.RESTRUCTUREE, StatutEcheanceCredit.valueOf("RESTRUCTUREE")); + } + + @Test + void testValueOfWithInvalidValue() { + // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide + assertThrows(IllegalArgumentException.class, () -> StatutEcheanceCredit.valueOf("INVALID")); + } + + @Test + void testGetLibelleAVenir() { + assertThat(StatutEcheanceCredit.A_VENIR.getLibelle()) + .isEqualTo("Échéance à venir"); + } + + @Test + void testGetLibelleExigible() { + assertThat(StatutEcheanceCredit.EXIGIBLE.getLibelle()) + .isEqualTo("Échéance exigible ce jour"); + } + + @Test + void testGetLibellePayee() { + assertThat(StatutEcheanceCredit.PAYEE.getLibelle()) + .isEqualTo("Intégralement payée"); + } + + @Test + void testGetLibellePayeePartiellement() { + assertThat(StatutEcheanceCredit.PAYEE_PARTIELLEMENT.getLibelle()) + .isEqualTo("Partiellement payée"); + } + + @Test + void testGetLibelleEnRetard() { + assertThat(StatutEcheanceCredit.EN_RETARD.getLibelle()) + .isEqualTo("En retard de paiement"); + } + + @Test + void testGetLibelleImpayee() { + assertThat(StatutEcheanceCredit.IMPAYEE.getLibelle()) + .isEqualTo("Déclarée impayée / Recouvrement"); + } + + @Test + void testGetLibelleRestructuree() { + assertThat(StatutEcheanceCredit.RESTRUCTUREE.getLibelle()) + .isEqualTo("Échéance restructurée / reportée"); + } + + @Test + void testAllLibellesAreNotNull() { + // Vérifie que tous les libellés sont non-null + for (StatutEcheanceCredit statut : StatutEcheanceCredit.values()) { + assertThat(statut.getLibelle()) + .isNotNull() + .isNotEmpty(); + } + } + + @Test + void testEnumToString() { + // Vérifie que toString() retourne le nom de la constante + assertThat(StatutEcheanceCredit.A_VENIR.toString()).isEqualTo("A_VENIR"); + assertThat(StatutEcheanceCredit.PAYEE.toString()).isEqualTo("PAYEE"); + assertThat(StatutEcheanceCredit.RESTRUCTUREE.toString()).isEqualTo("RESTRUCTUREE"); + } + + @Test + void testEnumName() { + // Vérifie que name() retourne le nom de la constante + assertThat(StatutEcheanceCredit.EXIGIBLE.name()).isEqualTo("EXIGIBLE"); + assertThat(StatutEcheanceCredit.IMPAYEE.name()).isEqualTo("IMPAYEE"); + } + + @Test + void testEnumOrdinal() { + // Vérifie les positions ordinales + assertThat(StatutEcheanceCredit.A_VENIR.ordinal()).isEqualTo(0); + assertThat(StatutEcheanceCredit.EXIGIBLE.ordinal()).isEqualTo(1); + assertThat(StatutEcheanceCredit.RESTRUCTUREE.ordinal()).isEqualTo(6); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeCreditTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeCreditTest.java index 55a8bef..e8d05f9 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeCreditTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeCreditTest.java @@ -1,111 +1,111 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.credit; - -import org.junit.jupiter.api.Test; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.junit.jupiter.api.Assertions.*; - -/** - * Tests unitaires pour l'enum {@link TypeCredit}. - */ -class TypeCreditTest { - - @Test - void testValues() { - // Vérifie que l'enum contient exactement 7 valeurs - assertEquals(7, TypeCredit.values().length); - } - - @Test - void testValueOf() { - // Teste valueOf() pour chaque valeur de l'enum - assertEquals(TypeCredit.CONSOMMATION, TypeCredit.valueOf("CONSOMMATION")); - assertEquals(TypeCredit.IMMOBILIER, TypeCredit.valueOf("IMMOBILIER")); - assertEquals(TypeCredit.PROFESSIONNEL, TypeCredit.valueOf("PROFESSIONNEL")); - assertEquals(TypeCredit.AGRICOLE, TypeCredit.valueOf("AGRICOLE")); - assertEquals(TypeCredit.SCOLAIRE, TypeCredit.valueOf("SCOLAIRE")); - assertEquals(TypeCredit.URGENCE, TypeCredit.valueOf("URGENCE")); - assertEquals(TypeCredit.DECOUVERT, TypeCredit.valueOf("DECOUVERT")); - } - - @Test - void testValueOfWithInvalidValue() { - // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide - assertThrows(IllegalArgumentException.class, () -> TypeCredit.valueOf("INVALID")); - } - - @Test - void testGetLibelleConsommation() { - assertThat(TypeCredit.CONSOMMATION.getLibelle()) - .isEqualTo("Crédit à la consommation"); - } - - @Test - void testGetLibelleImmobilier() { - assertThat(TypeCredit.IMMOBILIER.getLibelle()) - .isEqualTo("Crédit immobilier / Construction"); - } - - @Test - void testGetLibelleProfessionnel() { - assertThat(TypeCredit.PROFESSIONNEL.getLibelle()) - .isEqualTo("Financement d'activité génératrice de revenus (AGR)"); - } - - @Test - void testGetLibelleAgricole() { - assertThat(TypeCredit.AGRICOLE.getLibelle()) - .isEqualTo("Campagne agricole / Matériel"); - } - - @Test - void testGetLibelleScolaire() { - assertThat(TypeCredit.SCOLAIRE.getLibelle()) - .isEqualTo("Crédit scolaire / Études"); - } - - @Test - void testGetLibelleUrgence() { - assertThat(TypeCredit.URGENCE.getLibelle()) - .isEqualTo("Prêt d'urgence (Santé, Social)"); - } - - @Test - void testGetLibelleDecouvert() { - assertThat(TypeCredit.DECOUVERT.getLibelle()) - .isEqualTo("Découvert autorisé"); - } - - @Test - void testAllLibellesAreNotNull() { - // Vérifie que tous les libellés sont non-null - for (TypeCredit type : TypeCredit.values()) { - assertThat(type.getLibelle()) - .isNotNull() - .isNotEmpty(); - } - } - - @Test - void testEnumToString() { - // Vérifie que toString() retourne le nom de la constante - assertThat(TypeCredit.CONSOMMATION.toString()).isEqualTo("CONSOMMATION"); - assertThat(TypeCredit.IMMOBILIER.toString()).isEqualTo("IMMOBILIER"); - assertThat(TypeCredit.DECOUVERT.toString()).isEqualTo("DECOUVERT"); - } - - @Test - void testEnumName() { - // Vérifie que name() retourne le nom de la constante - assertThat(TypeCredit.PROFESSIONNEL.name()).isEqualTo("PROFESSIONNEL"); - assertThat(TypeCredit.URGENCE.name()).isEqualTo("URGENCE"); - } - - @Test - void testEnumOrdinal() { - // Vérifie les positions ordinales - assertThat(TypeCredit.CONSOMMATION.ordinal()).isEqualTo(0); - assertThat(TypeCredit.IMMOBILIER.ordinal()).isEqualTo(1); - assertThat(TypeCredit.DECOUVERT.ordinal()).isEqualTo(6); - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.credit; + +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.junit.jupiter.api.Assertions.*; + +/** + * Tests unitaires pour l'enum {@link TypeCredit}. + */ +class TypeCreditTest { + + @Test + void testValues() { + // Vérifie que l'enum contient exactement 7 valeurs + assertEquals(7, TypeCredit.values().length); + } + + @Test + void testValueOf() { + // Teste valueOf() pour chaque valeur de l'enum + assertEquals(TypeCredit.CONSOMMATION, TypeCredit.valueOf("CONSOMMATION")); + assertEquals(TypeCredit.IMMOBILIER, TypeCredit.valueOf("IMMOBILIER")); + assertEquals(TypeCredit.PROFESSIONNEL, TypeCredit.valueOf("PROFESSIONNEL")); + assertEquals(TypeCredit.AGRICOLE, TypeCredit.valueOf("AGRICOLE")); + assertEquals(TypeCredit.SCOLAIRE, TypeCredit.valueOf("SCOLAIRE")); + assertEquals(TypeCredit.URGENCE, TypeCredit.valueOf("URGENCE")); + assertEquals(TypeCredit.DECOUVERT, TypeCredit.valueOf("DECOUVERT")); + } + + @Test + void testValueOfWithInvalidValue() { + // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide + assertThrows(IllegalArgumentException.class, () -> TypeCredit.valueOf("INVALID")); + } + + @Test + void testGetLibelleConsommation() { + assertThat(TypeCredit.CONSOMMATION.getLibelle()) + .isEqualTo("Crédit à la consommation"); + } + + @Test + void testGetLibelleImmobilier() { + assertThat(TypeCredit.IMMOBILIER.getLibelle()) + .isEqualTo("Crédit immobilier / Construction"); + } + + @Test + void testGetLibelleProfessionnel() { + assertThat(TypeCredit.PROFESSIONNEL.getLibelle()) + .isEqualTo("Financement d'activité génératrice de revenus (AGR)"); + } + + @Test + void testGetLibelleAgricole() { + assertThat(TypeCredit.AGRICOLE.getLibelle()) + .isEqualTo("Campagne agricole / Matériel"); + } + + @Test + void testGetLibelleScolaire() { + assertThat(TypeCredit.SCOLAIRE.getLibelle()) + .isEqualTo("Crédit scolaire / Études"); + } + + @Test + void testGetLibelleUrgence() { + assertThat(TypeCredit.URGENCE.getLibelle()) + .isEqualTo("Prêt d'urgence (Santé, Social)"); + } + + @Test + void testGetLibelleDecouvert() { + assertThat(TypeCredit.DECOUVERT.getLibelle()) + .isEqualTo("Découvert autorisé"); + } + + @Test + void testAllLibellesAreNotNull() { + // Vérifie que tous les libellés sont non-null + for (TypeCredit type : TypeCredit.values()) { + assertThat(type.getLibelle()) + .isNotNull() + .isNotEmpty(); + } + } + + @Test + void testEnumToString() { + // Vérifie que toString() retourne le nom de la constante + assertThat(TypeCredit.CONSOMMATION.toString()).isEqualTo("CONSOMMATION"); + assertThat(TypeCredit.IMMOBILIER.toString()).isEqualTo("IMMOBILIER"); + assertThat(TypeCredit.DECOUVERT.toString()).isEqualTo("DECOUVERT"); + } + + @Test + void testEnumName() { + // Vérifie que name() retourne le nom de la constante + assertThat(TypeCredit.PROFESSIONNEL.name()).isEqualTo("PROFESSIONNEL"); + assertThat(TypeCredit.URGENCE.name()).isEqualTo("URGENCE"); + } + + @Test + void testEnumOrdinal() { + // Vérifie les positions ordinales + assertThat(TypeCredit.CONSOMMATION.ordinal()).isEqualTo(0); + assertThat(TypeCredit.IMMOBILIER.ordinal()).isEqualTo(1); + assertThat(TypeCredit.DECOUVERT.ordinal()).isEqualTo(6); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeGarantieTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeGarantieTest.java index 51425c1..487c667 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeGarantieTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/credit/TypeGarantieTest.java @@ -1,97 +1,97 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.credit; - -import org.junit.jupiter.api.Test; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.junit.jupiter.api.Assertions.*; - -/** - * Tests unitaires pour l'enum {@link TypeGarantie}. - */ -class TypeGarantieTest { - - @Test - void testValues() { - // Vérifie que l'enum contient exactement 5 valeurs - assertEquals(5, TypeGarantie.values().length); - } - - @Test - void testValueOf() { - // Teste valueOf() pour chaque valeur de l'enum - assertEquals(TypeGarantie.EPARGNE_BLOQUEE, TypeGarantie.valueOf("EPARGNE_BLOQUEE")); - assertEquals(TypeGarantie.CAUTION_SOLIDAIRE, TypeGarantie.valueOf("CAUTION_SOLIDAIRE")); - assertEquals(TypeGarantie.MATERIELLE, TypeGarantie.valueOf("MATERIELLE")); - assertEquals(TypeGarantie.IMMOBILIERE, TypeGarantie.valueOf("IMMOBILIERE")); - assertEquals(TypeGarantie.FOND_GARANTIE, TypeGarantie.valueOf("FOND_GARANTIE")); - } - - @Test - void testValueOfWithInvalidValue() { - // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide - assertThrows(IllegalArgumentException.class, () -> TypeGarantie.valueOf("INVALID")); - } - - @Test - void testGetLibelleEpargneBloquee() { - assertThat(TypeGarantie.EPARGNE_BLOQUEE.getLibelle()) - .isEqualTo("Fonds bloqués sur compte d'épargne (Nantissement)"); - } - - @Test - void testGetLibelleCautionSolidaire() { - assertThat(TypeGarantie.CAUTION_SOLIDAIRE.getLibelle()) - .isEqualTo("Avaliseurs / Cautions solidaires (Membres phys.)"); - } - - @Test - void testGetLibelleMaterielle() { - assertThat(TypeGarantie.MATERIELLE.getLibelle()) - .isEqualTo("Garantie sur équipement / Véhicule"); - } - - @Test - void testGetLibelleImmobiliere() { - assertThat(TypeGarantie.IMMOBILIERE.getLibelle()) - .isEqualTo("Hypothèque / Titre foncier"); - } - - @Test - void testGetLibelleFondGarantie() { - assertThat(TypeGarantie.FOND_GARANTIE.getLibelle()) - .isEqualTo("Fonds de garantie externe (ex. FONGIP)"); - } - - @Test - void testAllLibellesAreNotNull() { - // Vérifie que tous les libellés sont non-null - for (TypeGarantie type : TypeGarantie.values()) { - assertThat(type.getLibelle()) - .isNotNull() - .isNotEmpty(); - } - } - - @Test - void testEnumToString() { - // Vérifie que toString() retourne le nom de la constante - assertThat(TypeGarantie.EPARGNE_BLOQUEE.toString()).isEqualTo("EPARGNE_BLOQUEE"); - assertThat(TypeGarantie.CAUTION_SOLIDAIRE.toString()).isEqualTo("CAUTION_SOLIDAIRE"); - assertThat(TypeGarantie.FOND_GARANTIE.toString()).isEqualTo("FOND_GARANTIE"); - } - - @Test - void testEnumName() { - // Vérifie que name() retourne le nom de la constante - assertThat(TypeGarantie.MATERIELLE.name()).isEqualTo("MATERIELLE"); - assertThat(TypeGarantie.IMMOBILIERE.name()).isEqualTo("IMMOBILIERE"); - } - - @Test - void testEnumOrdinal() { - // Vérifie les positions ordinales - assertThat(TypeGarantie.EPARGNE_BLOQUEE.ordinal()).isEqualTo(0); - assertThat(TypeGarantie.CAUTION_SOLIDAIRE.ordinal()).isEqualTo(1); - assertThat(TypeGarantie.FOND_GARANTIE.ordinal()).isEqualTo(4); - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.credit; + +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.junit.jupiter.api.Assertions.*; + +/** + * Tests unitaires pour l'enum {@link TypeGarantie}. + */ +class TypeGarantieTest { + + @Test + void testValues() { + // Vérifie que l'enum contient exactement 5 valeurs + assertEquals(5, TypeGarantie.values().length); + } + + @Test + void testValueOf() { + // Teste valueOf() pour chaque valeur de l'enum + assertEquals(TypeGarantie.EPARGNE_BLOQUEE, TypeGarantie.valueOf("EPARGNE_BLOQUEE")); + assertEquals(TypeGarantie.CAUTION_SOLIDAIRE, TypeGarantie.valueOf("CAUTION_SOLIDAIRE")); + assertEquals(TypeGarantie.MATERIELLE, TypeGarantie.valueOf("MATERIELLE")); + assertEquals(TypeGarantie.IMMOBILIERE, TypeGarantie.valueOf("IMMOBILIERE")); + assertEquals(TypeGarantie.FOND_GARANTIE, TypeGarantie.valueOf("FOND_GARANTIE")); + } + + @Test + void testValueOfWithInvalidValue() { + // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide + assertThrows(IllegalArgumentException.class, () -> TypeGarantie.valueOf("INVALID")); + } + + @Test + void testGetLibelleEpargneBloquee() { + assertThat(TypeGarantie.EPARGNE_BLOQUEE.getLibelle()) + .isEqualTo("Fonds bloqués sur compte d'épargne (Nantissement)"); + } + + @Test + void testGetLibelleCautionSolidaire() { + assertThat(TypeGarantie.CAUTION_SOLIDAIRE.getLibelle()) + .isEqualTo("Avaliseurs / Cautions solidaires (Membres phys.)"); + } + + @Test + void testGetLibelleMaterielle() { + assertThat(TypeGarantie.MATERIELLE.getLibelle()) + .isEqualTo("Garantie sur équipement / Véhicule"); + } + + @Test + void testGetLibelleImmobiliere() { + assertThat(TypeGarantie.IMMOBILIERE.getLibelle()) + .isEqualTo("Hypothèque / Titre foncier"); + } + + @Test + void testGetLibelleFondGarantie() { + assertThat(TypeGarantie.FOND_GARANTIE.getLibelle()) + .isEqualTo("Fonds de garantie externe (ex. FONGIP)"); + } + + @Test + void testAllLibellesAreNotNull() { + // Vérifie que tous les libellés sont non-null + for (TypeGarantie type : TypeGarantie.values()) { + assertThat(type.getLibelle()) + .isNotNull() + .isNotEmpty(); + } + } + + @Test + void testEnumToString() { + // Vérifie que toString() retourne le nom de la constante + assertThat(TypeGarantie.EPARGNE_BLOQUEE.toString()).isEqualTo("EPARGNE_BLOQUEE"); + assertThat(TypeGarantie.CAUTION_SOLIDAIRE.toString()).isEqualTo("CAUTION_SOLIDAIRE"); + assertThat(TypeGarantie.FOND_GARANTIE.toString()).isEqualTo("FOND_GARANTIE"); + } + + @Test + void testEnumName() { + // Vérifie que name() retourne le nom de la constante + assertThat(TypeGarantie.MATERIELLE.name()).isEqualTo("MATERIELLE"); + assertThat(TypeGarantie.IMMOBILIERE.name()).isEqualTo("IMMOBILIERE"); + } + + @Test + void testEnumOrdinal() { + // Vérifie les positions ordinales + assertThat(TypeGarantie.EPARGNE_BLOQUEE.ordinal()).isEqualTo(0); + assertThat(TypeGarantie.CAUTION_SOLIDAIRE.ordinal()).isEqualTo(1); + assertThat(TypeGarantie.FOND_GARANTIE.ordinal()).isEqualTo(4); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/StatutCompteEpargneTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/StatutCompteEpargneTest.java index fd41e3b..b56ddc2 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/StatutCompteEpargneTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/StatutCompteEpargneTest.java @@ -1,97 +1,97 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.epargne; - -import org.junit.jupiter.api.Test; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.junit.jupiter.api.Assertions.*; - -/** - * Tests unitaires pour l'enum {@link StatutCompteEpargne}. - */ -class StatutCompteEpargneTest { - - @Test - void testValues() { - // Vérifie que l'enum contient exactement 5 valeurs - assertEquals(5, StatutCompteEpargne.values().length); - } - - @Test - void testValueOf() { - // Teste valueOf() pour chaque valeur de l'enum - assertEquals(StatutCompteEpargne.ACTIF, StatutCompteEpargne.valueOf("ACTIF")); - assertEquals(StatutCompteEpargne.INACTIF, StatutCompteEpargne.valueOf("INACTIF")); - assertEquals(StatutCompteEpargne.BLOQUE, StatutCompteEpargne.valueOf("BLOQUE")); - assertEquals(StatutCompteEpargne.EN_CLOTURE, StatutCompteEpargne.valueOf("EN_CLOTURE")); - assertEquals(StatutCompteEpargne.CLOTURE, StatutCompteEpargne.valueOf("CLOTURE")); - } - - @Test - void testValueOfWithInvalidValue() { - // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide - assertThrows(IllegalArgumentException.class, () -> StatutCompteEpargne.valueOf("INVALID")); - } - - @Test - void testGetLibelleActif() { - assertThat(StatutCompteEpargne.ACTIF.getLibelle()) - .isEqualTo("Actif et fonctionnel"); - } - - @Test - void testGetLibelleInactif() { - assertThat(StatutCompteEpargne.INACTIF.getLibelle()) - .isEqualTo("Inactif (sans mouvement prolongé)"); - } - - @Test - void testGetLibelleBloque() { - assertThat(StatutCompteEpargne.BLOQUE.getLibelle()) - .isEqualTo("Bloqué (saisie, garantie, ou décision CA)"); - } - - @Test - void testGetLibelleEnCloture() { - assertThat(StatutCompteEpargne.EN_CLOTURE.getLibelle()) - .isEqualTo("En cours de clôture"); - } - - @Test - void testGetLibelleCloture() { - assertThat(StatutCompteEpargne.CLOTURE.getLibelle()) - .isEqualTo("Clôturé"); - } - - @Test - void testAllLibellesAreNotNull() { - // Vérifie que tous les libellés sont non-null - for (StatutCompteEpargne statut : StatutCompteEpargne.values()) { - assertThat(statut.getLibelle()) - .isNotNull() - .isNotEmpty(); - } - } - - @Test - void testEnumToString() { - // Vérifie que toString() retourne le nom de la constante - assertThat(StatutCompteEpargne.ACTIF.toString()).isEqualTo("ACTIF"); - assertThat(StatutCompteEpargne.BLOQUE.toString()).isEqualTo("BLOQUE"); - assertThat(StatutCompteEpargne.CLOTURE.toString()).isEqualTo("CLOTURE"); - } - - @Test - void testEnumName() { - // Vérifie que name() retourne le nom de la constante - assertThat(StatutCompteEpargne.INACTIF.name()).isEqualTo("INACTIF"); - assertThat(StatutCompteEpargne.EN_CLOTURE.name()).isEqualTo("EN_CLOTURE"); - } - - @Test - void testEnumOrdinal() { - // Vérifie les positions ordinales - assertThat(StatutCompteEpargne.ACTIF.ordinal()).isEqualTo(0); - assertThat(StatutCompteEpargne.INACTIF.ordinal()).isEqualTo(1); - assertThat(StatutCompteEpargne.CLOTURE.ordinal()).isEqualTo(4); - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.epargne; + +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.junit.jupiter.api.Assertions.*; + +/** + * Tests unitaires pour l'enum {@link StatutCompteEpargne}. + */ +class StatutCompteEpargneTest { + + @Test + void testValues() { + // Vérifie que l'enum contient exactement 5 valeurs + assertEquals(5, StatutCompteEpargne.values().length); + } + + @Test + void testValueOf() { + // Teste valueOf() pour chaque valeur de l'enum + assertEquals(StatutCompteEpargne.ACTIF, StatutCompteEpargne.valueOf("ACTIF")); + assertEquals(StatutCompteEpargne.INACTIF, StatutCompteEpargne.valueOf("INACTIF")); + assertEquals(StatutCompteEpargne.BLOQUE, StatutCompteEpargne.valueOf("BLOQUE")); + assertEquals(StatutCompteEpargne.EN_CLOTURE, StatutCompteEpargne.valueOf("EN_CLOTURE")); + assertEquals(StatutCompteEpargne.CLOTURE, StatutCompteEpargne.valueOf("CLOTURE")); + } + + @Test + void testValueOfWithInvalidValue() { + // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide + assertThrows(IllegalArgumentException.class, () -> StatutCompteEpargne.valueOf("INVALID")); + } + + @Test + void testGetLibelleActif() { + assertThat(StatutCompteEpargne.ACTIF.getLibelle()) + .isEqualTo("Actif et fonctionnel"); + } + + @Test + void testGetLibelleInactif() { + assertThat(StatutCompteEpargne.INACTIF.getLibelle()) + .isEqualTo("Inactif (sans mouvement prolongé)"); + } + + @Test + void testGetLibelleBloque() { + assertThat(StatutCompteEpargne.BLOQUE.getLibelle()) + .isEqualTo("Bloqué (saisie, garantie, ou décision CA)"); + } + + @Test + void testGetLibelleEnCloture() { + assertThat(StatutCompteEpargne.EN_CLOTURE.getLibelle()) + .isEqualTo("En cours de clôture"); + } + + @Test + void testGetLibelleCloture() { + assertThat(StatutCompteEpargne.CLOTURE.getLibelle()) + .isEqualTo("Clôturé"); + } + + @Test + void testAllLibellesAreNotNull() { + // Vérifie que tous les libellés sont non-null + for (StatutCompteEpargne statut : StatutCompteEpargne.values()) { + assertThat(statut.getLibelle()) + .isNotNull() + .isNotEmpty(); + } + } + + @Test + void testEnumToString() { + // Vérifie que toString() retourne le nom de la constante + assertThat(StatutCompteEpargne.ACTIF.toString()).isEqualTo("ACTIF"); + assertThat(StatutCompteEpargne.BLOQUE.toString()).isEqualTo("BLOQUE"); + assertThat(StatutCompteEpargne.CLOTURE.toString()).isEqualTo("CLOTURE"); + } + + @Test + void testEnumName() { + // Vérifie que name() retourne le nom de la constante + assertThat(StatutCompteEpargne.INACTIF.name()).isEqualTo("INACTIF"); + assertThat(StatutCompteEpargne.EN_CLOTURE.name()).isEqualTo("EN_CLOTURE"); + } + + @Test + void testEnumOrdinal() { + // Vérifie les positions ordinales + assertThat(StatutCompteEpargne.ACTIF.ordinal()).isEqualTo(0); + assertThat(StatutCompteEpargne.INACTIF.ordinal()).isEqualTo(1); + assertThat(StatutCompteEpargne.CLOTURE.ordinal()).isEqualTo(4); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeCompteEpargneTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeCompteEpargneTest.java index f371883..e820e39 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeCompteEpargneTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeCompteEpargneTest.java @@ -1,97 +1,97 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.epargne; - -import org.junit.jupiter.api.Test; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.junit.jupiter.api.Assertions.*; - -/** - * Tests unitaires pour l'enum {@link TypeCompteEpargne}. - */ -class TypeCompteEpargneTest { - - @Test - void testValues() { - // Vérifie que l'enum contient exactement 5 valeurs - assertEquals(5, TypeCompteEpargne.values().length); - } - - @Test - void testValueOf() { - // Teste valueOf() pour chaque valeur de l'enum - assertEquals(TypeCompteEpargne.COURANT, TypeCompteEpargne.valueOf("COURANT")); - assertEquals(TypeCompteEpargne.EPARGNE_LIBRE, TypeCompteEpargne.valueOf("EPARGNE_LIBRE")); - assertEquals(TypeCompteEpargne.EPARGNE_BLOQUEE, TypeCompteEpargne.valueOf("EPARGNE_BLOQUEE")); - assertEquals(TypeCompteEpargne.DEPOT_A_TERME, TypeCompteEpargne.valueOf("DEPOT_A_TERME")); - assertEquals(TypeCompteEpargne.EPARGNE_PROJET, TypeCompteEpargne.valueOf("EPARGNE_PROJET")); - } - - @Test - void testValueOfWithInvalidValue() { - // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide - assertThrows(IllegalArgumentException.class, () -> TypeCompteEpargne.valueOf("INVALID")); - } - - @Test - void testGetLibelleCourant() { - assertThat(TypeCompteEpargne.COURANT.getLibelle()) - .isEqualTo("Compte courant / de transit"); - } - - @Test - void testGetLibelleEpargneLibre() { - assertThat(TypeCompteEpargne.EPARGNE_LIBRE.getLibelle()) - .isEqualTo("Épargne libre / classique"); - } - - @Test - void testGetLibelleEpargneBloquee() { - assertThat(TypeCompteEpargne.EPARGNE_BLOQUEE.getLibelle()) - .isEqualTo("Épargne bloquée (Garantie de crédit)"); - } - - @Test - void testGetLibelleDepotATerme() { - assertThat(TypeCompteEpargne.DEPOT_A_TERME.getLibelle()) - .isEqualTo("Dépôt à terme (DAT)"); - } - - @Test - void testGetLibelleEpargneProjet() { - assertThat(TypeCompteEpargne.EPARGNE_PROJET.getLibelle()) - .isEqualTo("Épargne projet / tontine"); - } - - @Test - void testAllLibellesAreNotNull() { - // Vérifie que tous les libellés sont non-null - for (TypeCompteEpargne type : TypeCompteEpargne.values()) { - assertThat(type.getLibelle()) - .isNotNull() - .isNotEmpty(); - } - } - - @Test - void testEnumToString() { - // Vérifie que toString() retourne le nom de la constante - assertThat(TypeCompteEpargne.COURANT.toString()).isEqualTo("COURANT"); - assertThat(TypeCompteEpargne.EPARGNE_LIBRE.toString()).isEqualTo("EPARGNE_LIBRE"); - assertThat(TypeCompteEpargne.EPARGNE_PROJET.toString()).isEqualTo("EPARGNE_PROJET"); - } - - @Test - void testEnumName() { - // Vérifie que name() retourne le nom de la constante - assertThat(TypeCompteEpargne.EPARGNE_BLOQUEE.name()).isEqualTo("EPARGNE_BLOQUEE"); - assertThat(TypeCompteEpargne.DEPOT_A_TERME.name()).isEqualTo("DEPOT_A_TERME"); - } - - @Test - void testEnumOrdinal() { - // Vérifie les positions ordinales - assertThat(TypeCompteEpargne.COURANT.ordinal()).isEqualTo(0); - assertThat(TypeCompteEpargne.EPARGNE_LIBRE.ordinal()).isEqualTo(1); - assertThat(TypeCompteEpargne.EPARGNE_PROJET.ordinal()).isEqualTo(4); - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.epargne; + +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.junit.jupiter.api.Assertions.*; + +/** + * Tests unitaires pour l'enum {@link TypeCompteEpargne}. + */ +class TypeCompteEpargneTest { + + @Test + void testValues() { + // Vérifie que l'enum contient exactement 5 valeurs + assertEquals(5, TypeCompteEpargne.values().length); + } + + @Test + void testValueOf() { + // Teste valueOf() pour chaque valeur de l'enum + assertEquals(TypeCompteEpargne.COURANT, TypeCompteEpargne.valueOf("COURANT")); + assertEquals(TypeCompteEpargne.EPARGNE_LIBRE, TypeCompteEpargne.valueOf("EPARGNE_LIBRE")); + assertEquals(TypeCompteEpargne.EPARGNE_BLOQUEE, TypeCompteEpargne.valueOf("EPARGNE_BLOQUEE")); + assertEquals(TypeCompteEpargne.DEPOT_A_TERME, TypeCompteEpargne.valueOf("DEPOT_A_TERME")); + assertEquals(TypeCompteEpargne.EPARGNE_PROJET, TypeCompteEpargne.valueOf("EPARGNE_PROJET")); + } + + @Test + void testValueOfWithInvalidValue() { + // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide + assertThrows(IllegalArgumentException.class, () -> TypeCompteEpargne.valueOf("INVALID")); + } + + @Test + void testGetLibelleCourant() { + assertThat(TypeCompteEpargne.COURANT.getLibelle()) + .isEqualTo("Compte courant / de transit"); + } + + @Test + void testGetLibelleEpargneLibre() { + assertThat(TypeCompteEpargne.EPARGNE_LIBRE.getLibelle()) + .isEqualTo("Épargne libre / classique"); + } + + @Test + void testGetLibelleEpargneBloquee() { + assertThat(TypeCompteEpargne.EPARGNE_BLOQUEE.getLibelle()) + .isEqualTo("Épargne bloquée (Garantie de crédit)"); + } + + @Test + void testGetLibelleDepotATerme() { + assertThat(TypeCompteEpargne.DEPOT_A_TERME.getLibelle()) + .isEqualTo("Dépôt à terme (DAT)"); + } + + @Test + void testGetLibelleEpargneProjet() { + assertThat(TypeCompteEpargne.EPARGNE_PROJET.getLibelle()) + .isEqualTo("Épargne projet / tontine"); + } + + @Test + void testAllLibellesAreNotNull() { + // Vérifie que tous les libellés sont non-null + for (TypeCompteEpargne type : TypeCompteEpargne.values()) { + assertThat(type.getLibelle()) + .isNotNull() + .isNotEmpty(); + } + } + + @Test + void testEnumToString() { + // Vérifie que toString() retourne le nom de la constante + assertThat(TypeCompteEpargne.COURANT.toString()).isEqualTo("COURANT"); + assertThat(TypeCompteEpargne.EPARGNE_LIBRE.toString()).isEqualTo("EPARGNE_LIBRE"); + assertThat(TypeCompteEpargne.EPARGNE_PROJET.toString()).isEqualTo("EPARGNE_PROJET"); + } + + @Test + void testEnumName() { + // Vérifie que name() retourne le nom de la constante + assertThat(TypeCompteEpargne.EPARGNE_BLOQUEE.name()).isEqualTo("EPARGNE_BLOQUEE"); + assertThat(TypeCompteEpargne.DEPOT_A_TERME.name()).isEqualTo("DEPOT_A_TERME"); + } + + @Test + void testEnumOrdinal() { + // Vérifie les positions ordinales + assertThat(TypeCompteEpargne.COURANT.ordinal()).isEqualTo(0); + assertThat(TypeCompteEpargne.EPARGNE_LIBRE.ordinal()).isEqualTo(1); + assertThat(TypeCompteEpargne.EPARGNE_PROJET.ordinal()).isEqualTo(4); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeTransactionEpargneTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeTransactionEpargneTest.java index 956e2e3..4a600ee 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeTransactionEpargneTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/mutuelle/epargne/TypeTransactionEpargneTest.java @@ -1,125 +1,125 @@ -package dev.lions.unionflow.server.api.enums.mutuelle.epargne; - -import org.junit.jupiter.api.Test; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.junit.jupiter.api.Assertions.*; - -/** - * Tests unitaires pour l'enum {@link TypeTransactionEpargne}. - */ -class TypeTransactionEpargneTest { - - @Test - void testValues() { - // Vérifie que l'enum contient exactement 9 valeurs - assertEquals(9, TypeTransactionEpargne.values().length); - } - - @Test - void testValueOf() { - // Teste valueOf() pour chaque valeur de l'enum - assertEquals(TypeTransactionEpargne.DEPOT, TypeTransactionEpargne.valueOf("DEPOT")); - assertEquals(TypeTransactionEpargne.RETRAIT, TypeTransactionEpargne.valueOf("RETRAIT")); - assertEquals(TypeTransactionEpargne.TRANSFERT_ENTRANT, TypeTransactionEpargne.valueOf("TRANSFERT_ENTRANT")); - assertEquals(TypeTransactionEpargne.TRANSFERT_SORTANT, TypeTransactionEpargne.valueOf("TRANSFERT_SORTANT")); - assertEquals(TypeTransactionEpargne.PAIEMENT_INTERETS, TypeTransactionEpargne.valueOf("PAIEMENT_INTERETS")); - assertEquals(TypeTransactionEpargne.PRELEVEMENT_FRAIS, TypeTransactionEpargne.valueOf("PRELEVEMENT_FRAIS")); - assertEquals(TypeTransactionEpargne.RETENUE_GARANTIE, TypeTransactionEpargne.valueOf("RETENUE_GARANTIE")); - assertEquals(TypeTransactionEpargne.LIBERATION_GARANTIE, TypeTransactionEpargne.valueOf("LIBERATION_GARANTIE")); - assertEquals(TypeTransactionEpargne.REMBOURSEMENT_CREDIT, TypeTransactionEpargne.valueOf("REMBOURSEMENT_CREDIT")); - } - - @Test - void testValueOfWithInvalidValue() { - // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide - assertThrows(IllegalArgumentException.class, () -> TypeTransactionEpargne.valueOf("INVALID")); - } - - @Test - void testGetLibelleDepot() { - assertThat(TypeTransactionEpargne.DEPOT.getLibelle()) - .isEqualTo("Dépôt sur le compte"); - } - - @Test - void testGetLibelleRetrait() { - assertThat(TypeTransactionEpargne.RETRAIT.getLibelle()) - .isEqualTo("Retrait d'espèces"); - } - - @Test - void testGetLibelleTransfertEntrant() { - assertThat(TypeTransactionEpargne.TRANSFERT_ENTRANT.getLibelle()) - .isEqualTo("Virement/Transfert entrant"); - } - - @Test - void testGetLibelleTransfertSortant() { - assertThat(TypeTransactionEpargne.TRANSFERT_SORTANT.getLibelle()) - .isEqualTo("Virement/Transfert sortant"); - } - - @Test - void testGetLibellePaiementInterets() { - assertThat(TypeTransactionEpargne.PAIEMENT_INTERETS.getLibelle()) - .isEqualTo("Paiement des intérêts créditeurs"); - } - - @Test - void testGetLibellePrelevementFrais() { - assertThat(TypeTransactionEpargne.PRELEVEMENT_FRAIS.getLibelle()) - .isEqualTo("Prélèvement de frais de tenue de compte"); - } - - @Test - void testGetLibelleRetenueGarantie() { - assertThat(TypeTransactionEpargne.RETENUE_GARANTIE.getLibelle()) - .isEqualTo("Gel/Retenue pour garantie de prêt"); - } - - @Test - void testGetLibelleLiberationGarantie() { - assertThat(TypeTransactionEpargne.LIBERATION_GARANTIE.getLibelle()) - .isEqualTo("Libération de fonds de garantie"); - } - - @Test - void testGetLibelleRemboursementCredit() { - assertThat(TypeTransactionEpargne.REMBOURSEMENT_CREDIT.getLibelle()) - .isEqualTo("Remboursement d'une échéance de crédit"); - } - - @Test - void testAllLibellesAreNotNull() { - // Vérifie que tous les libellés sont non-null - for (TypeTransactionEpargne type : TypeTransactionEpargne.values()) { - assertThat(type.getLibelle()) - .isNotNull() - .isNotEmpty(); - } - } - - @Test - void testEnumToString() { - // Vérifie que toString() retourne le nom de la constante - assertThat(TypeTransactionEpargne.DEPOT.toString()).isEqualTo("DEPOT"); - assertThat(TypeTransactionEpargne.RETRAIT.toString()).isEqualTo("RETRAIT"); - assertThat(TypeTransactionEpargne.REMBOURSEMENT_CREDIT.toString()).isEqualTo("REMBOURSEMENT_CREDIT"); - } - - @Test - void testEnumName() { - // Vérifie que name() retourne le nom de la constante - assertThat(TypeTransactionEpargne.TRANSFERT_ENTRANT.name()).isEqualTo("TRANSFERT_ENTRANT"); - assertThat(TypeTransactionEpargne.PAIEMENT_INTERETS.name()).isEqualTo("PAIEMENT_INTERETS"); - } - - @Test - void testEnumOrdinal() { - // Vérifie les positions ordinales - assertThat(TypeTransactionEpargne.DEPOT.ordinal()).isEqualTo(0); - assertThat(TypeTransactionEpargne.RETRAIT.ordinal()).isEqualTo(1); - assertThat(TypeTransactionEpargne.REMBOURSEMENT_CREDIT.ordinal()).isEqualTo(8); - } -} +package dev.lions.unionflow.server.api.enums.mutuelle.epargne; + +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.junit.jupiter.api.Assertions.*; + +/** + * Tests unitaires pour l'enum {@link TypeTransactionEpargne}. + */ +class TypeTransactionEpargneTest { + + @Test + void testValues() { + // Vérifie que l'enum contient exactement 9 valeurs + assertEquals(9, TypeTransactionEpargne.values().length); + } + + @Test + void testValueOf() { + // Teste valueOf() pour chaque valeur de l'enum + assertEquals(TypeTransactionEpargne.DEPOT, TypeTransactionEpargne.valueOf("DEPOT")); + assertEquals(TypeTransactionEpargne.RETRAIT, TypeTransactionEpargne.valueOf("RETRAIT")); + assertEquals(TypeTransactionEpargne.TRANSFERT_ENTRANT, TypeTransactionEpargne.valueOf("TRANSFERT_ENTRANT")); + assertEquals(TypeTransactionEpargne.TRANSFERT_SORTANT, TypeTransactionEpargne.valueOf("TRANSFERT_SORTANT")); + assertEquals(TypeTransactionEpargne.PAIEMENT_INTERETS, TypeTransactionEpargne.valueOf("PAIEMENT_INTERETS")); + assertEquals(TypeTransactionEpargne.PRELEVEMENT_FRAIS, TypeTransactionEpargne.valueOf("PRELEVEMENT_FRAIS")); + assertEquals(TypeTransactionEpargne.RETENUE_GARANTIE, TypeTransactionEpargne.valueOf("RETENUE_GARANTIE")); + assertEquals(TypeTransactionEpargne.LIBERATION_GARANTIE, TypeTransactionEpargne.valueOf("LIBERATION_GARANTIE")); + assertEquals(TypeTransactionEpargne.REMBOURSEMENT_CREDIT, TypeTransactionEpargne.valueOf("REMBOURSEMENT_CREDIT")); + } + + @Test + void testValueOfWithInvalidValue() { + // Vérifie qu'une IllegalArgumentException est levée pour une valeur invalide + assertThrows(IllegalArgumentException.class, () -> TypeTransactionEpargne.valueOf("INVALID")); + } + + @Test + void testGetLibelleDepot() { + assertThat(TypeTransactionEpargne.DEPOT.getLibelle()) + .isEqualTo("Dépôt sur le compte"); + } + + @Test + void testGetLibelleRetrait() { + assertThat(TypeTransactionEpargne.RETRAIT.getLibelle()) + .isEqualTo("Retrait d'espèces"); + } + + @Test + void testGetLibelleTransfertEntrant() { + assertThat(TypeTransactionEpargne.TRANSFERT_ENTRANT.getLibelle()) + .isEqualTo("Virement/Transfert entrant"); + } + + @Test + void testGetLibelleTransfertSortant() { + assertThat(TypeTransactionEpargne.TRANSFERT_SORTANT.getLibelle()) + .isEqualTo("Virement/Transfert sortant"); + } + + @Test + void testGetLibellePaiementInterets() { + assertThat(TypeTransactionEpargne.PAIEMENT_INTERETS.getLibelle()) + .isEqualTo("Paiement des intérêts créditeurs"); + } + + @Test + void testGetLibellePrelevementFrais() { + assertThat(TypeTransactionEpargne.PRELEVEMENT_FRAIS.getLibelle()) + .isEqualTo("Prélèvement de frais de tenue de compte"); + } + + @Test + void testGetLibelleRetenueGarantie() { + assertThat(TypeTransactionEpargne.RETENUE_GARANTIE.getLibelle()) + .isEqualTo("Gel/Retenue pour garantie de prêt"); + } + + @Test + void testGetLibelleLiberationGarantie() { + assertThat(TypeTransactionEpargne.LIBERATION_GARANTIE.getLibelle()) + .isEqualTo("Libération de fonds de garantie"); + } + + @Test + void testGetLibelleRemboursementCredit() { + assertThat(TypeTransactionEpargne.REMBOURSEMENT_CREDIT.getLibelle()) + .isEqualTo("Remboursement d'une échéance de crédit"); + } + + @Test + void testAllLibellesAreNotNull() { + // Vérifie que tous les libellés sont non-null + for (TypeTransactionEpargne type : TypeTransactionEpargne.values()) { + assertThat(type.getLibelle()) + .isNotNull() + .isNotEmpty(); + } + } + + @Test + void testEnumToString() { + // Vérifie que toString() retourne le nom de la constante + assertThat(TypeTransactionEpargne.DEPOT.toString()).isEqualTo("DEPOT"); + assertThat(TypeTransactionEpargne.RETRAIT.toString()).isEqualTo("RETRAIT"); + assertThat(TypeTransactionEpargne.REMBOURSEMENT_CREDIT.toString()).isEqualTo("REMBOURSEMENT_CREDIT"); + } + + @Test + void testEnumName() { + // Vérifie que name() retourne le nom de la constante + assertThat(TypeTransactionEpargne.TRANSFERT_ENTRANT.name()).isEqualTo("TRANSFERT_ENTRANT"); + assertThat(TypeTransactionEpargne.PAIEMENT_INTERETS.name()).isEqualTo("PAIEMENT_INTERETS"); + } + + @Test + void testEnumOrdinal() { + // Vérifie les positions ordinales + assertThat(TypeTransactionEpargne.DEPOT.ordinal()).isEqualTo(0); + assertThat(TypeTransactionEpargne.RETRAIT.ordinal()).isEqualTo(1); + assertThat(TypeTransactionEpargne.REMBOURSEMENT_CREDIT.ordinal()).isEqualTo(8); + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/notification/CanalNotificationTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/notification/CanalNotificationTest.java index d437a1e..4d5ab23 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/notification/CanalNotificationTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/notification/CanalNotificationTest.java @@ -1,424 +1,424 @@ -package dev.lions.unionflow.server.api.enums.notification; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour CanalNotification") -class CanalNotificationTest { - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - CanalNotification[] values = CanalNotification.values(); - assertThat(values).hasSize(16); - } - - @ParameterizedTest - @EnumSource(CanalNotification.class) - @DisplayName("Test getters de base pour toutes les valeurs") - void testGettersBase(CanalNotification canal) { - assertThat(canal.getId()).isNotNull().isNotEmpty(); - assertThat(canal.getNom()).isNotNull().isNotEmpty(); - assertThat(canal.getDescription()).isNotNull().isNotEmpty(); - assertThat(canal.getImportance()).isBetween(1, 5); - assertThat(canal.getCouleur()).isNotNull().matches("#[0-9A-Fa-f]{6}"); - assertThat(canal.getTypeDefaut()).isNotNull().isNotEmpty(); - } - - @ParameterizedTest - @CsvSource({ - "URGENT_CHANNEL, true", - "ERROR_CHANNEL, true", - "WARNING_CHANNEL, true", - "IMPORTANT_CHANNEL, true", - "REMINDER_CHANNEL, true", - "SUCCESS_CHANNEL, false", - "CELEBRATION_CHANNEL, false", - "DEFAULT_CHANNEL, false" - }) - @DisplayName("isSonActive - canaux avec son activé") - void testIsSonActive(CanalNotification canal, Boolean expected) { - assertThat(canal.isSonActive()).isEqualTo(expected); - } - - @ParameterizedTest - @CsvSource({ - "URGENT_CHANNEL, true", - "ERROR_CHANNEL, true", - "WARNING_CHANNEL, true", - "IMPORTANT_CHANNEL, true", - "REMINDER_CHANNEL, true", - "SUCCESS_CHANNEL, false", - "CELEBRATION_CHANNEL, false", - "DEFAULT_CHANNEL, false" - }) - @DisplayName("isVibrationActive - canaux avec vibration activée") - void testIsVibrationActive(CanalNotification canal, Boolean expected) { - assertThat(canal.isVibrationActive()).isEqualTo(expected); - } - - @ParameterizedTest - @CsvSource({ - "URGENT_CHANNEL, true", - "ERROR_CHANNEL, false", - "WARNING_CHANNEL, false", - "IMPORTANT_CHANNEL, false", - "REMINDER_CHANNEL, false", - "SUCCESS_CHANNEL, false", - "CELEBRATION_CHANNEL, false", - "DEFAULT_CHANNEL, false" - }) - @DisplayName("isLumiereLED - canaux avec lumière LED activée") - void testIsLumiereLED(CanalNotification canal, Boolean expected) { - assertThat(canal.isLumiereLED()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isCritique") - class IsCritiqueTests { - - @ParameterizedTest - @CsvSource({ - "URGENT_CHANNEL, true", - "ERROR_CHANNEL, true", - "WARNING_CHANNEL, true", - "IMPORTANT_CHANNEL, true", - "REMINDER_CHANNEL, false", - "SUCCESS_CHANNEL, false", - "DEFAULT_CHANNEL, false" - }) - @DisplayName("isCritique - importance >= 4") - void testIsCritique(CanalNotification canal, Boolean expected) { - assertThat(canal.isCritique()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isSilencieux") - class IsSilencieuxTests { - - @ParameterizedTest - @CsvSource({ - "URGENT_CHANNEL, false", - "EVENTS_CHANNEL, false", - "SUCCESS_CHANNEL, true", - "CELEBRATION_CHANNEL, true", - "DEFAULT_CHANNEL, true" - }) - @DisplayName("isSilencieux - pas de son ni vibration") - void testIsSilencieux(CanalNotification canal, Boolean expected) { - assertThat(canal.isSilencieux()).isEqualTo(expected); - } - - @Test - @DisplayName("isSilencieux true quand son et vibration désactivés") - void testIsSilencieuxTrue() { - assertThat(CanalNotification.SUCCESS_CHANNEL.isSilencieux()).isTrue(); - assertThat(CanalNotification.DEFAULT_CHANNEL.isSilencieux()).isTrue(); - } - - @Test - @DisplayName("isSilencieux false quand son ou vibration activé") - void testIsSilencieuxFalse() { - assertThat(CanalNotification.URGENT_CHANNEL.isSilencieux()).isFalse(); - assertThat(CanalNotification.REMINDER_CHANNEL.isSilencieux()).isFalse(); - } - } - - @Nested - @DisplayName("Tests getImportanceAndroid") - class GetImportanceAndroidTests { - - @ParameterizedTest - @CsvSource({ - "URGENT_CHANNEL, 5, IMPORTANCE_MAX", - "ERROR_CHANNEL, 4, IMPORTANCE_HIGH", - "WARNING_CHANNEL, 4, IMPORTANCE_HIGH", - "IMPORTANT_CHANNEL, 4, IMPORTANCE_HIGH", - "REMINDER_CHANNEL, 3, IMPORTANCE_DEFAULT", - "SUCCESS_CHANNEL, 2, IMPORTANCE_LOW", - "CELEBRATION_CHANNEL, 2, IMPORTANCE_LOW", - "DEFAULT_CHANNEL, 2, IMPORTANCE_LOW" - }) - @DisplayName("getImportanceAndroid - mapping correct") - void testGetImportanceAndroid(CanalNotification canal, int importance, String expected) { - assertThat(canal.getImportance()).isEqualTo(importance); - assertThat(canal.getImportanceAndroid()).isEqualTo(expected); - } - - @Test - @DisplayName("getImportanceAndroid - importance 1 = IMPORTANCE_MIN") - void testGetImportanceAndroidMin() { - // Tester avec la réflexion pour créer un canal avec importance 1 - try { - java.lang.reflect.Field importanceField = CanalNotification.class.getDeclaredField("importance"); - importanceField.setAccessible(true); - int importanceOriginale = (int) importanceField.get(CanalNotification.DEFAULT_CHANNEL); - - // Modifier temporairement l'importance à 1 - importanceField.setInt(CanalNotification.DEFAULT_CHANNEL, 1); - - // Maintenant importance = 1 devrait retourner IMPORTANCE_MIN - assertThat(CanalNotification.DEFAULT_CHANNEL.getImportanceAndroid()).isEqualTo("IMPORTANCE_MIN"); - - // Restaurer l'importance originale - importanceField.setInt(CanalNotification.DEFAULT_CHANNEL, importanceOriginale); - } catch (Exception e) { - org.junit.jupiter.api.Assumptions.assumeTrue(false, "Réflexion non disponible"); - } - } - - @Test - @DisplayName("getImportanceAndroid - importance invalide = IMPORTANCE_DEFAULT") - void testGetImportanceAndroidDefault() { - // Tester avec la réflexion pour créer un canal avec importance invalide - try { - java.lang.reflect.Field importanceField = CanalNotification.class.getDeclaredField("importance"); - importanceField.setAccessible(true); - int importanceOriginale = (int) importanceField.get(CanalNotification.DEFAULT_CHANNEL); - - // Modifier temporairement l'importance à 99 (invalide) - importanceField.setInt(CanalNotification.DEFAULT_CHANNEL, 99); - - // Maintenant importance = 99 devrait retourner IMPORTANCE_DEFAULT (default) - assertThat(CanalNotification.DEFAULT_CHANNEL.getImportanceAndroid()).isEqualTo("IMPORTANCE_DEFAULT"); - - // Restaurer l'importance originale - importanceField.setInt(CanalNotification.DEFAULT_CHANNEL, importanceOriginale); - } catch (Exception e) { - org.junit.jupiter.api.Assumptions.assumeTrue(false, "Réflexion non disponible"); - } - } - } - - @Nested - @DisplayName("Tests getPrioriteIOS") - class GetPrioriteIOSTests { - - @Test - @DisplayName("getPrioriteIOS - importance >= 4 = high") - void testGetPrioriteIOSHigh() { - CanalNotification canal = CanalNotification.URGENT_CHANNEL; - assertThat(canal.getPrioriteIOS()).isEqualTo("high"); - } - - @Test - @DisplayName("getPrioriteIOS - importance < 4 = low") - void testGetPrioriteIOSLow() { - CanalNotification canal = CanalNotification.DEFAULT_CHANNEL; - assertThat(canal.getPrioriteIOS()).isEqualTo("low"); - } - } - - @Nested - @DisplayName("Tests getSonDefaut") - class GetSonDefautTests { - - @ParameterizedTest - @CsvSource({ - "URGENT_CHANNEL, urgent_sound.mp3", - "ERROR_CHANNEL, error_sound.mp3", - "WARNING_CHANNEL, warning_sound.mp3", - "IMPORTANT_CHANNEL, important_sound.mp3", - "REMINDER_CHANNEL, reminder_sound.mp3", - "SUCCESS_CHANNEL, success_sound.mp3", - "CELEBRATION_CHANNEL, celebration_sound.mp3", - "DEFAULT_CHANNEL, default" - }) - @DisplayName("getSonDefaut - tous les canaux") - void testGetSonDefaut(CanalNotification canal, String expected) { - assertThat(canal.getSonDefaut()).isEqualTo(expected); - } - - @Test - @DisplayName("getSonDefaut - canaux catégoriels (default)") - void testGetSonDefautCanauxCategories() { - assertThat(CanalNotification.EVENTS_CHANNEL.getSonDefaut()).isEqualTo("default"); - assertThat(CanalNotification.PAYMENTS_CHANNEL.getSonDefaut()).isEqualTo("default"); - assertThat(CanalNotification.SOLIDARITY_CHANNEL.getSonDefaut()).isEqualTo("default"); - assertThat(CanalNotification.MEMBERS_CHANNEL.getSonDefaut()).isEqualTo("default"); - assertThat(CanalNotification.ORGANIZATION_CHANNEL.getSonDefaut()).isEqualTo("default"); - assertThat(CanalNotification.SYSTEM_CHANNEL.getSonDefaut()).isEqualTo("default"); - assertThat(CanalNotification.MESSAGES_CHANNEL.getSonDefaut()).isEqualTo("default"); - assertThat(CanalNotification.LOCATION_CHANNEL.getSonDefaut()).isEqualTo("default"); - } - } - - @Nested - @DisplayName("Tests getPatternVibration") - class GetPatternVibrationTests { - - @Test - @DisplayName("getPatternVibration - URGENT_CHANNEL") - void testGetPatternVibrationUrgent() { - long[] pattern = CanalNotification.URGENT_CHANNEL.getPatternVibration(); - assertThat(pattern).isNotEmpty(); - assertThat(pattern[0]).isEqualTo(0); - assertThat(pattern).hasSize(6); // Triple vibration - } - - @Test - @DisplayName("getPatternVibration - ERROR_CHANNEL") - void testGetPatternVibrationError() { - long[] pattern = CanalNotification.ERROR_CHANNEL.getPatternVibration(); - assertThat(pattern).hasSize(4); // Double vibration longue - assertThat(pattern[0]).isEqualTo(0); - } - - @Test - @DisplayName("getPatternVibration - WARNING_CHANNEL") - void testGetPatternVibrationWarning() { - long[] pattern = CanalNotification.WARNING_CHANNEL.getPatternVibration(); - assertThat(pattern).hasSize(4); // Double vibration courte - assertThat(pattern[0]).isEqualTo(0); - } - - @Test - @DisplayName("getPatternVibration - IMPORTANT_CHANNEL") - void testGetPatternVibrationImportant() { - long[] pattern = CanalNotification.IMPORTANT_CHANNEL.getPatternVibration(); - assertThat(pattern).hasSize(4); // Vibration distinctive - assertThat(pattern[0]).isEqualTo(0); - } - - @Test - @DisplayName("getPatternVibration - REMINDER_CHANNEL") - void testGetPatternVibrationReminder() { - long[] pattern = CanalNotification.REMINDER_CHANNEL.getPatternVibration(); - assertThat(pattern).hasSize(4); // Vibration douce - assertThat(pattern[0]).isEqualTo(0); - } - - @Test - @DisplayName("getPatternVibration - autres canaux (default)") - void testGetPatternVibrationDefault() { - long[] pattern = CanalNotification.SUCCESS_CHANNEL.getPatternVibration(); - assertThat(pattern).hasSize(2); // Vibration simple - assertThat(pattern[0]).isEqualTo(0); - - pattern = CanalNotification.DEFAULT_CHANNEL.getPatternVibration(); - assertThat(pattern).hasSize(2); // Vibration simple - assertThat(pattern[0]).isEqualTo(0); - } - - @ParameterizedTest - @EnumSource(CanalNotification.class) - @DisplayName("getPatternVibration - tous les canaux retournent un pattern valide") - void testGetPatternVibrationTousCanaux(CanalNotification canal) { - long[] pattern = canal.getPatternVibration(); - assertThat(pattern).isNotNull(); - assertThat(pattern.length).isGreaterThan(0); - assertThat(pattern[0]).isEqualTo(0); - } - } - - @Nested - @DisplayName("Tests peutEtreDesactive") - class PeutEtreDesactiveTests { - - @Test - @DisplayName("peutEtreDesactive - URGENT_CHANNEL ne peut pas être désactivé") - void testPeutEtreDesactiveUrgent() { - assertThat(CanalNotification.URGENT_CHANNEL.peutEtreDesactive()).isFalse(); - } - - @Test - @DisplayName("peutEtreDesactive - ERROR_CHANNEL ne peut pas être désactivé") - void testPeutEtreDesactiveError() { - assertThat(CanalNotification.ERROR_CHANNEL.peutEtreDesactive()).isFalse(); - } - - @Test - @DisplayName("peutEtreDesactive - autres canaux peuvent être désactivés") - void testPeutEtreDesactiveAutres() { - assertThat(CanalNotification.DEFAULT_CHANNEL.peutEtreDesactive()).isTrue(); - assertThat(CanalNotification.SUCCESS_CHANNEL.peutEtreDesactive()).isTrue(); - } - } - - @Nested - @DisplayName("Tests getDureeVieMs") - class GetDureeVieMsTests { - - @ParameterizedTest - @CsvSource({ - "URGENT_CHANNEL, 3600000", - "ERROR_CHANNEL, 86400000", - "WARNING_CHANNEL, 172800000", - "IMPORTANT_CHANNEL, 259200000", - "REMINDER_CHANNEL, 86400000", - "SUCCESS_CHANNEL, 172800000", - "CELEBRATION_CHANNEL, 259200000", - "DEFAULT_CHANNEL, 604800000" - }) - @DisplayName("getDureeVieMs - toutes les durées") - void testGetDureeVieMs(CanalNotification canal, long expectedMs) { - assertThat(canal.getDureeVieMs()).isEqualTo(expectedMs); - } - - @Test - @DisplayName("getDureeVieMs - canaux catégoriels (default = 1 semaine)") - void testGetDureeVieMsCanauxCategories() { - assertThat(CanalNotification.EVENTS_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); - assertThat(CanalNotification.PAYMENTS_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); - assertThat(CanalNotification.SOLIDARITY_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); - assertThat(CanalNotification.MEMBERS_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); - assertThat(CanalNotification.ORGANIZATION_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); - assertThat(CanalNotification.SYSTEM_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); - assertThat(CanalNotification.MESSAGES_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); - assertThat(CanalNotification.LOCATION_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); - } - } - - @Nested - @DisplayName("Tests méthodes statiques") - class MethodesStatiquesTests { - - @Test - @DisplayName("parId - trouve le canal") - void testParId() { - assertThat(CanalNotification.parId("urgent")).isEqualTo(CanalNotification.URGENT_CHANNEL); - assertThat(CanalNotification.parId("default")).isEqualTo(CanalNotification.DEFAULT_CHANNEL); - } - - @Test - @DisplayName("parId - id inexistant retourne DEFAULT_CHANNEL") - void testParIdInexistant() { - assertThat(CanalNotification.parId("inexistant")).isEqualTo(CanalNotification.DEFAULT_CHANNEL); - } - - @Test - @DisplayName("getCanauxCritiques - retourne les canaux critiques") - void testGetCanauxCritiques() { - CanalNotification[] canaux = CanalNotification.getCanauxCritiques(); - assertThat(canaux).hasSize(4); - assertThat(canaux).containsExactly( - CanalNotification.URGENT_CHANNEL, - CanalNotification.ERROR_CHANNEL, - CanalNotification.WARNING_CHANNEL, - CanalNotification.IMPORTANT_CHANNEL); - } - - @Test - @DisplayName("getCanauxCategories - retourne les canaux catégoriels") - void testGetCanauxCategories() { - CanalNotification[] canaux = CanalNotification.getCanauxCategories(); - assertThat(canaux).hasSize(8); - assertThat(canaux).contains( - CanalNotification.EVENTS_CHANNEL, - CanalNotification.PAYMENTS_CHANNEL, - CanalNotification.SOLIDARITY_CHANNEL); - } - } -} +package dev.lions.unionflow.server.api.enums.notification; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour CanalNotification") +class CanalNotificationTest { + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + CanalNotification[] values = CanalNotification.values(); + assertThat(values).hasSize(16); + } + + @ParameterizedTest + @EnumSource(CanalNotification.class) + @DisplayName("Test getters de base pour toutes les valeurs") + void testGettersBase(CanalNotification canal) { + assertThat(canal.getId()).isNotNull().isNotEmpty(); + assertThat(canal.getNom()).isNotNull().isNotEmpty(); + assertThat(canal.getDescription()).isNotNull().isNotEmpty(); + assertThat(canal.getImportance()).isBetween(1, 5); + assertThat(canal.getCouleur()).isNotNull().matches("#[0-9A-Fa-f]{6}"); + assertThat(canal.getTypeDefaut()).isNotNull().isNotEmpty(); + } + + @ParameterizedTest + @CsvSource({ + "URGENT_CHANNEL, true", + "ERROR_CHANNEL, true", + "WARNING_CHANNEL, true", + "IMPORTANT_CHANNEL, true", + "REMINDER_CHANNEL, true", + "SUCCESS_CHANNEL, false", + "CELEBRATION_CHANNEL, false", + "DEFAULT_CHANNEL, false" + }) + @DisplayName("isSonActive - canaux avec son activé") + void testIsSonActive(CanalNotification canal, Boolean expected) { + assertThat(canal.isSonActive()).isEqualTo(expected); + } + + @ParameterizedTest + @CsvSource({ + "URGENT_CHANNEL, true", + "ERROR_CHANNEL, true", + "WARNING_CHANNEL, true", + "IMPORTANT_CHANNEL, true", + "REMINDER_CHANNEL, true", + "SUCCESS_CHANNEL, false", + "CELEBRATION_CHANNEL, false", + "DEFAULT_CHANNEL, false" + }) + @DisplayName("isVibrationActive - canaux avec vibration activée") + void testIsVibrationActive(CanalNotification canal, Boolean expected) { + assertThat(canal.isVibrationActive()).isEqualTo(expected); + } + + @ParameterizedTest + @CsvSource({ + "URGENT_CHANNEL, true", + "ERROR_CHANNEL, false", + "WARNING_CHANNEL, false", + "IMPORTANT_CHANNEL, false", + "REMINDER_CHANNEL, false", + "SUCCESS_CHANNEL, false", + "CELEBRATION_CHANNEL, false", + "DEFAULT_CHANNEL, false" + }) + @DisplayName("isLumiereLED - canaux avec lumière LED activée") + void testIsLumiereLED(CanalNotification canal, Boolean expected) { + assertThat(canal.isLumiereLED()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isCritique") + class IsCritiqueTests { + + @ParameterizedTest + @CsvSource({ + "URGENT_CHANNEL, true", + "ERROR_CHANNEL, true", + "WARNING_CHANNEL, true", + "IMPORTANT_CHANNEL, true", + "REMINDER_CHANNEL, false", + "SUCCESS_CHANNEL, false", + "DEFAULT_CHANNEL, false" + }) + @DisplayName("isCritique - importance >= 4") + void testIsCritique(CanalNotification canal, Boolean expected) { + assertThat(canal.isCritique()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isSilencieux") + class IsSilencieuxTests { + + @ParameterizedTest + @CsvSource({ + "URGENT_CHANNEL, false", + "EVENTS_CHANNEL, false", + "SUCCESS_CHANNEL, true", + "CELEBRATION_CHANNEL, true", + "DEFAULT_CHANNEL, true" + }) + @DisplayName("isSilencieux - pas de son ni vibration") + void testIsSilencieux(CanalNotification canal, Boolean expected) { + assertThat(canal.isSilencieux()).isEqualTo(expected); + } + + @Test + @DisplayName("isSilencieux true quand son et vibration désactivés") + void testIsSilencieuxTrue() { + assertThat(CanalNotification.SUCCESS_CHANNEL.isSilencieux()).isTrue(); + assertThat(CanalNotification.DEFAULT_CHANNEL.isSilencieux()).isTrue(); + } + + @Test + @DisplayName("isSilencieux false quand son ou vibration activé") + void testIsSilencieuxFalse() { + assertThat(CanalNotification.URGENT_CHANNEL.isSilencieux()).isFalse(); + assertThat(CanalNotification.REMINDER_CHANNEL.isSilencieux()).isFalse(); + } + } + + @Nested + @DisplayName("Tests getImportanceAndroid") + class GetImportanceAndroidTests { + + @ParameterizedTest + @CsvSource({ + "URGENT_CHANNEL, 5, IMPORTANCE_MAX", + "ERROR_CHANNEL, 4, IMPORTANCE_HIGH", + "WARNING_CHANNEL, 4, IMPORTANCE_HIGH", + "IMPORTANT_CHANNEL, 4, IMPORTANCE_HIGH", + "REMINDER_CHANNEL, 3, IMPORTANCE_DEFAULT", + "SUCCESS_CHANNEL, 2, IMPORTANCE_LOW", + "CELEBRATION_CHANNEL, 2, IMPORTANCE_LOW", + "DEFAULT_CHANNEL, 2, IMPORTANCE_LOW" + }) + @DisplayName("getImportanceAndroid - mapping correct") + void testGetImportanceAndroid(CanalNotification canal, int importance, String expected) { + assertThat(canal.getImportance()).isEqualTo(importance); + assertThat(canal.getImportanceAndroid()).isEqualTo(expected); + } + + @Test + @DisplayName("getImportanceAndroid - importance 1 = IMPORTANCE_MIN") + void testGetImportanceAndroidMin() { + // Tester avec la réflexion pour créer un canal avec importance 1 + try { + java.lang.reflect.Field importanceField = CanalNotification.class.getDeclaredField("importance"); + importanceField.setAccessible(true); + int importanceOriginale = (int) importanceField.get(CanalNotification.DEFAULT_CHANNEL); + + // Modifier temporairement l'importance à 1 + importanceField.setInt(CanalNotification.DEFAULT_CHANNEL, 1); + + // Maintenant importance = 1 devrait retourner IMPORTANCE_MIN + assertThat(CanalNotification.DEFAULT_CHANNEL.getImportanceAndroid()).isEqualTo("IMPORTANCE_MIN"); + + // Restaurer l'importance originale + importanceField.setInt(CanalNotification.DEFAULT_CHANNEL, importanceOriginale); + } catch (Exception e) { + org.junit.jupiter.api.Assumptions.assumeTrue(false, "Réflexion non disponible"); + } + } + + @Test + @DisplayName("getImportanceAndroid - importance invalide = IMPORTANCE_DEFAULT") + void testGetImportanceAndroidDefault() { + // Tester avec la réflexion pour créer un canal avec importance invalide + try { + java.lang.reflect.Field importanceField = CanalNotification.class.getDeclaredField("importance"); + importanceField.setAccessible(true); + int importanceOriginale = (int) importanceField.get(CanalNotification.DEFAULT_CHANNEL); + + // Modifier temporairement l'importance à 99 (invalide) + importanceField.setInt(CanalNotification.DEFAULT_CHANNEL, 99); + + // Maintenant importance = 99 devrait retourner IMPORTANCE_DEFAULT (default) + assertThat(CanalNotification.DEFAULT_CHANNEL.getImportanceAndroid()).isEqualTo("IMPORTANCE_DEFAULT"); + + // Restaurer l'importance originale + importanceField.setInt(CanalNotification.DEFAULT_CHANNEL, importanceOriginale); + } catch (Exception e) { + org.junit.jupiter.api.Assumptions.assumeTrue(false, "Réflexion non disponible"); + } + } + } + + @Nested + @DisplayName("Tests getPrioriteIOS") + class GetPrioriteIOSTests { + + @Test + @DisplayName("getPrioriteIOS - importance >= 4 = high") + void testGetPrioriteIOSHigh() { + CanalNotification canal = CanalNotification.URGENT_CHANNEL; + assertThat(canal.getPrioriteIOS()).isEqualTo("high"); + } + + @Test + @DisplayName("getPrioriteIOS - importance < 4 = low") + void testGetPrioriteIOSLow() { + CanalNotification canal = CanalNotification.DEFAULT_CHANNEL; + assertThat(canal.getPrioriteIOS()).isEqualTo("low"); + } + } + + @Nested + @DisplayName("Tests getSonDefaut") + class GetSonDefautTests { + + @ParameterizedTest + @CsvSource({ + "URGENT_CHANNEL, urgent_sound.mp3", + "ERROR_CHANNEL, error_sound.mp3", + "WARNING_CHANNEL, warning_sound.mp3", + "IMPORTANT_CHANNEL, important_sound.mp3", + "REMINDER_CHANNEL, reminder_sound.mp3", + "SUCCESS_CHANNEL, success_sound.mp3", + "CELEBRATION_CHANNEL, celebration_sound.mp3", + "DEFAULT_CHANNEL, default" + }) + @DisplayName("getSonDefaut - tous les canaux") + void testGetSonDefaut(CanalNotification canal, String expected) { + assertThat(canal.getSonDefaut()).isEqualTo(expected); + } + + @Test + @DisplayName("getSonDefaut - canaux catégoriels (default)") + void testGetSonDefautCanauxCategories() { + assertThat(CanalNotification.EVENTS_CHANNEL.getSonDefaut()).isEqualTo("default"); + assertThat(CanalNotification.PAYMENTS_CHANNEL.getSonDefaut()).isEqualTo("default"); + assertThat(CanalNotification.SOLIDARITY_CHANNEL.getSonDefaut()).isEqualTo("default"); + assertThat(CanalNotification.MEMBERS_CHANNEL.getSonDefaut()).isEqualTo("default"); + assertThat(CanalNotification.ORGANIZATION_CHANNEL.getSonDefaut()).isEqualTo("default"); + assertThat(CanalNotification.SYSTEM_CHANNEL.getSonDefaut()).isEqualTo("default"); + assertThat(CanalNotification.MESSAGES_CHANNEL.getSonDefaut()).isEqualTo("default"); + assertThat(CanalNotification.LOCATION_CHANNEL.getSonDefaut()).isEqualTo("default"); + } + } + + @Nested + @DisplayName("Tests getPatternVibration") + class GetPatternVibrationTests { + + @Test + @DisplayName("getPatternVibration - URGENT_CHANNEL") + void testGetPatternVibrationUrgent() { + long[] pattern = CanalNotification.URGENT_CHANNEL.getPatternVibration(); + assertThat(pattern).isNotEmpty(); + assertThat(pattern[0]).isEqualTo(0); + assertThat(pattern).hasSize(6); // Triple vibration + } + + @Test + @DisplayName("getPatternVibration - ERROR_CHANNEL") + void testGetPatternVibrationError() { + long[] pattern = CanalNotification.ERROR_CHANNEL.getPatternVibration(); + assertThat(pattern).hasSize(4); // Double vibration longue + assertThat(pattern[0]).isEqualTo(0); + } + + @Test + @DisplayName("getPatternVibration - WARNING_CHANNEL") + void testGetPatternVibrationWarning() { + long[] pattern = CanalNotification.WARNING_CHANNEL.getPatternVibration(); + assertThat(pattern).hasSize(4); // Double vibration courte + assertThat(pattern[0]).isEqualTo(0); + } + + @Test + @DisplayName("getPatternVibration - IMPORTANT_CHANNEL") + void testGetPatternVibrationImportant() { + long[] pattern = CanalNotification.IMPORTANT_CHANNEL.getPatternVibration(); + assertThat(pattern).hasSize(4); // Vibration distinctive + assertThat(pattern[0]).isEqualTo(0); + } + + @Test + @DisplayName("getPatternVibration - REMINDER_CHANNEL") + void testGetPatternVibrationReminder() { + long[] pattern = CanalNotification.REMINDER_CHANNEL.getPatternVibration(); + assertThat(pattern).hasSize(4); // Vibration douce + assertThat(pattern[0]).isEqualTo(0); + } + + @Test + @DisplayName("getPatternVibration - autres canaux (default)") + void testGetPatternVibrationDefault() { + long[] pattern = CanalNotification.SUCCESS_CHANNEL.getPatternVibration(); + assertThat(pattern).hasSize(2); // Vibration simple + assertThat(pattern[0]).isEqualTo(0); + + pattern = CanalNotification.DEFAULT_CHANNEL.getPatternVibration(); + assertThat(pattern).hasSize(2); // Vibration simple + assertThat(pattern[0]).isEqualTo(0); + } + + @ParameterizedTest + @EnumSource(CanalNotification.class) + @DisplayName("getPatternVibration - tous les canaux retournent un pattern valide") + void testGetPatternVibrationTousCanaux(CanalNotification canal) { + long[] pattern = canal.getPatternVibration(); + assertThat(pattern).isNotNull(); + assertThat(pattern.length).isGreaterThan(0); + assertThat(pattern[0]).isEqualTo(0); + } + } + + @Nested + @DisplayName("Tests peutEtreDesactive") + class PeutEtreDesactiveTests { + + @Test + @DisplayName("peutEtreDesactive - URGENT_CHANNEL ne peut pas être désactivé") + void testPeutEtreDesactiveUrgent() { + assertThat(CanalNotification.URGENT_CHANNEL.peutEtreDesactive()).isFalse(); + } + + @Test + @DisplayName("peutEtreDesactive - ERROR_CHANNEL ne peut pas être désactivé") + void testPeutEtreDesactiveError() { + assertThat(CanalNotification.ERROR_CHANNEL.peutEtreDesactive()).isFalse(); + } + + @Test + @DisplayName("peutEtreDesactive - autres canaux peuvent être désactivés") + void testPeutEtreDesactiveAutres() { + assertThat(CanalNotification.DEFAULT_CHANNEL.peutEtreDesactive()).isTrue(); + assertThat(CanalNotification.SUCCESS_CHANNEL.peutEtreDesactive()).isTrue(); + } + } + + @Nested + @DisplayName("Tests getDureeVieMs") + class GetDureeVieMsTests { + + @ParameterizedTest + @CsvSource({ + "URGENT_CHANNEL, 3600000", + "ERROR_CHANNEL, 86400000", + "WARNING_CHANNEL, 172800000", + "IMPORTANT_CHANNEL, 259200000", + "REMINDER_CHANNEL, 86400000", + "SUCCESS_CHANNEL, 172800000", + "CELEBRATION_CHANNEL, 259200000", + "DEFAULT_CHANNEL, 604800000" + }) + @DisplayName("getDureeVieMs - toutes les durées") + void testGetDureeVieMs(CanalNotification canal, long expectedMs) { + assertThat(canal.getDureeVieMs()).isEqualTo(expectedMs); + } + + @Test + @DisplayName("getDureeVieMs - canaux catégoriels (default = 1 semaine)") + void testGetDureeVieMsCanauxCategories() { + assertThat(CanalNotification.EVENTS_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); + assertThat(CanalNotification.PAYMENTS_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); + assertThat(CanalNotification.SOLIDARITY_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); + assertThat(CanalNotification.MEMBERS_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); + assertThat(CanalNotification.ORGANIZATION_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); + assertThat(CanalNotification.SYSTEM_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); + assertThat(CanalNotification.MESSAGES_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); + assertThat(CanalNotification.LOCATION_CHANNEL.getDureeVieMs()).isEqualTo(604800000L); + } + } + + @Nested + @DisplayName("Tests méthodes statiques") + class MethodesStatiquesTests { + + @Test + @DisplayName("parId - trouve le canal") + void testParId() { + assertThat(CanalNotification.parId("urgent")).isEqualTo(CanalNotification.URGENT_CHANNEL); + assertThat(CanalNotification.parId("default")).isEqualTo(CanalNotification.DEFAULT_CHANNEL); + } + + @Test + @DisplayName("parId - id inexistant retourne DEFAULT_CHANNEL") + void testParIdInexistant() { + assertThat(CanalNotification.parId("inexistant")).isEqualTo(CanalNotification.DEFAULT_CHANNEL); + } + + @Test + @DisplayName("getCanauxCritiques - retourne les canaux critiques") + void testGetCanauxCritiques() { + CanalNotification[] canaux = CanalNotification.getCanauxCritiques(); + assertThat(canaux).hasSize(4); + assertThat(canaux).containsExactly( + CanalNotification.URGENT_CHANNEL, + CanalNotification.ERROR_CHANNEL, + CanalNotification.WARNING_CHANNEL, + CanalNotification.IMPORTANT_CHANNEL); + } + + @Test + @DisplayName("getCanauxCategories - retourne les canaux catégoriels") + void testGetCanauxCategories() { + CanalNotification[] canaux = CanalNotification.getCanauxCategories(); + assertThat(canaux).hasSize(8); + assertThat(canaux).contains( + CanalNotification.EVENTS_CHANNEL, + CanalNotification.PAYMENTS_CHANNEL, + CanalNotification.SOLIDARITY_CHANNEL); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/notification/PrioriteNotificationTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/notification/PrioriteNotificationTest.java index cdd3450..f96dc46 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/notification/PrioriteNotificationTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/notification/PrioriteNotificationTest.java @@ -1,62 +1,62 @@ -package dev.lions.unionflow.server.api.enums.notification; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour PrioriteNotification. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests PrioriteNotification") -class PrioriteNotificationTest { - - @Test - @DisplayName("Toutes les priorités doivent avoir un libellé") - void testToutesLesPrioritesOntLibelle() { - for (PrioriteNotification priorite : PrioriteNotification.values()) { - assertThat(priorite.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("CRITIQUE doit avoir le libellé correct") - void testCritique() { - assertThat(PrioriteNotification.CRITIQUE.getLibelle()).isEqualTo("Critique"); - } - - @Test - @DisplayName("HAUTE doit avoir le libellé correct") - void testHaute() { - assertThat(PrioriteNotification.HAUTE.getLibelle()).isEqualTo("Haute"); - } - - @Test - @DisplayName("NORMALE doit avoir le libellé correct") - void testNormale() { - assertThat(PrioriteNotification.NORMALE.getLibelle()).isEqualTo("Normale"); - } - - @Test - @DisplayName("BASSE doit avoir le libellé correct") - void testBasse() { - assertThat(PrioriteNotification.BASSE.getLibelle()).isEqualTo("Basse"); - } - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(PrioriteNotification.values()).hasSize(4); - assertThat(PrioriteNotification.values()) - .containsExactlyInAnyOrder( - PrioriteNotification.CRITIQUE, - PrioriteNotification.HAUTE, - PrioriteNotification.NORMALE, - PrioriteNotification.BASSE); - } -} - +package dev.lions.unionflow.server.api.enums.notification; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour PrioriteNotification. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests PrioriteNotification") +class PrioriteNotificationTest { + + @Test + @DisplayName("Toutes les priorités doivent avoir un libellé") + void testToutesLesPrioritesOntLibelle() { + for (PrioriteNotification priorite : PrioriteNotification.values()) { + assertThat(priorite.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("CRITIQUE doit avoir le libellé correct") + void testCritique() { + assertThat(PrioriteNotification.CRITIQUE.getLibelle()).isEqualTo("Critique"); + } + + @Test + @DisplayName("HAUTE doit avoir le libellé correct") + void testHaute() { + assertThat(PrioriteNotification.HAUTE.getLibelle()).isEqualTo("Haute"); + } + + @Test + @DisplayName("NORMALE doit avoir le libellé correct") + void testNormale() { + assertThat(PrioriteNotification.NORMALE.getLibelle()).isEqualTo("Normale"); + } + + @Test + @DisplayName("BASSE doit avoir le libellé correct") + void testBasse() { + assertThat(PrioriteNotification.BASSE.getLibelle()).isEqualTo("Basse"); + } + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(PrioriteNotification.values()).hasSize(4); + assertThat(PrioriteNotification.values()) + .containsExactlyInAnyOrder( + PrioriteNotification.CRITIQUE, + PrioriteNotification.HAUTE, + PrioriteNotification.NORMALE, + PrioriteNotification.BASSE); + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/notification/StatutNotificationTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/notification/StatutNotificationTest.java index 0574938..747f801 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/notification/StatutNotificationTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/notification/StatutNotificationTest.java @@ -1,394 +1,394 @@ -package dev.lions.unionflow.server.api.enums.notification; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutNotification") -class StatutNotificationTest { - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutNotification[] values = StatutNotification.values(); - assertThat(values).hasSize(23); - } - - @ParameterizedTest - @EnumSource(StatutNotification.class) - @DisplayName("Test getters de base pour toutes les valeurs") - void testGettersBase(StatutNotification statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - assertThat(statut.getCode()).isNotNull().isNotEmpty(); - assertThat(statut.getDescription()).isNotNull().isNotEmpty(); - assertThat(statut.getIcone()).isNotNull().isNotEmpty(); - assertThat(statut.getCouleur()).isNotNull().matches("#[0-9A-Fa-f]{6}"); - } - - @ParameterizedTest - @CsvSource({ - "ENVOYEE, true", - "RECUE, true", - "AFFICHEE, true", - "OUVERTE, true", - "LUE, true", - "ACTION_EXECUTEE, true", - "BROUILLON, false", - "PROGRAMMEE, false", - "EN_ATTENTE, false" - }) - @DisplayName("isVisibleUtilisateur - statuts visibles") - void testIsVisibleUtilisateur(StatutNotification statut, Boolean expected) { - assertThat(statut.isVisibleUtilisateur()).isEqualTo(expected); - } - - @ParameterizedTest - @CsvSource({ - "ECHEC_ENVOI, true", - "PARTIELLEMENT_ENVOYEE, true", - "ANNULEE, true", - "ERREUR_TECHNIQUE, true", - "DESTINATAIRE_INVALIDE, true", - "TOKEN_INVALIDE, true", - "QUOTA_DEPASSE, true", - "ENVOYEE, false", - "RECUE, false", - "BROUILLON, false" - }) - @DisplayName("isNecessiteAttention - statuts nécessitant attention") - void testIsNecessiteAttention(StatutNotification statut, Boolean expected) { - assertThat(statut.isNecessiteAttention()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isSucces") - class IsSuccesTests { - - @ParameterizedTest - @CsvSource({ - "ENVOYEE, true", - "RECUE, true", - "AFFICHEE, true", - "OUVERTE, true", - "LUE, true", - "ACTION_EXECUTEE, true", - "BROUILLON, false", - "ECHEC_ENVOI, false" - }) - @DisplayName("isSucces - statuts de succès") - void testIsSucces(StatutNotification statut, Boolean expected) { - assertThat(statut.isSucces()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isErreur") - class IsErreurTests { - - @ParameterizedTest - @CsvSource({ - "ECHEC_ENVOI, true", - "ERREUR_TECHNIQUE, true", - "DESTINATAIRE_INVALIDE, true", - "TOKEN_INVALIDE, true", - "QUOTA_DEPASSE, true", - "ENVOYEE, false", - "RECUE, false" - }) - @DisplayName("isErreur - statuts d'erreur") - void testIsErreur(StatutNotification statut, Boolean expected) { - assertThat(statut.isErreur()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isEnCours") - class IsEnCoursTests { - - @ParameterizedTest - @CsvSource({ - "PROGRAMMEE, true", - "EN_ATTENTE, true", - "EN_COURS_ENVOI, true", - "ENVOYEE, false", - "RECUE, false" - }) - @DisplayName("isEnCours - statuts en cours") - void testIsEnCours(StatutNotification statut, Boolean expected) { - assertThat(statut.isEnCours()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests isFinal") - class IsFinalTests { - - @ParameterizedTest - @CsvSource({ - "SUPPRIMEE, true", - "ARCHIVEE, true", - "EXPIREE, true", - "ANNULEE, true", - "ERREUR_TECHNIQUE, true", - "ENVOYEE, false", - "RECUE, false" - }) - @DisplayName("isFinal - statuts finaux") - void testIsFinal(StatutNotification statut, Boolean expected) { - assertThat(statut.isFinal()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests permetModification") - class PermetModificationTests { - - @ParameterizedTest - @CsvSource({ - "BROUILLON, true", - "PROGRAMMEE, true", - "EN_ATTENTE, false", - "ENVOYEE, false" - }) - @DisplayName("permetModification - statuts modifiables") - void testPermetModification(StatutNotification statut, Boolean expected) { - assertThat(statut.permetModification()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests permetAnnulation") - class PermetAnnulationTests { - - @ParameterizedTest - @CsvSource({ - "PROGRAMMEE, true", - "EN_ATTENTE, true", - "BROUILLON, false", - "ENVOYEE, false" - }) - @DisplayName("permetAnnulation - statuts annulables") - void testPermetAnnulation(StatutNotification statut, Boolean expected) { - assertThat(statut.permetAnnulation()).isEqualTo(expected); - } - } - - @Nested - @DisplayName("Tests getPrioriteAffichage") - class GetPrioriteAffichageTests { - - @Test - @DisplayName("getPrioriteAffichage - erreur = priorité 1") - void testGetPrioriteAffichageErreur() { - assertThat(StatutNotification.ERREUR_TECHNIQUE.getPrioriteAffichage()).isEqualTo(1); - assertThat(StatutNotification.ECHEC_ENVOI.getPrioriteAffichage()).isEqualTo(1); - assertThat(StatutNotification.DESTINATAIRE_INVALIDE.getPrioriteAffichage()).isEqualTo(1); - } - - @Test - @DisplayName("getPrioriteAffichage - nécessite attention = priorité 2") - void testGetPrioriteAffichageNecessiteAttention() { - // PARTIELLEMENT_ENVOYEE nécessite attention mais n'est pas une erreur - assertThat(StatutNotification.PARTIELLEMENT_ENVOYEE.getPrioriteAffichage()).isEqualTo(2); - assertThat(StatutNotification.ANNULEE.getPrioriteAffichage()).isEqualTo(2); - } - - @Test - @DisplayName("getPrioriteAffichage - en cours = priorité 3") - void testGetPrioriteAffichageEnCours() { - assertThat(StatutNotification.EN_COURS_ENVOI.getPrioriteAffichage()).isEqualTo(3); - assertThat(StatutNotification.PROGRAMMEE.getPrioriteAffichage()).isEqualTo(3); - assertThat(StatutNotification.EN_ATTENTE.getPrioriteAffichage()).isEqualTo(3); - } - - @Test - @DisplayName("getPrioriteAffichage - succès = priorité 4") - void testGetPrioriteAffichageSucces() { - assertThat(StatutNotification.ENVOYEE.getPrioriteAffichage()).isEqualTo(4); - assertThat(StatutNotification.RECUE.getPrioriteAffichage()).isEqualTo(4); - assertThat(StatutNotification.AFFICHEE.getPrioriteAffichage()).isEqualTo(4); - assertThat(StatutNotification.OUVERTE.getPrioriteAffichage()).isEqualTo(4); - assertThat(StatutNotification.LUE.getPrioriteAffichage()).isEqualTo(4); - assertThat(StatutNotification.ACTION_EXECUTEE.getPrioriteAffichage()).isEqualTo(4); - } - - @Test - @DisplayName("getPrioriteAffichage - autres statuts = priorité 5") - void testGetPrioriteAffichageAutres() { - assertThat(StatutNotification.BROUILLON.getPrioriteAffichage()).isEqualTo(5); - assertThat(StatutNotification.SUPPRIMEE.getPrioriteAffichage()).isEqualTo(5); - assertThat(StatutNotification.ARCHIVEE.getPrioriteAffichage()).isEqualTo(5); - assertThat(StatutNotification.EXPIREE.getPrioriteAffichage()).isEqualTo(5); - assertThat(StatutNotification.IGNOREE.getPrioriteAffichage()).isEqualTo(5); - assertThat(StatutNotification.NON_LUE.getPrioriteAffichage()).isEqualTo(5); - assertThat(StatutNotification.MARQUEE_IMPORTANTE.getPrioriteAffichage()).isEqualTo(5); - } - } - - @Nested - @DisplayName("Tests getStatutsSuivantsPossibles") - class GetStatutsSuivantsPossiblesTests { - - @Test - @DisplayName("getStatutsSuivantsPossibles - BROUILLON") - void testGetStatutsSuivantsPossiblesBrouillon() { - StatutNotification[] suivants = StatutNotification.BROUILLON.getStatutsSuivantsPossibles(); - assertThat(suivants).containsExactlyInAnyOrder( - StatutNotification.PROGRAMMEE, - StatutNotification.EN_ATTENTE, - StatutNotification.ANNULEE); - } - - @Test - @DisplayName("getStatutsSuivantsPossibles - PROGRAMMEE") - void testGetStatutsSuivantsPossiblesProgrammee() { - StatutNotification[] suivants = StatutNotification.PROGRAMMEE.getStatutsSuivantsPossibles(); - assertThat(suivants).containsExactlyInAnyOrder( - StatutNotification.EN_ATTENTE, - StatutNotification.EN_COURS_ENVOI, - StatutNotification.ANNULEE); - } - - @Test - @DisplayName("getStatutsSuivantsPossibles - EN_ATTENTE") - void testGetStatutsSuivantsPossiblesEnAttente() { - StatutNotification[] suivants = StatutNotification.EN_ATTENTE.getStatutsSuivantsPossibles(); - assertThat(suivants).containsExactlyInAnyOrder( - StatutNotification.EN_COURS_ENVOI, - StatutNotification.ECHEC_ENVOI, - StatutNotification.ANNULEE); - } - - @Test - @DisplayName("getStatutsSuivantsPossibles - EN_COURS_ENVOI") - void testGetStatutsSuivantsPossiblesEnCoursEnvoi() { - StatutNotification[] suivants = StatutNotification.EN_COURS_ENVOI.getStatutsSuivantsPossibles(); - assertThat(suivants).containsExactlyInAnyOrder( - StatutNotification.ENVOYEE, - StatutNotification.PARTIELLEMENT_ENVOYEE, - StatutNotification.ECHEC_ENVOI); - } - - @Test - @DisplayName("getStatutsSuivantsPossibles - ENVOYEE") - void testGetStatutsSuivantsPossiblesEnvoyee() { - StatutNotification[] suivants = StatutNotification.ENVOYEE.getStatutsSuivantsPossibles(); - assertThat(suivants).containsExactlyInAnyOrder( - StatutNotification.RECUE, - StatutNotification.ECHEC_ENVOI); - } - - @Test - @DisplayName("getStatutsSuivantsPossibles - RECUE") - void testGetStatutsSuivantsPossiblesRecue() { - StatutNotification[] suivants = StatutNotification.RECUE.getStatutsSuivantsPossibles(); - assertThat(suivants).containsExactlyInAnyOrder( - StatutNotification.AFFICHEE, - StatutNotification.IGNOREE); - } - - @Test - @DisplayName("getStatutsSuivantsPossibles - AFFICHEE") - void testGetStatutsSuivantsPossiblesAffichee() { - StatutNotification[] suivants = StatutNotification.AFFICHEE.getStatutsSuivantsPossibles(); - assertThat(suivants).containsExactlyInAnyOrder( - StatutNotification.OUVERTE, - StatutNotification.LUE, - StatutNotification.NON_LUE, - StatutNotification.IGNOREE); - } - - @Test - @DisplayName("getStatutsSuivantsPossibles - OUVERTE") - void testGetStatutsSuivantsPossiblesOuverte() { - StatutNotification[] suivants = StatutNotification.OUVERTE.getStatutsSuivantsPossibles(); - assertThat(suivants).containsExactlyInAnyOrder( - StatutNotification.LUE, - StatutNotification.ACTION_EXECUTEE, - StatutNotification.MARQUEE_IMPORTANTE); - } - - @Test - @DisplayName("getStatutsSuivantsPossibles - NON_LUE") - void testGetStatutsSuivantsPossiblesNonLue() { - StatutNotification[] suivants = StatutNotification.NON_LUE.getStatutsSuivantsPossibles(); - assertThat(suivants).containsExactlyInAnyOrder( - StatutNotification.LUE, - StatutNotification.OUVERTE, - StatutNotification.SUPPRIMEE, - StatutNotification.ARCHIVEE); - } - - @Test - @DisplayName("getStatutsSuivantsPossibles - LUE") - void testGetStatutsSuivantsPossiblesLue() { - StatutNotification[] suivants = StatutNotification.LUE.getStatutsSuivantsPossibles(); - assertThat(suivants).containsExactlyInAnyOrder( - StatutNotification.ACTION_EXECUTEE, - StatutNotification.MARQUEE_IMPORTANTE, - StatutNotification.SUPPRIMEE, - StatutNotification.ARCHIVEE); - } - - @Test - @DisplayName("getStatutsSuivantsPossibles - statuts non couverts (default)") - void testGetStatutsSuivantsPossiblesDefault() { - // Les statuts non couverts par le switch retournent un tableau vide - StatutNotification[] suivants = StatutNotification.SUPPRIMEE.getStatutsSuivantsPossibles(); - assertThat(suivants).isEmpty(); - - suivants = StatutNotification.ARCHIVEE.getStatutsSuivantsPossibles(); - assertThat(suivants).isEmpty(); - - suivants = StatutNotification.EXPIREE.getStatutsSuivantsPossibles(); - assertThat(suivants).isEmpty(); - } - } - - @Nested - @DisplayName("Tests méthodes statiques") - class MethodesStatiquesTests { - - @Test - @DisplayName("parCode - trouve le statut par code") - void testParCode() { - assertThat(StatutNotification.parCode("sent")).isEqualTo(StatutNotification.ENVOYEE); - assertThat(StatutNotification.parCode("read")).isEqualTo(StatutNotification.LUE); - } - - @Test - @DisplayName("parCode - code inexistant retourne null") - void testParCodeInexistant() { - assertThat(StatutNotification.parCode("inexistant")).isNull(); - assertThat(StatutNotification.parCode("")).isNull(); - assertThat(StatutNotification.parCode(null)).isNull(); - } - - @Test - @DisplayName("getStatutsVisibles - retourne les statuts visibles") - void testGetStatutsVisibles() { - StatutNotification[] statuts = StatutNotification.getStatutsVisibles(); - assertThat(statuts).isNotEmpty(); - assertThat(statuts).allMatch(StatutNotification::isVisibleUtilisateur); - } - - @Test - @DisplayName("getStatutsErreur - retourne les statuts d'erreur") - void testGetStatutsErreur() { - StatutNotification[] statuts = StatutNotification.getStatutsErreur(); - assertThat(statuts).isNotEmpty(); - assertThat(statuts).allMatch(StatutNotification::isErreur); - } - } -} - +package dev.lions.unionflow.server.api.enums.notification; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutNotification") +class StatutNotificationTest { + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutNotification[] values = StatutNotification.values(); + assertThat(values).hasSize(23); + } + + @ParameterizedTest + @EnumSource(StatutNotification.class) + @DisplayName("Test getters de base pour toutes les valeurs") + void testGettersBase(StatutNotification statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + assertThat(statut.getCode()).isNotNull().isNotEmpty(); + assertThat(statut.getDescription()).isNotNull().isNotEmpty(); + assertThat(statut.getIcone()).isNotNull().isNotEmpty(); + assertThat(statut.getCouleur()).isNotNull().matches("#[0-9A-Fa-f]{6}"); + } + + @ParameterizedTest + @CsvSource({ + "ENVOYEE, true", + "RECUE, true", + "AFFICHEE, true", + "OUVERTE, true", + "LUE, true", + "ACTION_EXECUTEE, true", + "BROUILLON, false", + "PROGRAMMEE, false", + "EN_ATTENTE, false" + }) + @DisplayName("isVisibleUtilisateur - statuts visibles") + void testIsVisibleUtilisateur(StatutNotification statut, Boolean expected) { + assertThat(statut.isVisibleUtilisateur()).isEqualTo(expected); + } + + @ParameterizedTest + @CsvSource({ + "ECHEC_ENVOI, true", + "PARTIELLEMENT_ENVOYEE, true", + "ANNULEE, true", + "ERREUR_TECHNIQUE, true", + "DESTINATAIRE_INVALIDE, true", + "TOKEN_INVALIDE, true", + "QUOTA_DEPASSE, true", + "ENVOYEE, false", + "RECUE, false", + "BROUILLON, false" + }) + @DisplayName("isNecessiteAttention - statuts nécessitant attention") + void testIsNecessiteAttention(StatutNotification statut, Boolean expected) { + assertThat(statut.isNecessiteAttention()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isSucces") + class IsSuccesTests { + + @ParameterizedTest + @CsvSource({ + "ENVOYEE, true", + "RECUE, true", + "AFFICHEE, true", + "OUVERTE, true", + "LUE, true", + "ACTION_EXECUTEE, true", + "BROUILLON, false", + "ECHEC_ENVOI, false" + }) + @DisplayName("isSucces - statuts de succès") + void testIsSucces(StatutNotification statut, Boolean expected) { + assertThat(statut.isSucces()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isErreur") + class IsErreurTests { + + @ParameterizedTest + @CsvSource({ + "ECHEC_ENVOI, true", + "ERREUR_TECHNIQUE, true", + "DESTINATAIRE_INVALIDE, true", + "TOKEN_INVALIDE, true", + "QUOTA_DEPASSE, true", + "ENVOYEE, false", + "RECUE, false" + }) + @DisplayName("isErreur - statuts d'erreur") + void testIsErreur(StatutNotification statut, Boolean expected) { + assertThat(statut.isErreur()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isEnCours") + class IsEnCoursTests { + + @ParameterizedTest + @CsvSource({ + "PROGRAMMEE, true", + "EN_ATTENTE, true", + "EN_COURS_ENVOI, true", + "ENVOYEE, false", + "RECUE, false" + }) + @DisplayName("isEnCours - statuts en cours") + void testIsEnCours(StatutNotification statut, Boolean expected) { + assertThat(statut.isEnCours()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests isFinal") + class IsFinalTests { + + @ParameterizedTest + @CsvSource({ + "SUPPRIMEE, true", + "ARCHIVEE, true", + "EXPIREE, true", + "ANNULEE, true", + "ERREUR_TECHNIQUE, true", + "ENVOYEE, false", + "RECUE, false" + }) + @DisplayName("isFinal - statuts finaux") + void testIsFinal(StatutNotification statut, Boolean expected) { + assertThat(statut.isFinal()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests permetModification") + class PermetModificationTests { + + @ParameterizedTest + @CsvSource({ + "BROUILLON, true", + "PROGRAMMEE, true", + "EN_ATTENTE, false", + "ENVOYEE, false" + }) + @DisplayName("permetModification - statuts modifiables") + void testPermetModification(StatutNotification statut, Boolean expected) { + assertThat(statut.permetModification()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests permetAnnulation") + class PermetAnnulationTests { + + @ParameterizedTest + @CsvSource({ + "PROGRAMMEE, true", + "EN_ATTENTE, true", + "BROUILLON, false", + "ENVOYEE, false" + }) + @DisplayName("permetAnnulation - statuts annulables") + void testPermetAnnulation(StatutNotification statut, Boolean expected) { + assertThat(statut.permetAnnulation()).isEqualTo(expected); + } + } + + @Nested + @DisplayName("Tests getPrioriteAffichage") + class GetPrioriteAffichageTests { + + @Test + @DisplayName("getPrioriteAffichage - erreur = priorité 1") + void testGetPrioriteAffichageErreur() { + assertThat(StatutNotification.ERREUR_TECHNIQUE.getPrioriteAffichage()).isEqualTo(1); + assertThat(StatutNotification.ECHEC_ENVOI.getPrioriteAffichage()).isEqualTo(1); + assertThat(StatutNotification.DESTINATAIRE_INVALIDE.getPrioriteAffichage()).isEqualTo(1); + } + + @Test + @DisplayName("getPrioriteAffichage - nécessite attention = priorité 2") + void testGetPrioriteAffichageNecessiteAttention() { + // PARTIELLEMENT_ENVOYEE nécessite attention mais n'est pas une erreur + assertThat(StatutNotification.PARTIELLEMENT_ENVOYEE.getPrioriteAffichage()).isEqualTo(2); + assertThat(StatutNotification.ANNULEE.getPrioriteAffichage()).isEqualTo(2); + } + + @Test + @DisplayName("getPrioriteAffichage - en cours = priorité 3") + void testGetPrioriteAffichageEnCours() { + assertThat(StatutNotification.EN_COURS_ENVOI.getPrioriteAffichage()).isEqualTo(3); + assertThat(StatutNotification.PROGRAMMEE.getPrioriteAffichage()).isEqualTo(3); + assertThat(StatutNotification.EN_ATTENTE.getPrioriteAffichage()).isEqualTo(3); + } + + @Test + @DisplayName("getPrioriteAffichage - succès = priorité 4") + void testGetPrioriteAffichageSucces() { + assertThat(StatutNotification.ENVOYEE.getPrioriteAffichage()).isEqualTo(4); + assertThat(StatutNotification.RECUE.getPrioriteAffichage()).isEqualTo(4); + assertThat(StatutNotification.AFFICHEE.getPrioriteAffichage()).isEqualTo(4); + assertThat(StatutNotification.OUVERTE.getPrioriteAffichage()).isEqualTo(4); + assertThat(StatutNotification.LUE.getPrioriteAffichage()).isEqualTo(4); + assertThat(StatutNotification.ACTION_EXECUTEE.getPrioriteAffichage()).isEqualTo(4); + } + + @Test + @DisplayName("getPrioriteAffichage - autres statuts = priorité 5") + void testGetPrioriteAffichageAutres() { + assertThat(StatutNotification.BROUILLON.getPrioriteAffichage()).isEqualTo(5); + assertThat(StatutNotification.SUPPRIMEE.getPrioriteAffichage()).isEqualTo(5); + assertThat(StatutNotification.ARCHIVEE.getPrioriteAffichage()).isEqualTo(5); + assertThat(StatutNotification.EXPIREE.getPrioriteAffichage()).isEqualTo(5); + assertThat(StatutNotification.IGNOREE.getPrioriteAffichage()).isEqualTo(5); + assertThat(StatutNotification.NON_LUE.getPrioriteAffichage()).isEqualTo(5); + assertThat(StatutNotification.MARQUEE_IMPORTANTE.getPrioriteAffichage()).isEqualTo(5); + } + } + + @Nested + @DisplayName("Tests getStatutsSuivantsPossibles") + class GetStatutsSuivantsPossiblesTests { + + @Test + @DisplayName("getStatutsSuivantsPossibles - BROUILLON") + void testGetStatutsSuivantsPossiblesBrouillon() { + StatutNotification[] suivants = StatutNotification.BROUILLON.getStatutsSuivantsPossibles(); + assertThat(suivants).containsExactlyInAnyOrder( + StatutNotification.PROGRAMMEE, + StatutNotification.EN_ATTENTE, + StatutNotification.ANNULEE); + } + + @Test + @DisplayName("getStatutsSuivantsPossibles - PROGRAMMEE") + void testGetStatutsSuivantsPossiblesProgrammee() { + StatutNotification[] suivants = StatutNotification.PROGRAMMEE.getStatutsSuivantsPossibles(); + assertThat(suivants).containsExactlyInAnyOrder( + StatutNotification.EN_ATTENTE, + StatutNotification.EN_COURS_ENVOI, + StatutNotification.ANNULEE); + } + + @Test + @DisplayName("getStatutsSuivantsPossibles - EN_ATTENTE") + void testGetStatutsSuivantsPossiblesEnAttente() { + StatutNotification[] suivants = StatutNotification.EN_ATTENTE.getStatutsSuivantsPossibles(); + assertThat(suivants).containsExactlyInAnyOrder( + StatutNotification.EN_COURS_ENVOI, + StatutNotification.ECHEC_ENVOI, + StatutNotification.ANNULEE); + } + + @Test + @DisplayName("getStatutsSuivantsPossibles - EN_COURS_ENVOI") + void testGetStatutsSuivantsPossiblesEnCoursEnvoi() { + StatutNotification[] suivants = StatutNotification.EN_COURS_ENVOI.getStatutsSuivantsPossibles(); + assertThat(suivants).containsExactlyInAnyOrder( + StatutNotification.ENVOYEE, + StatutNotification.PARTIELLEMENT_ENVOYEE, + StatutNotification.ECHEC_ENVOI); + } + + @Test + @DisplayName("getStatutsSuivantsPossibles - ENVOYEE") + void testGetStatutsSuivantsPossiblesEnvoyee() { + StatutNotification[] suivants = StatutNotification.ENVOYEE.getStatutsSuivantsPossibles(); + assertThat(suivants).containsExactlyInAnyOrder( + StatutNotification.RECUE, + StatutNotification.ECHEC_ENVOI); + } + + @Test + @DisplayName("getStatutsSuivantsPossibles - RECUE") + void testGetStatutsSuivantsPossiblesRecue() { + StatutNotification[] suivants = StatutNotification.RECUE.getStatutsSuivantsPossibles(); + assertThat(suivants).containsExactlyInAnyOrder( + StatutNotification.AFFICHEE, + StatutNotification.IGNOREE); + } + + @Test + @DisplayName("getStatutsSuivantsPossibles - AFFICHEE") + void testGetStatutsSuivantsPossiblesAffichee() { + StatutNotification[] suivants = StatutNotification.AFFICHEE.getStatutsSuivantsPossibles(); + assertThat(suivants).containsExactlyInAnyOrder( + StatutNotification.OUVERTE, + StatutNotification.LUE, + StatutNotification.NON_LUE, + StatutNotification.IGNOREE); + } + + @Test + @DisplayName("getStatutsSuivantsPossibles - OUVERTE") + void testGetStatutsSuivantsPossiblesOuverte() { + StatutNotification[] suivants = StatutNotification.OUVERTE.getStatutsSuivantsPossibles(); + assertThat(suivants).containsExactlyInAnyOrder( + StatutNotification.LUE, + StatutNotification.ACTION_EXECUTEE, + StatutNotification.MARQUEE_IMPORTANTE); + } + + @Test + @DisplayName("getStatutsSuivantsPossibles - NON_LUE") + void testGetStatutsSuivantsPossiblesNonLue() { + StatutNotification[] suivants = StatutNotification.NON_LUE.getStatutsSuivantsPossibles(); + assertThat(suivants).containsExactlyInAnyOrder( + StatutNotification.LUE, + StatutNotification.OUVERTE, + StatutNotification.SUPPRIMEE, + StatutNotification.ARCHIVEE); + } + + @Test + @DisplayName("getStatutsSuivantsPossibles - LUE") + void testGetStatutsSuivantsPossiblesLue() { + StatutNotification[] suivants = StatutNotification.LUE.getStatutsSuivantsPossibles(); + assertThat(suivants).containsExactlyInAnyOrder( + StatutNotification.ACTION_EXECUTEE, + StatutNotification.MARQUEE_IMPORTANTE, + StatutNotification.SUPPRIMEE, + StatutNotification.ARCHIVEE); + } + + @Test + @DisplayName("getStatutsSuivantsPossibles - statuts non couverts (default)") + void testGetStatutsSuivantsPossiblesDefault() { + // Les statuts non couverts par le switch retournent un tableau vide + StatutNotification[] suivants = StatutNotification.SUPPRIMEE.getStatutsSuivantsPossibles(); + assertThat(suivants).isEmpty(); + + suivants = StatutNotification.ARCHIVEE.getStatutsSuivantsPossibles(); + assertThat(suivants).isEmpty(); + + suivants = StatutNotification.EXPIREE.getStatutsSuivantsPossibles(); + assertThat(suivants).isEmpty(); + } + } + + @Nested + @DisplayName("Tests méthodes statiques") + class MethodesStatiquesTests { + + @Test + @DisplayName("parCode - trouve le statut par code") + void testParCode() { + assertThat(StatutNotification.parCode("sent")).isEqualTo(StatutNotification.ENVOYEE); + assertThat(StatutNotification.parCode("read")).isEqualTo(StatutNotification.LUE); + } + + @Test + @DisplayName("parCode - code inexistant retourne null") + void testParCodeInexistant() { + assertThat(StatutNotification.parCode("inexistant")).isNull(); + assertThat(StatutNotification.parCode("")).isNull(); + assertThat(StatutNotification.parCode(null)).isNull(); + } + + @Test + @DisplayName("getStatutsVisibles - retourne les statuts visibles") + void testGetStatutsVisibles() { + StatutNotification[] statuts = StatutNotification.getStatutsVisibles(); + assertThat(statuts).isNotEmpty(); + assertThat(statuts).allMatch(StatutNotification::isVisibleUtilisateur); + } + + @Test + @DisplayName("getStatutsErreur - retourne les statuts d'erreur") + void testGetStatutsErreur() { + StatutNotification[] statuts = StatutNotification.getStatutsErreur(); + assertThat(statuts).isNotEmpty(); + assertThat(statuts).allMatch(StatutNotification::isErreur); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/notification/TypeNotificationTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/notification/TypeNotificationTest.java index 377f919..ae57164 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/notification/TypeNotificationTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/notification/TypeNotificationTest.java @@ -1,79 +1,79 @@ -package dev.lions.unionflow.server.api.enums.notification; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour TypeNotification. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests TypeNotification") -class TypeNotificationTest { - - @Test - @DisplayName("Tous les types de notification doivent avoir un libellé") - void testTousLesTypesOntLibelle() { - for (TypeNotification type : TypeNotification.values()) { - assertThat(type.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("EMAIL doit avoir le libellé correct") - void testEmail() { - assertThat(TypeNotification.EMAIL.getLibelle()).isEqualTo("Email"); - } - - @Test - @DisplayName("SMS doit avoir le libellé correct") - void testSMS() { - assertThat(TypeNotification.SMS.getLibelle()).isEqualTo("SMS"); - } - - @Test - @DisplayName("PUSH doit avoir le libellé correct") - void testPush() { - assertThat(TypeNotification.PUSH.getLibelle()).isEqualTo("Push Notification"); - } - - @Test - @DisplayName("IN_APP doit avoir le libellé correct") - void testInApp() { - assertThat(TypeNotification.IN_APP.getLibelle()).isEqualTo("Notification In-App"); - } - - @Test - @DisplayName("SYSTEME doit avoir le libellé correct") - void testSysteme() { - assertThat(TypeNotification.SYSTEME.getLibelle()).isEqualTo("Notification Système"); - } - - @Test - @DisplayName("isActiveeParDefaut doit retourner true pour tous sauf SYSTEME") - void testIsActiveeParDefaut() { - assertThat(TypeNotification.EMAIL.isActiveeParDefaut()).isTrue(); - assertThat(TypeNotification.SMS.isActiveeParDefaut()).isTrue(); - assertThat(TypeNotification.PUSH.isActiveeParDefaut()).isTrue(); - assertThat(TypeNotification.IN_APP.isActiveeParDefaut()).isTrue(); - assertThat(TypeNotification.SYSTEME.isActiveeParDefaut()).isFalse(); - } - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(TypeNotification.values()).hasSize(5); - assertThat(TypeNotification.values()) - .containsExactlyInAnyOrder( - TypeNotification.EMAIL, - TypeNotification.SMS, - TypeNotification.PUSH, - TypeNotification.IN_APP, - TypeNotification.SYSTEME); - } -} - +package dev.lions.unionflow.server.api.enums.notification; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour TypeNotification. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests TypeNotification") +class TypeNotificationTest { + + @Test + @DisplayName("Tous les types de notification doivent avoir un libellé") + void testTousLesTypesOntLibelle() { + for (TypeNotification type : TypeNotification.values()) { + assertThat(type.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("EMAIL doit avoir le libellé correct") + void testEmail() { + assertThat(TypeNotification.EMAIL.getLibelle()).isEqualTo("Email"); + } + + @Test + @DisplayName("SMS doit avoir le libellé correct") + void testSMS() { + assertThat(TypeNotification.SMS.getLibelle()).isEqualTo("SMS"); + } + + @Test + @DisplayName("PUSH doit avoir le libellé correct") + void testPush() { + assertThat(TypeNotification.PUSH.getLibelle()).isEqualTo("Push Notification"); + } + + @Test + @DisplayName("IN_APP doit avoir le libellé correct") + void testInApp() { + assertThat(TypeNotification.IN_APP.getLibelle()).isEqualTo("Notification In-App"); + } + + @Test + @DisplayName("SYSTEME doit avoir le libellé correct") + void testSysteme() { + assertThat(TypeNotification.SYSTEME.getLibelle()).isEqualTo("Notification Système"); + } + + @Test + @DisplayName("isActiveeParDefaut doit retourner true pour tous sauf SYSTEME") + void testIsActiveeParDefaut() { + assertThat(TypeNotification.EMAIL.isActiveeParDefaut()).isTrue(); + assertThat(TypeNotification.SMS.isActiveeParDefaut()).isTrue(); + assertThat(TypeNotification.PUSH.isActiveeParDefaut()).isTrue(); + assertThat(TypeNotification.IN_APP.isActiveeParDefaut()).isTrue(); + assertThat(TypeNotification.SYSTEME.isActiveeParDefaut()).isFalse(); + } + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(TypeNotification.values()).hasSize(5); + assertThat(TypeNotification.values()) + .containsExactlyInAnyOrder( + TypeNotification.EMAIL, + TypeNotification.SMS, + TypeNotification.PUSH, + TypeNotification.IN_APP, + TypeNotification.SYSTEME); + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/ong/StatutProjetOngTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/ong/StatutProjetOngTest.java index 37dd8ca..94dffd4 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/ong/StatutProjetOngTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/ong/StatutProjetOngTest.java @@ -1,76 +1,76 @@ -package dev.lions.unionflow.server.api.enums.ong; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutProjetOng") -class StatutProjetOngTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutProjetOng.EN_ETUDE).isNotNull(); - assertThat(StatutProjetOng.EN_COURS).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutProjetOng[] values = StatutProjetOng.values(); - assertThat(values).hasSize(5); - assertThat(values).containsExactly( - StatutProjetOng.EN_ETUDE, - StatutProjetOng.FINANCEMENT, - StatutProjetOng.EN_COURS, - StatutProjetOng.EVALUE, - StatutProjetOng.CLOTURE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(StatutProjetOng.valueOf("EN_ETUDE")).isEqualTo(StatutProjetOng.EN_ETUDE); - assertThat(StatutProjetOng.valueOf("FINANCEMENT")).isEqualTo(StatutProjetOng.FINANCEMENT); - assertThat(StatutProjetOng.valueOf("EN_COURS")).isEqualTo(StatutProjetOng.EN_COURS); - assertThat(StatutProjetOng.valueOf("EVALUE")).isEqualTo(StatutProjetOng.EVALUE); - assertThat(StatutProjetOng.valueOf("CLOTURE")).isEqualTo(StatutProjetOng.CLOTURE); - - assertThatThrownBy(() -> StatutProjetOng.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutProjetOng.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutProjetOng statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(StatutProjetOng.EN_ETUDE.getLibelle()).isEqualTo("Étude de faisabilité / Évaluation"); - assertThat(StatutProjetOng.FINANCEMENT.getLibelle()).isEqualTo("En recherche de financements"); - assertThat(StatutProjetOng.EN_COURS.getLibelle()).isEqualTo("Déploiement opérationnel sur le terrain"); - assertThat(StatutProjetOng.EVALUE.getLibelle()).isEqualTo("Opérations terminées, en cours d'évaluation"); - assertThat(StatutProjetOng.CLOTURE.getLibelle()).isEqualTo("Projet définitivement clôturé"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(StatutProjetOng.EN_ETUDE.name()).isEqualTo("EN_ETUDE"); - assertThat(StatutProjetOng.FINANCEMENT.name()).isEqualTo("FINANCEMENT"); - } - } -} +package dev.lions.unionflow.server.api.enums.ong; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutProjetOng") +class StatutProjetOngTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutProjetOng.EN_ETUDE).isNotNull(); + assertThat(StatutProjetOng.EN_COURS).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutProjetOng[] values = StatutProjetOng.values(); + assertThat(values).hasSize(5); + assertThat(values).containsExactly( + StatutProjetOng.EN_ETUDE, + StatutProjetOng.FINANCEMENT, + StatutProjetOng.EN_COURS, + StatutProjetOng.EVALUE, + StatutProjetOng.CLOTURE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(StatutProjetOng.valueOf("EN_ETUDE")).isEqualTo(StatutProjetOng.EN_ETUDE); + assertThat(StatutProjetOng.valueOf("FINANCEMENT")).isEqualTo(StatutProjetOng.FINANCEMENT); + assertThat(StatutProjetOng.valueOf("EN_COURS")).isEqualTo(StatutProjetOng.EN_COURS); + assertThat(StatutProjetOng.valueOf("EVALUE")).isEqualTo(StatutProjetOng.EVALUE); + assertThat(StatutProjetOng.valueOf("CLOTURE")).isEqualTo(StatutProjetOng.CLOTURE); + + assertThatThrownBy(() -> StatutProjetOng.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutProjetOng.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutProjetOng statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(StatutProjetOng.EN_ETUDE.getLibelle()).isEqualTo("Étude de faisabilité / Évaluation"); + assertThat(StatutProjetOng.FINANCEMENT.getLibelle()).isEqualTo("En recherche de financements"); + assertThat(StatutProjetOng.EN_COURS.getLibelle()).isEqualTo("Déploiement opérationnel sur le terrain"); + assertThat(StatutProjetOng.EVALUE.getLibelle()).isEqualTo("Opérations terminées, en cours d'évaluation"); + assertThat(StatutProjetOng.CLOTURE.getLibelle()).isEqualTo("Projet définitivement clôturé"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(StatutProjetOng.EN_ETUDE.name()).isEqualTo("EN_ETUDE"); + assertThat(StatutProjetOng.FINANCEMENT.name()).isEqualTo("FINANCEMENT"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/organisation/StatutOrganisationTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/organisation/StatutOrganisationTest.java index 869ebfd..d6c8d65 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/organisation/StatutOrganisationTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/organisation/StatutOrganisationTest.java @@ -1,89 +1,89 @@ -package dev.lions.unionflow.server.api.enums.organisation; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutOrganisation") -class StatutOrganisationTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutOrganisation.ACTIVE).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutOrganisation[] values = StatutOrganisation.values(); - assertThat(values).hasSize(5); - assertThat(values).containsExactly( - StatutOrganisation.ACTIVE, - StatutOrganisation.INACTIVE, - StatutOrganisation.SUSPENDUE, - StatutOrganisation.EN_CREATION, - StatutOrganisation.DISSOUTE); - } - - @Test - @DisplayName("Test valueOf") - void testValueOf() { - assertThat(StatutOrganisation.valueOf("ACTIVE")).isEqualTo(StatutOrganisation.ACTIVE); - assertThat(StatutOrganisation.valueOf("INACTIVE")).isEqualTo(StatutOrganisation.INACTIVE); - assertThat(StatutOrganisation.valueOf("SUSPENDUE")).isEqualTo(StatutOrganisation.SUSPENDUE); - assertThat(StatutOrganisation.valueOf("EN_CREATION")).isEqualTo(StatutOrganisation.EN_CREATION); - assertThat(StatutOrganisation.valueOf("DISSOUTE")).isEqualTo(StatutOrganisation.DISSOUTE); - - assertThatThrownBy(() -> StatutOrganisation.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutOrganisation.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutOrganisation statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @ParameterizedTest - @CsvSource({ - "ACTIVE, Active", - "INACTIVE, Inactive", - "SUSPENDUE, Suspendue", - "EN_CREATION, En Création", - "DISSOUTE, Dissoute" - }) - @DisplayName("Test getLibelle avec valeurs exactes") - void testGetLibelleValeursExactes(StatutOrganisation statut, String expectedLibelle) { - assertThat(statut.getLibelle()).isEqualTo(expectedLibelle); - } - - @Test - @DisplayName("Test ordinal et name") - void testOrdinalEtName() { - assertThat(StatutOrganisation.ACTIVE.ordinal()).isEqualTo(0); - assertThat(StatutOrganisation.INACTIVE.ordinal()).isEqualTo(1); - assertThat(StatutOrganisation.SUSPENDUE.ordinal()).isEqualTo(2); - assertThat(StatutOrganisation.EN_CREATION.ordinal()).isEqualTo(3); - assertThat(StatutOrganisation.DISSOUTE.ordinal()).isEqualTo(4); - - assertThat(StatutOrganisation.ACTIVE.name()).isEqualTo("ACTIVE"); - assertThat(StatutOrganisation.INACTIVE.name()).isEqualTo("INACTIVE"); - assertThat(StatutOrganisation.SUSPENDUE.name()).isEqualTo("SUSPENDUE"); - assertThat(StatutOrganisation.EN_CREATION.name()).isEqualTo("EN_CREATION"); - assertThat(StatutOrganisation.DISSOUTE.name()).isEqualTo("DISSOUTE"); - } - } -} - +package dev.lions.unionflow.server.api.enums.organisation; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutOrganisation") +class StatutOrganisationTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutOrganisation.ACTIVE).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutOrganisation[] values = StatutOrganisation.values(); + assertThat(values).hasSize(5); + assertThat(values).containsExactly( + StatutOrganisation.ACTIVE, + StatutOrganisation.INACTIVE, + StatutOrganisation.SUSPENDUE, + StatutOrganisation.EN_CREATION, + StatutOrganisation.DISSOUTE); + } + + @Test + @DisplayName("Test valueOf") + void testValueOf() { + assertThat(StatutOrganisation.valueOf("ACTIVE")).isEqualTo(StatutOrganisation.ACTIVE); + assertThat(StatutOrganisation.valueOf("INACTIVE")).isEqualTo(StatutOrganisation.INACTIVE); + assertThat(StatutOrganisation.valueOf("SUSPENDUE")).isEqualTo(StatutOrganisation.SUSPENDUE); + assertThat(StatutOrganisation.valueOf("EN_CREATION")).isEqualTo(StatutOrganisation.EN_CREATION); + assertThat(StatutOrganisation.valueOf("DISSOUTE")).isEqualTo(StatutOrganisation.DISSOUTE); + + assertThatThrownBy(() -> StatutOrganisation.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutOrganisation.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutOrganisation statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @ParameterizedTest + @CsvSource({ + "ACTIVE, Active", + "INACTIVE, Inactive", + "SUSPENDUE, Suspendue", + "EN_CREATION, En Création", + "DISSOUTE, Dissoute" + }) + @DisplayName("Test getLibelle avec valeurs exactes") + void testGetLibelleValeursExactes(StatutOrganisation statut, String expectedLibelle) { + assertThat(statut.getLibelle()).isEqualTo(expectedLibelle); + } + + @Test + @DisplayName("Test ordinal et name") + void testOrdinalEtName() { + assertThat(StatutOrganisation.ACTIVE.ordinal()).isEqualTo(0); + assertThat(StatutOrganisation.INACTIVE.ordinal()).isEqualTo(1); + assertThat(StatutOrganisation.SUSPENDUE.ordinal()).isEqualTo(2); + assertThat(StatutOrganisation.EN_CREATION.ordinal()).isEqualTo(3); + assertThat(StatutOrganisation.DISSOUTE.ordinal()).isEqualTo(4); + + assertThat(StatutOrganisation.ACTIVE.name()).isEqualTo("ACTIVE"); + assertThat(StatutOrganisation.INACTIVE.name()).isEqualTo("INACTIVE"); + assertThat(StatutOrganisation.SUSPENDUE.name()).isEqualTo("SUSPENDUE"); + assertThat(StatutOrganisation.EN_CREATION.name()).isEqualTo("EN_CREATION"); + assertThat(StatutOrganisation.DISSOUTE.name()).isEqualTo("DISSOUTE"); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/MethodePaiementTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/MethodePaiementTest.java index e47155a..5c4ccdf 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/MethodePaiementTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/MethodePaiementTest.java @@ -1,55 +1,55 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour MethodePaiement. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests MethodePaiement") -class MethodePaiementTest { - - @Test - @DisplayName("Toutes les méthodes de paiement doivent avoir un libellé") - void testToutesLesMethodesOntLibelle() { - for (MethodePaiement methode : MethodePaiement.values()) { - assertThat(methode.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(MethodePaiement.values().length).isGreaterThan(0); - for (MethodePaiement methode : MethodePaiement.values()) { - assertThat(methode).isNotNull(); - assertThat(methode.name()).isNotBlank(); - } - } - - @Test - @DisplayName("isMobileMoney - méthodes mobile money retournent true") - void testIsMobileMoneyTrue() { - assertThat(MethodePaiement.WAVE_MOBILE_MONEY.isMobileMoney()).isTrue(); - assertThat(MethodePaiement.ORANGE_MONEY.isMobileMoney()).isTrue(); - assertThat(MethodePaiement.MTN_MOBILE_MONEY.isMobileMoney()).isTrue(); - assertThat(MethodePaiement.MOOV_MONEY.isMobileMoney()).isTrue(); - } - - @Test - @DisplayName("isMobileMoney - autres méthodes retournent false") - void testIsMobileMoneyFalse() { - assertThat(MethodePaiement.VIREMENT_BANCAIRE.isMobileMoney()).isFalse(); - assertThat(MethodePaiement.CARTE_BANCAIRE.isMobileMoney()).isFalse(); - assertThat(MethodePaiement.ESPECES.isMobileMoney()).isFalse(); - assertThat(MethodePaiement.CHEQUE.isMobileMoney()).isFalse(); - assertThat(MethodePaiement.AUTRE.isMobileMoney()).isFalse(); - } -} - +package dev.lions.unionflow.server.api.enums.paiement; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour MethodePaiement. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests MethodePaiement") +class MethodePaiementTest { + + @Test + @DisplayName("Toutes les méthodes de paiement doivent avoir un libellé") + void testToutesLesMethodesOntLibelle() { + for (MethodePaiement methode : MethodePaiement.values()) { + assertThat(methode.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(MethodePaiement.values().length).isGreaterThan(0); + for (MethodePaiement methode : MethodePaiement.values()) { + assertThat(methode).isNotNull(); + assertThat(methode.name()).isNotBlank(); + } + } + + @Test + @DisplayName("isMobileMoney - méthodes mobile money retournent true") + void testIsMobileMoneyTrue() { + assertThat(MethodePaiement.WAVE_MOBILE_MONEY.isMobileMoney()).isTrue(); + assertThat(MethodePaiement.ORANGE_MONEY.isMobileMoney()).isTrue(); + assertThat(MethodePaiement.MTN_MOBILE_MONEY.isMobileMoney()).isTrue(); + assertThat(MethodePaiement.MOOV_MONEY.isMobileMoney()).isTrue(); + } + + @Test + @DisplayName("isMobileMoney - autres méthodes retournent false") + void testIsMobileMoneyFalse() { + assertThat(MethodePaiement.VIREMENT_BANCAIRE.isMobileMoney()).isFalse(); + assertThat(MethodePaiement.CARTE_BANCAIRE.isMobileMoney()).isFalse(); + assertThat(MethodePaiement.ESPECES.isMobileMoney()).isFalse(); + assertThat(MethodePaiement.CHEQUE.isMobileMoney()).isFalse(); + assertThat(MethodePaiement.AUTRE.isMobileMoney()).isFalse(); + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutIntentionPaiementTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutIntentionPaiementTest.java index 4d19e7a..a7a4757 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutIntentionPaiementTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutIntentionPaiementTest.java @@ -1,74 +1,74 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutIntentionPaiement") -class StatutIntentionPaiementTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutIntentionPaiement.INITIEE).isNotNull(); - assertThat(StatutIntentionPaiement.COMPLETEE).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutIntentionPaiement[] values = StatutIntentionPaiement.values(); - assertThat(values).hasSize(5); - assertThat(values).containsExactly( - StatutIntentionPaiement.INITIEE, - StatutIntentionPaiement.EN_COURS, - StatutIntentionPaiement.COMPLETEE, - StatutIntentionPaiement.EXPIREE, - StatutIntentionPaiement.ECHOUEE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(StatutIntentionPaiement.valueOf("INITIEE")).isEqualTo(StatutIntentionPaiement.INITIEE); - assertThat(StatutIntentionPaiement.valueOf("EN_COURS")).isEqualTo(StatutIntentionPaiement.EN_COURS); - assertThat(StatutIntentionPaiement.valueOf("COMPLETEE")).isEqualTo(StatutIntentionPaiement.COMPLETEE); - assertThat(StatutIntentionPaiement.valueOf("EXPIREE")).isEqualTo(StatutIntentionPaiement.EXPIREE); - assertThat(StatutIntentionPaiement.valueOf("ECHOUEE")).isEqualTo(StatutIntentionPaiement.ECHOUEE); - - assertThatThrownBy(() -> StatutIntentionPaiement.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutIntentionPaiement.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutIntentionPaiement statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle contient libellé attendu") - void testGetLibelleContenu() { - assertThat(StatutIntentionPaiement.INITIEE.getLibelle()).contains("Initiée"); - assertThat(StatutIntentionPaiement.COMPLETEE.getLibelle()).contains("Complétée"); - assertThat(StatutIntentionPaiement.ECHOUEE.getLibelle()).contains("Échouée"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(StatutIntentionPaiement.INITIEE.name()).isEqualTo("INITIEE"); - assertThat(StatutIntentionPaiement.EN_COURS.name()).isEqualTo("EN_COURS"); - } - } -} +package dev.lions.unionflow.server.api.enums.paiement; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutIntentionPaiement") +class StatutIntentionPaiementTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutIntentionPaiement.INITIEE).isNotNull(); + assertThat(StatutIntentionPaiement.COMPLETEE).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutIntentionPaiement[] values = StatutIntentionPaiement.values(); + assertThat(values).hasSize(5); + assertThat(values).containsExactly( + StatutIntentionPaiement.INITIEE, + StatutIntentionPaiement.EN_COURS, + StatutIntentionPaiement.COMPLETEE, + StatutIntentionPaiement.EXPIREE, + StatutIntentionPaiement.ECHOUEE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(StatutIntentionPaiement.valueOf("INITIEE")).isEqualTo(StatutIntentionPaiement.INITIEE); + assertThat(StatutIntentionPaiement.valueOf("EN_COURS")).isEqualTo(StatutIntentionPaiement.EN_COURS); + assertThat(StatutIntentionPaiement.valueOf("COMPLETEE")).isEqualTo(StatutIntentionPaiement.COMPLETEE); + assertThat(StatutIntentionPaiement.valueOf("EXPIREE")).isEqualTo(StatutIntentionPaiement.EXPIREE); + assertThat(StatutIntentionPaiement.valueOf("ECHOUEE")).isEqualTo(StatutIntentionPaiement.ECHOUEE); + + assertThatThrownBy(() -> StatutIntentionPaiement.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutIntentionPaiement.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutIntentionPaiement statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle contient libellé attendu") + void testGetLibelleContenu() { + assertThat(StatutIntentionPaiement.INITIEE.getLibelle()).contains("Initiée"); + assertThat(StatutIntentionPaiement.COMPLETEE.getLibelle()).contains("Complétée"); + assertThat(StatutIntentionPaiement.ECHOUEE.getLibelle()).contains("Échouée"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(StatutIntentionPaiement.INITIEE.name()).isEqualTo("INITIEE"); + assertThat(StatutIntentionPaiement.EN_COURS.name()).isEqualTo("EN_COURS"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutPaiementTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutPaiementTest.java index 0ef1740..c4af716 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutPaiementTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutPaiementTest.java @@ -1,119 +1,119 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour StatutPaiement. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests StatutPaiement") -class StatutPaiementTest { - - @Test - @DisplayName("Tous les statuts de paiement doivent avoir un libellé") - void testTousLesStatutsOntLibelle() { - for (StatutPaiement statut : StatutPaiement.values()) { - assertThat(statut.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(StatutPaiement.values().length).isGreaterThan(0); - for (StatutPaiement statut : StatutPaiement.values()) { - assertThat(statut).isNotNull(); - assertThat(statut.name()).isNotBlank(); - } - } - - @Nested - @DisplayName("isFinalise") - class IsFinalise { - - @Test - @DisplayName("VALIDE est finalisé") - void testValide() { - assertThat(StatutPaiement.VALIDE.isFinalise()).isTrue(); - } - - @Test - @DisplayName("ECHOUE est finalisé") - void testEchoue() { - assertThat(StatutPaiement.ECHOUE.isFinalise()).isTrue(); - } - - @Test - @DisplayName("ANNULE est finalisé") - void testAnnule() { - assertThat(StatutPaiement.ANNULE.isFinalise()).isTrue(); - } - - @Test - @DisplayName("REMBOURSE est finalisé") - void testRembourse() { - assertThat(StatutPaiement.REMBOURSE.isFinalise()).isTrue(); - } - - @Test - @DisplayName("EN_ATTENTE n'est pas finalisé") - void testEnAttente() { - assertThat(StatutPaiement.EN_ATTENTE.isFinalise()).isFalse(); - } - - @Test - @DisplayName("EN_COURS n'est pas finalisé") - void testEnCours() { - assertThat(StatutPaiement.EN_COURS.isFinalise()).isFalse(); - } - } - - @Nested - @DisplayName("isEnTraitement") - class IsEnTraitement { - - @Test - @DisplayName("EN_ATTENTE est en traitement") - void testEnAttente() { - assertThat(StatutPaiement.EN_ATTENTE.isEnTraitement()).isTrue(); - } - - @Test - @DisplayName("EN_COURS est en traitement") - void testEnCours() { - assertThat(StatutPaiement.EN_COURS.isEnTraitement()).isTrue(); - } - - @Test - @DisplayName("VALIDE n'est pas en traitement") - void testValide() { - assertThat(StatutPaiement.VALIDE.isEnTraitement()).isFalse(); - } - - @Test - @DisplayName("ECHOUE n'est pas en traitement") - void testEchoue() { - assertThat(StatutPaiement.ECHOUE.isEnTraitement()).isFalse(); - } - - @Test - @DisplayName("ANNULE n'est pas en traitement") - void testAnnule() { - assertThat(StatutPaiement.ANNULE.isEnTraitement()).isFalse(); - } - - @Test - @DisplayName("REMBOURSE n'est pas en traitement") - void testRembourse() { - assertThat(StatutPaiement.REMBOURSE.isEnTraitement()).isFalse(); - } - } -} - +package dev.lions.unionflow.server.api.enums.paiement; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour StatutPaiement. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests StatutPaiement") +class StatutPaiementTest { + + @Test + @DisplayName("Tous les statuts de paiement doivent avoir un libellé") + void testTousLesStatutsOntLibelle() { + for (StatutPaiement statut : StatutPaiement.values()) { + assertThat(statut.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(StatutPaiement.values().length).isGreaterThan(0); + for (StatutPaiement statut : StatutPaiement.values()) { + assertThat(statut).isNotNull(); + assertThat(statut.name()).isNotBlank(); + } + } + + @Nested + @DisplayName("isFinalise") + class IsFinalise { + + @Test + @DisplayName("VALIDE est finalisé") + void testValide() { + assertThat(StatutPaiement.VALIDE.isFinalise()).isTrue(); + } + + @Test + @DisplayName("ECHOUE est finalisé") + void testEchoue() { + assertThat(StatutPaiement.ECHOUE.isFinalise()).isTrue(); + } + + @Test + @DisplayName("ANNULE est finalisé") + void testAnnule() { + assertThat(StatutPaiement.ANNULE.isFinalise()).isTrue(); + } + + @Test + @DisplayName("REMBOURSE est finalisé") + void testRembourse() { + assertThat(StatutPaiement.REMBOURSE.isFinalise()).isTrue(); + } + + @Test + @DisplayName("EN_ATTENTE n'est pas finalisé") + void testEnAttente() { + assertThat(StatutPaiement.EN_ATTENTE.isFinalise()).isFalse(); + } + + @Test + @DisplayName("EN_COURS n'est pas finalisé") + void testEnCours() { + assertThat(StatutPaiement.EN_COURS.isFinalise()).isFalse(); + } + } + + @Nested + @DisplayName("isEnTraitement") + class IsEnTraitement { + + @Test + @DisplayName("EN_ATTENTE est en traitement") + void testEnAttente() { + assertThat(StatutPaiement.EN_ATTENTE.isEnTraitement()).isTrue(); + } + + @Test + @DisplayName("EN_COURS est en traitement") + void testEnCours() { + assertThat(StatutPaiement.EN_COURS.isEnTraitement()).isTrue(); + } + + @Test + @DisplayName("VALIDE n'est pas en traitement") + void testValide() { + assertThat(StatutPaiement.VALIDE.isEnTraitement()).isFalse(); + } + + @Test + @DisplayName("ECHOUE n'est pas en traitement") + void testEchoue() { + assertThat(StatutPaiement.ECHOUE.isEnTraitement()).isFalse(); + } + + @Test + @DisplayName("ANNULE n'est pas en traitement") + void testAnnule() { + assertThat(StatutPaiement.ANNULE.isEnTraitement()).isFalse(); + } + + @Test + @DisplayName("REMBOURSE n'est pas en traitement") + void testRembourse() { + assertThat(StatutPaiement.REMBOURSE.isEnTraitement()).isFalse(); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutSessionTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutSessionTest.java index 12ed4d7..9966768 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutSessionTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutSessionTest.java @@ -1,54 +1,54 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutSession") -class StatutSessionTest { - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutSession[] values = StatutSession.values(); - assertThat(values).hasSize(5); - assertThat(values).containsExactly( - StatutSession.PENDING, - StatutSession.COMPLETED, - StatutSession.CANCELLED, - StatutSession.EXPIRED, - StatutSession.FAILED); - } - - @ParameterizedTest - @EnumSource(StatutSession.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutSession statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @ParameterizedTest - @CsvSource({ - "PENDING, En attente", - "COMPLETED, Complétée", - "CANCELLED, Annulée", - "EXPIRED, Expirée", - "FAILED, Échouée" - }) - @DisplayName("Test getLibelle avec valeurs exactes") - void testGetLibelleValeursExactes(StatutSession statut, String expectedLibelle) { - assertThat(statut.getLibelle()).isEqualTo(expectedLibelle); - } - } -} - +package dev.lions.unionflow.server.api.enums.paiement; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutSession") +class StatutSessionTest { + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutSession[] values = StatutSession.values(); + assertThat(values).hasSize(5); + assertThat(values).containsExactly( + StatutSession.PENDING, + StatutSession.COMPLETED, + StatutSession.CANCELLED, + StatutSession.EXPIRED, + StatutSession.FAILED); + } + + @ParameterizedTest + @EnumSource(StatutSession.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutSession statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @ParameterizedTest + @CsvSource({ + "PENDING, En attente", + "COMPLETED, Complétée", + "CANCELLED, Annulée", + "EXPIRED, Expirée", + "FAILED, Échouée" + }) + @DisplayName("Test getLibelle avec valeurs exactes") + void testGetLibelleValeursExactes(StatutSession statut, String expectedLibelle) { + assertThat(statut.getLibelle()).isEqualTo(expectedLibelle); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutTraitementTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutTraitementTest.java index c660be8..bd0de92 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutTraitementTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/StatutTraitementTest.java @@ -1,54 +1,54 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutTraitement") -class StatutTraitementTest { - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutTraitement[] values = StatutTraitement.values(); - assertThat(values).hasSize(5); - assertThat(values).containsExactly( - StatutTraitement.RECU, - StatutTraitement.EN_COURS, - StatutTraitement.TRAITE, - StatutTraitement.ECHEC, - StatutTraitement.IGNORE); - } - - @ParameterizedTest - @EnumSource(StatutTraitement.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutTraitement statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @ParameterizedTest - @CsvSource({ - "RECU, Reçu", - "EN_COURS, En cours de traitement", - "TRAITE, Traité avec succès", - "ECHEC, Échec de traitement", - "IGNORE, Ignoré" - }) - @DisplayName("Test getLibelle avec valeurs exactes") - void testGetLibelleValeursExactes(StatutTraitement statut, String expectedLibelle) { - assertThat(statut.getLibelle()).isEqualTo(expectedLibelle); - } - } -} - +package dev.lions.unionflow.server.api.enums.paiement; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutTraitement") +class StatutTraitementTest { + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutTraitement[] values = StatutTraitement.values(); + assertThat(values).hasSize(5); + assertThat(values).containsExactly( + StatutTraitement.RECU, + StatutTraitement.EN_COURS, + StatutTraitement.TRAITE, + StatutTraitement.ECHEC, + StatutTraitement.IGNORE); + } + + @ParameterizedTest + @EnumSource(StatutTraitement.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutTraitement statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @ParameterizedTest + @CsvSource({ + "RECU, Reçu", + "EN_COURS, En cours de traitement", + "TRAITE, Traité avec succès", + "ECHEC, Échec de traitement", + "IGNORE, Ignoré" + }) + @DisplayName("Test getLibelle avec valeurs exactes") + void testGetLibelleValeursExactes(StatutTraitement statut, String expectedLibelle) { + assertThat(statut.getLibelle()).isEqualTo(expectedLibelle); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/TypeEvenementTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/TypeEvenementTest.java index 2907cd9..681217c 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/TypeEvenementTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/TypeEvenementTest.java @@ -1,93 +1,93 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.CsvSource; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour TypeEvenement") -class TypeEvenementTest { - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - TypeEvenement[] values = TypeEvenement.values(); - assertThat(values).hasSize(8); - assertThat(values).containsExactly( - TypeEvenement.CHECKOUT_COMPLETE, - TypeEvenement.CHECKOUT_CANCELLED, - TypeEvenement.CHECKOUT_EXPIRED, - TypeEvenement.PAYOUT_COMPLETE, - TypeEvenement.PAYOUT_FAILED, - TypeEvenement.BALANCE_UPDATED, - TypeEvenement.TRANSACTION_CREATED, - TypeEvenement.TRANSACTION_UPDATED); - } - - @ParameterizedTest - @EnumSource(TypeEvenement.class) - @DisplayName("Test getCodeWave pour toutes les valeurs") - void testGetCodeWave(TypeEvenement type) { - assertThat(type.getCodeWave()).isNotNull().isNotEmpty(); - } - - @ParameterizedTest - @CsvSource({ - "CHECKOUT_COMPLETE, checkout.complete", - "CHECKOUT_CANCELLED, checkout.cancelled", - "CHECKOUT_EXPIRED, checkout.expired", - "PAYOUT_COMPLETE, payout.complete", - "PAYOUT_FAILED, payout.failed", - "BALANCE_UPDATED, balance.updated", - "TRANSACTION_CREATED, transaction.created", - "TRANSACTION_UPDATED, transaction.updated" - }) - @DisplayName("Test getCodeWave avec valeurs exactes") - void testGetCodeWaveValeursExactes(TypeEvenement type, String expectedCode) { - assertThat(type.getCodeWave()).isEqualTo(expectedCode); - } - } - - @Nested - @DisplayName("Tests fromCode") - class FromCodeTests { - - @ParameterizedTest - @CsvSource({ - "checkout.complete, CHECKOUT_COMPLETE", - "checkout.cancelled, CHECKOUT_CANCELLED", - "checkout.expired, CHECKOUT_EXPIRED", - "payout.complete, PAYOUT_COMPLETE", - "payout.failed, PAYOUT_FAILED", - "balance.updated, BALANCE_UPDATED", - "transaction.created, TRANSACTION_CREATED", - "transaction.updated, TRANSACTION_UPDATED" - }) - @DisplayName("fromCode - trouve le bon type") - void testFromCode(String code, TypeEvenement expected) { - assertThat(TypeEvenement.fromCode(code)).isEqualTo(expected); - } - - @Test - @DisplayName("fromCode - code inexistant") - void testFromCodeInexistant() { - assertThat(TypeEvenement.fromCode("inexistant")).isNull(); - } - - @Test - @DisplayName("fromCode - code null") - void testFromCodeNull() { - assertThat(TypeEvenement.fromCode(null)).isNull(); - } - } -} - +package dev.lions.unionflow.server.api.enums.paiement; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.CsvSource; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour TypeEvenement") +class TypeEvenementTest { + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + TypeEvenement[] values = TypeEvenement.values(); + assertThat(values).hasSize(8); + assertThat(values).containsExactly( + TypeEvenement.CHECKOUT_COMPLETE, + TypeEvenement.CHECKOUT_CANCELLED, + TypeEvenement.CHECKOUT_EXPIRED, + TypeEvenement.PAYOUT_COMPLETE, + TypeEvenement.PAYOUT_FAILED, + TypeEvenement.BALANCE_UPDATED, + TypeEvenement.TRANSACTION_CREATED, + TypeEvenement.TRANSACTION_UPDATED); + } + + @ParameterizedTest + @EnumSource(TypeEvenement.class) + @DisplayName("Test getCodeWave pour toutes les valeurs") + void testGetCodeWave(TypeEvenement type) { + assertThat(type.getCodeWave()).isNotNull().isNotEmpty(); + } + + @ParameterizedTest + @CsvSource({ + "CHECKOUT_COMPLETE, checkout.complete", + "CHECKOUT_CANCELLED, checkout.cancelled", + "CHECKOUT_EXPIRED, checkout.expired", + "PAYOUT_COMPLETE, payout.complete", + "PAYOUT_FAILED, payout.failed", + "BALANCE_UPDATED, balance.updated", + "TRANSACTION_CREATED, transaction.created", + "TRANSACTION_UPDATED, transaction.updated" + }) + @DisplayName("Test getCodeWave avec valeurs exactes") + void testGetCodeWaveValeursExactes(TypeEvenement type, String expectedCode) { + assertThat(type.getCodeWave()).isEqualTo(expectedCode); + } + } + + @Nested + @DisplayName("Tests fromCode") + class FromCodeTests { + + @ParameterizedTest + @CsvSource({ + "checkout.complete, CHECKOUT_COMPLETE", + "checkout.cancelled, CHECKOUT_CANCELLED", + "checkout.expired, CHECKOUT_EXPIRED", + "payout.complete, PAYOUT_COMPLETE", + "payout.failed, PAYOUT_FAILED", + "balance.updated, BALANCE_UPDATED", + "transaction.created, TRANSACTION_CREATED", + "transaction.updated, TRANSACTION_UPDATED" + }) + @DisplayName("fromCode - trouve le bon type") + void testFromCode(String code, TypeEvenement expected) { + assertThat(TypeEvenement.fromCode(code)).isEqualTo(expected); + } + + @Test + @DisplayName("fromCode - code inexistant") + void testFromCodeInexistant() { + assertThat(TypeEvenement.fromCode("inexistant")).isNull(); + } + + @Test + @DisplayName("fromCode - code null") + void testFromCodeNull() { + assertThat(TypeEvenement.fromCode(null)).isNull(); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/TypeObjetIntentionPaiementTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/TypeObjetIntentionPaiementTest.java index 4cb588b..b1a71e4 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/paiement/TypeObjetIntentionPaiementTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/paiement/TypeObjetIntentionPaiementTest.java @@ -1,82 +1,82 @@ -package dev.lions.unionflow.server.api.enums.paiement; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour TypeObjetIntentionPaiement") -class TypeObjetIntentionPaiementTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(TypeObjetIntentionPaiement.COTISATION).isNotNull(); - assertThat(TypeObjetIntentionPaiement.ADHESION).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - TypeObjetIntentionPaiement[] values = TypeObjetIntentionPaiement.values(); - assertThat(values).hasSize(7); - assertThat(values).containsExactly( - TypeObjetIntentionPaiement.COTISATION, - TypeObjetIntentionPaiement.ADHESION, - TypeObjetIntentionPaiement.EVENEMENT, - TypeObjetIntentionPaiement.ABONNEMENT_UNIONFLOW, - TypeObjetIntentionPaiement.DEPOT_EPARGNE, - TypeObjetIntentionPaiement.RETRAIT_EPARGNE, - TypeObjetIntentionPaiement.CREDIT_REMBOURSEMENT); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(TypeObjetIntentionPaiement.valueOf("COTISATION")).isEqualTo(TypeObjetIntentionPaiement.COTISATION); - assertThat(TypeObjetIntentionPaiement.valueOf("ADHESION")).isEqualTo(TypeObjetIntentionPaiement.ADHESION); - assertThat(TypeObjetIntentionPaiement.valueOf("EVENEMENT")).isEqualTo(TypeObjetIntentionPaiement.EVENEMENT); - assertThat(TypeObjetIntentionPaiement.valueOf("ABONNEMENT_UNIONFLOW")).isEqualTo(TypeObjetIntentionPaiement.ABONNEMENT_UNIONFLOW); - assertThat(TypeObjetIntentionPaiement.valueOf("DEPOT_EPARGNE")).isEqualTo(TypeObjetIntentionPaiement.DEPOT_EPARGNE); - assertThat(TypeObjetIntentionPaiement.valueOf("RETRAIT_EPARGNE")).isEqualTo(TypeObjetIntentionPaiement.RETRAIT_EPARGNE); - assertThat(TypeObjetIntentionPaiement.valueOf("CREDIT_REMBOURSEMENT")).isEqualTo(TypeObjetIntentionPaiement.CREDIT_REMBOURSEMENT); - - assertThatThrownBy(() -> TypeObjetIntentionPaiement.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(TypeObjetIntentionPaiement.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(TypeObjetIntentionPaiement type) { - assertThat(type.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(TypeObjetIntentionPaiement.COTISATION.getLibelle()).isEqualTo("Cotisation membre"); - assertThat(TypeObjetIntentionPaiement.ADHESION.getLibelle()).isEqualTo("Frais d'adhésion"); - assertThat(TypeObjetIntentionPaiement.EVENEMENT.getLibelle()).isEqualTo("Participation événement"); - assertThat(TypeObjetIntentionPaiement.ABONNEMENT_UNIONFLOW.getLibelle()).isEqualTo("Abonnement forfait UnionFlow"); - assertThat(TypeObjetIntentionPaiement.DEPOT_EPARGNE.getLibelle()).isEqualTo("Dépôt compte épargne"); - assertThat(TypeObjetIntentionPaiement.RETRAIT_EPARGNE.getLibelle()).isEqualTo("Retrait compte épargne"); - assertThat(TypeObjetIntentionPaiement.CREDIT_REMBOURSEMENT.getLibelle()).isEqualTo("Remboursement crédit"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(TypeObjetIntentionPaiement.COTISATION.name()).isEqualTo("COTISATION"); - assertThat(TypeObjetIntentionPaiement.ABONNEMENT_UNIONFLOW.name()).isEqualTo("ABONNEMENT_UNIONFLOW"); - } - } -} +package dev.lions.unionflow.server.api.enums.paiement; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour TypeObjetIntentionPaiement") +class TypeObjetIntentionPaiementTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(TypeObjetIntentionPaiement.COTISATION).isNotNull(); + assertThat(TypeObjetIntentionPaiement.ADHESION).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + TypeObjetIntentionPaiement[] values = TypeObjetIntentionPaiement.values(); + assertThat(values).hasSize(7); + assertThat(values).containsExactly( + TypeObjetIntentionPaiement.COTISATION, + TypeObjetIntentionPaiement.ADHESION, + TypeObjetIntentionPaiement.EVENEMENT, + TypeObjetIntentionPaiement.ABONNEMENT_UNIONFLOW, + TypeObjetIntentionPaiement.DEPOT_EPARGNE, + TypeObjetIntentionPaiement.RETRAIT_EPARGNE, + TypeObjetIntentionPaiement.CREDIT_REMBOURSEMENT); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(TypeObjetIntentionPaiement.valueOf("COTISATION")).isEqualTo(TypeObjetIntentionPaiement.COTISATION); + assertThat(TypeObjetIntentionPaiement.valueOf("ADHESION")).isEqualTo(TypeObjetIntentionPaiement.ADHESION); + assertThat(TypeObjetIntentionPaiement.valueOf("EVENEMENT")).isEqualTo(TypeObjetIntentionPaiement.EVENEMENT); + assertThat(TypeObjetIntentionPaiement.valueOf("ABONNEMENT_UNIONFLOW")).isEqualTo(TypeObjetIntentionPaiement.ABONNEMENT_UNIONFLOW); + assertThat(TypeObjetIntentionPaiement.valueOf("DEPOT_EPARGNE")).isEqualTo(TypeObjetIntentionPaiement.DEPOT_EPARGNE); + assertThat(TypeObjetIntentionPaiement.valueOf("RETRAIT_EPARGNE")).isEqualTo(TypeObjetIntentionPaiement.RETRAIT_EPARGNE); + assertThat(TypeObjetIntentionPaiement.valueOf("CREDIT_REMBOURSEMENT")).isEqualTo(TypeObjetIntentionPaiement.CREDIT_REMBOURSEMENT); + + assertThatThrownBy(() -> TypeObjetIntentionPaiement.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(TypeObjetIntentionPaiement.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(TypeObjetIntentionPaiement type) { + assertThat(type.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(TypeObjetIntentionPaiement.COTISATION.getLibelle()).isEqualTo("Cotisation membre"); + assertThat(TypeObjetIntentionPaiement.ADHESION.getLibelle()).isEqualTo("Frais d'adhésion"); + assertThat(TypeObjetIntentionPaiement.EVENEMENT.getLibelle()).isEqualTo("Participation événement"); + assertThat(TypeObjetIntentionPaiement.ABONNEMENT_UNIONFLOW.getLibelle()).isEqualTo("Abonnement forfait UnionFlow"); + assertThat(TypeObjetIntentionPaiement.DEPOT_EPARGNE.getLibelle()).isEqualTo("Dépôt compte épargne"); + assertThat(TypeObjetIntentionPaiement.RETRAIT_EPARGNE.getLibelle()).isEqualTo("Retrait compte épargne"); + assertThat(TypeObjetIntentionPaiement.CREDIT_REMBOURSEMENT.getLibelle()).isEqualTo("Remboursement crédit"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(TypeObjetIntentionPaiement.COTISATION.name()).isEqualTo("COTISATION"); + assertThat(TypeObjetIntentionPaiement.ABONNEMENT_UNIONFLOW.name()).isEqualTo("ABONNEMENT_UNIONFLOW"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/registre/StatutAgrementTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/registre/StatutAgrementTest.java index b8f016b..2cee30b 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/registre/StatutAgrementTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/registre/StatutAgrementTest.java @@ -1,73 +1,73 @@ -package dev.lions.unionflow.server.api.enums.registre; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutAgrement") -class StatutAgrementTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutAgrement.PROVISOIRE).isNotNull(); - assertThat(StatutAgrement.VALIDE).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutAgrement[] values = StatutAgrement.values(); - assertThat(values).hasSize(4); - assertThat(values).containsExactly( - StatutAgrement.PROVISOIRE, - StatutAgrement.VALIDE, - StatutAgrement.SUSPENDU, - StatutAgrement.RETRETIRE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(StatutAgrement.valueOf("PROVISOIRE")).isEqualTo(StatutAgrement.PROVISOIRE); - assertThat(StatutAgrement.valueOf("VALIDE")).isEqualTo(StatutAgrement.VALIDE); - assertThat(StatutAgrement.valueOf("SUSPENDU")).isEqualTo(StatutAgrement.SUSPENDU); - assertThat(StatutAgrement.valueOf("RETRETIRE")).isEqualTo(StatutAgrement.RETRETIRE); - - assertThatThrownBy(() -> StatutAgrement.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutAgrement.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutAgrement statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(StatutAgrement.PROVISOIRE.getLibelle()).isEqualTo("Agréé provisoirement sous condition"); - assertThat(StatutAgrement.VALIDE.getLibelle()).isEqualTo("Agréé - Dossier complet et vérifié"); - assertThat(StatutAgrement.SUSPENDU.getLibelle()).isEqualTo("Agrément temporairement suspendu"); - assertThat(StatutAgrement.RETRETIRE.getLibelle()).isEqualTo("Agrément définitivement radié"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(StatutAgrement.PROVISOIRE.name()).isEqualTo("PROVISOIRE"); - assertThat(StatutAgrement.RETRETIRE.name()).isEqualTo("RETRETIRE"); - } - } -} +package dev.lions.unionflow.server.api.enums.registre; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutAgrement") +class StatutAgrementTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutAgrement.PROVISOIRE).isNotNull(); + assertThat(StatutAgrement.VALIDE).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutAgrement[] values = StatutAgrement.values(); + assertThat(values).hasSize(4); + assertThat(values).containsExactly( + StatutAgrement.PROVISOIRE, + StatutAgrement.VALIDE, + StatutAgrement.SUSPENDU, + StatutAgrement.RETRETIRE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(StatutAgrement.valueOf("PROVISOIRE")).isEqualTo(StatutAgrement.PROVISOIRE); + assertThat(StatutAgrement.valueOf("VALIDE")).isEqualTo(StatutAgrement.VALIDE); + assertThat(StatutAgrement.valueOf("SUSPENDU")).isEqualTo(StatutAgrement.SUSPENDU); + assertThat(StatutAgrement.valueOf("RETRETIRE")).isEqualTo(StatutAgrement.RETRETIRE); + + assertThatThrownBy(() -> StatutAgrement.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutAgrement.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutAgrement statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(StatutAgrement.PROVISOIRE.getLibelle()).isEqualTo("Agréé provisoirement sous condition"); + assertThat(StatutAgrement.VALIDE.getLibelle()).isEqualTo("Agréé - Dossier complet et vérifié"); + assertThat(StatutAgrement.SUSPENDU.getLibelle()).isEqualTo("Agrément temporairement suspendu"); + assertThat(StatutAgrement.RETRETIRE.getLibelle()).isEqualTo("Agrément définitivement radié"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(StatutAgrement.PROVISOIRE.name()).isEqualTo("PROVISOIRE"); + assertThat(StatutAgrement.RETRETIRE.name()).isEqualTo("RETRETIRE"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/PrioriteAideTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/PrioriteAideTest.java index 99204dc..981d712 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/PrioriteAideTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/PrioriteAideTest.java @@ -1,424 +1,424 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.time.LocalDateTime; -import java.util.List; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour PrioriteAide. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests PrioriteAide") -class PrioriteAideTest { - - @Test - @DisplayName("Toutes les priorités doivent avoir un libellé") - void testToutesLesPrioritesOntLibelle() { - for (PrioriteAide priorite : PrioriteAide.values()) { - assertThat(priorite.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("Toutes les priorités doivent avoir un code") - void testToutesLesPrioritesOntCode() { - for (PrioriteAide priorite : PrioriteAide.values()) { - assertThat(priorite.getCode()).isNotNull().isNotBlank(); - } - } - - @Nested - @DisplayName("Tests isUrgente") - class IsUrgenteTests { - - @Test - @DisplayName("isUrgente doit retourner true pour CRITIQUE et URGENTE") - void testIsUrgente() { - assertThat(PrioriteAide.CRITIQUE.isUrgente()).isTrue(); - assertThat(PrioriteAide.URGENTE.isUrgente()).isTrue(); - - assertThat(PrioriteAide.ELEVEE.isUrgente()).isFalse(); - assertThat(PrioriteAide.NORMALE.isUrgente()).isFalse(); - assertThat(PrioriteAide.FAIBLE.isUrgente()).isFalse(); - } - } - - @Nested - @DisplayName("Tests necessiteTraitementImmediat") - class NecessiteTraitementImmediatTests { - - @Test - @DisplayName("necessiteTraitementImmediat doit retourner true pour niveau <= 2") - void testNecessiteTraitementImmediat() { - assertThat(PrioriteAide.CRITIQUE.necessiteTraitementImmediat()).isTrue(); - assertThat(PrioriteAide.URGENTE.necessiteTraitementImmediat()).isTrue(); - - assertThat(PrioriteAide.ELEVEE.necessiteTraitementImmediat()).isFalse(); - assertThat(PrioriteAide.NORMALE.necessiteTraitementImmediat()).isFalse(); - assertThat(PrioriteAide.FAIBLE.necessiteTraitementImmediat()).isFalse(); - } - } - - @Nested - @DisplayName("Tests getDateLimiteTraitement") - class GetDateLimiteTraitementTests { - - @Test - @DisplayName("getDateLimiteTraitement doit retourner une date future") - void testGetDateLimiteTraitement() { - LocalDateTime maintenant = LocalDateTime.now(); - LocalDateTime dateLimite = PrioriteAide.CRITIQUE.getDateLimiteTraitement(); - - assertThat(dateLimite).isAfter(maintenant); - assertThat(dateLimite).isBefore(maintenant.plusHours(25)); // CRITIQUE = 24h - } - } - - @Nested - @DisplayName("Tests getPrioriteEscalade") - class GetPrioriteEscaladeTests { - - @Test - @DisplayName("getPrioriteEscalade doit retourner la priorité suivante") - void testGetPrioriteEscalade() { - assertThat(PrioriteAide.FAIBLE.getPrioriteEscalade()).isEqualTo(PrioriteAide.NORMALE); - assertThat(PrioriteAide.NORMALE.getPrioriteEscalade()).isEqualTo(PrioriteAide.ELEVEE); - assertThat(PrioriteAide.ELEVEE.getPrioriteEscalade()).isEqualTo(PrioriteAide.URGENTE); - assertThat(PrioriteAide.URGENTE.getPrioriteEscalade()).isEqualTo(PrioriteAide.CRITIQUE); - assertThat(PrioriteAide.CRITIQUE.getPrioriteEscalade()).isEqualTo(PrioriteAide.CRITIQUE); - } - } - - @Nested - @DisplayName("Tests determinerPriorite") - class DeterminerPrioriteTests { - - @Test - @DisplayName("determinerPriorite doit retourner CRITIQUE pour AIDE_FINANCIERE_URGENTE") - void testDeterminerPrioriteCritique() { - assertThat(PrioriteAide.determinerPriorite(TypeAide.AIDE_FINANCIERE_URGENTE)) - .isEqualTo(PrioriteAide.CRITIQUE); - assertThat(PrioriteAide.determinerPriorite(TypeAide.AIDE_FRAIS_MEDICAUX)) - .isEqualTo(PrioriteAide.CRITIQUE); - } - - @Test - @DisplayName("determinerPriorite doit retourner URGENTE pour HEBERGEMENT_URGENCE et AIDE_ALIMENTAIRE") - void testDeterminerPrioriteUrgente() { - assertThat(PrioriteAide.determinerPriorite(TypeAide.HEBERGEMENT_URGENCE)) - .isEqualTo(PrioriteAide.URGENTE); - assertThat(PrioriteAide.determinerPriorite(TypeAide.AIDE_ALIMENTAIRE)) - .isEqualTo(PrioriteAide.URGENTE); - } - - @Test - @DisplayName("determinerPriorite doit retourner ELEVEE pour types urgents non spécifiques") - void testDeterminerPrioriteElevee() { - assertThat(PrioriteAide.determinerPriorite(TypeAide.PRET_SANS_INTERET)) - .isEqualTo(PrioriteAide.ELEVEE); - } - - @Test - @DisplayName("determinerPriorite retourne ELEVEE (default switch) pour type urgent non listé (reflection)") - void testDeterminerPrioriteUrgentDefault() throws Exception { - java.lang.reflect.Field prioriteField = TypeAide.class.getDeclaredField("priorite"); - prioriteField.setAccessible(true); - String backupPriorite = (String) prioriteField.get(TypeAide.AIDE_VESTIMENTAIRE); - try { - prioriteField.set(TypeAide.AIDE_VESTIMENTAIRE, "urgent"); - assertThat(TypeAide.AIDE_VESTIMENTAIRE.isUrgent()).isTrue(); - assertThat(PrioriteAide.determinerPriorite(TypeAide.AIDE_VESTIMENTAIRE)) - .isEqualTo(PrioriteAide.ELEVEE); - } finally { - prioriteField.set(TypeAide.AIDE_VESTIMENTAIRE, backupPriorite); - } - } - - @Test - @DisplayName("determinerPriorite doit retourner ELEVEE pour types avec priorite important") - void testDeterminerPrioriteImportant() { - assertThat(PrioriteAide.determinerPriorite(TypeAide.PRET_SANS_INTERET)) - .isEqualTo(PrioriteAide.ELEVEE); - assertThat(PrioriteAide.determinerPriorite(TypeAide.AIDE_FRAIS_SCOLARITE)) - .isEqualTo(PrioriteAide.ELEVEE); - } - - @Test - @DisplayName("determinerPriorite doit retourner NORMALE par défaut") - void testDeterminerPrioriteNormale() { - assertThat(PrioriteAide.determinerPriorite(TypeAide.DON_MATERIEL)) - .isEqualTo(PrioriteAide.NORMALE); - assertThat(PrioriteAide.determinerPriorite(TypeAide.TRANSPORT)) - .isEqualTo(PrioriteAide.NORMALE); - } - } - - @Nested - @DisplayName("Tests getPrioritesUrgentes") - class GetPrioritesUrgentesTests { - - @Test - @DisplayName("getPrioritesUrgentes doit retourner CRITIQUE et URGENTE") - void testGetPrioritesUrgentes() { - List prioritésUrgentes = PrioriteAide.getPrioritesUrgentes(); - - assertThat(prioritésUrgentes).hasSize(2); - assertThat(prioritésUrgentes).contains(PrioriteAide.CRITIQUE); - assertThat(prioritésUrgentes).contains(PrioriteAide.URGENTE); - } - } - - @Nested - @DisplayName("Tests getParNiveauCroissant") - class GetParNiveauCroissantTests { - - @Test - @DisplayName("getParNiveauCroissant doit retourner les priorités triées par niveau croissant") - void testGetParNiveauCroissant() { - List priorités = PrioriteAide.getParNiveauCroissant(); - - assertThat(priorités).hasSize(5); - assertThat(priorités.get(0)).isEqualTo(PrioriteAide.CRITIQUE); - assertThat(priorités.get(1)).isEqualTo(PrioriteAide.URGENTE); - assertThat(priorités.get(2)).isEqualTo(PrioriteAide.ELEVEE); - assertThat(priorités.get(3)).isEqualTo(PrioriteAide.NORMALE); - assertThat(priorités.get(4)).isEqualTo(PrioriteAide.FAIBLE); - } - } - - @Nested - @DisplayName("Tests getParNiveauDecroissant") - class GetParNiveauDecroissantTests { - - @Test - @DisplayName("getParNiveauDecroissant doit retourner les priorités triées par niveau décroissant") - void testGetParNiveauDecroissant() { - List priorités = PrioriteAide.getParNiveauDecroissant(); - - assertThat(priorités).hasSize(5); - assertThat(priorités.get(0)).isEqualTo(PrioriteAide.FAIBLE); - assertThat(priorités.get(1)).isEqualTo(PrioriteAide.NORMALE); - assertThat(priorités.get(2)).isEqualTo(PrioriteAide.ELEVEE); - assertThat(priorités.get(3)).isEqualTo(PrioriteAide.URGENTE); - assertThat(priorités.get(4)).isEqualTo(PrioriteAide.CRITIQUE); - } - } - - @Nested - @DisplayName("Tests parCode") - class ParCodeTests { - - @Test - @DisplayName("parCode doit retourner la priorité correspondante") - void testParCode() { - assertThat(PrioriteAide.parCode("critical")).isEqualTo(PrioriteAide.CRITIQUE); - assertThat(PrioriteAide.parCode("urgent")).isEqualTo(PrioriteAide.URGENTE); - assertThat(PrioriteAide.parCode("high")).isEqualTo(PrioriteAide.ELEVEE); - assertThat(PrioriteAide.parCode("normal")).isEqualTo(PrioriteAide.NORMALE); - assertThat(PrioriteAide.parCode("low")).isEqualTo(PrioriteAide.FAIBLE); - } - - @Test - @DisplayName("parCode doit retourner NORMALE pour un code inconnu") - void testParCodeInconnu() { - assertThat(PrioriteAide.parCode("unknown")).isEqualTo(PrioriteAide.NORMALE); - assertThat(PrioriteAide.parCode("")).isEqualTo(PrioriteAide.NORMALE); - } - } - - @Nested - @DisplayName("Tests getScorePriorite") - class GetScorePrioriteTests { - - @Test - @DisplayName("getScorePriorite doit calculer correctement") - void testGetScorePriorite() { - // CRITIQUE: niveau=1, notificationImmediate=true, escaladeAutomatique=true - // Score = 1 - 0.5 - 0.3 = 0.2 - double scoreCritique = PrioriteAide.CRITIQUE.getScorePriorite(); - assertThat(scoreCritique).isLessThan(1.0); - - // URGENTE: niveau=2, notificationImmediate=true, escaladeAutomatique=false - // Score = 2 - 0.5 = 1.5 - double scoreUrgente = PrioriteAide.URGENTE.getScorePriorite(); - assertThat(scoreUrgente).isLessThan(2.0); - - // FAIBLE: niveau=5, notificationImmediate=false, escaladeAutomatique=false, - // delaiTraitementHeures=720 > 168 - // Score = 5 + 0.2 = 5.2 - double scoreFaible = PrioriteAide.FAIBLE.getScorePriorite(); - assertThat(scoreFaible).isGreaterThan(5.0); - } - } - - @Nested - @DisplayName("Tests isDelaiDepasse") - class IsDelaiDepasseTests { - - @Test - @DisplayName("isDelaiDepasse doit retourner false si le délai n'est pas dépassé") - void testIsDelaiDepasseNonDepasse() { - LocalDateTime dateCreation = LocalDateTime.now().minusHours(10); - assertThat(PrioriteAide.CRITIQUE.isDelaiDepasse(dateCreation)).isFalse(); - } - - @Test - @DisplayName("isDelaiDepasse doit retourner true si le délai est dépassé") - void testIsDelaiDepasseDepasse() { - LocalDateTime dateCreation = LocalDateTime.now().minusHours(25); - assertThat(PrioriteAide.CRITIQUE.isDelaiDepasse(dateCreation)).isTrue(); - } - - @Test - @DisplayName("isDelaiDepasse avec date de référence doit fonctionner correctement") - void testIsDelaiDepasseAvecDateReference() { - LocalDateTime dateCreation = LocalDateTime.now().minusHours(10); - LocalDateTime maintenant = LocalDateTime.now().plusHours(20); - assertThat(PrioriteAide.CRITIQUE.isDelaiDepasse(dateCreation, maintenant)).isTrue(); - - maintenant = LocalDateTime.now().plusHours(10); - assertThat(PrioriteAide.CRITIQUE.isDelaiDepasse(dateCreation, maintenant)).isFalse(); - } - - @Test - @DisplayName("isDelaiDepasse doit retourner false si exactement à la limite") - void testIsDelaiDepasseALaLimite() { - // Pour être exactement à la limite dans isDelaiDepasse(dateCreation, - // maintenant), - // il faut passer maintenant = dateCreation.plusHours(delai) - LocalDateTime dateCreation = LocalDateTime.now().minusHours(24); - LocalDateTime maintenant = dateCreation.plusHours(24); // Ex: CRITIQUE - - assertThat(PrioriteAide.CRITIQUE.isDelaiDepasse(dateCreation, maintenant)).isFalse(); - } - } - - @Nested - @DisplayName("Tests getPourcentageTempsEcoule") - class GetPourcentageTempsEcouleTests { - - @Test - @DisplayName("getPourcentageTempsEcoule doit calculer correctement") - void testGetPourcentageTempsEcoule() { - LocalDateTime dateCreation = LocalDateTime.now().minusHours(12); - // CRITIQUE = 24h, donc 12h = 50% - double pourcentage = PrioriteAide.CRITIQUE.getPourcentageTempsEcoule(dateCreation); - assertThat(pourcentage).isBetween(45.0, 55.0); - } - - @Test - @DisplayName("getPourcentageTempsEcoule doit retourner 100 si délai dépassé") - void testGetPourcentageTempsEcouleDepasse() { - LocalDateTime dateCreation = LocalDateTime.now().minusHours(30); - double pourcentage = PrioriteAide.CRITIQUE.getPourcentageTempsEcoule(dateCreation); - assertThat(pourcentage).isEqualTo(100.0); - } - - @Test - @DisplayName("getPourcentageTempsEcoule doit gérer dureeTotal <= 0") - void testGetPourcentageTempsEcouleDureeZero() { - double pourcentage = PrioriteAide.CRITIQUE.getPourcentageTempsEcoule(LocalDateTime.now()); - assertThat(pourcentage).isGreaterThanOrEqualTo(0.0); - assertThat(pourcentage).isLessThanOrEqualTo(100.0); - } - - @Test - @DisplayName("getPourcentageTempsEcoule retourne 100 quand dureeTotal <= 0 (reflection)") - void testGetPourcentageTempsEcouleDureeTotalZero() throws Exception { - java.lang.reflect.Field f = PrioriteAide.class.getDeclaredField("delaiTraitementHeures"); - f.setAccessible(true); - int backup = (int) f.get(PrioriteAide.CRITIQUE); - try { - f.setInt(PrioriteAide.CRITIQUE, 0); - LocalDateTime dateCreation = LocalDateTime.now(); - assertThat(PrioriteAide.CRITIQUE.getPourcentageTempsEcoule(dateCreation)).isEqualTo(100.0); - } finally { - f.setInt(PrioriteAide.CRITIQUE, backup); - } - } - } - - @Nested - @DisplayName("Tests getMessageAlerte") - class GetMessageAlerteTests { - - @Test - @DisplayName("getMessageAlerte doit retourner le bon message selon le pourcentage") - void testGetMessageAlerte() { - // Pourcentage >= 100 - LocalDateTime dateCreation = LocalDateTime.now().minusHours(30); - assertThat(PrioriteAide.CRITIQUE.getMessageAlerte(dateCreation)) - .isEqualTo("Délai de traitement dépassé !"); - - // Pourcentage >= 80 - dateCreation = LocalDateTime.now().minusHours(20); - assertThat(PrioriteAide.CRITIQUE.getMessageAlerte(dateCreation)) - .isEqualTo("Délai de traitement bientôt dépassé"); - - // Pourcentage >= 60 - dateCreation = LocalDateTime.now().minusHours(15); - assertThat(PrioriteAide.CRITIQUE.getMessageAlerte(dateCreation)) - .isEqualTo("Plus de la moitié du délai écoulé"); - - // Pourcentage < 60 - dateCreation = LocalDateTime.now().minusHours(5); - assertThat(PrioriteAide.CRITIQUE.getMessageAlerte(dateCreation)).isNull(); - } - } - - @Nested - @DisplayName("Tests getters simples") - class GettersSimples { - - @Test - @DisplayName("getDescription doit retourner la description") - void testGetDescription() { - assertThat(PrioriteAide.CRITIQUE.getDescription()) - .isEqualTo("Situation critique nécessitant une intervention immédiate"); - assertThat(PrioriteAide.NORMALE.getDescription()) - .isEqualTo("Priorité normale, traitement selon les délais standards"); - } - - @Test - @DisplayName("getCouleur doit retourner la couleur") - void testGetCouleur() { - assertThat(PrioriteAide.CRITIQUE.getCouleur()).isEqualTo("#F44336"); - assertThat(PrioriteAide.NORMALE.getCouleur()).isEqualTo("#2196F3"); - } - - @Test - @DisplayName("getIcone doit retourner l'icône") - void testGetIcone() { - assertThat(PrioriteAide.CRITIQUE.getIcone()).isEqualTo("emergency"); - assertThat(PrioriteAide.NORMALE.getIcone()).isEqualTo("remove"); - } - - @Test - @DisplayName("getDelaiTraitementHeures doit retourner le délai en heures") - void testGetDelaiTraitementHeures() { - assertThat(PrioriteAide.CRITIQUE.getDelaiTraitementHeures()).isEqualTo(24); - assertThat(PrioriteAide.NORMALE.getDelaiTraitementHeures()).isEqualTo(336); - } - - @Test - @DisplayName("isNotificationImmediate doit retourner la valeur du champ") - void testIsNotificationImmediate() { - assertThat(PrioriteAide.CRITIQUE.isNotificationImmediate()).isTrue(); - assertThat(PrioriteAide.NORMALE.isNotificationImmediate()).isFalse(); - } - - @Test - @DisplayName("isEscaladeAutomatique doit retourner la valeur du champ") - void testIsEscaladeAutomatique() { - assertThat(PrioriteAide.CRITIQUE.isEscaladeAutomatique()).isTrue(); - assertThat(PrioriteAide.NORMALE.isEscaladeAutomatique()).isFalse(); - } - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.time.LocalDateTime; +import java.util.List; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour PrioriteAide. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests PrioriteAide") +class PrioriteAideTest { + + @Test + @DisplayName("Toutes les priorités doivent avoir un libellé") + void testToutesLesPrioritesOntLibelle() { + for (PrioriteAide priorite : PrioriteAide.values()) { + assertThat(priorite.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("Toutes les priorités doivent avoir un code") + void testToutesLesPrioritesOntCode() { + for (PrioriteAide priorite : PrioriteAide.values()) { + assertThat(priorite.getCode()).isNotNull().isNotBlank(); + } + } + + @Nested + @DisplayName("Tests isUrgente") + class IsUrgenteTests { + + @Test + @DisplayName("isUrgente doit retourner true pour CRITIQUE et URGENTE") + void testIsUrgente() { + assertThat(PrioriteAide.CRITIQUE.isUrgente()).isTrue(); + assertThat(PrioriteAide.URGENTE.isUrgente()).isTrue(); + + assertThat(PrioriteAide.ELEVEE.isUrgente()).isFalse(); + assertThat(PrioriteAide.NORMALE.isUrgente()).isFalse(); + assertThat(PrioriteAide.FAIBLE.isUrgente()).isFalse(); + } + } + + @Nested + @DisplayName("Tests necessiteTraitementImmediat") + class NecessiteTraitementImmediatTests { + + @Test + @DisplayName("necessiteTraitementImmediat doit retourner true pour niveau <= 2") + void testNecessiteTraitementImmediat() { + assertThat(PrioriteAide.CRITIQUE.necessiteTraitementImmediat()).isTrue(); + assertThat(PrioriteAide.URGENTE.necessiteTraitementImmediat()).isTrue(); + + assertThat(PrioriteAide.ELEVEE.necessiteTraitementImmediat()).isFalse(); + assertThat(PrioriteAide.NORMALE.necessiteTraitementImmediat()).isFalse(); + assertThat(PrioriteAide.FAIBLE.necessiteTraitementImmediat()).isFalse(); + } + } + + @Nested + @DisplayName("Tests getDateLimiteTraitement") + class GetDateLimiteTraitementTests { + + @Test + @DisplayName("getDateLimiteTraitement doit retourner une date future") + void testGetDateLimiteTraitement() { + LocalDateTime maintenant = LocalDateTime.now(); + LocalDateTime dateLimite = PrioriteAide.CRITIQUE.getDateLimiteTraitement(); + + assertThat(dateLimite).isAfter(maintenant); + assertThat(dateLimite).isBefore(maintenant.plusHours(25)); // CRITIQUE = 24h + } + } + + @Nested + @DisplayName("Tests getPrioriteEscalade") + class GetPrioriteEscaladeTests { + + @Test + @DisplayName("getPrioriteEscalade doit retourner la priorité suivante") + void testGetPrioriteEscalade() { + assertThat(PrioriteAide.FAIBLE.getPrioriteEscalade()).isEqualTo(PrioriteAide.NORMALE); + assertThat(PrioriteAide.NORMALE.getPrioriteEscalade()).isEqualTo(PrioriteAide.ELEVEE); + assertThat(PrioriteAide.ELEVEE.getPrioriteEscalade()).isEqualTo(PrioriteAide.URGENTE); + assertThat(PrioriteAide.URGENTE.getPrioriteEscalade()).isEqualTo(PrioriteAide.CRITIQUE); + assertThat(PrioriteAide.CRITIQUE.getPrioriteEscalade()).isEqualTo(PrioriteAide.CRITIQUE); + } + } + + @Nested + @DisplayName("Tests determinerPriorite") + class DeterminerPrioriteTests { + + @Test + @DisplayName("determinerPriorite doit retourner CRITIQUE pour AIDE_FINANCIERE_URGENTE") + void testDeterminerPrioriteCritique() { + assertThat(PrioriteAide.determinerPriorite(TypeAide.AIDE_FINANCIERE_URGENTE)) + .isEqualTo(PrioriteAide.CRITIQUE); + assertThat(PrioriteAide.determinerPriorite(TypeAide.AIDE_FRAIS_MEDICAUX)) + .isEqualTo(PrioriteAide.CRITIQUE); + } + + @Test + @DisplayName("determinerPriorite doit retourner URGENTE pour HEBERGEMENT_URGENCE et AIDE_ALIMENTAIRE") + void testDeterminerPrioriteUrgente() { + assertThat(PrioriteAide.determinerPriorite(TypeAide.HEBERGEMENT_URGENCE)) + .isEqualTo(PrioriteAide.URGENTE); + assertThat(PrioriteAide.determinerPriorite(TypeAide.AIDE_ALIMENTAIRE)) + .isEqualTo(PrioriteAide.URGENTE); + } + + @Test + @DisplayName("determinerPriorite doit retourner ELEVEE pour types urgents non spécifiques") + void testDeterminerPrioriteElevee() { + assertThat(PrioriteAide.determinerPriorite(TypeAide.PRET_SANS_INTERET)) + .isEqualTo(PrioriteAide.ELEVEE); + } + + @Test + @DisplayName("determinerPriorite retourne ELEVEE (default switch) pour type urgent non listé (reflection)") + void testDeterminerPrioriteUrgentDefault() throws Exception { + java.lang.reflect.Field prioriteField = TypeAide.class.getDeclaredField("priorite"); + prioriteField.setAccessible(true); + String backupPriorite = (String) prioriteField.get(TypeAide.AIDE_VESTIMENTAIRE); + try { + prioriteField.set(TypeAide.AIDE_VESTIMENTAIRE, "urgent"); + assertThat(TypeAide.AIDE_VESTIMENTAIRE.isUrgent()).isTrue(); + assertThat(PrioriteAide.determinerPriorite(TypeAide.AIDE_VESTIMENTAIRE)) + .isEqualTo(PrioriteAide.ELEVEE); + } finally { + prioriteField.set(TypeAide.AIDE_VESTIMENTAIRE, backupPriorite); + } + } + + @Test + @DisplayName("determinerPriorite doit retourner ELEVEE pour types avec priorite important") + void testDeterminerPrioriteImportant() { + assertThat(PrioriteAide.determinerPriorite(TypeAide.PRET_SANS_INTERET)) + .isEqualTo(PrioriteAide.ELEVEE); + assertThat(PrioriteAide.determinerPriorite(TypeAide.AIDE_FRAIS_SCOLARITE)) + .isEqualTo(PrioriteAide.ELEVEE); + } + + @Test + @DisplayName("determinerPriorite doit retourner NORMALE par défaut") + void testDeterminerPrioriteNormale() { + assertThat(PrioriteAide.determinerPriorite(TypeAide.DON_MATERIEL)) + .isEqualTo(PrioriteAide.NORMALE); + assertThat(PrioriteAide.determinerPriorite(TypeAide.TRANSPORT)) + .isEqualTo(PrioriteAide.NORMALE); + } + } + + @Nested + @DisplayName("Tests getPrioritesUrgentes") + class GetPrioritesUrgentesTests { + + @Test + @DisplayName("getPrioritesUrgentes doit retourner CRITIQUE et URGENTE") + void testGetPrioritesUrgentes() { + List prioritésUrgentes = PrioriteAide.getPrioritesUrgentes(); + + assertThat(prioritésUrgentes).hasSize(2); + assertThat(prioritésUrgentes).contains(PrioriteAide.CRITIQUE); + assertThat(prioritésUrgentes).contains(PrioriteAide.URGENTE); + } + } + + @Nested + @DisplayName("Tests getParNiveauCroissant") + class GetParNiveauCroissantTests { + + @Test + @DisplayName("getParNiveauCroissant doit retourner les priorités triées par niveau croissant") + void testGetParNiveauCroissant() { + List priorités = PrioriteAide.getParNiveauCroissant(); + + assertThat(priorités).hasSize(5); + assertThat(priorités.get(0)).isEqualTo(PrioriteAide.CRITIQUE); + assertThat(priorités.get(1)).isEqualTo(PrioriteAide.URGENTE); + assertThat(priorités.get(2)).isEqualTo(PrioriteAide.ELEVEE); + assertThat(priorités.get(3)).isEqualTo(PrioriteAide.NORMALE); + assertThat(priorités.get(4)).isEqualTo(PrioriteAide.FAIBLE); + } + } + + @Nested + @DisplayName("Tests getParNiveauDecroissant") + class GetParNiveauDecroissantTests { + + @Test + @DisplayName("getParNiveauDecroissant doit retourner les priorités triées par niveau décroissant") + void testGetParNiveauDecroissant() { + List priorités = PrioriteAide.getParNiveauDecroissant(); + + assertThat(priorités).hasSize(5); + assertThat(priorités.get(0)).isEqualTo(PrioriteAide.FAIBLE); + assertThat(priorités.get(1)).isEqualTo(PrioriteAide.NORMALE); + assertThat(priorités.get(2)).isEqualTo(PrioriteAide.ELEVEE); + assertThat(priorités.get(3)).isEqualTo(PrioriteAide.URGENTE); + assertThat(priorités.get(4)).isEqualTo(PrioriteAide.CRITIQUE); + } + } + + @Nested + @DisplayName("Tests parCode") + class ParCodeTests { + + @Test + @DisplayName("parCode doit retourner la priorité correspondante") + void testParCode() { + assertThat(PrioriteAide.parCode("critical")).isEqualTo(PrioriteAide.CRITIQUE); + assertThat(PrioriteAide.parCode("urgent")).isEqualTo(PrioriteAide.URGENTE); + assertThat(PrioriteAide.parCode("high")).isEqualTo(PrioriteAide.ELEVEE); + assertThat(PrioriteAide.parCode("normal")).isEqualTo(PrioriteAide.NORMALE); + assertThat(PrioriteAide.parCode("low")).isEqualTo(PrioriteAide.FAIBLE); + } + + @Test + @DisplayName("parCode doit retourner NORMALE pour un code inconnu") + void testParCodeInconnu() { + assertThat(PrioriteAide.parCode("unknown")).isEqualTo(PrioriteAide.NORMALE); + assertThat(PrioriteAide.parCode("")).isEqualTo(PrioriteAide.NORMALE); + } + } + + @Nested + @DisplayName("Tests getScorePriorite") + class GetScorePrioriteTests { + + @Test + @DisplayName("getScorePriorite doit calculer correctement") + void testGetScorePriorite() { + // CRITIQUE: niveau=1, notificationImmediate=true, escaladeAutomatique=true + // Score = 1 - 0.5 - 0.3 = 0.2 + double scoreCritique = PrioriteAide.CRITIQUE.getScorePriorite(); + assertThat(scoreCritique).isLessThan(1.0); + + // URGENTE: niveau=2, notificationImmediate=true, escaladeAutomatique=false + // Score = 2 - 0.5 = 1.5 + double scoreUrgente = PrioriteAide.URGENTE.getScorePriorite(); + assertThat(scoreUrgente).isLessThan(2.0); + + // FAIBLE: niveau=5, notificationImmediate=false, escaladeAutomatique=false, + // delaiTraitementHeures=720 > 168 + // Score = 5 + 0.2 = 5.2 + double scoreFaible = PrioriteAide.FAIBLE.getScorePriorite(); + assertThat(scoreFaible).isGreaterThan(5.0); + } + } + + @Nested + @DisplayName("Tests isDelaiDepasse") + class IsDelaiDepasseTests { + + @Test + @DisplayName("isDelaiDepasse doit retourner false si le délai n'est pas dépassé") + void testIsDelaiDepasseNonDepasse() { + LocalDateTime dateCreation = LocalDateTime.now().minusHours(10); + assertThat(PrioriteAide.CRITIQUE.isDelaiDepasse(dateCreation)).isFalse(); + } + + @Test + @DisplayName("isDelaiDepasse doit retourner true si le délai est dépassé") + void testIsDelaiDepasseDepasse() { + LocalDateTime dateCreation = LocalDateTime.now().minusHours(25); + assertThat(PrioriteAide.CRITIQUE.isDelaiDepasse(dateCreation)).isTrue(); + } + + @Test + @DisplayName("isDelaiDepasse avec date de référence doit fonctionner correctement") + void testIsDelaiDepasseAvecDateReference() { + LocalDateTime dateCreation = LocalDateTime.now().minusHours(10); + LocalDateTime maintenant = LocalDateTime.now().plusHours(20); + assertThat(PrioriteAide.CRITIQUE.isDelaiDepasse(dateCreation, maintenant)).isTrue(); + + maintenant = LocalDateTime.now().plusHours(10); + assertThat(PrioriteAide.CRITIQUE.isDelaiDepasse(dateCreation, maintenant)).isFalse(); + } + + @Test + @DisplayName("isDelaiDepasse doit retourner false si exactement à la limite") + void testIsDelaiDepasseALaLimite() { + // Pour être exactement à la limite dans isDelaiDepasse(dateCreation, + // maintenant), + // il faut passer maintenant = dateCreation.plusHours(delai) + LocalDateTime dateCreation = LocalDateTime.now().minusHours(24); + LocalDateTime maintenant = dateCreation.plusHours(24); // Ex: CRITIQUE + + assertThat(PrioriteAide.CRITIQUE.isDelaiDepasse(dateCreation, maintenant)).isFalse(); + } + } + + @Nested + @DisplayName("Tests getPourcentageTempsEcoule") + class GetPourcentageTempsEcouleTests { + + @Test + @DisplayName("getPourcentageTempsEcoule doit calculer correctement") + void testGetPourcentageTempsEcoule() { + LocalDateTime dateCreation = LocalDateTime.now().minusHours(12); + // CRITIQUE = 24h, donc 12h = 50% + double pourcentage = PrioriteAide.CRITIQUE.getPourcentageTempsEcoule(dateCreation); + assertThat(pourcentage).isBetween(45.0, 55.0); + } + + @Test + @DisplayName("getPourcentageTempsEcoule doit retourner 100 si délai dépassé") + void testGetPourcentageTempsEcouleDepasse() { + LocalDateTime dateCreation = LocalDateTime.now().minusHours(30); + double pourcentage = PrioriteAide.CRITIQUE.getPourcentageTempsEcoule(dateCreation); + assertThat(pourcentage).isEqualTo(100.0); + } + + @Test + @DisplayName("getPourcentageTempsEcoule doit gérer dureeTotal <= 0") + void testGetPourcentageTempsEcouleDureeZero() { + double pourcentage = PrioriteAide.CRITIQUE.getPourcentageTempsEcoule(LocalDateTime.now()); + assertThat(pourcentage).isGreaterThanOrEqualTo(0.0); + assertThat(pourcentage).isLessThanOrEqualTo(100.0); + } + + @Test + @DisplayName("getPourcentageTempsEcoule retourne 100 quand dureeTotal <= 0 (reflection)") + void testGetPourcentageTempsEcouleDureeTotalZero() throws Exception { + java.lang.reflect.Field f = PrioriteAide.class.getDeclaredField("delaiTraitementHeures"); + f.setAccessible(true); + int backup = (int) f.get(PrioriteAide.CRITIQUE); + try { + f.setInt(PrioriteAide.CRITIQUE, 0); + LocalDateTime dateCreation = LocalDateTime.now(); + assertThat(PrioriteAide.CRITIQUE.getPourcentageTempsEcoule(dateCreation)).isEqualTo(100.0); + } finally { + f.setInt(PrioriteAide.CRITIQUE, backup); + } + } + } + + @Nested + @DisplayName("Tests getMessageAlerte") + class GetMessageAlerteTests { + + @Test + @DisplayName("getMessageAlerte doit retourner le bon message selon le pourcentage") + void testGetMessageAlerte() { + // Pourcentage >= 100 + LocalDateTime dateCreation = LocalDateTime.now().minusHours(30); + assertThat(PrioriteAide.CRITIQUE.getMessageAlerte(dateCreation)) + .isEqualTo("Délai de traitement dépassé !"); + + // Pourcentage >= 80 + dateCreation = LocalDateTime.now().minusHours(20); + assertThat(PrioriteAide.CRITIQUE.getMessageAlerte(dateCreation)) + .isEqualTo("Délai de traitement bientôt dépassé"); + + // Pourcentage >= 60 + dateCreation = LocalDateTime.now().minusHours(15); + assertThat(PrioriteAide.CRITIQUE.getMessageAlerte(dateCreation)) + .isEqualTo("Plus de la moitié du délai écoulé"); + + // Pourcentage < 60 + dateCreation = LocalDateTime.now().minusHours(5); + assertThat(PrioriteAide.CRITIQUE.getMessageAlerte(dateCreation)).isNull(); + } + } + + @Nested + @DisplayName("Tests getters simples") + class GettersSimples { + + @Test + @DisplayName("getDescription doit retourner la description") + void testGetDescription() { + assertThat(PrioriteAide.CRITIQUE.getDescription()) + .isEqualTo("Situation critique nécessitant une intervention immédiate"); + assertThat(PrioriteAide.NORMALE.getDescription()) + .isEqualTo("Priorité normale, traitement selon les délais standards"); + } + + @Test + @DisplayName("getCouleur doit retourner la couleur") + void testGetCouleur() { + assertThat(PrioriteAide.CRITIQUE.getCouleur()).isEqualTo("#F44336"); + assertThat(PrioriteAide.NORMALE.getCouleur()).isEqualTo("#2196F3"); + } + + @Test + @DisplayName("getIcone doit retourner l'icône") + void testGetIcone() { + assertThat(PrioriteAide.CRITIQUE.getIcone()).isEqualTo("emergency"); + assertThat(PrioriteAide.NORMALE.getIcone()).isEqualTo("remove"); + } + + @Test + @DisplayName("getDelaiTraitementHeures doit retourner le délai en heures") + void testGetDelaiTraitementHeures() { + assertThat(PrioriteAide.CRITIQUE.getDelaiTraitementHeures()).isEqualTo(24); + assertThat(PrioriteAide.NORMALE.getDelaiTraitementHeures()).isEqualTo(336); + } + + @Test + @DisplayName("isNotificationImmediate doit retourner la valeur du champ") + void testIsNotificationImmediate() { + assertThat(PrioriteAide.CRITIQUE.isNotificationImmediate()).isTrue(); + assertThat(PrioriteAide.NORMALE.isNotificationImmediate()).isFalse(); + } + + @Test + @DisplayName("isEscaladeAutomatique doit retourner la valeur du champ") + void testIsEscaladeAutomatique() { + assertThat(PrioriteAide.CRITIQUE.isEscaladeAutomatique()).isTrue(); + assertThat(PrioriteAide.NORMALE.isEscaladeAutomatique()).isFalse(); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutAideTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutAideTest.java index afb64cc..85aadf2 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutAideTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutAideTest.java @@ -1,368 +1,368 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.util.List; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour StatutAide. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests StatutAide") -class StatutAideTest { - - @Test - @DisplayName("Tous les statuts doivent avoir un libellé") - void testTousLesStatutsOntLibelle() { - for (StatutAide statut : StatutAide.values()) { - assertThat(statut.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("Tous les statuts doivent avoir un code") - void testTousLesStatutsOntCode() { - for (StatutAide statut : StatutAide.values()) { - assertThat(statut.getCode()).isNotNull().isNotBlank(); - } - } - - @Nested - @DisplayName("Tests isSucces") - class IsSuccesTests { - - @Test - @DisplayName("isSucces doit retourner true pour VERSEE, LIVREE, TERMINEE") - void testIsSucces() { - assertThat(StatutAide.VERSEE.isSucces()).isTrue(); - assertThat(StatutAide.LIVREE.isSucces()).isTrue(); - assertThat(StatutAide.TERMINEE.isSucces()).isTrue(); - - assertThat(StatutAide.APPROUVEE.isSucces()).isFalse(); - assertThat(StatutAide.REJETEE.isSucces()).isFalse(); - assertThat(StatutAide.EN_ATTENTE.isSucces()).isFalse(); - } - } - - @Nested - @DisplayName("Tests isEnCours") - class IsEnCoursTests { - - @Test - @DisplayName("isEnCours doit retourner true pour les statuts en cours") - void testIsEnCours() { - assertThat(StatutAide.EN_COURS_EVALUATION.isEnCours()).isTrue(); - assertThat(StatutAide.EN_COURS_TRAITEMENT.isEnCours()).isTrue(); - assertThat(StatutAide.EN_COURS_VERSEMENT.isEnCours()).isTrue(); - - assertThat(StatutAide.EN_ATTENTE.isEnCours()).isFalse(); - assertThat(StatutAide.APPROUVEE.isEnCours()).isFalse(); - assertThat(StatutAide.TERMINEE.isEnCours()).isFalse(); - } - } - - @Nested - @DisplayName("Tests permetModification") - class PermetModificationTests { - - @Test - @DisplayName("permetModification doit retourner true pour BROUILLON et INFORMATIONS_REQUISES") - void testPermetModification() { - assertThat(StatutAide.BROUILLON.permetModification()).isTrue(); - assertThat(StatutAide.INFORMATIONS_REQUISES.permetModification()).isTrue(); - - assertThat(StatutAide.EN_ATTENTE.permetModification()).isFalse(); - assertThat(StatutAide.APPROUVEE.permetModification()).isFalse(); - assertThat(StatutAide.TERMINEE.permetModification()).isFalse(); - } - } - - @Nested - @DisplayName("Tests permetAnnulation") - class PermetAnnulationTests { - - @Test - @DisplayName("permetAnnulation doit retourner false pour les statuts finaux et ANNULEE") - void testPermetAnnulation() { - assertThat(StatutAide.ANNULEE.permetAnnulation()).isFalse(); - assertThat(StatutAide.TERMINEE.permetAnnulation()).isFalse(); - assertThat(StatutAide.VERSEE.permetAnnulation()).isFalse(); - assertThat(StatutAide.REJETEE.permetAnnulation()).isFalse(); - assertThat(StatutAide.EXPIREE.permetAnnulation()).isFalse(); - assertThat(StatutAide.CLOTUREE.permetAnnulation()).isFalse(); - - assertThat(StatutAide.BROUILLON.permetAnnulation()).isTrue(); - assertThat(StatutAide.EN_ATTENTE.permetAnnulation()).isTrue(); - assertThat(StatutAide.EN_COURS_EVALUATION.permetAnnulation()).isTrue(); - assertThat(StatutAide.INFORMATIONS_REQUISES.permetAnnulation()).isTrue(); - assertThat(StatutAide.SUSPENDUE.permetAnnulation()).isTrue(); - } - } - - @Nested - @DisplayName("Tests getStatutsFinaux") - class GetStatutsFinauxTests { - - @Test - @DisplayName("getStatutsFinaux doit retourner tous les statuts finaux") - void testGetStatutsFinaux() { - List statutsFinaux = StatutAide.getStatutsFinaux(); - - assertThat(statutsFinaux).isNotEmpty(); - assertThat(statutsFinaux).contains(StatutAide.APPROUVEE); - assertThat(statutsFinaux).contains(StatutAide.APPROUVEE_PARTIELLEMENT); - assertThat(statutsFinaux).contains(StatutAide.REJETEE); - assertThat(statutsFinaux).contains(StatutAide.VERSEE); - assertThat(statutsFinaux).contains(StatutAide.LIVREE); - assertThat(statutsFinaux).contains(StatutAide.TERMINEE); - assertThat(statutsFinaux).contains(StatutAide.ANNULEE); - assertThat(statutsFinaux).contains(StatutAide.EXPIREE); - assertThat(statutsFinaux).contains(StatutAide.CLOTUREE); - - assertThat(statutsFinaux).doesNotContain(StatutAide.BROUILLON); - assertThat(statutsFinaux).doesNotContain(StatutAide.EN_ATTENTE); - } - } - - @Nested - @DisplayName("Tests getStatutsEchec") - class GetStatutsEchecTests { - - @Test - @DisplayName("getStatutsEchec doit retourner tous les statuts d'échec") - void testGetStatutsEchec() { - List statutsEchec = StatutAide.getStatutsEchec(); - - assertThat(statutsEchec).isNotEmpty(); - assertThat(statutsEchec).contains(StatutAide.REJETEE); - assertThat(statutsEchec).contains(StatutAide.ANNULEE); - assertThat(statutsEchec).contains(StatutAide.EXPIREE); - - assertThat(statutsEchec).doesNotContain(StatutAide.VERSEE); - assertThat(statutsEchec).doesNotContain(StatutAide.TERMINEE); - } - } - - @Nested - @DisplayName("Tests getStatutsSucces") - class GetStatutsSuccesTests { - - @Test - @DisplayName("getStatutsSucces doit retourner tous les statuts de succès") - void testGetStatutsSucces() { - List statutsSucces = StatutAide.getStatutsSucces(); - - assertThat(statutsSucces).isNotEmpty(); - assertThat(statutsSucces).contains(StatutAide.VERSEE); - assertThat(statutsSucces).contains(StatutAide.LIVREE); - assertThat(statutsSucces).contains(StatutAide.TERMINEE); - - assertThat(statutsSucces).doesNotContain(StatutAide.REJETEE); - assertThat(statutsSucces).doesNotContain(StatutAide.APPROUVEE); - } - } - - @Nested - @DisplayName("Tests getStatutsEnCours") - class GetStatutsEnCoursTests { - - @Test - @DisplayName("getStatutsEnCours doit retourner tous les statuts en cours") - void testGetStatutsEnCours() { - List statutsEnCours = StatutAide.getStatutsEnCours(); - - assertThat(statutsEnCours).isNotEmpty(); - assertThat(statutsEnCours).contains(StatutAide.EN_COURS_EVALUATION); - assertThat(statutsEnCours).contains(StatutAide.EN_COURS_TRAITEMENT); - assertThat(statutsEnCours).contains(StatutAide.EN_COURS_VERSEMENT); - - assertThat(statutsEnCours).doesNotContain(StatutAide.EN_ATTENTE); - assertThat(statutsEnCours).doesNotContain(StatutAide.APPROUVEE); - } - } - - @Nested - @DisplayName("Tests peutTransitionnerVers") - class PeutTransitionnerVersTests { - - @Test - @DisplayName("peutTransitionnerVers doit retourner false si même statut") - void testMemeStatut() { - assertThat(StatutAide.BROUILLON.peutTransitionnerVers(StatutAide.BROUILLON)).isFalse(); - assertThat(StatutAide.EN_ATTENTE.peutTransitionnerVers(StatutAide.EN_ATTENTE)).isFalse(); - } - - @Test - @DisplayName("peutTransitionnerVers - BROUILLON peut aller vers SOUMISE ou ANNULEE") - void testBrouillon() { - assertThat(StatutAide.BROUILLON.peutTransitionnerVers(StatutAide.SOUMISE)).isTrue(); - assertThat(StatutAide.BROUILLON.peutTransitionnerVers(StatutAide.ANNULEE)).isTrue(); - assertThat(StatutAide.BROUILLON.peutTransitionnerVers(StatutAide.EN_ATTENTE)).isFalse(); - } - - @Test - @DisplayName("peutTransitionnerVers - SOUMISE peut aller vers EN_ATTENTE ou ANNULEE") - void testSoumise() { - assertThat(StatutAide.SOUMISE.peutTransitionnerVers(StatutAide.EN_ATTENTE)).isTrue(); - assertThat(StatutAide.SOUMISE.peutTransitionnerVers(StatutAide.ANNULEE)).isTrue(); - assertThat(StatutAide.SOUMISE.peutTransitionnerVers(StatutAide.APPROUVEE)).isFalse(); - } - - @Test - @DisplayName("peutTransitionnerVers - EN_ATTENTE peut aller vers EN_COURS_EVALUATION ou ANNULEE") - void testEnAttente() { - assertThat(StatutAide.EN_ATTENTE.peutTransitionnerVers(StatutAide.EN_COURS_EVALUATION)) - .isTrue(); - assertThat(StatutAide.EN_ATTENTE.peutTransitionnerVers(StatutAide.ANNULEE)).isTrue(); - assertThat(StatutAide.EN_ATTENTE.peutTransitionnerVers(StatutAide.APPROUVEE)).isFalse(); - } - - @Test - @DisplayName("peutTransitionnerVers - EN_COURS_EVALUATION peut aller vers plusieurs statuts") - void testEnCoursEvaluation() { - assertThat(StatutAide.EN_COURS_EVALUATION.peutTransitionnerVers(StatutAide.APPROUVEE)) - .isTrue(); - assertThat( - StatutAide.EN_COURS_EVALUATION.peutTransitionnerVers(StatutAide.APPROUVEE_PARTIELLEMENT)) - .isTrue(); - assertThat(StatutAide.EN_COURS_EVALUATION.peutTransitionnerVers(StatutAide.REJETEE)).isTrue(); - assertThat( - StatutAide.EN_COURS_EVALUATION.peutTransitionnerVers(StatutAide.INFORMATIONS_REQUISES)) - .isTrue(); - assertThat(StatutAide.EN_COURS_EVALUATION.peutTransitionnerVers(StatutAide.SUSPENDUE)) - .isTrue(); - assertThat(StatutAide.EN_COURS_EVALUATION.peutTransitionnerVers(StatutAide.TERMINEE)) - .isFalse(); - } - - @Test - @DisplayName("peutTransitionnerVers - INFORMATIONS_REQUISES peut aller vers EN_COURS_EVALUATION ou ANNULEE") - void testInformationsRequises() { - assertThat( - StatutAide.INFORMATIONS_REQUISES.peutTransitionnerVers(StatutAide.EN_COURS_EVALUATION)) - .isTrue(); - assertThat(StatutAide.INFORMATIONS_REQUISES.peutTransitionnerVers(StatutAide.ANNULEE)) - .isTrue(); - assertThat(StatutAide.INFORMATIONS_REQUISES.peutTransitionnerVers(StatutAide.APPROUVEE)) - .isFalse(); - } - - @Test - @DisplayName("peutTransitionnerVers - APPROUVEE peut aller vers EN_COURS_TRAITEMENT ou SUSPENDUE") - void testApprouvee() { - assertThat(StatutAide.APPROUVEE.peutTransitionnerVers(StatutAide.EN_COURS_TRAITEMENT)) - .isTrue(); - assertThat(StatutAide.APPROUVEE.peutTransitionnerVers(StatutAide.SUSPENDUE)).isTrue(); - assertThat(StatutAide.APPROUVEE.peutTransitionnerVers(StatutAide.VERSEE)).isFalse(); - } - - @Test - @DisplayName("peutTransitionnerVers - EN_COURS_TRAITEMENT peut aller vers plusieurs statuts") - void testEnCoursTraitement() { - assertThat(StatutAide.EN_COURS_TRAITEMENT.peutTransitionnerVers(StatutAide.EN_COURS_VERSEMENT)) - .isTrue(); - assertThat(StatutAide.EN_COURS_TRAITEMENT.peutTransitionnerVers(StatutAide.LIVREE)).isTrue(); - assertThat(StatutAide.EN_COURS_TRAITEMENT.peutTransitionnerVers(StatutAide.TERMINEE)) - .isTrue(); - assertThat(StatutAide.EN_COURS_TRAITEMENT.peutTransitionnerVers(StatutAide.SUSPENDUE)) - .isTrue(); - assertThat(StatutAide.EN_COURS_TRAITEMENT.peutTransitionnerVers(StatutAide.APPROUVEE)) - .isFalse(); - } - - @Test - @DisplayName("peutTransitionnerVers - EN_COURS_VERSEMENT peut aller vers VERSEE ou SUSPENDUE") - void testEnCoursVersement() { - assertThat(StatutAide.EN_COURS_VERSEMENT.peutTransitionnerVers(StatutAide.VERSEE)).isTrue(); - assertThat(StatutAide.EN_COURS_VERSEMENT.peutTransitionnerVers(StatutAide.SUSPENDUE)) - .isTrue(); - assertThat(StatutAide.EN_COURS_VERSEMENT.peutTransitionnerVers(StatutAide.TERMINEE)) - .isFalse(); - } - - @Test - @DisplayName("peutTransitionnerVers - SUSPENDUE peut aller vers EN_COURS_EVALUATION ou ANNULEE") - void testSuspendue() { - assertThat(StatutAide.SUSPENDUE.peutTransitionnerVers(StatutAide.EN_COURS_EVALUATION)) - .isTrue(); - assertThat(StatutAide.SUSPENDUE.peutTransitionnerVers(StatutAide.ANNULEE)).isTrue(); - assertThat(StatutAide.SUSPENDUE.peutTransitionnerVers(StatutAide.APPROUVEE)).isFalse(); - } - - @Test - @DisplayName("peutTransitionnerVers - Les statuts finaux ne peuvent pas transitionner (sauf APPROUVEE)") - void testStatutsFinaux() { - // Les statuts finaux (sauf APPROUVEE et APPROUVEE_PARTIELLEMENT) ne peuvent pas transitionner - // car le switch retourne false par défaut - assertThat(StatutAide.TERMINEE.peutTransitionnerVers(StatutAide.EN_SUIVI)).isFalse(); - assertThat(StatutAide.VERSEE.peutTransitionnerVers(StatutAide.EN_SUIVI)).isFalse(); - assertThat(StatutAide.TERMINEE.peutTransitionnerVers(StatutAide.APPROUVEE)).isFalse(); - assertThat(StatutAide.VERSEE.peutTransitionnerVers(StatutAide.APPROUVEE)).isFalse(); - assertThat(StatutAide.REJETEE.peutTransitionnerVers(StatutAide.EN_SUIVI)).isFalse(); - assertThat(StatutAide.ANNULEE.peutTransitionnerVers(StatutAide.EN_SUIVI)).isFalse(); - - // APPROUVEE et APPROUVEE_PARTIELLEMENT peuvent transitionner vers EN_COURS_TRAITEMENT ou SUSPENDUE - assertThat(StatutAide.APPROUVEE.peutTransitionnerVers(StatutAide.EN_COURS_TRAITEMENT)) - .isTrue(); - assertThat(StatutAide.APPROUVEE_PARTIELLEMENT.peutTransitionnerVers(StatutAide.EN_COURS_TRAITEMENT)) - .isTrue(); - assertThat(StatutAide.APPROUVEE.peutTransitionnerVers(StatutAide.SUSPENDUE)).isTrue(); - } - } - - @Nested - @DisplayName("Tests getNiveauPriorite") - class GetNiveauPrioriteTests { - - @Test - @DisplayName("getNiveauPriorite doit retourner le bon niveau") - void testGetNiveauPriorite() { - assertThat(StatutAide.INFORMATIONS_REQUISES.getNiveauPriorite()).isEqualTo(1); - assertThat(StatutAide.EN_COURS_EVALUATION.getNiveauPriorite()).isEqualTo(2); - assertThat(StatutAide.EN_COURS_TRAITEMENT.getNiveauPriorite()).isEqualTo(2); - assertThat(StatutAide.EN_COURS_VERSEMENT.getNiveauPriorite()).isEqualTo(2); - assertThat(StatutAide.APPROUVEE.getNiveauPriorite()).isEqualTo(3); - assertThat(StatutAide.APPROUVEE_PARTIELLEMENT.getNiveauPriorite()).isEqualTo(3); - assertThat(StatutAide.EN_ATTENTE.getNiveauPriorite()).isEqualTo(4); - assertThat(StatutAide.SOUMISE.getNiveauPriorite()).isEqualTo(4); - assertThat(StatutAide.SUSPENDUE.getNiveauPriorite()).isEqualTo(5); - assertThat(StatutAide.BROUILLON.getNiveauPriorite()).isEqualTo(6); - assertThat(StatutAide.EN_SUIVI.getNiveauPriorite()).isEqualTo(7); - assertThat(StatutAide.TERMINEE.getNiveauPriorite()).isEqualTo(8); - assertThat(StatutAide.VERSEE.getNiveauPriorite()).isEqualTo(8); - } - } - - @Nested - @DisplayName("Tests getters simples") - class GettersSimples { - - @Test - @DisplayName("getDescription doit retourner la description") - void testGetDescription() { - assertThat(StatutAide.BROUILLON.getDescription()) - .isEqualTo("La demande est en cours de rédaction"); - assertThat(StatutAide.APPROUVEE.getDescription()).isEqualTo("La demande a été approuvée"); - } - - @Test - @DisplayName("getCouleur doit retourner la couleur") - void testGetCouleur() { - assertThat(StatutAide.BROUILLON.getCouleur()).isEqualTo("#9E9E9E"); - assertThat(StatutAide.APPROUVEE.getCouleur()).isEqualTo("#4CAF50"); - } - - @Test - @DisplayName("getIcone doit retourner l'icône") - void testGetIcone() { - assertThat(StatutAide.BROUILLON.getIcone()).isEqualTo("edit"); - assertThat(StatutAide.APPROUVEE.getIcone()).isEqualTo("check_circle"); - } - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.List; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour StatutAide. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests StatutAide") +class StatutAideTest { + + @Test + @DisplayName("Tous les statuts doivent avoir un libellé") + void testTousLesStatutsOntLibelle() { + for (StatutAide statut : StatutAide.values()) { + assertThat(statut.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("Tous les statuts doivent avoir un code") + void testTousLesStatutsOntCode() { + for (StatutAide statut : StatutAide.values()) { + assertThat(statut.getCode()).isNotNull().isNotBlank(); + } + } + + @Nested + @DisplayName("Tests isSucces") + class IsSuccesTests { + + @Test + @DisplayName("isSucces doit retourner true pour VERSEE, LIVREE, TERMINEE") + void testIsSucces() { + assertThat(StatutAide.VERSEE.isSucces()).isTrue(); + assertThat(StatutAide.LIVREE.isSucces()).isTrue(); + assertThat(StatutAide.TERMINEE.isSucces()).isTrue(); + + assertThat(StatutAide.APPROUVEE.isSucces()).isFalse(); + assertThat(StatutAide.REJETEE.isSucces()).isFalse(); + assertThat(StatutAide.EN_ATTENTE.isSucces()).isFalse(); + } + } + + @Nested + @DisplayName("Tests isEnCours") + class IsEnCoursTests { + + @Test + @DisplayName("isEnCours doit retourner true pour les statuts en cours") + void testIsEnCours() { + assertThat(StatutAide.EN_COURS_EVALUATION.isEnCours()).isTrue(); + assertThat(StatutAide.EN_COURS_TRAITEMENT.isEnCours()).isTrue(); + assertThat(StatutAide.EN_COURS_VERSEMENT.isEnCours()).isTrue(); + + assertThat(StatutAide.EN_ATTENTE.isEnCours()).isFalse(); + assertThat(StatutAide.APPROUVEE.isEnCours()).isFalse(); + assertThat(StatutAide.TERMINEE.isEnCours()).isFalse(); + } + } + + @Nested + @DisplayName("Tests permetModification") + class PermetModificationTests { + + @Test + @DisplayName("permetModification doit retourner true pour BROUILLON et INFORMATIONS_REQUISES") + void testPermetModification() { + assertThat(StatutAide.BROUILLON.permetModification()).isTrue(); + assertThat(StatutAide.INFORMATIONS_REQUISES.permetModification()).isTrue(); + + assertThat(StatutAide.EN_ATTENTE.permetModification()).isFalse(); + assertThat(StatutAide.APPROUVEE.permetModification()).isFalse(); + assertThat(StatutAide.TERMINEE.permetModification()).isFalse(); + } + } + + @Nested + @DisplayName("Tests permetAnnulation") + class PermetAnnulationTests { + + @Test + @DisplayName("permetAnnulation doit retourner false pour les statuts finaux et ANNULEE") + void testPermetAnnulation() { + assertThat(StatutAide.ANNULEE.permetAnnulation()).isFalse(); + assertThat(StatutAide.TERMINEE.permetAnnulation()).isFalse(); + assertThat(StatutAide.VERSEE.permetAnnulation()).isFalse(); + assertThat(StatutAide.REJETEE.permetAnnulation()).isFalse(); + assertThat(StatutAide.EXPIREE.permetAnnulation()).isFalse(); + assertThat(StatutAide.CLOTUREE.permetAnnulation()).isFalse(); + + assertThat(StatutAide.BROUILLON.permetAnnulation()).isTrue(); + assertThat(StatutAide.EN_ATTENTE.permetAnnulation()).isTrue(); + assertThat(StatutAide.EN_COURS_EVALUATION.permetAnnulation()).isTrue(); + assertThat(StatutAide.INFORMATIONS_REQUISES.permetAnnulation()).isTrue(); + assertThat(StatutAide.SUSPENDUE.permetAnnulation()).isTrue(); + } + } + + @Nested + @DisplayName("Tests getStatutsFinaux") + class GetStatutsFinauxTests { + + @Test + @DisplayName("getStatutsFinaux doit retourner tous les statuts finaux") + void testGetStatutsFinaux() { + List statutsFinaux = StatutAide.getStatutsFinaux(); + + assertThat(statutsFinaux).isNotEmpty(); + assertThat(statutsFinaux).contains(StatutAide.APPROUVEE); + assertThat(statutsFinaux).contains(StatutAide.APPROUVEE_PARTIELLEMENT); + assertThat(statutsFinaux).contains(StatutAide.REJETEE); + assertThat(statutsFinaux).contains(StatutAide.VERSEE); + assertThat(statutsFinaux).contains(StatutAide.LIVREE); + assertThat(statutsFinaux).contains(StatutAide.TERMINEE); + assertThat(statutsFinaux).contains(StatutAide.ANNULEE); + assertThat(statutsFinaux).contains(StatutAide.EXPIREE); + assertThat(statutsFinaux).contains(StatutAide.CLOTUREE); + + assertThat(statutsFinaux).doesNotContain(StatutAide.BROUILLON); + assertThat(statutsFinaux).doesNotContain(StatutAide.EN_ATTENTE); + } + } + + @Nested + @DisplayName("Tests getStatutsEchec") + class GetStatutsEchecTests { + + @Test + @DisplayName("getStatutsEchec doit retourner tous les statuts d'échec") + void testGetStatutsEchec() { + List statutsEchec = StatutAide.getStatutsEchec(); + + assertThat(statutsEchec).isNotEmpty(); + assertThat(statutsEchec).contains(StatutAide.REJETEE); + assertThat(statutsEchec).contains(StatutAide.ANNULEE); + assertThat(statutsEchec).contains(StatutAide.EXPIREE); + + assertThat(statutsEchec).doesNotContain(StatutAide.VERSEE); + assertThat(statutsEchec).doesNotContain(StatutAide.TERMINEE); + } + } + + @Nested + @DisplayName("Tests getStatutsSucces") + class GetStatutsSuccesTests { + + @Test + @DisplayName("getStatutsSucces doit retourner tous les statuts de succès") + void testGetStatutsSucces() { + List statutsSucces = StatutAide.getStatutsSucces(); + + assertThat(statutsSucces).isNotEmpty(); + assertThat(statutsSucces).contains(StatutAide.VERSEE); + assertThat(statutsSucces).contains(StatutAide.LIVREE); + assertThat(statutsSucces).contains(StatutAide.TERMINEE); + + assertThat(statutsSucces).doesNotContain(StatutAide.REJETEE); + assertThat(statutsSucces).doesNotContain(StatutAide.APPROUVEE); + } + } + + @Nested + @DisplayName("Tests getStatutsEnCours") + class GetStatutsEnCoursTests { + + @Test + @DisplayName("getStatutsEnCours doit retourner tous les statuts en cours") + void testGetStatutsEnCours() { + List statutsEnCours = StatutAide.getStatutsEnCours(); + + assertThat(statutsEnCours).isNotEmpty(); + assertThat(statutsEnCours).contains(StatutAide.EN_COURS_EVALUATION); + assertThat(statutsEnCours).contains(StatutAide.EN_COURS_TRAITEMENT); + assertThat(statutsEnCours).contains(StatutAide.EN_COURS_VERSEMENT); + + assertThat(statutsEnCours).doesNotContain(StatutAide.EN_ATTENTE); + assertThat(statutsEnCours).doesNotContain(StatutAide.APPROUVEE); + } + } + + @Nested + @DisplayName("Tests peutTransitionnerVers") + class PeutTransitionnerVersTests { + + @Test + @DisplayName("peutTransitionnerVers doit retourner false si même statut") + void testMemeStatut() { + assertThat(StatutAide.BROUILLON.peutTransitionnerVers(StatutAide.BROUILLON)).isFalse(); + assertThat(StatutAide.EN_ATTENTE.peutTransitionnerVers(StatutAide.EN_ATTENTE)).isFalse(); + } + + @Test + @DisplayName("peutTransitionnerVers - BROUILLON peut aller vers SOUMISE ou ANNULEE") + void testBrouillon() { + assertThat(StatutAide.BROUILLON.peutTransitionnerVers(StatutAide.SOUMISE)).isTrue(); + assertThat(StatutAide.BROUILLON.peutTransitionnerVers(StatutAide.ANNULEE)).isTrue(); + assertThat(StatutAide.BROUILLON.peutTransitionnerVers(StatutAide.EN_ATTENTE)).isFalse(); + } + + @Test + @DisplayName("peutTransitionnerVers - SOUMISE peut aller vers EN_ATTENTE ou ANNULEE") + void testSoumise() { + assertThat(StatutAide.SOUMISE.peutTransitionnerVers(StatutAide.EN_ATTENTE)).isTrue(); + assertThat(StatutAide.SOUMISE.peutTransitionnerVers(StatutAide.ANNULEE)).isTrue(); + assertThat(StatutAide.SOUMISE.peutTransitionnerVers(StatutAide.APPROUVEE)).isFalse(); + } + + @Test + @DisplayName("peutTransitionnerVers - EN_ATTENTE peut aller vers EN_COURS_EVALUATION ou ANNULEE") + void testEnAttente() { + assertThat(StatutAide.EN_ATTENTE.peutTransitionnerVers(StatutAide.EN_COURS_EVALUATION)) + .isTrue(); + assertThat(StatutAide.EN_ATTENTE.peutTransitionnerVers(StatutAide.ANNULEE)).isTrue(); + assertThat(StatutAide.EN_ATTENTE.peutTransitionnerVers(StatutAide.APPROUVEE)).isFalse(); + } + + @Test + @DisplayName("peutTransitionnerVers - EN_COURS_EVALUATION peut aller vers plusieurs statuts") + void testEnCoursEvaluation() { + assertThat(StatutAide.EN_COURS_EVALUATION.peutTransitionnerVers(StatutAide.APPROUVEE)) + .isTrue(); + assertThat( + StatutAide.EN_COURS_EVALUATION.peutTransitionnerVers(StatutAide.APPROUVEE_PARTIELLEMENT)) + .isTrue(); + assertThat(StatutAide.EN_COURS_EVALUATION.peutTransitionnerVers(StatutAide.REJETEE)).isTrue(); + assertThat( + StatutAide.EN_COURS_EVALUATION.peutTransitionnerVers(StatutAide.INFORMATIONS_REQUISES)) + .isTrue(); + assertThat(StatutAide.EN_COURS_EVALUATION.peutTransitionnerVers(StatutAide.SUSPENDUE)) + .isTrue(); + assertThat(StatutAide.EN_COURS_EVALUATION.peutTransitionnerVers(StatutAide.TERMINEE)) + .isFalse(); + } + + @Test + @DisplayName("peutTransitionnerVers - INFORMATIONS_REQUISES peut aller vers EN_COURS_EVALUATION ou ANNULEE") + void testInformationsRequises() { + assertThat( + StatutAide.INFORMATIONS_REQUISES.peutTransitionnerVers(StatutAide.EN_COURS_EVALUATION)) + .isTrue(); + assertThat(StatutAide.INFORMATIONS_REQUISES.peutTransitionnerVers(StatutAide.ANNULEE)) + .isTrue(); + assertThat(StatutAide.INFORMATIONS_REQUISES.peutTransitionnerVers(StatutAide.APPROUVEE)) + .isFalse(); + } + + @Test + @DisplayName("peutTransitionnerVers - APPROUVEE peut aller vers EN_COURS_TRAITEMENT ou SUSPENDUE") + void testApprouvee() { + assertThat(StatutAide.APPROUVEE.peutTransitionnerVers(StatutAide.EN_COURS_TRAITEMENT)) + .isTrue(); + assertThat(StatutAide.APPROUVEE.peutTransitionnerVers(StatutAide.SUSPENDUE)).isTrue(); + assertThat(StatutAide.APPROUVEE.peutTransitionnerVers(StatutAide.VERSEE)).isFalse(); + } + + @Test + @DisplayName("peutTransitionnerVers - EN_COURS_TRAITEMENT peut aller vers plusieurs statuts") + void testEnCoursTraitement() { + assertThat(StatutAide.EN_COURS_TRAITEMENT.peutTransitionnerVers(StatutAide.EN_COURS_VERSEMENT)) + .isTrue(); + assertThat(StatutAide.EN_COURS_TRAITEMENT.peutTransitionnerVers(StatutAide.LIVREE)).isTrue(); + assertThat(StatutAide.EN_COURS_TRAITEMENT.peutTransitionnerVers(StatutAide.TERMINEE)) + .isTrue(); + assertThat(StatutAide.EN_COURS_TRAITEMENT.peutTransitionnerVers(StatutAide.SUSPENDUE)) + .isTrue(); + assertThat(StatutAide.EN_COURS_TRAITEMENT.peutTransitionnerVers(StatutAide.APPROUVEE)) + .isFalse(); + } + + @Test + @DisplayName("peutTransitionnerVers - EN_COURS_VERSEMENT peut aller vers VERSEE ou SUSPENDUE") + void testEnCoursVersement() { + assertThat(StatutAide.EN_COURS_VERSEMENT.peutTransitionnerVers(StatutAide.VERSEE)).isTrue(); + assertThat(StatutAide.EN_COURS_VERSEMENT.peutTransitionnerVers(StatutAide.SUSPENDUE)) + .isTrue(); + assertThat(StatutAide.EN_COURS_VERSEMENT.peutTransitionnerVers(StatutAide.TERMINEE)) + .isFalse(); + } + + @Test + @DisplayName("peutTransitionnerVers - SUSPENDUE peut aller vers EN_COURS_EVALUATION ou ANNULEE") + void testSuspendue() { + assertThat(StatutAide.SUSPENDUE.peutTransitionnerVers(StatutAide.EN_COURS_EVALUATION)) + .isTrue(); + assertThat(StatutAide.SUSPENDUE.peutTransitionnerVers(StatutAide.ANNULEE)).isTrue(); + assertThat(StatutAide.SUSPENDUE.peutTransitionnerVers(StatutAide.APPROUVEE)).isFalse(); + } + + @Test + @DisplayName("peutTransitionnerVers - Les statuts finaux ne peuvent pas transitionner (sauf APPROUVEE)") + void testStatutsFinaux() { + // Les statuts finaux (sauf APPROUVEE et APPROUVEE_PARTIELLEMENT) ne peuvent pas transitionner + // car le switch retourne false par défaut + assertThat(StatutAide.TERMINEE.peutTransitionnerVers(StatutAide.EN_SUIVI)).isFalse(); + assertThat(StatutAide.VERSEE.peutTransitionnerVers(StatutAide.EN_SUIVI)).isFalse(); + assertThat(StatutAide.TERMINEE.peutTransitionnerVers(StatutAide.APPROUVEE)).isFalse(); + assertThat(StatutAide.VERSEE.peutTransitionnerVers(StatutAide.APPROUVEE)).isFalse(); + assertThat(StatutAide.REJETEE.peutTransitionnerVers(StatutAide.EN_SUIVI)).isFalse(); + assertThat(StatutAide.ANNULEE.peutTransitionnerVers(StatutAide.EN_SUIVI)).isFalse(); + + // APPROUVEE et APPROUVEE_PARTIELLEMENT peuvent transitionner vers EN_COURS_TRAITEMENT ou SUSPENDUE + assertThat(StatutAide.APPROUVEE.peutTransitionnerVers(StatutAide.EN_COURS_TRAITEMENT)) + .isTrue(); + assertThat(StatutAide.APPROUVEE_PARTIELLEMENT.peutTransitionnerVers(StatutAide.EN_COURS_TRAITEMENT)) + .isTrue(); + assertThat(StatutAide.APPROUVEE.peutTransitionnerVers(StatutAide.SUSPENDUE)).isTrue(); + } + } + + @Nested + @DisplayName("Tests getNiveauPriorite") + class GetNiveauPrioriteTests { + + @Test + @DisplayName("getNiveauPriorite doit retourner le bon niveau") + void testGetNiveauPriorite() { + assertThat(StatutAide.INFORMATIONS_REQUISES.getNiveauPriorite()).isEqualTo(1); + assertThat(StatutAide.EN_COURS_EVALUATION.getNiveauPriorite()).isEqualTo(2); + assertThat(StatutAide.EN_COURS_TRAITEMENT.getNiveauPriorite()).isEqualTo(2); + assertThat(StatutAide.EN_COURS_VERSEMENT.getNiveauPriorite()).isEqualTo(2); + assertThat(StatutAide.APPROUVEE.getNiveauPriorite()).isEqualTo(3); + assertThat(StatutAide.APPROUVEE_PARTIELLEMENT.getNiveauPriorite()).isEqualTo(3); + assertThat(StatutAide.EN_ATTENTE.getNiveauPriorite()).isEqualTo(4); + assertThat(StatutAide.SOUMISE.getNiveauPriorite()).isEqualTo(4); + assertThat(StatutAide.SUSPENDUE.getNiveauPriorite()).isEqualTo(5); + assertThat(StatutAide.BROUILLON.getNiveauPriorite()).isEqualTo(6); + assertThat(StatutAide.EN_SUIVI.getNiveauPriorite()).isEqualTo(7); + assertThat(StatutAide.TERMINEE.getNiveauPriorite()).isEqualTo(8); + assertThat(StatutAide.VERSEE.getNiveauPriorite()).isEqualTo(8); + } + } + + @Nested + @DisplayName("Tests getters simples") + class GettersSimples { + + @Test + @DisplayName("getDescription doit retourner la description") + void testGetDescription() { + assertThat(StatutAide.BROUILLON.getDescription()) + .isEqualTo("La demande est en cours de rédaction"); + assertThat(StatutAide.APPROUVEE.getDescription()).isEqualTo("La demande a été approuvée"); + } + + @Test + @DisplayName("getCouleur doit retourner la couleur") + void testGetCouleur() { + assertThat(StatutAide.BROUILLON.getCouleur()).isEqualTo("#9E9E9E"); + assertThat(StatutAide.APPROUVEE.getCouleur()).isEqualTo("#4CAF50"); + } + + @Test + @DisplayName("getIcone doit retourner l'icône") + void testGetIcone() { + assertThat(StatutAide.BROUILLON.getIcone()).isEqualTo("edit"); + assertThat(StatutAide.APPROUVEE.getIcone()).isEqualTo("check_circle"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutEvaluationTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutEvaluationTest.java index c713849..0df778c 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutEvaluationTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutEvaluationTest.java @@ -1,76 +1,76 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutEvaluation") -class StatutEvaluationTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutEvaluation.ACTIVE).isNotNull(); - assertThat(StatutEvaluation.BROUILLON).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutEvaluation[] values = StatutEvaluation.values(); - assertThat(values).hasSize(5); - assertThat(values).containsExactly( - StatutEvaluation.BROUILLON, - StatutEvaluation.ACTIVE, - StatutEvaluation.MASQUEE, - StatutEvaluation.SIGNALEE, - StatutEvaluation.SUPPRIMEE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(StatutEvaluation.valueOf("BROUILLON")).isEqualTo(StatutEvaluation.BROUILLON); - assertThat(StatutEvaluation.valueOf("ACTIVE")).isEqualTo(StatutEvaluation.ACTIVE); - assertThat(StatutEvaluation.valueOf("MASQUEE")).isEqualTo(StatutEvaluation.MASQUEE); - assertThat(StatutEvaluation.valueOf("SIGNALEE")).isEqualTo(StatutEvaluation.SIGNALEE); - assertThat(StatutEvaluation.valueOf("SUPPRIMEE")).isEqualTo(StatutEvaluation.SUPPRIMEE); - - assertThatThrownBy(() -> StatutEvaluation.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutEvaluation.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutEvaluation statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(StatutEvaluation.BROUILLON.getLibelle()).isEqualTo("Brouillon"); - assertThat(StatutEvaluation.ACTIVE.getLibelle()).isEqualTo("Active"); - assertThat(StatutEvaluation.MASQUEE.getLibelle()).isEqualTo("Masquée"); - assertThat(StatutEvaluation.SIGNALEE.getLibelle()).isEqualTo("Signalée"); - assertThat(StatutEvaluation.SUPPRIMEE.getLibelle()).isEqualTo("Supprimée"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(StatutEvaluation.ACTIVE.name()).isEqualTo("ACTIVE"); - assertThat(StatutEvaluation.BROUILLON.name()).isEqualTo("BROUILLON"); - } - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutEvaluation") +class StatutEvaluationTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutEvaluation.ACTIVE).isNotNull(); + assertThat(StatutEvaluation.BROUILLON).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutEvaluation[] values = StatutEvaluation.values(); + assertThat(values).hasSize(5); + assertThat(values).containsExactly( + StatutEvaluation.BROUILLON, + StatutEvaluation.ACTIVE, + StatutEvaluation.MASQUEE, + StatutEvaluation.SIGNALEE, + StatutEvaluation.SUPPRIMEE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(StatutEvaluation.valueOf("BROUILLON")).isEqualTo(StatutEvaluation.BROUILLON); + assertThat(StatutEvaluation.valueOf("ACTIVE")).isEqualTo(StatutEvaluation.ACTIVE); + assertThat(StatutEvaluation.valueOf("MASQUEE")).isEqualTo(StatutEvaluation.MASQUEE); + assertThat(StatutEvaluation.valueOf("SIGNALEE")).isEqualTo(StatutEvaluation.SIGNALEE); + assertThat(StatutEvaluation.valueOf("SUPPRIMEE")).isEqualTo(StatutEvaluation.SUPPRIMEE); + + assertThatThrownBy(() -> StatutEvaluation.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutEvaluation.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutEvaluation statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(StatutEvaluation.BROUILLON.getLibelle()).isEqualTo("Brouillon"); + assertThat(StatutEvaluation.ACTIVE.getLibelle()).isEqualTo("Active"); + assertThat(StatutEvaluation.MASQUEE.getLibelle()).isEqualTo("Masquée"); + assertThat(StatutEvaluation.SIGNALEE.getLibelle()).isEqualTo("Signalée"); + assertThat(StatutEvaluation.SUPPRIMEE.getLibelle()).isEqualTo("Supprimée"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(StatutEvaluation.ACTIVE.name()).isEqualTo("ACTIVE"); + assertThat(StatutEvaluation.BROUILLON.name()).isEqualTo("BROUILLON"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutPropositionTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutPropositionTest.java index 94d9cce..acf35dd 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutPropositionTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutPropositionTest.java @@ -1,77 +1,77 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutProposition") -class StatutPropositionTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutProposition.ACTIVE).isNotNull(); - assertThat(StatutProposition.BROUILLON).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutProposition[] values = StatutProposition.values(); - assertThat(values).hasSize(6); - assertThat(values).containsExactly( - StatutProposition.BROUILLON, - StatutProposition.ACTIVE, - StatutProposition.SUSPENDUE, - StatutProposition.EXPIREE, - StatutProposition.TERMINEE, - StatutProposition.ANNULEE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(StatutProposition.valueOf("BROUILLON")).isEqualTo(StatutProposition.BROUILLON); - assertThat(StatutProposition.valueOf("ACTIVE")).isEqualTo(StatutProposition.ACTIVE); - assertThat(StatutProposition.valueOf("SUSPENDUE")).isEqualTo(StatutProposition.SUSPENDUE); - assertThat(StatutProposition.valueOf("EXPIREE")).isEqualTo(StatutProposition.EXPIREE); - assertThat(StatutProposition.valueOf("TERMINEE")).isEqualTo(StatutProposition.TERMINEE); - assertThat(StatutProposition.valueOf("ANNULEE")).isEqualTo(StatutProposition.ANNULEE); - - assertThatThrownBy(() -> StatutProposition.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutProposition.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutProposition statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(StatutProposition.BROUILLON.getLibelle()).isEqualTo("Brouillon"); - assertThat(StatutProposition.ACTIVE.getLibelle()).isEqualTo("Active"); - assertThat(StatutProposition.TERMINEE.getLibelle()).isEqualTo("Terminée"); - assertThat(StatutProposition.ANNULEE.getLibelle()).isEqualTo("Annulée"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(StatutProposition.ACTIVE.name()).isEqualTo("ACTIVE"); - assertThat(StatutProposition.EXPIREE.name()).isEqualTo("EXPIREE"); - } - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutProposition") +class StatutPropositionTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutProposition.ACTIVE).isNotNull(); + assertThat(StatutProposition.BROUILLON).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutProposition[] values = StatutProposition.values(); + assertThat(values).hasSize(6); + assertThat(values).containsExactly( + StatutProposition.BROUILLON, + StatutProposition.ACTIVE, + StatutProposition.SUSPENDUE, + StatutProposition.EXPIREE, + StatutProposition.TERMINEE, + StatutProposition.ANNULEE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(StatutProposition.valueOf("BROUILLON")).isEqualTo(StatutProposition.BROUILLON); + assertThat(StatutProposition.valueOf("ACTIVE")).isEqualTo(StatutProposition.ACTIVE); + assertThat(StatutProposition.valueOf("SUSPENDUE")).isEqualTo(StatutProposition.SUSPENDUE); + assertThat(StatutProposition.valueOf("EXPIREE")).isEqualTo(StatutProposition.EXPIREE); + assertThat(StatutProposition.valueOf("TERMINEE")).isEqualTo(StatutProposition.TERMINEE); + assertThat(StatutProposition.valueOf("ANNULEE")).isEqualTo(StatutProposition.ANNULEE); + + assertThatThrownBy(() -> StatutProposition.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutProposition.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutProposition statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(StatutProposition.BROUILLON.getLibelle()).isEqualTo("Brouillon"); + assertThat(StatutProposition.ACTIVE.getLibelle()).isEqualTo("Active"); + assertThat(StatutProposition.TERMINEE.getLibelle()).isEqualTo("Terminée"); + assertThat(StatutProposition.ANNULEE.getLibelle()).isEqualTo("Annulée"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(StatutProposition.ACTIVE.name()).isEqualTo("ACTIVE"); + assertThat(StatutProposition.EXPIREE.name()).isEqualTo("EXPIREE"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutValidationEtapeTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutValidationEtapeTest.java index 807cedd..00e16b1 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutValidationEtapeTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/StatutValidationEtapeTest.java @@ -1,76 +1,76 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutValidationEtape") -class StatutValidationEtapeTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutValidationEtape.EN_ATTENTE).isNotNull(); - assertThat(StatutValidationEtape.APPROUVEE).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutValidationEtape[] values = StatutValidationEtape.values(); - assertThat(values).hasSize(5); - assertThat(values).containsExactly( - StatutValidationEtape.EN_ATTENTE, - StatutValidationEtape.APPROUVEE, - StatutValidationEtape.REJETEE, - StatutValidationEtape.DELEGUEE, - StatutValidationEtape.EXPIREE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(StatutValidationEtape.valueOf("EN_ATTENTE")).isEqualTo(StatutValidationEtape.EN_ATTENTE); - assertThat(StatutValidationEtape.valueOf("APPROUVEE")).isEqualTo(StatutValidationEtape.APPROUVEE); - assertThat(StatutValidationEtape.valueOf("REJETEE")).isEqualTo(StatutValidationEtape.REJETEE); - assertThat(StatutValidationEtape.valueOf("DELEGUEE")).isEqualTo(StatutValidationEtape.DELEGUEE); - assertThat(StatutValidationEtape.valueOf("EXPIREE")).isEqualTo(StatutValidationEtape.EXPIREE); - - assertThatThrownBy(() -> StatutValidationEtape.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutValidationEtape.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutValidationEtape statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(StatutValidationEtape.EN_ATTENTE.getLibelle()).isEqualTo("En attente du valideur"); - assertThat(StatutValidationEtape.APPROUVEE.getLibelle()).isEqualTo("Approuvée"); - assertThat(StatutValidationEtape.REJETEE.getLibelle()).isEqualTo("Rejetée"); - assertThat(StatutValidationEtape.DELEGUEE.getLibelle()).contains("Déléguée"); - assertThat(StatutValidationEtape.EXPIREE.getLibelle()).contains("Expirée"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(StatutValidationEtape.EN_ATTENTE.name()).isEqualTo("EN_ATTENTE"); - assertThat(StatutValidationEtape.APPROUVEE.name()).isEqualTo("APPROUVEE"); - } - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutValidationEtape") +class StatutValidationEtapeTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutValidationEtape.EN_ATTENTE).isNotNull(); + assertThat(StatutValidationEtape.APPROUVEE).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutValidationEtape[] values = StatutValidationEtape.values(); + assertThat(values).hasSize(5); + assertThat(values).containsExactly( + StatutValidationEtape.EN_ATTENTE, + StatutValidationEtape.APPROUVEE, + StatutValidationEtape.REJETEE, + StatutValidationEtape.DELEGUEE, + StatutValidationEtape.EXPIREE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(StatutValidationEtape.valueOf("EN_ATTENTE")).isEqualTo(StatutValidationEtape.EN_ATTENTE); + assertThat(StatutValidationEtape.valueOf("APPROUVEE")).isEqualTo(StatutValidationEtape.APPROUVEE); + assertThat(StatutValidationEtape.valueOf("REJETEE")).isEqualTo(StatutValidationEtape.REJETEE); + assertThat(StatutValidationEtape.valueOf("DELEGUEE")).isEqualTo(StatutValidationEtape.DELEGUEE); + assertThat(StatutValidationEtape.valueOf("EXPIREE")).isEqualTo(StatutValidationEtape.EXPIREE); + + assertThatThrownBy(() -> StatutValidationEtape.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutValidationEtape.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutValidationEtape statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(StatutValidationEtape.EN_ATTENTE.getLibelle()).isEqualTo("En attente du valideur"); + assertThat(StatutValidationEtape.APPROUVEE.getLibelle()).isEqualTo("Approuvée"); + assertThat(StatutValidationEtape.REJETEE.getLibelle()).isEqualTo("Rejetée"); + assertThat(StatutValidationEtape.DELEGUEE.getLibelle()).contains("Déléguée"); + assertThat(StatutValidationEtape.EXPIREE.getLibelle()).contains("Expirée"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(StatutValidationEtape.EN_ATTENTE.name()).isEqualTo("EN_ATTENTE"); + assertThat(StatutValidationEtape.APPROUVEE.name()).isEqualTo("APPROUVEE"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/TypeAideTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/TypeAideTest.java index b1238c8..269e442 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/TypeAideTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/TypeAideTest.java @@ -1,470 +1,470 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.util.List; -import java.util.Set; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour TypeAide. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests TypeAide") -class TypeAideTest { - - @Test - @DisplayName("Tous les types d'aide doivent avoir un libellé") - void testTousLesTypesOntLibelle() { - for (TypeAide type : TypeAide.values()) { - assertThat(type.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("Tous les types d'aide doivent avoir une catégorie") - void testTousLesTypesOntCategorie() { - for (TypeAide type : TypeAide.values()) { - assertThat(type.getCategorie()).isNotNull().isNotBlank(); - } - } - - @Nested - @DisplayName("Tests isUrgent") - class IsUrgentTests { - - @Test - @DisplayName("isUrgent doit retourner true pour les types avec priorite urgent") - void testIsUrgent() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isUrgent()).isTrue(); - assertThat(TypeAide.AIDE_FRAIS_MEDICAUX.isUrgent()).isTrue(); - assertThat(TypeAide.HEBERGEMENT_URGENCE.isUrgent()).isTrue(); - assertThat(TypeAide.AIDE_ALIMENTAIRE.isUrgent()).isTrue(); - - assertThat(TypeAide.DON_MATERIEL.isUrgent()).isFalse(); - assertThat(TypeAide.TRANSPORT.isUrgent()).isFalse(); - assertThat(TypeAide.AIDE_COTISATION.isUrgent()).isFalse(); - } - } - - @Nested - @DisplayName("Tests isFinancier") - class IsFinancierTests { - - @Test - @DisplayName("isFinancier doit retourner true pour les types financiers") - void testIsFinancier() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isFinancier()).isTrue(); - assertThat(TypeAide.PRET_SANS_INTERET.isFinancier()).isTrue(); - assertThat(TypeAide.AIDE_COTISATION.isFinancier()).isTrue(); - assertThat(TypeAide.AIDE_FRAIS_MEDICAUX.isFinancier()).isTrue(); - assertThat(TypeAide.AIDE_FRAIS_SCOLARITE.isFinancier()).isTrue(); - - assertThat(TypeAide.DON_MATERIEL.isFinancier()).isFalse(); - assertThat(TypeAide.TRANSPORT.isFinancier()).isFalse(); - } - } - - @Nested - @DisplayName("Tests isMateriel") - class IsMaterielTests { - - @Test - @DisplayName("isMateriel doit retourner true pour les types matériels") - void testIsMateriel() { - assertThat(TypeAide.DON_MATERIEL.isMateriel()).isTrue(); - assertThat(TypeAide.PRET_MATERIEL.isMateriel()).isTrue(); - assertThat(TypeAide.AIDE_DEMENAGEMENT.isMateriel()).isTrue(); - assertThat(TypeAide.AIDE_TRAVAUX.isMateriel()).isTrue(); - - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMateriel()).isFalse(); - assertThat(TypeAide.TRANSPORT.isMateriel()).isFalse(); - } - } - - @Nested - @DisplayName("Tests isMontantValide") - class IsMontantValideTests { - - @Test - @DisplayName("isMontantValide doit retourner true si necessiteMontant est false") - void testIsMontantValideNonNecessaire() { - assertThat(TypeAide.DON_MATERIEL.isMontantValide(null)).isTrue(); - assertThat(TypeAide.DON_MATERIEL.isMontantValide(1000.0)).isTrue(); - } - - @Test - @DisplayName("isMontantValide doit retourner true si montant est null et necessiteMontant est true") - void testIsMontantValideNull() { - // Si necessiteMontant est true mais montant est null, retourne true - // (la validation du null se fait ailleurs) - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(null)).isTrue(); - } - - @Test - @DisplayName("isMontantValide doit valider la fourchette") - void testIsMontantValideFourchette() { - // AIDE_FINANCIERE_URGENTE: montantMin=5000, montantMax=50000 - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(10000.0)).isTrue(); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(5000.0)).isTrue(); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(50000.0)).isTrue(); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(4000.0)).isFalse(); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(51000.0)).isFalse(); - } - - @Test - @DisplayName("isMontantValide doit gérer montantMin null") - void testIsMontantValideMontantMinNull() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(1000.0)).isFalse(); - } - - @Test - @DisplayName("isMontantValide skip montantMin quand null (reflection)") - void testIsMontantValideMontantMinNullSkip() throws Exception { - java.lang.reflect.Field minF = TypeAide.class.getDeclaredField("montantMin"); - minF.setAccessible(true); - Object backup = minF.get(TypeAide.AIDE_FINANCIERE_URGENTE); - try { - minF.set(TypeAide.AIDE_FINANCIERE_URGENTE, null); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(60000.0)).isFalse(); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(25000.0)).isTrue(); - } finally { - minF.set(TypeAide.AIDE_FINANCIERE_URGENTE, backup); - } - } - - @Test - @DisplayName("isMontantValide skip montantMax quand null (reflection)") - void testIsMontantValideMontantMaxNullSkip() throws Exception { - java.lang.reflect.Field maxF = TypeAide.class.getDeclaredField("montantMax"); - maxF.setAccessible(true); - Object backup = maxF.get(TypeAide.AIDE_FINANCIERE_URGENTE); - try { - maxF.set(TypeAide.AIDE_FINANCIERE_URGENTE, null); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(10000.0)).isTrue(); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(4000.0)).isFalse(); - } finally { - maxF.set(TypeAide.AIDE_FINANCIERE_URGENTE, backup); - } - } - } - - @Nested - @DisplayName("Tests getNiveauPriorite") - class GetNiveauPrioriteTests { - - @Test - @DisplayName("getNiveauPriorite doit retourner le bon niveau") - void testGetNiveauPriorite() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getNiveauPriorite()).isEqualTo(1); - assertThat(TypeAide.PRET_SANS_INTERET.getNiveauPriorite()).isEqualTo(2); - assertThat(TypeAide.AIDE_COTISATION.getNiveauPriorite()).isEqualTo(3); - assertThat(TypeAide.DON_MATERIEL.getNiveauPriorite()).isEqualTo(3); - } - } - - @Nested - @DisplayName("Tests getDateLimiteReponse") - class GetDateLimiteReponseTests { - - @Test - @DisplayName("getDateLimiteReponse doit retourner une date future") - void testGetDateLimiteReponse() { - var maintenant = java.time.LocalDateTime.now(); - var dateLimite = TypeAide.AIDE_FINANCIERE_URGENTE.getDateLimiteReponse(); - - assertThat(dateLimite).isAfter(maintenant); - assertThat(dateLimite).isBefore(maintenant.plusDays(8)); // 7 jours - } - } - - @Nested - @DisplayName("Tests getParCategorie") - class GetParCategorieTests { - - @Test - @DisplayName("getParCategorie doit retourner les types de la catégorie") - void testGetParCategorie() { - List financiers = TypeAide.getParCategorie("financiere"); - assertThat(financiers).isNotEmpty(); - assertThat(financiers).contains(TypeAide.AIDE_FINANCIERE_URGENTE); - assertThat(financiers).contains(TypeAide.PRET_SANS_INTERET); - assertThat(financiers).doesNotContain(TypeAide.DON_MATERIEL); - - List materiels = TypeAide.getParCategorie("materielle"); - assertThat(materiels).isNotEmpty(); - assertThat(materiels).contains(TypeAide.DON_MATERIEL); - assertThat(materiels).doesNotContain(TypeAide.AIDE_FINANCIERE_URGENTE); - } - } - - @Nested - @DisplayName("Tests getUrgents") - class GetUrgentsTests { - - @Test - @DisplayName("getUrgents doit retourner tous les types urgents") - void testGetUrgents() { - List urgents = TypeAide.getUrgents(); - - assertThat(urgents).isNotEmpty(); - assertThat(urgents).contains(TypeAide.AIDE_FINANCIERE_URGENTE); - assertThat(urgents).contains(TypeAide.AIDE_FRAIS_MEDICAUX); - assertThat(urgents).contains(TypeAide.HEBERGEMENT_URGENCE); - assertThat(urgents).contains(TypeAide.AIDE_ALIMENTAIRE); - assertThat(urgents).doesNotContain(TypeAide.DON_MATERIEL); - } - } - - @Nested - @DisplayName("Tests getFinanciers") - class GetFinanciersTests { - - @Test - @DisplayName("getFinanciers doit retourner tous les types financiers") - void testGetFinanciers() { - List financiers = TypeAide.getFinanciers(); - - assertThat(financiers).isNotEmpty(); - assertThat(financiers).contains(TypeAide.AIDE_FINANCIERE_URGENTE); - assertThat(financiers).contains(TypeAide.PRET_SANS_INTERET); - assertThat(financiers).contains(TypeAide.AIDE_COTISATION); - assertThat(financiers).contains(TypeAide.AIDE_FRAIS_MEDICAUX); - assertThat(financiers).contains(TypeAide.AIDE_FRAIS_SCOLARITE); - assertThat(financiers).doesNotContain(TypeAide.DON_MATERIEL); - } - } - - @Nested - @DisplayName("Tests getCategories") - class GetCategoriesTests { - - @Test - @DisplayName("getCategories doit retourner toutes les catégories uniques") - void testGetCategories() { - Set categories = TypeAide.getCategories(); - - assertThat(categories).isNotEmpty(); - assertThat(categories).contains("financiere"); - assertThat(categories).contains("materielle"); - assertThat(categories).contains("professionnelle"); - assertThat(categories).contains("sociale"); - assertThat(categories).contains("urgence"); - assertThat(categories).contains("specialisee"); - assertThat(categories).contains("autre"); - } - } - - @Nested - @DisplayName("Tests getLibelleCategorie") - class GetLibelleCategorieTests { - - @Test - @DisplayName("getLibelleCategorie doit retourner le bon libellé") - void testGetLibelleCategorie() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getLibelleCategorie()) - .isEqualTo("Aide financière"); - assertThat(TypeAide.DON_MATERIEL.getLibelleCategorie()).isEqualTo("Aide matérielle"); - assertThat(TypeAide.AIDE_RECHERCHE_EMPLOI.getLibelleCategorie()) - .isEqualTo("Aide professionnelle"); - assertThat(TypeAide.GARDE_ENFANTS.getLibelleCategorie()).isEqualTo("Aide sociale"); - assertThat(TypeAide.HEBERGEMENT_URGENCE.getLibelleCategorie()).isEqualTo("Aide d'urgence"); - assertThat(TypeAide.SOUTIEN_PSYCHOLOGIQUE.getLibelleCategorie()) - .isEqualTo("Aide spécialisée"); - assertThat(TypeAide.AUTRE.getLibelleCategorie()).isEqualTo("Autre"); - } - - @Test - @DisplayName("getLibelleCategorie retourne default (catégorie brute) pour catégorie inconnue") - void testGetLibelleCategorieInconnue() throws Exception { - java.lang.reflect.Field f = TypeAide.class.getDeclaredField("categorie"); - f.setAccessible(true); - String backup = TypeAide.AUTRE.getCategorie(); - try { - f.set(TypeAide.AUTRE, "inconnue"); - assertThat(TypeAide.AUTRE.getLibelleCategorie()).isEqualTo("inconnue"); - } finally { - f.set(TypeAide.AUTRE, backup); - } - } - } - - @Nested - @DisplayName("getNiveauPriorite default") - class GetNiveauPrioriteDefault { - - @Test - @DisplayName("getNiveauPriorite retourne 3 (default) pour priorite inconnue") - void testDefault() throws Exception { - java.lang.reflect.Field f = TypeAide.class.getDeclaredField("priorite"); - f.setAccessible(true); - String backup = TypeAide.AUTRE.getPriorite(); - try { - f.set(TypeAide.AUTRE, "inconnu"); - assertThat(TypeAide.AUTRE.getNiveauPriorite()).isEqualTo(3); - } finally { - f.set(TypeAide.AUTRE, backup); - } - } - } - - @Nested - @DisplayName("Tests getUniteMontant") - class GetUniteMontantTests { - - @Test - @DisplayName("getUniteMontant doit retourner FCFA si necessiteMontant est true") - void testGetUniteMontant() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getUniteMontant()).isEqualTo("FCFA"); - assertThat(TypeAide.PRET_SANS_INTERET.getUniteMontant()).isEqualTo("FCFA"); - assertThat(TypeAide.DON_MATERIEL.getUniteMontant()).isNull(); - assertThat(TypeAide.TRANSPORT.getUniteMontant()).isNull(); - } - } - - @Nested - @DisplayName("Tests getters simples") - class GettersSimples { - - @Test - @DisplayName("getDescription doit retourner la description") - void testGetDescription() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getDescription()) - .isEqualTo("Aide financière pour situation d'urgence"); - assertThat(TypeAide.DON_MATERIEL.getDescription()) - .isEqualTo("Don d'objets, équipements ou matériel"); - } - - @Test - @DisplayName("getIcone doit retourner l'icône") - void testGetIcone() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getIcone()).isEqualTo("emergency_fund"); - assertThat(TypeAide.DON_MATERIEL.getIcone()).isEqualTo("inventory"); - } - - @Test - @DisplayName("getCouleur doit retourner la couleur") - void testGetCouleur() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getCouleur()).isEqualTo("#F44336"); - assertThat(TypeAide.DON_MATERIEL.getCouleur()).isEqualTo("#4CAF50"); - } - - @Test - @DisplayName("isNecessiteMontant doit retourner la valeur du champ") - void testIsNecessiteMontant() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isNecessiteMontant()).isTrue(); - assertThat(TypeAide.DON_MATERIEL.isNecessiteMontant()).isFalse(); - } - - @Test - @DisplayName("isNecessiteValidation doit retourner la valeur du champ") - void testIsNecessiteValidation() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isNecessiteValidation()).isTrue(); - assertThat(TypeAide.DON_MATERIEL.isNecessiteValidation()).isFalse(); - } - - @Test - @DisplayName("getMontantMin doit retourner le montant minimum") - void testGetMontantMin() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMontantMin()).isEqualTo(5000.0); - assertThat(TypeAide.PRET_SANS_INTERET.getMontantMin()).isEqualTo(10000.0); - } - - @Test - @DisplayName("getMontantMax doit retourner le montant maximum") - void testGetMontantMax() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMontantMax()).isEqualTo(50000.0); - assertThat(TypeAide.PRET_SANS_INTERET.getMontantMax()).isEqualTo(100000.0); - } - - @Test - @DisplayName("getDelaiReponseJours doit retourner le délai de réponse") - void testGetDelaiReponseJours() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getDelaiReponseJours()).isEqualTo(7); - assertThat(TypeAide.PRET_SANS_INTERET.getDelaiReponseJours()).isEqualTo(30); - } - } - - @Nested - @DisplayName("Tests getMessageValidationMontant") - class GetMessageValidationMontantTests { - - @Test - @DisplayName("getMessageValidationMontant doit retourner null si necessiteMontant est false") - void testGetMessageValidationMontantNonNecessaire() { - assertThat(TypeAide.DON_MATERIEL.getMessageValidationMontant(null)).isNull(); - assertThat(TypeAide.DON_MATERIEL.getMessageValidationMontant(1000.0)).isNull(); - } - - @Test - @DisplayName("getMessageValidationMontant doit retourner message si montant est null") - void testGetMessageValidationMontantNull() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(null)) - .isEqualTo("Le montant est obligatoire"); - } - - @Test - @DisplayName("getMessageValidationMontant doit retourner message si montant < montantMin") - void testGetMessageValidationMontantTropBas() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(4000.0)) - .contains("minimum"); - } - - @Test - @DisplayName("getMessageValidationMontant doit retourner message si montant > montantMax") - void testGetMessageValidationMontantTropHaut() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(51000.0)) - .contains("maximum"); - } - - @Test - @DisplayName("getMessageValidationMontant doit retourner null si montant est valide") - void testGetMessageValidationMontantValide() { - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(10000.0)) - .isNull(); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(5000.0)) - .isNull(); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(50000.0)) - .isNull(); - } - - @Test - @DisplayName("getMessageValidationMontant skip montantMin quand null (reflection)") - void testGetMessageValidationMontantMontantMinNull() throws Exception { - java.lang.reflect.Field minF = TypeAide.class.getDeclaredField("montantMin"); - minF.setAccessible(true); - Object backup = minF.get(TypeAide.AIDE_FINANCIERE_URGENTE); - try { - minF.set(TypeAide.AIDE_FINANCIERE_URGENTE, null); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(60000.0)) - .contains("maximum"); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(25000.0)) - .isNull(); - } finally { - minF.set(TypeAide.AIDE_FINANCIERE_URGENTE, backup); - } - } - - @Test - @DisplayName("getMessageValidationMontant skip montantMax quand null (reflection)") - void testGetMessageValidationMontantMontantMaxNull() throws Exception { - java.lang.reflect.Field maxF = TypeAide.class.getDeclaredField("montantMax"); - maxF.setAccessible(true); - Object backup = maxF.get(TypeAide.AIDE_FINANCIERE_URGENTE); - try { - maxF.set(TypeAide.AIDE_FINANCIERE_URGENTE, null); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(4000.0)) - .contains("minimum"); - assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(10000.0)) - .isNull(); - } finally { - maxF.set(TypeAide.AIDE_FINANCIERE_URGENTE, backup); - } - } - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.List; +import java.util.Set; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour TypeAide. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests TypeAide") +class TypeAideTest { + + @Test + @DisplayName("Tous les types d'aide doivent avoir un libellé") + void testTousLesTypesOntLibelle() { + for (TypeAide type : TypeAide.values()) { + assertThat(type.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("Tous les types d'aide doivent avoir une catégorie") + void testTousLesTypesOntCategorie() { + for (TypeAide type : TypeAide.values()) { + assertThat(type.getCategorie()).isNotNull().isNotBlank(); + } + } + + @Nested + @DisplayName("Tests isUrgent") + class IsUrgentTests { + + @Test + @DisplayName("isUrgent doit retourner true pour les types avec priorite urgent") + void testIsUrgent() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isUrgent()).isTrue(); + assertThat(TypeAide.AIDE_FRAIS_MEDICAUX.isUrgent()).isTrue(); + assertThat(TypeAide.HEBERGEMENT_URGENCE.isUrgent()).isTrue(); + assertThat(TypeAide.AIDE_ALIMENTAIRE.isUrgent()).isTrue(); + + assertThat(TypeAide.DON_MATERIEL.isUrgent()).isFalse(); + assertThat(TypeAide.TRANSPORT.isUrgent()).isFalse(); + assertThat(TypeAide.AIDE_COTISATION.isUrgent()).isFalse(); + } + } + + @Nested + @DisplayName("Tests isFinancier") + class IsFinancierTests { + + @Test + @DisplayName("isFinancier doit retourner true pour les types financiers") + void testIsFinancier() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isFinancier()).isTrue(); + assertThat(TypeAide.PRET_SANS_INTERET.isFinancier()).isTrue(); + assertThat(TypeAide.AIDE_COTISATION.isFinancier()).isTrue(); + assertThat(TypeAide.AIDE_FRAIS_MEDICAUX.isFinancier()).isTrue(); + assertThat(TypeAide.AIDE_FRAIS_SCOLARITE.isFinancier()).isTrue(); + + assertThat(TypeAide.DON_MATERIEL.isFinancier()).isFalse(); + assertThat(TypeAide.TRANSPORT.isFinancier()).isFalse(); + } + } + + @Nested + @DisplayName("Tests isMateriel") + class IsMaterielTests { + + @Test + @DisplayName("isMateriel doit retourner true pour les types matériels") + void testIsMateriel() { + assertThat(TypeAide.DON_MATERIEL.isMateriel()).isTrue(); + assertThat(TypeAide.PRET_MATERIEL.isMateriel()).isTrue(); + assertThat(TypeAide.AIDE_DEMENAGEMENT.isMateriel()).isTrue(); + assertThat(TypeAide.AIDE_TRAVAUX.isMateriel()).isTrue(); + + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMateriel()).isFalse(); + assertThat(TypeAide.TRANSPORT.isMateriel()).isFalse(); + } + } + + @Nested + @DisplayName("Tests isMontantValide") + class IsMontantValideTests { + + @Test + @DisplayName("isMontantValide doit retourner true si necessiteMontant est false") + void testIsMontantValideNonNecessaire() { + assertThat(TypeAide.DON_MATERIEL.isMontantValide(null)).isTrue(); + assertThat(TypeAide.DON_MATERIEL.isMontantValide(1000.0)).isTrue(); + } + + @Test + @DisplayName("isMontantValide doit retourner true si montant est null et necessiteMontant est true") + void testIsMontantValideNull() { + // Si necessiteMontant est true mais montant est null, retourne true + // (la validation du null se fait ailleurs) + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(null)).isTrue(); + } + + @Test + @DisplayName("isMontantValide doit valider la fourchette") + void testIsMontantValideFourchette() { + // AIDE_FINANCIERE_URGENTE: montantMin=5000, montantMax=50000 + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(10000.0)).isTrue(); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(5000.0)).isTrue(); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(50000.0)).isTrue(); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(4000.0)).isFalse(); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(51000.0)).isFalse(); + } + + @Test + @DisplayName("isMontantValide doit gérer montantMin null") + void testIsMontantValideMontantMinNull() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(1000.0)).isFalse(); + } + + @Test + @DisplayName("isMontantValide skip montantMin quand null (reflection)") + void testIsMontantValideMontantMinNullSkip() throws Exception { + java.lang.reflect.Field minF = TypeAide.class.getDeclaredField("montantMin"); + minF.setAccessible(true); + Object backup = minF.get(TypeAide.AIDE_FINANCIERE_URGENTE); + try { + minF.set(TypeAide.AIDE_FINANCIERE_URGENTE, null); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(60000.0)).isFalse(); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(25000.0)).isTrue(); + } finally { + minF.set(TypeAide.AIDE_FINANCIERE_URGENTE, backup); + } + } + + @Test + @DisplayName("isMontantValide skip montantMax quand null (reflection)") + void testIsMontantValideMontantMaxNullSkip() throws Exception { + java.lang.reflect.Field maxF = TypeAide.class.getDeclaredField("montantMax"); + maxF.setAccessible(true); + Object backup = maxF.get(TypeAide.AIDE_FINANCIERE_URGENTE); + try { + maxF.set(TypeAide.AIDE_FINANCIERE_URGENTE, null); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(10000.0)).isTrue(); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isMontantValide(4000.0)).isFalse(); + } finally { + maxF.set(TypeAide.AIDE_FINANCIERE_URGENTE, backup); + } + } + } + + @Nested + @DisplayName("Tests getNiveauPriorite") + class GetNiveauPrioriteTests { + + @Test + @DisplayName("getNiveauPriorite doit retourner le bon niveau") + void testGetNiveauPriorite() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getNiveauPriorite()).isEqualTo(1); + assertThat(TypeAide.PRET_SANS_INTERET.getNiveauPriorite()).isEqualTo(2); + assertThat(TypeAide.AIDE_COTISATION.getNiveauPriorite()).isEqualTo(3); + assertThat(TypeAide.DON_MATERIEL.getNiveauPriorite()).isEqualTo(3); + } + } + + @Nested + @DisplayName("Tests getDateLimiteReponse") + class GetDateLimiteReponseTests { + + @Test + @DisplayName("getDateLimiteReponse doit retourner une date future") + void testGetDateLimiteReponse() { + var maintenant = java.time.LocalDateTime.now(); + var dateLimite = TypeAide.AIDE_FINANCIERE_URGENTE.getDateLimiteReponse(); + + assertThat(dateLimite).isAfter(maintenant); + assertThat(dateLimite).isBefore(maintenant.plusDays(8)); // 7 jours + } + } + + @Nested + @DisplayName("Tests getParCategorie") + class GetParCategorieTests { + + @Test + @DisplayName("getParCategorie doit retourner les types de la catégorie") + void testGetParCategorie() { + List financiers = TypeAide.getParCategorie("financiere"); + assertThat(financiers).isNotEmpty(); + assertThat(financiers).contains(TypeAide.AIDE_FINANCIERE_URGENTE); + assertThat(financiers).contains(TypeAide.PRET_SANS_INTERET); + assertThat(financiers).doesNotContain(TypeAide.DON_MATERIEL); + + List materiels = TypeAide.getParCategorie("materielle"); + assertThat(materiels).isNotEmpty(); + assertThat(materiels).contains(TypeAide.DON_MATERIEL); + assertThat(materiels).doesNotContain(TypeAide.AIDE_FINANCIERE_URGENTE); + } + } + + @Nested + @DisplayName("Tests getUrgents") + class GetUrgentsTests { + + @Test + @DisplayName("getUrgents doit retourner tous les types urgents") + void testGetUrgents() { + List urgents = TypeAide.getUrgents(); + + assertThat(urgents).isNotEmpty(); + assertThat(urgents).contains(TypeAide.AIDE_FINANCIERE_URGENTE); + assertThat(urgents).contains(TypeAide.AIDE_FRAIS_MEDICAUX); + assertThat(urgents).contains(TypeAide.HEBERGEMENT_URGENCE); + assertThat(urgents).contains(TypeAide.AIDE_ALIMENTAIRE); + assertThat(urgents).doesNotContain(TypeAide.DON_MATERIEL); + } + } + + @Nested + @DisplayName("Tests getFinanciers") + class GetFinanciersTests { + + @Test + @DisplayName("getFinanciers doit retourner tous les types financiers") + void testGetFinanciers() { + List financiers = TypeAide.getFinanciers(); + + assertThat(financiers).isNotEmpty(); + assertThat(financiers).contains(TypeAide.AIDE_FINANCIERE_URGENTE); + assertThat(financiers).contains(TypeAide.PRET_SANS_INTERET); + assertThat(financiers).contains(TypeAide.AIDE_COTISATION); + assertThat(financiers).contains(TypeAide.AIDE_FRAIS_MEDICAUX); + assertThat(financiers).contains(TypeAide.AIDE_FRAIS_SCOLARITE); + assertThat(financiers).doesNotContain(TypeAide.DON_MATERIEL); + } + } + + @Nested + @DisplayName("Tests getCategories") + class GetCategoriesTests { + + @Test + @DisplayName("getCategories doit retourner toutes les catégories uniques") + void testGetCategories() { + Set categories = TypeAide.getCategories(); + + assertThat(categories).isNotEmpty(); + assertThat(categories).contains("financiere"); + assertThat(categories).contains("materielle"); + assertThat(categories).contains("professionnelle"); + assertThat(categories).contains("sociale"); + assertThat(categories).contains("urgence"); + assertThat(categories).contains("specialisee"); + assertThat(categories).contains("autre"); + } + } + + @Nested + @DisplayName("Tests getLibelleCategorie") + class GetLibelleCategorieTests { + + @Test + @DisplayName("getLibelleCategorie doit retourner le bon libellé") + void testGetLibelleCategorie() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getLibelleCategorie()) + .isEqualTo("Aide financière"); + assertThat(TypeAide.DON_MATERIEL.getLibelleCategorie()).isEqualTo("Aide matérielle"); + assertThat(TypeAide.AIDE_RECHERCHE_EMPLOI.getLibelleCategorie()) + .isEqualTo("Aide professionnelle"); + assertThat(TypeAide.GARDE_ENFANTS.getLibelleCategorie()).isEqualTo("Aide sociale"); + assertThat(TypeAide.HEBERGEMENT_URGENCE.getLibelleCategorie()).isEqualTo("Aide d'urgence"); + assertThat(TypeAide.SOUTIEN_PSYCHOLOGIQUE.getLibelleCategorie()) + .isEqualTo("Aide spécialisée"); + assertThat(TypeAide.AUTRE.getLibelleCategorie()).isEqualTo("Autre"); + } + + @Test + @DisplayName("getLibelleCategorie retourne default (catégorie brute) pour catégorie inconnue") + void testGetLibelleCategorieInconnue() throws Exception { + java.lang.reflect.Field f = TypeAide.class.getDeclaredField("categorie"); + f.setAccessible(true); + String backup = TypeAide.AUTRE.getCategorie(); + try { + f.set(TypeAide.AUTRE, "inconnue"); + assertThat(TypeAide.AUTRE.getLibelleCategorie()).isEqualTo("inconnue"); + } finally { + f.set(TypeAide.AUTRE, backup); + } + } + } + + @Nested + @DisplayName("getNiveauPriorite default") + class GetNiveauPrioriteDefault { + + @Test + @DisplayName("getNiveauPriorite retourne 3 (default) pour priorite inconnue") + void testDefault() throws Exception { + java.lang.reflect.Field f = TypeAide.class.getDeclaredField("priorite"); + f.setAccessible(true); + String backup = TypeAide.AUTRE.getPriorite(); + try { + f.set(TypeAide.AUTRE, "inconnu"); + assertThat(TypeAide.AUTRE.getNiveauPriorite()).isEqualTo(3); + } finally { + f.set(TypeAide.AUTRE, backup); + } + } + } + + @Nested + @DisplayName("Tests getUniteMontant") + class GetUniteMontantTests { + + @Test + @DisplayName("getUniteMontant doit retourner FCFA si necessiteMontant est true") + void testGetUniteMontant() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getUniteMontant()).isEqualTo("FCFA"); + assertThat(TypeAide.PRET_SANS_INTERET.getUniteMontant()).isEqualTo("FCFA"); + assertThat(TypeAide.DON_MATERIEL.getUniteMontant()).isNull(); + assertThat(TypeAide.TRANSPORT.getUniteMontant()).isNull(); + } + } + + @Nested + @DisplayName("Tests getters simples") + class GettersSimples { + + @Test + @DisplayName("getDescription doit retourner la description") + void testGetDescription() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getDescription()) + .isEqualTo("Aide financière pour situation d'urgence"); + assertThat(TypeAide.DON_MATERIEL.getDescription()) + .isEqualTo("Don d'objets, équipements ou matériel"); + } + + @Test + @DisplayName("getIcone doit retourner l'icône") + void testGetIcone() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getIcone()).isEqualTo("emergency_fund"); + assertThat(TypeAide.DON_MATERIEL.getIcone()).isEqualTo("inventory"); + } + + @Test + @DisplayName("getCouleur doit retourner la couleur") + void testGetCouleur() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getCouleur()).isEqualTo("#F44336"); + assertThat(TypeAide.DON_MATERIEL.getCouleur()).isEqualTo("#4CAF50"); + } + + @Test + @DisplayName("isNecessiteMontant doit retourner la valeur du champ") + void testIsNecessiteMontant() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isNecessiteMontant()).isTrue(); + assertThat(TypeAide.DON_MATERIEL.isNecessiteMontant()).isFalse(); + } + + @Test + @DisplayName("isNecessiteValidation doit retourner la valeur du champ") + void testIsNecessiteValidation() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.isNecessiteValidation()).isTrue(); + assertThat(TypeAide.DON_MATERIEL.isNecessiteValidation()).isFalse(); + } + + @Test + @DisplayName("getMontantMin doit retourner le montant minimum") + void testGetMontantMin() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMontantMin()).isEqualTo(5000.0); + assertThat(TypeAide.PRET_SANS_INTERET.getMontantMin()).isEqualTo(10000.0); + } + + @Test + @DisplayName("getMontantMax doit retourner le montant maximum") + void testGetMontantMax() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMontantMax()).isEqualTo(50000.0); + assertThat(TypeAide.PRET_SANS_INTERET.getMontantMax()).isEqualTo(100000.0); + } + + @Test + @DisplayName("getDelaiReponseJours doit retourner le délai de réponse") + void testGetDelaiReponseJours() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getDelaiReponseJours()).isEqualTo(7); + assertThat(TypeAide.PRET_SANS_INTERET.getDelaiReponseJours()).isEqualTo(30); + } + } + + @Nested + @DisplayName("Tests getMessageValidationMontant") + class GetMessageValidationMontantTests { + + @Test + @DisplayName("getMessageValidationMontant doit retourner null si necessiteMontant est false") + void testGetMessageValidationMontantNonNecessaire() { + assertThat(TypeAide.DON_MATERIEL.getMessageValidationMontant(null)).isNull(); + assertThat(TypeAide.DON_MATERIEL.getMessageValidationMontant(1000.0)).isNull(); + } + + @Test + @DisplayName("getMessageValidationMontant doit retourner message si montant est null") + void testGetMessageValidationMontantNull() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(null)) + .isEqualTo("Le montant est obligatoire"); + } + + @Test + @DisplayName("getMessageValidationMontant doit retourner message si montant < montantMin") + void testGetMessageValidationMontantTropBas() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(4000.0)) + .contains("minimum"); + } + + @Test + @DisplayName("getMessageValidationMontant doit retourner message si montant > montantMax") + void testGetMessageValidationMontantTropHaut() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(51000.0)) + .contains("maximum"); + } + + @Test + @DisplayName("getMessageValidationMontant doit retourner null si montant est valide") + void testGetMessageValidationMontantValide() { + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(10000.0)) + .isNull(); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(5000.0)) + .isNull(); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(50000.0)) + .isNull(); + } + + @Test + @DisplayName("getMessageValidationMontant skip montantMin quand null (reflection)") + void testGetMessageValidationMontantMontantMinNull() throws Exception { + java.lang.reflect.Field minF = TypeAide.class.getDeclaredField("montantMin"); + minF.setAccessible(true); + Object backup = minF.get(TypeAide.AIDE_FINANCIERE_URGENTE); + try { + minF.set(TypeAide.AIDE_FINANCIERE_URGENTE, null); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(60000.0)) + .contains("maximum"); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(25000.0)) + .isNull(); + } finally { + minF.set(TypeAide.AIDE_FINANCIERE_URGENTE, backup); + } + } + + @Test + @DisplayName("getMessageValidationMontant skip montantMax quand null (reflection)") + void testGetMessageValidationMontantMontantMaxNull() throws Exception { + java.lang.reflect.Field maxF = TypeAide.class.getDeclaredField("montantMax"); + maxF.setAccessible(true); + Object backup = maxF.get(TypeAide.AIDE_FINANCIERE_URGENTE); + try { + maxF.set(TypeAide.AIDE_FINANCIERE_URGENTE, null); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(4000.0)) + .contains("minimum"); + assertThat(TypeAide.AIDE_FINANCIERE_URGENTE.getMessageValidationMontant(10000.0)) + .isNull(); + } finally { + maxF.set(TypeAide.AIDE_FINANCIERE_URGENTE, backup); + } + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/TypeEvaluationTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/TypeEvaluationTest.java index a9215f3..9a79361 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/TypeEvaluationTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/TypeEvaluationTest.java @@ -1,76 +1,76 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour TypeEvaluation") -class TypeEvaluationTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(TypeEvaluation.SATISFACTION_BENEFICIAIRE).isNotNull(); - assertThat(TypeEvaluation.EVALUATION_IMPACT).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - TypeEvaluation[] values = TypeEvaluation.values(); - assertThat(values).hasSize(6); - assertThat(values).containsExactly( - TypeEvaluation.SATISFACTION_BENEFICIAIRE, - TypeEvaluation.EVALUATION_PROPOSANT, - TypeEvaluation.EVALUATION_PROCESSUS, - TypeEvaluation.SUIVI_POST_AIDE, - TypeEvaluation.EVALUATION_IMPACT, - TypeEvaluation.RETOUR_EXPERIENCE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(TypeEvaluation.valueOf("SATISFACTION_BENEFICIAIRE")).isEqualTo(TypeEvaluation.SATISFACTION_BENEFICIAIRE); - assertThat(TypeEvaluation.valueOf("EVALUATION_PROPOSANT")).isEqualTo(TypeEvaluation.EVALUATION_PROPOSANT); - assertThat(TypeEvaluation.valueOf("EVALUATION_PROCESSUS")).isEqualTo(TypeEvaluation.EVALUATION_PROCESSUS); - assertThat(TypeEvaluation.valueOf("SUIVI_POST_AIDE")).isEqualTo(TypeEvaluation.SUIVI_POST_AIDE); - assertThat(TypeEvaluation.valueOf("EVALUATION_IMPACT")).isEqualTo(TypeEvaluation.EVALUATION_IMPACT); - assertThat(TypeEvaluation.valueOf("RETOUR_EXPERIENCE")).isEqualTo(TypeEvaluation.RETOUR_EXPERIENCE); - - assertThatThrownBy(() -> TypeEvaluation.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(TypeEvaluation.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(TypeEvaluation type) { - assertThat(type.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(TypeEvaluation.SATISFACTION_BENEFICIAIRE.getLibelle()).isEqualTo("Satisfaction du bénéficiaire"); - assertThat(TypeEvaluation.EVALUATION_IMPACT.getLibelle()).isEqualTo("Évaluation d'impact"); - assertThat(TypeEvaluation.RETOUR_EXPERIENCE.getLibelle()).isEqualTo("Retour d'expérience"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(TypeEvaluation.SATISFACTION_BENEFICIAIRE.name()).isEqualTo("SATISFACTION_BENEFICIAIRE"); - assertThat(TypeEvaluation.EVALUATION_IMPACT.name()).isEqualTo("EVALUATION_IMPACT"); - } - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour TypeEvaluation") +class TypeEvaluationTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(TypeEvaluation.SATISFACTION_BENEFICIAIRE).isNotNull(); + assertThat(TypeEvaluation.EVALUATION_IMPACT).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + TypeEvaluation[] values = TypeEvaluation.values(); + assertThat(values).hasSize(6); + assertThat(values).containsExactly( + TypeEvaluation.SATISFACTION_BENEFICIAIRE, + TypeEvaluation.EVALUATION_PROPOSANT, + TypeEvaluation.EVALUATION_PROCESSUS, + TypeEvaluation.SUIVI_POST_AIDE, + TypeEvaluation.EVALUATION_IMPACT, + TypeEvaluation.RETOUR_EXPERIENCE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(TypeEvaluation.valueOf("SATISFACTION_BENEFICIAIRE")).isEqualTo(TypeEvaluation.SATISFACTION_BENEFICIAIRE); + assertThat(TypeEvaluation.valueOf("EVALUATION_PROPOSANT")).isEqualTo(TypeEvaluation.EVALUATION_PROPOSANT); + assertThat(TypeEvaluation.valueOf("EVALUATION_PROCESSUS")).isEqualTo(TypeEvaluation.EVALUATION_PROCESSUS); + assertThat(TypeEvaluation.valueOf("SUIVI_POST_AIDE")).isEqualTo(TypeEvaluation.SUIVI_POST_AIDE); + assertThat(TypeEvaluation.valueOf("EVALUATION_IMPACT")).isEqualTo(TypeEvaluation.EVALUATION_IMPACT); + assertThat(TypeEvaluation.valueOf("RETOUR_EXPERIENCE")).isEqualTo(TypeEvaluation.RETOUR_EXPERIENCE); + + assertThatThrownBy(() -> TypeEvaluation.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(TypeEvaluation.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(TypeEvaluation type) { + assertThat(type.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(TypeEvaluation.SATISFACTION_BENEFICIAIRE.getLibelle()).isEqualTo("Satisfaction du bénéficiaire"); + assertThat(TypeEvaluation.EVALUATION_IMPACT.getLibelle()).isEqualTo("Évaluation d'impact"); + assertThat(TypeEvaluation.RETOUR_EXPERIENCE.getLibelle()).isEqualTo("Retour d'expérience"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(TypeEvaluation.SATISFACTION_BENEFICIAIRE.name()).isEqualTo("SATISFACTION_BENEFICIAIRE"); + assertThat(TypeEvaluation.EVALUATION_IMPACT.name()).isEqualTo("EVALUATION_IMPACT"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/TypeWorkflowTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/TypeWorkflowTest.java index a482b3e..926dc0a 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/TypeWorkflowTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/solidarite/TypeWorkflowTest.java @@ -1,70 +1,70 @@ -package dev.lions.unionflow.server.api.enums.solidarite; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour TypeWorkflow") -class TypeWorkflowTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(TypeWorkflow.DEMANDE_AIDE).isNotNull(); - assertThat(TypeWorkflow.ADHESION).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - TypeWorkflow[] values = TypeWorkflow.values(); - assertThat(values).hasSize(3); - assertThat(values).containsExactly( - TypeWorkflow.DEMANDE_AIDE, - TypeWorkflow.ADHESION, - TypeWorkflow.AUTRE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(TypeWorkflow.valueOf("DEMANDE_AIDE")).isEqualTo(TypeWorkflow.DEMANDE_AIDE); - assertThat(TypeWorkflow.valueOf("ADHESION")).isEqualTo(TypeWorkflow.ADHESION); - assertThat(TypeWorkflow.valueOf("AUTRE")).isEqualTo(TypeWorkflow.AUTRE); - - assertThatThrownBy(() -> TypeWorkflow.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(TypeWorkflow.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(TypeWorkflow type) { - assertThat(type.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(TypeWorkflow.DEMANDE_AIDE.getLibelle()).isEqualTo("Workflow demande d'aide solidarité"); - assertThat(TypeWorkflow.ADHESION.getLibelle()).isEqualTo("Workflow validation adhésion"); - assertThat(TypeWorkflow.AUTRE.getLibelle()).isEqualTo("Workflow personnalisé"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(TypeWorkflow.DEMANDE_AIDE.name()).isEqualTo("DEMANDE_AIDE"); - assertThat(TypeWorkflow.AUTRE.name()).isEqualTo("AUTRE"); - } - } -} +package dev.lions.unionflow.server.api.enums.solidarite; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour TypeWorkflow") +class TypeWorkflowTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(TypeWorkflow.DEMANDE_AIDE).isNotNull(); + assertThat(TypeWorkflow.ADHESION).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + TypeWorkflow[] values = TypeWorkflow.values(); + assertThat(values).hasSize(3); + assertThat(values).containsExactly( + TypeWorkflow.DEMANDE_AIDE, + TypeWorkflow.ADHESION, + TypeWorkflow.AUTRE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(TypeWorkflow.valueOf("DEMANDE_AIDE")).isEqualTo(TypeWorkflow.DEMANDE_AIDE); + assertThat(TypeWorkflow.valueOf("ADHESION")).isEqualTo(TypeWorkflow.ADHESION); + assertThat(TypeWorkflow.valueOf("AUTRE")).isEqualTo(TypeWorkflow.AUTRE); + + assertThatThrownBy(() -> TypeWorkflow.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(TypeWorkflow.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(TypeWorkflow type) { + assertThat(type.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(TypeWorkflow.DEMANDE_AIDE.getLibelle()).isEqualTo("Workflow demande d'aide solidarité"); + assertThat(TypeWorkflow.ADHESION.getLibelle()).isEqualTo("Workflow validation adhésion"); + assertThat(TypeWorkflow.AUTRE.getLibelle()).isEqualTo("Workflow personnalisé"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(TypeWorkflow.DEMANDE_AIDE.name()).isEqualTo("DEMANDE_AIDE"); + assertThat(TypeWorkflow.AUTRE.name()).isEqualTo("AUTRE"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/tontine/FrequenceTourTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/tontine/FrequenceTourTest.java index 70c4386..a554243 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/tontine/FrequenceTourTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/tontine/FrequenceTourTest.java @@ -1,79 +1,79 @@ -package dev.lions.unionflow.server.api.enums.tontine; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour FrequenceTour") -class FrequenceTourTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(FrequenceTour.JOURNALIERE).isNotNull(); - assertThat(FrequenceTour.MENSUELLE).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - FrequenceTour[] values = FrequenceTour.values(); - assertThat(values).hasSize(6); - assertThat(values).containsExactly( - FrequenceTour.JOURNALIERE, - FrequenceTour.HEBDOMADAIRE, - FrequenceTour.DECADE, - FrequenceTour.QUINZAINE, - FrequenceTour.MENSUELLE, - FrequenceTour.TRIMESTRIELLE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(FrequenceTour.valueOf("JOURNALIERE")).isEqualTo(FrequenceTour.JOURNALIERE); - assertThat(FrequenceTour.valueOf("HEBDOMADAIRE")).isEqualTo(FrequenceTour.HEBDOMADAIRE); - assertThat(FrequenceTour.valueOf("DECADE")).isEqualTo(FrequenceTour.DECADE); - assertThat(FrequenceTour.valueOf("QUINZAINE")).isEqualTo(FrequenceTour.QUINZAINE); - assertThat(FrequenceTour.valueOf("MENSUELLE")).isEqualTo(FrequenceTour.MENSUELLE); - assertThat(FrequenceTour.valueOf("TRIMESTRIELLE")).isEqualTo(FrequenceTour.TRIMESTRIELLE); - - assertThatThrownBy(() -> FrequenceTour.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(FrequenceTour.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(FrequenceTour frequence) { - assertThat(frequence.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(FrequenceTour.JOURNALIERE.getLibelle()).isEqualTo("Chaque jour"); - assertThat(FrequenceTour.HEBDOMADAIRE.getLibelle()).isEqualTo("Chaque semaine"); - assertThat(FrequenceTour.DECADE.getLibelle()).isEqualTo("Tous les 10 jours"); - assertThat(FrequenceTour.QUINZAINE.getLibelle()).isEqualTo("Chaque quinzaine (tous les 15 jours)"); - assertThat(FrequenceTour.MENSUELLE.getLibelle()).isEqualTo("Chaque mois"); - assertThat(FrequenceTour.TRIMESTRIELLE.getLibelle()).isEqualTo("Chaque trimestre"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(FrequenceTour.JOURNALIERE.name()).isEqualTo("JOURNALIERE"); - assertThat(FrequenceTour.TRIMESTRIELLE.name()).isEqualTo("TRIMESTRIELLE"); - } - } -} +package dev.lions.unionflow.server.api.enums.tontine; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour FrequenceTour") +class FrequenceTourTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(FrequenceTour.JOURNALIERE).isNotNull(); + assertThat(FrequenceTour.MENSUELLE).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + FrequenceTour[] values = FrequenceTour.values(); + assertThat(values).hasSize(6); + assertThat(values).containsExactly( + FrequenceTour.JOURNALIERE, + FrequenceTour.HEBDOMADAIRE, + FrequenceTour.DECADE, + FrequenceTour.QUINZAINE, + FrequenceTour.MENSUELLE, + FrequenceTour.TRIMESTRIELLE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(FrequenceTour.valueOf("JOURNALIERE")).isEqualTo(FrequenceTour.JOURNALIERE); + assertThat(FrequenceTour.valueOf("HEBDOMADAIRE")).isEqualTo(FrequenceTour.HEBDOMADAIRE); + assertThat(FrequenceTour.valueOf("DECADE")).isEqualTo(FrequenceTour.DECADE); + assertThat(FrequenceTour.valueOf("QUINZAINE")).isEqualTo(FrequenceTour.QUINZAINE); + assertThat(FrequenceTour.valueOf("MENSUELLE")).isEqualTo(FrequenceTour.MENSUELLE); + assertThat(FrequenceTour.valueOf("TRIMESTRIELLE")).isEqualTo(FrequenceTour.TRIMESTRIELLE); + + assertThatThrownBy(() -> FrequenceTour.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(FrequenceTour.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(FrequenceTour frequence) { + assertThat(frequence.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(FrequenceTour.JOURNALIERE.getLibelle()).isEqualTo("Chaque jour"); + assertThat(FrequenceTour.HEBDOMADAIRE.getLibelle()).isEqualTo("Chaque semaine"); + assertThat(FrequenceTour.DECADE.getLibelle()).isEqualTo("Tous les 10 jours"); + assertThat(FrequenceTour.QUINZAINE.getLibelle()).isEqualTo("Chaque quinzaine (tous les 15 jours)"); + assertThat(FrequenceTour.MENSUELLE.getLibelle()).isEqualTo("Chaque mois"); + assertThat(FrequenceTour.TRIMESTRIELLE.getLibelle()).isEqualTo("Chaque trimestre"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(FrequenceTour.JOURNALIERE.name()).isEqualTo("JOURNALIERE"); + assertThat(FrequenceTour.TRIMESTRIELLE.name()).isEqualTo("TRIMESTRIELLE"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/tontine/StatutTontineTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/tontine/StatutTontineTest.java index 0e13ccb..f8c3079 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/tontine/StatutTontineTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/tontine/StatutTontineTest.java @@ -1,76 +1,76 @@ -package dev.lions.unionflow.server.api.enums.tontine; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutTontine") -class StatutTontineTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutTontine.PLANIFIEE).isNotNull(); - assertThat(StatutTontine.EN_COURS).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutTontine[] values = StatutTontine.values(); - assertThat(values).hasSize(5); - assertThat(values).containsExactly( - StatutTontine.PLANIFIEE, - StatutTontine.EN_COURS, - StatutTontine.EN_PAUSE, - StatutTontine.CLOTUREE, - StatutTontine.ANNULEE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(StatutTontine.valueOf("PLANIFIEE")).isEqualTo(StatutTontine.PLANIFIEE); - assertThat(StatutTontine.valueOf("EN_COURS")).isEqualTo(StatutTontine.EN_COURS); - assertThat(StatutTontine.valueOf("EN_PAUSE")).isEqualTo(StatutTontine.EN_PAUSE); - assertThat(StatutTontine.valueOf("CLOTUREE")).isEqualTo(StatutTontine.CLOTUREE); - assertThat(StatutTontine.valueOf("ANNULEE")).isEqualTo(StatutTontine.ANNULEE); - - assertThatThrownBy(() -> StatutTontine.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutTontine.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutTontine statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(StatutTontine.PLANIFIEE.getLibelle()).isEqualTo("En cours de planification / Enrôlement des membres"); - assertThat(StatutTontine.EN_COURS.getLibelle()).isEqualTo("Active et en cours de déroulement"); - assertThat(StatutTontine.EN_PAUSE.getLibelle()).isEqualTo("Suspendue temporairement par l'administration"); - assertThat(StatutTontine.CLOTUREE.getLibelle()).isEqualTo("Terminée avec succès (tous les tours finis)"); - assertThat(StatutTontine.ANNULEE.getLibelle()).isEqualTo("Annulée avant son terme"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(StatutTontine.PLANIFIEE.name()).isEqualTo("PLANIFIEE"); - assertThat(StatutTontine.EN_PAUSE.name()).isEqualTo("EN_PAUSE"); - } - } -} +package dev.lions.unionflow.server.api.enums.tontine; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutTontine") +class StatutTontineTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutTontine.PLANIFIEE).isNotNull(); + assertThat(StatutTontine.EN_COURS).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutTontine[] values = StatutTontine.values(); + assertThat(values).hasSize(5); + assertThat(values).containsExactly( + StatutTontine.PLANIFIEE, + StatutTontine.EN_COURS, + StatutTontine.EN_PAUSE, + StatutTontine.CLOTUREE, + StatutTontine.ANNULEE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(StatutTontine.valueOf("PLANIFIEE")).isEqualTo(StatutTontine.PLANIFIEE); + assertThat(StatutTontine.valueOf("EN_COURS")).isEqualTo(StatutTontine.EN_COURS); + assertThat(StatutTontine.valueOf("EN_PAUSE")).isEqualTo(StatutTontine.EN_PAUSE); + assertThat(StatutTontine.valueOf("CLOTUREE")).isEqualTo(StatutTontine.CLOTUREE); + assertThat(StatutTontine.valueOf("ANNULEE")).isEqualTo(StatutTontine.ANNULEE); + + assertThatThrownBy(() -> StatutTontine.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutTontine.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutTontine statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(StatutTontine.PLANIFIEE.getLibelle()).isEqualTo("En cours de planification / Enrôlement des membres"); + assertThat(StatutTontine.EN_COURS.getLibelle()).isEqualTo("Active et en cours de déroulement"); + assertThat(StatutTontine.EN_PAUSE.getLibelle()).isEqualTo("Suspendue temporairement par l'administration"); + assertThat(StatutTontine.CLOTUREE.getLibelle()).isEqualTo("Terminée avec succès (tous les tours finis)"); + assertThat(StatutTontine.ANNULEE.getLibelle()).isEqualTo("Annulée avant son terme"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(StatutTontine.PLANIFIEE.name()).isEqualTo("PLANIFIEE"); + assertThat(StatutTontine.EN_PAUSE.name()).isEqualTo("EN_PAUSE"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/tontine/TypeTontineTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/tontine/TypeTontineTest.java index 511676b..ff00b75 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/tontine/TypeTontineTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/tontine/TypeTontineTest.java @@ -1,70 +1,70 @@ -package dev.lions.unionflow.server.api.enums.tontine; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour TypeTontine") -class TypeTontineTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(TypeTontine.ROTATIVE_CLASSIQUE).isNotNull(); - assertThat(TypeTontine.ACCUMULATIVE).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - TypeTontine[] values = TypeTontine.values(); - assertThat(values).hasSize(3); - assertThat(values).containsExactly( - TypeTontine.ROTATIVE_CLASSIQUE, - TypeTontine.VARIABLE, - TypeTontine.ACCUMULATIVE); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(TypeTontine.valueOf("ROTATIVE_CLASSIQUE")).isEqualTo(TypeTontine.ROTATIVE_CLASSIQUE); - assertThat(TypeTontine.valueOf("VARIABLE")).isEqualTo(TypeTontine.VARIABLE); - assertThat(TypeTontine.valueOf("ACCUMULATIVE")).isEqualTo(TypeTontine.ACCUMULATIVE); - - assertThatThrownBy(() -> TypeTontine.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(TypeTontine.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(TypeTontine type) { - assertThat(type.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(TypeTontine.ROTATIVE_CLASSIQUE.getLibelle()).isEqualTo("Tontine rotative classique avec cotisations fixes"); - assertThat(TypeTontine.VARIABLE.getLibelle()).isEqualTo("Tontine à cotisations variables (Vente aux enchères/Mise)"); - assertThat(TypeTontine.ACCUMULATIVE.getLibelle()).isEqualTo("Tontine accumulative / Caisse de secours"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(TypeTontine.ROTATIVE_CLASSIQUE.name()).isEqualTo("ROTATIVE_CLASSIQUE"); - assertThat(TypeTontine.VARIABLE.name()).isEqualTo("VARIABLE"); - } - } -} +package dev.lions.unionflow.server.api.enums.tontine; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour TypeTontine") +class TypeTontineTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(TypeTontine.ROTATIVE_CLASSIQUE).isNotNull(); + assertThat(TypeTontine.ACCUMULATIVE).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + TypeTontine[] values = TypeTontine.values(); + assertThat(values).hasSize(3); + assertThat(values).containsExactly( + TypeTontine.ROTATIVE_CLASSIQUE, + TypeTontine.VARIABLE, + TypeTontine.ACCUMULATIVE); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(TypeTontine.valueOf("ROTATIVE_CLASSIQUE")).isEqualTo(TypeTontine.ROTATIVE_CLASSIQUE); + assertThat(TypeTontine.valueOf("VARIABLE")).isEqualTo(TypeTontine.VARIABLE); + assertThat(TypeTontine.valueOf("ACCUMULATIVE")).isEqualTo(TypeTontine.ACCUMULATIVE); + + assertThatThrownBy(() -> TypeTontine.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(TypeTontine.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(TypeTontine type) { + assertThat(type.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(TypeTontine.ROTATIVE_CLASSIQUE.getLibelle()).isEqualTo("Tontine rotative classique avec cotisations fixes"); + assertThat(TypeTontine.VARIABLE.getLibelle()).isEqualTo("Tontine à cotisations variables (Vente aux enchères/Mise)"); + assertThat(TypeTontine.ACCUMULATIVE.getLibelle()).isEqualTo("Tontine accumulative / Caisse de secours"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(TypeTontine.ROTATIVE_CLASSIQUE.name()).isEqualTo("ROTATIVE_CLASSIQUE"); + assertThat(TypeTontine.VARIABLE.name()).isEqualTo("VARIABLE"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/vote/ModeScrutinTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/vote/ModeScrutinTest.java index 615afb6..1f7dd7e 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/vote/ModeScrutinTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/vote/ModeScrutinTest.java @@ -1,73 +1,73 @@ -package dev.lions.unionflow.server.api.enums.vote; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour ModeScrutin") -class ModeScrutinTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(ModeScrutin.MAJORITAIRE_UN_TOUR).isNotNull(); - assertThat(ModeScrutin.PROPORTIONNEL).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - ModeScrutin[] values = ModeScrutin.values(); - assertThat(values).hasSize(4); - assertThat(values).containsExactly( - ModeScrutin.MAJORITAIRE_UN_TOUR, - ModeScrutin.MAJORITAIRE_DEUX_TOURS, - ModeScrutin.PROPORTIONNEL, - ModeScrutin.BUREAU_CONSENSUEL); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(ModeScrutin.valueOf("MAJORITAIRE_UN_TOUR")).isEqualTo(ModeScrutin.MAJORITAIRE_UN_TOUR); - assertThat(ModeScrutin.valueOf("MAJORITAIRE_DEUX_TOURS")).isEqualTo(ModeScrutin.MAJORITAIRE_DEUX_TOURS); - assertThat(ModeScrutin.valueOf("PROPORTIONNEL")).isEqualTo(ModeScrutin.PROPORTIONNEL); - assertThat(ModeScrutin.valueOf("BUREAU_CONSENSUEL")).isEqualTo(ModeScrutin.BUREAU_CONSENSUEL); - - assertThatThrownBy(() -> ModeScrutin.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(ModeScrutin.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(ModeScrutin mode) { - assertThat(mode.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(ModeScrutin.MAJORITAIRE_UN_TOUR.getLibelle()).isEqualTo("Scrutin majoritaire à un seul tour"); - assertThat(ModeScrutin.MAJORITAIRE_DEUX_TOURS.getLibelle()).isEqualTo("Scrutin majoritaire à deux tours"); - assertThat(ModeScrutin.PROPORTIONNEL.getLibelle()).isEqualTo("Scrutin proportionnel de listes"); - assertThat(ModeScrutin.BUREAU_CONSENSUEL.getLibelle()).isEqualTo("Vote d'approbation globale de bureau (OUI/NON)"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(ModeScrutin.MAJORITAIRE_UN_TOUR.name()).isEqualTo("MAJORITAIRE_UN_TOUR"); - assertThat(ModeScrutin.BUREAU_CONSENSUEL.name()).isEqualTo("BUREAU_CONSENSUEL"); - } - } -} +package dev.lions.unionflow.server.api.enums.vote; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour ModeScrutin") +class ModeScrutinTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(ModeScrutin.MAJORITAIRE_UN_TOUR).isNotNull(); + assertThat(ModeScrutin.PROPORTIONNEL).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + ModeScrutin[] values = ModeScrutin.values(); + assertThat(values).hasSize(4); + assertThat(values).containsExactly( + ModeScrutin.MAJORITAIRE_UN_TOUR, + ModeScrutin.MAJORITAIRE_DEUX_TOURS, + ModeScrutin.PROPORTIONNEL, + ModeScrutin.BUREAU_CONSENSUEL); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(ModeScrutin.valueOf("MAJORITAIRE_UN_TOUR")).isEqualTo(ModeScrutin.MAJORITAIRE_UN_TOUR); + assertThat(ModeScrutin.valueOf("MAJORITAIRE_DEUX_TOURS")).isEqualTo(ModeScrutin.MAJORITAIRE_DEUX_TOURS); + assertThat(ModeScrutin.valueOf("PROPORTIONNEL")).isEqualTo(ModeScrutin.PROPORTIONNEL); + assertThat(ModeScrutin.valueOf("BUREAU_CONSENSUEL")).isEqualTo(ModeScrutin.BUREAU_CONSENSUEL); + + assertThatThrownBy(() -> ModeScrutin.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(ModeScrutin.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(ModeScrutin mode) { + assertThat(mode.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(ModeScrutin.MAJORITAIRE_UN_TOUR.getLibelle()).isEqualTo("Scrutin majoritaire à un seul tour"); + assertThat(ModeScrutin.MAJORITAIRE_DEUX_TOURS.getLibelle()).isEqualTo("Scrutin majoritaire à deux tours"); + assertThat(ModeScrutin.PROPORTIONNEL.getLibelle()).isEqualTo("Scrutin proportionnel de listes"); + assertThat(ModeScrutin.BUREAU_CONSENSUEL.getLibelle()).isEqualTo("Vote d'approbation globale de bureau (OUI/NON)"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(ModeScrutin.MAJORITAIRE_UN_TOUR.name()).isEqualTo("MAJORITAIRE_UN_TOUR"); + assertThat(ModeScrutin.BUREAU_CONSENSUEL.name()).isEqualTo("BUREAU_CONSENSUEL"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/vote/StatutVoteTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/vote/StatutVoteTest.java index a578253..be9bf4e 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/vote/StatutVoteTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/vote/StatutVoteTest.java @@ -1,79 +1,79 @@ -package dev.lions.unionflow.server.api.enums.vote; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour StatutVote") -class StatutVoteTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(StatutVote.BROUILLON).isNotNull(); - assertThat(StatutVote.OUVERT).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - StatutVote[] values = StatutVote.values(); - assertThat(values).hasSize(6); - assertThat(values).containsExactly( - StatutVote.BROUILLON, - StatutVote.PLANIFIE, - StatutVote.OUVERT, - StatutVote.SUSPENDU, - StatutVote.CLOTURE, - StatutVote.RESULTATS_PUBLIES); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(StatutVote.valueOf("BROUILLON")).isEqualTo(StatutVote.BROUILLON); - assertThat(StatutVote.valueOf("PLANIFIE")).isEqualTo(StatutVote.PLANIFIE); - assertThat(StatutVote.valueOf("OUVERT")).isEqualTo(StatutVote.OUVERT); - assertThat(StatutVote.valueOf("SUSPENDU")).isEqualTo(StatutVote.SUSPENDU); - assertThat(StatutVote.valueOf("CLOTURE")).isEqualTo(StatutVote.CLOTURE); - assertThat(StatutVote.valueOf("RESULTATS_PUBLIES")).isEqualTo(StatutVote.RESULTATS_PUBLIES); - - assertThatThrownBy(() -> StatutVote.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(StatutVote.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(StatutVote statut) { - assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(StatutVote.BROUILLON.getLibelle()).isEqualTo("Paramétrage de la campagne en cours"); - assertThat(StatutVote.PLANIFIE.getLibelle()).isEqualTo("Campagne planifiée (pas encore ouverte aux votes)"); - assertThat(StatutVote.OUVERT.getLibelle()).isEqualTo("Les membres peuvent voter activement"); - assertThat(StatutVote.SUSPENDU.getLibelle()).isEqualTo("Campagne de vote suspendue suite à une contestation"); - assertThat(StatutVote.CLOTURE.getLibelle()).isEqualTo("Dispositif de vote fermé (Calcul en cours)"); - assertThat(StatutVote.RESULTATS_PUBLIES.getLibelle()).isEqualTo("Résultats définitifs publiés et accessibles"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(StatutVote.BROUILLON.name()).isEqualTo("BROUILLON"); - assertThat(StatutVote.RESULTATS_PUBLIES.name()).isEqualTo("RESULTATS_PUBLIES"); - } - } -} +package dev.lions.unionflow.server.api.enums.vote; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour StatutVote") +class StatutVoteTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(StatutVote.BROUILLON).isNotNull(); + assertThat(StatutVote.OUVERT).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + StatutVote[] values = StatutVote.values(); + assertThat(values).hasSize(6); + assertThat(values).containsExactly( + StatutVote.BROUILLON, + StatutVote.PLANIFIE, + StatutVote.OUVERT, + StatutVote.SUSPENDU, + StatutVote.CLOTURE, + StatutVote.RESULTATS_PUBLIES); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(StatutVote.valueOf("BROUILLON")).isEqualTo(StatutVote.BROUILLON); + assertThat(StatutVote.valueOf("PLANIFIE")).isEqualTo(StatutVote.PLANIFIE); + assertThat(StatutVote.valueOf("OUVERT")).isEqualTo(StatutVote.OUVERT); + assertThat(StatutVote.valueOf("SUSPENDU")).isEqualTo(StatutVote.SUSPENDU); + assertThat(StatutVote.valueOf("CLOTURE")).isEqualTo(StatutVote.CLOTURE); + assertThat(StatutVote.valueOf("RESULTATS_PUBLIES")).isEqualTo(StatutVote.RESULTATS_PUBLIES); + + assertThatThrownBy(() -> StatutVote.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(StatutVote.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(StatutVote statut) { + assertThat(statut.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(StatutVote.BROUILLON.getLibelle()).isEqualTo("Paramétrage de la campagne en cours"); + assertThat(StatutVote.PLANIFIE.getLibelle()).isEqualTo("Campagne planifiée (pas encore ouverte aux votes)"); + assertThat(StatutVote.OUVERT.getLibelle()).isEqualTo("Les membres peuvent voter activement"); + assertThat(StatutVote.SUSPENDU.getLibelle()).isEqualTo("Campagne de vote suspendue suite à une contestation"); + assertThat(StatutVote.CLOTURE.getLibelle()).isEqualTo("Dispositif de vote fermé (Calcul en cours)"); + assertThat(StatutVote.RESULTATS_PUBLIES.getLibelle()).isEqualTo("Résultats définitifs publiés et accessibles"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(StatutVote.BROUILLON.name()).isEqualTo("BROUILLON"); + assertThat(StatutVote.RESULTATS_PUBLIES.name()).isEqualTo("RESULTATS_PUBLIES"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/vote/TypeVoteTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/vote/TypeVoteTest.java index 009ce33..be11103 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/vote/TypeVoteTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/vote/TypeVoteTest.java @@ -1,76 +1,76 @@ -package dev.lions.unionflow.server.api.enums.vote; - -import static org.assertj.core.api.Assertions.assertThat; -import static org.assertj.core.api.Assertions.assertThatThrownBy; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.EnumSource; - -@DisplayName("Tests pour TypeVote") -class TypeVoteTest { - - @Test - @DisplayName("Test de base - enum peut être utilisé") - void testEnumUtilisable() { - assertThat(TypeVote.ELECTION_BUREAU).isNotNull(); - assertThat(TypeVote.REFERENDUM).isNotNull(); - } - - @Nested - @DisplayName("Tests des valeurs enum") - class TestsValeursEnum { - - @Test - @DisplayName("Test toutes les valeurs enum") - void testToutesValeurs() { - TypeVote[] values = TypeVote.values(); - assertThat(values).hasSize(5); - assertThat(values).containsExactly( - TypeVote.ELECTION_BUREAU, - TypeVote.ADOPTION_RESOLUTION, - TypeVote.MODIFICATION_STATUTS, - TypeVote.EXCLUSION_MEMBRE, - TypeVote.REFERENDUM); - } - - @Test - @DisplayName("Test valueOf - toutes les constantes") - void testValueOf() { - assertThat(TypeVote.valueOf("ELECTION_BUREAU")).isEqualTo(TypeVote.ELECTION_BUREAU); - assertThat(TypeVote.valueOf("ADOPTION_RESOLUTION")).isEqualTo(TypeVote.ADOPTION_RESOLUTION); - assertThat(TypeVote.valueOf("MODIFICATION_STATUTS")).isEqualTo(TypeVote.MODIFICATION_STATUTS); - assertThat(TypeVote.valueOf("EXCLUSION_MEMBRE")).isEqualTo(TypeVote.EXCLUSION_MEMBRE); - assertThat(TypeVote.valueOf("REFERENDUM")).isEqualTo(TypeVote.REFERENDUM); - - assertThatThrownBy(() -> TypeVote.valueOf("INEXISTANT")) - .isInstanceOf(IllegalArgumentException.class); - } - - @ParameterizedTest - @EnumSource(TypeVote.class) - @DisplayName("Test getLibelle pour toutes les valeurs") - void testGetLibelle(TypeVote type) { - assertThat(type.getLibelle()).isNotNull().isNotEmpty(); - } - - @Test - @DisplayName("Test getLibelle valeurs exactes") - void testGetLibelleValeursExactes() { - assertThat(TypeVote.ELECTION_BUREAU.getLibelle()).isEqualTo("Élection des membres du bureau exécutif"); - assertThat(TypeVote.ADOPTION_RESOLUTION.getLibelle()).isEqualTo("Vote pour ou contre une résolution"); - assertThat(TypeVote.MODIFICATION_STATUTS.getLibelle()).isEqualTo("Vote d'amendement des statuts de la mutuelle"); - assertThat(TypeVote.EXCLUSION_MEMBRE.getLibelle()).isEqualTo("Vote d'exclusion d'un membre pour manquements"); - assertThat(TypeVote.REFERENDUM.getLibelle()).isEqualTo("Référendum interne ou consultation générale"); - } - - @Test - @DisplayName("Test name()") - void testName() { - assertThat(TypeVote.ELECTION_BUREAU.name()).isEqualTo("ELECTION_BUREAU"); - assertThat(TypeVote.MODIFICATION_STATUTS.name()).isEqualTo("MODIFICATION_STATUTS"); - } - } -} +package dev.lions.unionflow.server.api.enums.vote; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatThrownBy; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.EnumSource; + +@DisplayName("Tests pour TypeVote") +class TypeVoteTest { + + @Test + @DisplayName("Test de base - enum peut être utilisé") + void testEnumUtilisable() { + assertThat(TypeVote.ELECTION_BUREAU).isNotNull(); + assertThat(TypeVote.REFERENDUM).isNotNull(); + } + + @Nested + @DisplayName("Tests des valeurs enum") + class TestsValeursEnum { + + @Test + @DisplayName("Test toutes les valeurs enum") + void testToutesValeurs() { + TypeVote[] values = TypeVote.values(); + assertThat(values).hasSize(5); + assertThat(values).containsExactly( + TypeVote.ELECTION_BUREAU, + TypeVote.ADOPTION_RESOLUTION, + TypeVote.MODIFICATION_STATUTS, + TypeVote.EXCLUSION_MEMBRE, + TypeVote.REFERENDUM); + } + + @Test + @DisplayName("Test valueOf - toutes les constantes") + void testValueOf() { + assertThat(TypeVote.valueOf("ELECTION_BUREAU")).isEqualTo(TypeVote.ELECTION_BUREAU); + assertThat(TypeVote.valueOf("ADOPTION_RESOLUTION")).isEqualTo(TypeVote.ADOPTION_RESOLUTION); + assertThat(TypeVote.valueOf("MODIFICATION_STATUTS")).isEqualTo(TypeVote.MODIFICATION_STATUTS); + assertThat(TypeVote.valueOf("EXCLUSION_MEMBRE")).isEqualTo(TypeVote.EXCLUSION_MEMBRE); + assertThat(TypeVote.valueOf("REFERENDUM")).isEqualTo(TypeVote.REFERENDUM); + + assertThatThrownBy(() -> TypeVote.valueOf("INEXISTANT")) + .isInstanceOf(IllegalArgumentException.class); + } + + @ParameterizedTest + @EnumSource(TypeVote.class) + @DisplayName("Test getLibelle pour toutes les valeurs") + void testGetLibelle(TypeVote type) { + assertThat(type.getLibelle()).isNotNull().isNotEmpty(); + } + + @Test + @DisplayName("Test getLibelle valeurs exactes") + void testGetLibelleValeursExactes() { + assertThat(TypeVote.ELECTION_BUREAU.getLibelle()).isEqualTo("Élection des membres du bureau exécutif"); + assertThat(TypeVote.ADOPTION_RESOLUTION.getLibelle()).isEqualTo("Vote pour ou contre une résolution"); + assertThat(TypeVote.MODIFICATION_STATUTS.getLibelle()).isEqualTo("Vote d'amendement des statuts de la mutuelle"); + assertThat(TypeVote.EXCLUSION_MEMBRE.getLibelle()).isEqualTo("Vote d'exclusion d'un membre pour manquements"); + assertThat(TypeVote.REFERENDUM.getLibelle()).isEqualTo("Référendum interne ou consultation générale"); + } + + @Test + @DisplayName("Test name()") + void testName() { + assertThat(TypeVote.ELECTION_BUREAU.name()).isEqualTo("ELECTION_BUREAU"); + assertThat(TypeVote.MODIFICATION_STATUTS.name()).isEqualTo("MODIFICATION_STATUTS"); + } + } +} diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/wave/StatutCompteWaveTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/wave/StatutCompteWaveTest.java index 67b5cba..984730a 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/wave/StatutCompteWaveTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/wave/StatutCompteWaveTest.java @@ -1,36 +1,36 @@ -package dev.lions.unionflow.server.api.enums.wave; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour StatutCompteWave. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests StatutCompteWave") -class StatutCompteWaveTest { - - @Test - @DisplayName("Tous les statuts de compte Wave doivent avoir un libellé") - void testTousLesStatutsOntLibelle() { - for (StatutCompteWave statut : StatutCompteWave.values()) { - assertThat(statut.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(StatutCompteWave.values().length).isGreaterThan(0); - for (StatutCompteWave statut : StatutCompteWave.values()) { - assertThat(statut).isNotNull(); - assertThat(statut.name()).isNotBlank(); - } - } -} - +package dev.lions.unionflow.server.api.enums.wave; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour StatutCompteWave. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests StatutCompteWave") +class StatutCompteWaveTest { + + @Test + @DisplayName("Tous les statuts de compte Wave doivent avoir un libellé") + void testTousLesStatutsOntLibelle() { + for (StatutCompteWave statut : StatutCompteWave.values()) { + assertThat(statut.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(StatutCompteWave.values().length).isGreaterThan(0); + for (StatutCompteWave statut : StatutCompteWave.values()) { + assertThat(statut).isNotNull(); + assertThat(statut.name()).isNotBlank(); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/wave/StatutTransactionWaveTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/wave/StatutTransactionWaveTest.java index 7cdc9eb..ded606f 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/wave/StatutTransactionWaveTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/wave/StatutTransactionWaveTest.java @@ -1,53 +1,53 @@ -package dev.lions.unionflow.server.api.enums.wave; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour StatutTransactionWave. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests StatutTransactionWave") -class StatutTransactionWaveTest { - - @Test - @DisplayName("Tous les statuts de transaction Wave doivent avoir un libellé") - void testTousLesStatutsOntLibelle() { - for (StatutTransactionWave statut : StatutTransactionWave.values()) { - assertThat(statut.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(StatutTransactionWave.values().length).isGreaterThan(0); - for (StatutTransactionWave statut : StatutTransactionWave.values()) { - assertThat(statut).isNotNull(); - assertThat(statut.name()).isNotBlank(); - } - } - - @Test - @DisplayName("isFinalise() retourne true pour statuts finalisés") - void testIsFinaliseRetourneTruePourStatutsFinales() { - assertThat(StatutTransactionWave.REUSSIE.isFinalise()).isTrue(); - assertThat(StatutTransactionWave.ECHOUE.isFinalise()).isTrue(); - assertThat(StatutTransactionWave.ANNULEE.isFinalise()).isTrue(); - assertThat(StatutTransactionWave.EXPIRED.isFinalise()).isTrue(); - } - - @Test - @DisplayName("isFinalise() retourne false pour statuts non finalisés") - void testIsFinaliseRetourneFalsePourStatutsNonFinales() { - assertThat(StatutTransactionWave.INITIALISE.isFinalise()).isFalse(); - assertThat(StatutTransactionWave.EN_ATTENTE.isFinalise()).isFalse(); - assertThat(StatutTransactionWave.EN_COURS.isFinalise()).isFalse(); - } -} - +package dev.lions.unionflow.server.api.enums.wave; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour StatutTransactionWave. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests StatutTransactionWave") +class StatutTransactionWaveTest { + + @Test + @DisplayName("Tous les statuts de transaction Wave doivent avoir un libellé") + void testTousLesStatutsOntLibelle() { + for (StatutTransactionWave statut : StatutTransactionWave.values()) { + assertThat(statut.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(StatutTransactionWave.values().length).isGreaterThan(0); + for (StatutTransactionWave statut : StatutTransactionWave.values()) { + assertThat(statut).isNotNull(); + assertThat(statut.name()).isNotBlank(); + } + } + + @Test + @DisplayName("isFinalise() retourne true pour statuts finalisés") + void testIsFinaliseRetourneTruePourStatutsFinales() { + assertThat(StatutTransactionWave.REUSSIE.isFinalise()).isTrue(); + assertThat(StatutTransactionWave.ECHOUE.isFinalise()).isTrue(); + assertThat(StatutTransactionWave.ANNULEE.isFinalise()).isTrue(); + assertThat(StatutTransactionWave.EXPIRED.isFinalise()).isTrue(); + } + + @Test + @DisplayName("isFinalise() retourne false pour statuts non finalisés") + void testIsFinaliseRetourneFalsePourStatutsNonFinales() { + assertThat(StatutTransactionWave.INITIALISE.isFinalise()).isFalse(); + assertThat(StatutTransactionWave.EN_ATTENTE.isFinalise()).isFalse(); + assertThat(StatutTransactionWave.EN_COURS.isFinalise()).isFalse(); + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/wave/StatutWebhookTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/wave/StatutWebhookTest.java index 23e44b7..4439bab 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/wave/StatutWebhookTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/wave/StatutWebhookTest.java @@ -1,36 +1,36 @@ -package dev.lions.unionflow.server.api.enums.wave; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour StatutWebhook. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests StatutWebhook") -class StatutWebhookTest { - - @Test - @DisplayName("Tous les statuts de webhook doivent avoir un libellé") - void testTousLesStatutsOntLibelle() { - for (StatutWebhook statut : StatutWebhook.values()) { - assertThat(statut.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(StatutWebhook.values().length).isGreaterThan(0); - for (StatutWebhook statut : StatutWebhook.values()) { - assertThat(statut).isNotNull(); - assertThat(statut.name()).isNotBlank(); - } - } -} - +package dev.lions.unionflow.server.api.enums.wave; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour StatutWebhook. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests StatutWebhook") +class StatutWebhookTest { + + @Test + @DisplayName("Tous les statuts de webhook doivent avoir un libellé") + void testTousLesStatutsOntLibelle() { + for (StatutWebhook statut : StatutWebhook.values()) { + assertThat(statut.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(StatutWebhook.values().length).isGreaterThan(0); + for (StatutWebhook statut : StatutWebhook.values()) { + assertThat(statut).isNotNull(); + assertThat(statut.name()).isNotBlank(); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/wave/TypeEvenementWebhookTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/wave/TypeEvenementWebhookTest.java index 4096931..07d9fa2 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/wave/TypeEvenementWebhookTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/wave/TypeEvenementWebhookTest.java @@ -1,36 +1,36 @@ -package dev.lions.unionflow.server.api.enums.wave; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour TypeEvenementWebhook. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests TypeEvenementWebhook") -class TypeEvenementWebhookTest { - - @Test - @DisplayName("Tous les types d'événement webhook doivent avoir un libellé") - void testTousLesTypesOntLibelle() { - for (TypeEvenementWebhook type : TypeEvenementWebhook.values()) { - assertThat(type.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(TypeEvenementWebhook.values().length).isGreaterThan(0); - for (TypeEvenementWebhook type : TypeEvenementWebhook.values()) { - assertThat(type).isNotNull(); - assertThat(type.name()).isNotBlank(); - } - } -} - +package dev.lions.unionflow.server.api.enums.wave; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour TypeEvenementWebhook. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests TypeEvenementWebhook") +class TypeEvenementWebhookTest { + + @Test + @DisplayName("Tous les types d'événement webhook doivent avoir un libellé") + void testTousLesTypesOntLibelle() { + for (TypeEvenementWebhook type : TypeEvenementWebhook.values()) { + assertThat(type.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(TypeEvenementWebhook.values().length).isGreaterThan(0); + for (TypeEvenementWebhook type : TypeEvenementWebhook.values()) { + assertThat(type).isNotNull(); + assertThat(type.name()).isNotBlank(); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/enums/wave/TypeTransactionWaveTest.java b/src/test/java/dev/lions/unionflow/server/api/enums/wave/TypeTransactionWaveTest.java index ab1d4ea..772e109 100644 --- a/src/test/java/dev/lions/unionflow/server/api/enums/wave/TypeTransactionWaveTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/enums/wave/TypeTransactionWaveTest.java @@ -1,36 +1,36 @@ -package dev.lions.unionflow.server.api.enums.wave; - -import static org.assertj.core.api.Assertions.assertThat; - -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour TypeTransactionWave. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests TypeTransactionWave") -class TypeTransactionWaveTest { - - @Test - @DisplayName("Tous les types de transaction Wave doivent avoir un libellé") - void testTousLesTypesOntLibelle() { - for (TypeTransactionWave type : TypeTransactionWave.values()) { - assertThat(type.getLibelle()).isNotNull().isNotBlank(); - } - } - - @Test - @DisplayName("Toutes les valeurs de l'enum doivent être présentes") - void testToutesLesValeurs() { - assertThat(TypeTransactionWave.values().length).isGreaterThan(0); - for (TypeTransactionWave type : TypeTransactionWave.values()) { - assertThat(type).isNotNull(); - assertThat(type.name()).isNotBlank(); - } - } -} - +package dev.lions.unionflow.server.api.enums.wave; + +import static org.assertj.core.api.Assertions.assertThat; + +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour TypeTransactionWave. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests TypeTransactionWave") +class TypeTransactionWaveTest { + + @Test + @DisplayName("Tous les types de transaction Wave doivent avoir un libellé") + void testTousLesTypesOntLibelle() { + for (TypeTransactionWave type : TypeTransactionWave.values()) { + assertThat(type.getLibelle()).isNotNull().isNotBlank(); + } + } + + @Test + @DisplayName("Toutes les valeurs de l'enum doivent être présentes") + void testToutesLesValeurs() { + assertThat(TypeTransactionWave.values().length).isGreaterThan(0); + for (TypeTransactionWave type : TypeTransactionWave.values()) { + assertThat(type).isNotNull(); + assertThat(type.name()).isNotBlank(); + } + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/service/dashboard/DashboardServiceTest.java b/src/test/java/dev/lions/unionflow/server/api/service/dashboard/DashboardServiceTest.java index 1c2bd77..d10b809 100644 --- a/src/test/java/dev/lions/unionflow/server/api/service/dashboard/DashboardServiceTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/service/dashboard/DashboardServiceTest.java @@ -1,91 +1,91 @@ -package dev.lions.unionflow.server.api.service.dashboard; - -import static org.assertj.core.api.Assertions.assertThat; - -import dev.lions.unionflow.server.api.dto.dashboard.DashboardDataResponse; -import dev.lions.unionflow.server.api.dto.dashboard.DashboardStatsResponse; -import dev.lions.unionflow.server.api.dto.dashboard.RecentActivityResponse; -import dev.lions.unionflow.server.api.dto.dashboard.UpcomingEventResponse; -import java.util.List; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour DashboardService. - * - * @author UnionFlow Team - * @version 1.0 - * @since 2025-12-09 - */ -@DisplayName("Tests DashboardService") -class DashboardServiceTest { - - /** - * Implémentation de test pour DashboardService. - */ - static class TestDashboardService implements DashboardService { - - @Override - public DashboardDataResponse getDashboardData(String organizationId, String userId) { - DashboardDataResponse data = new DashboardDataResponse(); - data.setStats(new DashboardStatsResponse()); - return data; - } - - @Override - public DashboardStatsResponse getDashboardStats(String organizationId, String userId) { - return new DashboardStatsResponse(); - } - - @Override - public List getRecentActivities( - String organizationId, String userId, int limit) { - return List.of(); - } - - @Override - public List getUpcomingEvents(String organizationId, String userId, int limit) { - return List.of(); - } - } - - @Test - @DisplayName("L'interface peut être implémentée") - void testInterfacePeutEtreImplementee() { - DashboardService service = new TestDashboardService(); - assertThat(service).isNotNull(); - } - - @Test - @DisplayName("getDashboardData retourne un DashboardDataResponse") - void testGetDashboardData() { - DashboardService service = new TestDashboardService(); - DashboardDataResponse result = service.getDashboardData("org1", "user1"); - assertThat(result).isNotNull(); - } - - @Test - @DisplayName("getDashboardStats retourne un DashboardStatsResponse") - void testGetDashboardStats() { - DashboardService service = new TestDashboardService(); - DashboardStatsResponse result = service.getDashboardStats("org1", "user1"); - assertThat(result).isNotNull(); - } - - @Test - @DisplayName("getRecentActivities retourne une liste") - void testGetRecentActivities() { - DashboardService service = new TestDashboardService(); - List result = service.getRecentActivities("org1", "user1", 10); - assertThat(result).isNotNull(); - } - - @Test - @DisplayName("getUpcomingEvents retourne une liste") - void testGetUpcomingEvents() { - DashboardService service = new TestDashboardService(); - List result = service.getUpcomingEvents("org1", "user1", 10); - assertThat(result).isNotNull(); - } -} - +package dev.lions.unionflow.server.api.service.dashboard; + +import static org.assertj.core.api.Assertions.assertThat; + +import dev.lions.unionflow.server.api.dto.dashboard.DashboardDataResponse; +import dev.lions.unionflow.server.api.dto.dashboard.DashboardStatsResponse; +import dev.lions.unionflow.server.api.dto.dashboard.RecentActivityResponse; +import dev.lions.unionflow.server.api.dto.dashboard.UpcomingEventResponse; +import java.util.List; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour DashboardService. + * + * @author UnionFlow Team + * @version 1.0 + * @since 2025-12-09 + */ +@DisplayName("Tests DashboardService") +class DashboardServiceTest { + + /** + * Implémentation de test pour DashboardService. + */ + static class TestDashboardService implements DashboardService { + + @Override + public DashboardDataResponse getDashboardData(String organizationId, String userId) { + DashboardDataResponse data = new DashboardDataResponse(); + data.setStats(new DashboardStatsResponse()); + return data; + } + + @Override + public DashboardStatsResponse getDashboardStats(String organizationId, String userId) { + return new DashboardStatsResponse(); + } + + @Override + public List getRecentActivities( + String organizationId, String userId, int limit) { + return List.of(); + } + + @Override + public List getUpcomingEvents(String organizationId, String userId, int limit) { + return List.of(); + } + } + + @Test + @DisplayName("L'interface peut être implémentée") + void testInterfacePeutEtreImplementee() { + DashboardService service = new TestDashboardService(); + assertThat(service).isNotNull(); + } + + @Test + @DisplayName("getDashboardData retourne un DashboardDataResponse") + void testGetDashboardData() { + DashboardService service = new TestDashboardService(); + DashboardDataResponse result = service.getDashboardData("org1", "user1"); + assertThat(result).isNotNull(); + } + + @Test + @DisplayName("getDashboardStats retourne un DashboardStatsResponse") + void testGetDashboardStats() { + DashboardService service = new TestDashboardService(); + DashboardStatsResponse result = service.getDashboardStats("org1", "user1"); + assertThat(result).isNotNull(); + } + + @Test + @DisplayName("getRecentActivities retourne une liste") + void testGetRecentActivities() { + DashboardService service = new TestDashboardService(); + List result = service.getRecentActivities("org1", "user1", 10); + assertThat(result).isNotNull(); + } + + @Test + @DisplayName("getUpcomingEvents retourne une liste") + void testGetUpcomingEvents() { + DashboardService service = new TestDashboardService(); + List result = service.getUpcomingEvents("org1", "user1", 10); + assertThat(result).isNotNull(); + } +} + diff --git a/src/test/java/dev/lions/unionflow/server/api/validation/ValidationConstantsTest.java b/src/test/java/dev/lions/unionflow/server/api/validation/ValidationConstantsTest.java index 43364cd..281159c 100644 --- a/src/test/java/dev/lions/unionflow/server/api/validation/ValidationConstantsTest.java +++ b/src/test/java/dev/lions/unionflow/server/api/validation/ValidationConstantsTest.java @@ -1,207 +1,207 @@ -package dev.lions.unionflow.server.api.validation; - -import static org.assertj.core.api.Assertions.assertThat; - -import java.lang.reflect.Constructor; -import org.junit.jupiter.api.DisplayName; -import org.junit.jupiter.api.Nested; -import org.junit.jupiter.api.Test; - -/** - * Tests unitaires pour ValidationConstants - Couverture 100% - * - * @author UnionFlow Team - * @version 2.0 - * @since 2025-01-16 - */ -@DisplayName("Tests ValidationConstants") -class ValidationConstantsTest { - - @Test - @DisplayName("Test constructeur privé") - void testConstructeurPrive() throws Exception { - Constructor constructor = ValidationConstants.class.getDeclaredConstructor(); - constructor.setAccessible(true); - - // Le constructeur doit être accessible et créer une instance - ValidationConstants instance = constructor.newInstance(); - assertThat(instance).isNotNull(); - } - - @Nested - @DisplayName("Tests des constantes de taille") - class TestsConstantesTaille { - - @Test - @DisplayName("Test constantes titre") - void testConstantesTitre() { - assertThat(ValidationConstants.TITRE_MIN_LENGTH).isEqualTo(5); - assertThat(ValidationConstants.TITRE_MAX_LENGTH).isEqualTo(100); - assertThat(ValidationConstants.TITRE_SIZE_MESSAGE).contains("5").contains("100").contains("titre"); - } - - @Test - @DisplayName("Test constantes nom organisation") - void testConstantesNomOrganisation() { - assertThat(ValidationConstants.NOM_ORGANISATION_MIN_LENGTH).isEqualTo(2); - assertThat(ValidationConstants.NOM_ORGANISATION_MAX_LENGTH).isEqualTo(200); - assertThat(ValidationConstants.NOM_ORGANISATION_SIZE_MESSAGE) - .contains("2") - .contains("200") - .contains("nom"); - } - - @Test - @DisplayName("Test constantes description") - void testConstantesDescription() { - assertThat(ValidationConstants.DESCRIPTION_MIN_LENGTH).isEqualTo(20); - assertThat(ValidationConstants.DESCRIPTION_MAX_LENGTH).isEqualTo(2000); - assertThat(ValidationConstants.DESCRIPTION_SIZE_MESSAGE) - .contains("20") - .contains("2000") - .contains("description"); - } - - @Test - @DisplayName("Test constantes description courte") - void testConstantesDescriptionCourte() { - assertThat(ValidationConstants.DESCRIPTION_COURTE_MAX_LENGTH).isEqualTo(1000); - assertThat(ValidationConstants.DESCRIPTION_COURTE_SIZE_MESSAGE) - .contains("1000") - .contains("description"); - } - - @Test - @DisplayName("Test constantes justification") - void testConstantesJustification() { - assertThat(ValidationConstants.JUSTIFICATION_MAX_LENGTH).isEqualTo(1000); - assertThat(ValidationConstants.JUSTIFICATION_SIZE_MESSAGE) - .contains("1000") - .contains("justification"); - } - - @Test - @DisplayName("Test constantes commentaires") - void testConstantesCommentaires() { - assertThat(ValidationConstants.COMMENTAIRES_MAX_LENGTH).isEqualTo(1000); - assertThat(ValidationConstants.COMMENTAIRES_SIZE_MESSAGE) - .contains("1000") - .contains("commentaires"); - } - - @Test - @DisplayName("Test constantes raison rejet") - void testConstantesRaisonRejet() { - assertThat(ValidationConstants.RAISON_REJET_MAX_LENGTH).isEqualTo(500); - assertThat(ValidationConstants.RAISON_REJET_SIZE_MESSAGE).contains("500").contains("rejet"); - } - - @Test - @DisplayName("Test constantes email") - void testConstantesEmail() { - assertThat(ValidationConstants.EMAIL_MAX_LENGTH).isEqualTo(100); - assertThat(ValidationConstants.EMAIL_SIZE_MESSAGE).contains("100").contains("email"); - } - - @Test - @DisplayName("Test constantes nom et prénom") - void testConstantesNomPrenom() { - assertThat(ValidationConstants.NOM_PRENOM_MIN_LENGTH).isEqualTo(2); - assertThat(ValidationConstants.NOM_PRENOM_MAX_LENGTH).isEqualTo(50); - assertThat(ValidationConstants.NOM_SIZE_MESSAGE).contains("2").contains("50").contains("nom"); - assertThat(ValidationConstants.PRENOM_SIZE_MESSAGE).contains("2").contains("50").contains("prénom"); - } - } - - @Nested - @DisplayName("Tests des patterns de validation") - class TestsPatternsValidation { - - @Test - @DisplayName("Test patterns téléphone") - void testPatternsTelephone() { - assertThat(ValidationConstants.TELEPHONE_PATTERN).isNotNull(); - assertThat(ValidationConstants.TELEPHONE_MESSAGE).contains("téléphone"); - } - - @Test - @DisplayName("Test patterns devise") - void testPatternsDevise() { - assertThat(ValidationConstants.DEVISE_PATTERN).isNotNull(); - assertThat(ValidationConstants.DEVISE_MESSAGE).contains("devise"); - } - - @Test - @DisplayName("Test patterns référence aide") - void testPatternsReferenceAide() { - assertThat(ValidationConstants.REFERENCE_AIDE_PATTERN).isNotNull(); - assertThat(ValidationConstants.REFERENCE_AIDE_MESSAGE).contains("référence"); - } - - @Test - @DisplayName("Test patterns numéro membre") - void testPatternsNumeroMembre() { - assertThat(ValidationConstants.NUMERO_MEMBRE_PATTERN).isNotNull(); - assertThat(ValidationConstants.NUMERO_MEMBRE_MESSAGE).contains("numéro"); - } - - @Test - @DisplayName("Test patterns couleur hexadécimale") - void testPatternsCouleurHex() { - assertThat(ValidationConstants.COULEUR_HEX_PATTERN).isNotNull(); - assertThat(ValidationConstants.COULEUR_HEX_MESSAGE).contains("couleur"); - } - } - - @Nested - @DisplayName("Tests des messages obligatoires") - class TestsMessagesObligatoires { - - @Test - @DisplayName("Test message obligatoire") - void testMessageObligatoire() { - assertThat(ValidationConstants.OBLIGATOIRE_MESSAGE).contains("obligatoire"); - } - - @Test - @DisplayName("Test message email format") - void testMessageEmailFormat() { - assertThat(ValidationConstants.EMAIL_FORMAT_MESSAGE).contains("email"); - } - - @Test - @DisplayName("Test messages de date") - void testMessagesDate() { - assertThat(ValidationConstants.DATE_PASSEE_MESSAGE).contains("passé"); - assertThat(ValidationConstants.DATE_FUTURE_MESSAGE).contains("futur"); - } - } - - @Nested - @DisplayName("Tests des constantes numériques") - class TestsConstantesNumeriques { - - @Test - @DisplayName("Test constantes montant") - void testConstantesMontant() { - assertThat(ValidationConstants.MONTANT_MIN_VALUE).isEqualTo("0.0"); - assertThat(ValidationConstants.MONTANT_INTEGER_DIGITS).isEqualTo(10); - assertThat(ValidationConstants.MONTANT_FRACTION_DIGITS).isEqualTo(2); - assertThat(ValidationConstants.MONTANT_DIGITS_MESSAGE).contains("10").contains("2"); - assertThat(ValidationConstants.MONTANT_POSITIF_MESSAGE).contains("positif"); - } - } - - @Test - @DisplayName("Test toutes les constantes sont non nulles") - void testToutesConstantesNonNulles() { - // Vérification que toutes les constantes String sont non nulles - assertThat(ValidationConstants.TITRE_SIZE_MESSAGE).isNotNull(); - assertThat(ValidationConstants.NOM_ORGANISATION_SIZE_MESSAGE).isNotNull(); - assertThat(ValidationConstants.DESCRIPTION_SIZE_MESSAGE).isNotNull(); - assertThat(ValidationConstants.TELEPHONE_PATTERN).isNotNull(); - assertThat(ValidationConstants.DEVISE_PATTERN).isNotNull(); - assertThat(ValidationConstants.OBLIGATOIRE_MESSAGE).isNotNull(); - assertThat(ValidationConstants.EMAIL_FORMAT_MESSAGE).isNotNull(); - } -} +package dev.lions.unionflow.server.api.validation; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.lang.reflect.Constructor; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Nested; +import org.junit.jupiter.api.Test; + +/** + * Tests unitaires pour ValidationConstants - Couverture 100% + * + * @author UnionFlow Team + * @version 2.0 + * @since 2025-01-16 + */ +@DisplayName("Tests ValidationConstants") +class ValidationConstantsTest { + + @Test + @DisplayName("Test constructeur privé") + void testConstructeurPrive() throws Exception { + Constructor constructor = ValidationConstants.class.getDeclaredConstructor(); + constructor.setAccessible(true); + + // Le constructeur doit être accessible et créer une instance + ValidationConstants instance = constructor.newInstance(); + assertThat(instance).isNotNull(); + } + + @Nested + @DisplayName("Tests des constantes de taille") + class TestsConstantesTaille { + + @Test + @DisplayName("Test constantes titre") + void testConstantesTitre() { + assertThat(ValidationConstants.TITRE_MIN_LENGTH).isEqualTo(5); + assertThat(ValidationConstants.TITRE_MAX_LENGTH).isEqualTo(100); + assertThat(ValidationConstants.TITRE_SIZE_MESSAGE).contains("5").contains("100").contains("titre"); + } + + @Test + @DisplayName("Test constantes nom organisation") + void testConstantesNomOrganisation() { + assertThat(ValidationConstants.NOM_ORGANISATION_MIN_LENGTH).isEqualTo(2); + assertThat(ValidationConstants.NOM_ORGANISATION_MAX_LENGTH).isEqualTo(200); + assertThat(ValidationConstants.NOM_ORGANISATION_SIZE_MESSAGE) + .contains("2") + .contains("200") + .contains("nom"); + } + + @Test + @DisplayName("Test constantes description") + void testConstantesDescription() { + assertThat(ValidationConstants.DESCRIPTION_MIN_LENGTH).isEqualTo(20); + assertThat(ValidationConstants.DESCRIPTION_MAX_LENGTH).isEqualTo(2000); + assertThat(ValidationConstants.DESCRIPTION_SIZE_MESSAGE) + .contains("20") + .contains("2000") + .contains("description"); + } + + @Test + @DisplayName("Test constantes description courte") + void testConstantesDescriptionCourte() { + assertThat(ValidationConstants.DESCRIPTION_COURTE_MAX_LENGTH).isEqualTo(1000); + assertThat(ValidationConstants.DESCRIPTION_COURTE_SIZE_MESSAGE) + .contains("1000") + .contains("description"); + } + + @Test + @DisplayName("Test constantes justification") + void testConstantesJustification() { + assertThat(ValidationConstants.JUSTIFICATION_MAX_LENGTH).isEqualTo(1000); + assertThat(ValidationConstants.JUSTIFICATION_SIZE_MESSAGE) + .contains("1000") + .contains("justification"); + } + + @Test + @DisplayName("Test constantes commentaires") + void testConstantesCommentaires() { + assertThat(ValidationConstants.COMMENTAIRES_MAX_LENGTH).isEqualTo(1000); + assertThat(ValidationConstants.COMMENTAIRES_SIZE_MESSAGE) + .contains("1000") + .contains("commentaires"); + } + + @Test + @DisplayName("Test constantes raison rejet") + void testConstantesRaisonRejet() { + assertThat(ValidationConstants.RAISON_REJET_MAX_LENGTH).isEqualTo(500); + assertThat(ValidationConstants.RAISON_REJET_SIZE_MESSAGE).contains("500").contains("rejet"); + } + + @Test + @DisplayName("Test constantes email") + void testConstantesEmail() { + assertThat(ValidationConstants.EMAIL_MAX_LENGTH).isEqualTo(100); + assertThat(ValidationConstants.EMAIL_SIZE_MESSAGE).contains("100").contains("email"); + } + + @Test + @DisplayName("Test constantes nom et prénom") + void testConstantesNomPrenom() { + assertThat(ValidationConstants.NOM_PRENOM_MIN_LENGTH).isEqualTo(2); + assertThat(ValidationConstants.NOM_PRENOM_MAX_LENGTH).isEqualTo(50); + assertThat(ValidationConstants.NOM_SIZE_MESSAGE).contains("2").contains("50").contains("nom"); + assertThat(ValidationConstants.PRENOM_SIZE_MESSAGE).contains("2").contains("50").contains("prénom"); + } + } + + @Nested + @DisplayName("Tests des patterns de validation") + class TestsPatternsValidation { + + @Test + @DisplayName("Test patterns téléphone") + void testPatternsTelephone() { + assertThat(ValidationConstants.TELEPHONE_PATTERN).isNotNull(); + assertThat(ValidationConstants.TELEPHONE_MESSAGE).contains("téléphone"); + } + + @Test + @DisplayName("Test patterns devise") + void testPatternsDevise() { + assertThat(ValidationConstants.DEVISE_PATTERN).isNotNull(); + assertThat(ValidationConstants.DEVISE_MESSAGE).contains("devise"); + } + + @Test + @DisplayName("Test patterns référence aide") + void testPatternsReferenceAide() { + assertThat(ValidationConstants.REFERENCE_AIDE_PATTERN).isNotNull(); + assertThat(ValidationConstants.REFERENCE_AIDE_MESSAGE).contains("référence"); + } + + @Test + @DisplayName("Test patterns numéro membre") + void testPatternsNumeroMembre() { + assertThat(ValidationConstants.NUMERO_MEMBRE_PATTERN).isNotNull(); + assertThat(ValidationConstants.NUMERO_MEMBRE_MESSAGE).contains("numéro"); + } + + @Test + @DisplayName("Test patterns couleur hexadécimale") + void testPatternsCouleurHex() { + assertThat(ValidationConstants.COULEUR_HEX_PATTERN).isNotNull(); + assertThat(ValidationConstants.COULEUR_HEX_MESSAGE).contains("couleur"); + } + } + + @Nested + @DisplayName("Tests des messages obligatoires") + class TestsMessagesObligatoires { + + @Test + @DisplayName("Test message obligatoire") + void testMessageObligatoire() { + assertThat(ValidationConstants.OBLIGATOIRE_MESSAGE).contains("obligatoire"); + } + + @Test + @DisplayName("Test message email format") + void testMessageEmailFormat() { + assertThat(ValidationConstants.EMAIL_FORMAT_MESSAGE).contains("email"); + } + + @Test + @DisplayName("Test messages de date") + void testMessagesDate() { + assertThat(ValidationConstants.DATE_PASSEE_MESSAGE).contains("passé"); + assertThat(ValidationConstants.DATE_FUTURE_MESSAGE).contains("futur"); + } + } + + @Nested + @DisplayName("Tests des constantes numériques") + class TestsConstantesNumeriques { + + @Test + @DisplayName("Test constantes montant") + void testConstantesMontant() { + assertThat(ValidationConstants.MONTANT_MIN_VALUE).isEqualTo("0.0"); + assertThat(ValidationConstants.MONTANT_INTEGER_DIGITS).isEqualTo(10); + assertThat(ValidationConstants.MONTANT_FRACTION_DIGITS).isEqualTo(2); + assertThat(ValidationConstants.MONTANT_DIGITS_MESSAGE).contains("10").contains("2"); + assertThat(ValidationConstants.MONTANT_POSITIF_MESSAGE).contains("positif"); + } + } + + @Test + @DisplayName("Test toutes les constantes sont non nulles") + void testToutesConstantesNonNulles() { + // Vérification que toutes les constantes String sont non nulles + assertThat(ValidationConstants.TITRE_SIZE_MESSAGE).isNotNull(); + assertThat(ValidationConstants.NOM_ORGANISATION_SIZE_MESSAGE).isNotNull(); + assertThat(ValidationConstants.DESCRIPTION_SIZE_MESSAGE).isNotNull(); + assertThat(ValidationConstants.TELEPHONE_PATTERN).isNotNull(); + assertThat(ValidationConstants.DEVISE_PATTERN).isNotNull(); + assertThat(ValidationConstants.OBLIGATOIRE_MESSAGE).isNotNull(); + assertThat(ValidationConstants.EMAIL_FORMAT_MESSAGE).isNotNull(); + } +}